Should be a simple issue... but one I'm unable to nail! This is a simple layout that aims to show an icon illustrating a header, with the text slightly taller than the icon. The intention is for the icon to be vertically centered with the text, but for some reason the icon is a few pixels higher than it should be no matter text / icon sizes. (Icon is a vector drawable in case it does matter.)
Layout
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginBottom="8dp">
<ImageView
android:id="@+id/icon_readings_raw"
android:src="@drawable/ic_equals"
android:tint="@color/colorPrimary"
android:layout_width="14dp"
android:layout_height="14dp"
android:layout_alignParentStart="true"
android:layout_centerVertical="true"
android:layout_marginEnd="7dp"/>
<TextView
android:text="Raw sensor readings"
android:textAllCaps="true"
android:textColor="@color/colorPrimary"
android:textAppearance="?android:attr/textAppearanceSmall"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_toEndOf="@id/icon_readings_raw"/>
</RelativeLayout>
Result
Question
How do I center the icon with the text? Not asking for hacky solutions and magic numbers, please tell me why android:layout_centerVertical="true"
is not working as expected.
Edit #1
Led on a small path of discovery by @AntonMakov I am coming to the conclusion that it might be down to sub-pixel rendering optimizations and the nature of the preview window. My preview is set to Nexus 5X & API27. With ?android:attr/textAppearanceSmall
TextView renders as exactly 19sp; playing with icon height I noticed that when it is set to {19,13,9,7,3}sp
the icon is rendered vertically centered. When subtracting these numbers from 19sp
we get {0,6,10,12,16}sp
... always an even number. And it makes sense as only then can you get an equal amount of screen top and bottom.
What I do not understand yet is why not all even deltas yield a correct result (eg. TextView set to 19sp
and ImageView set to 15sp
for a delta of 4). Furthermore, the "right" combinations depend on the device selected (Nexus 6 behaves slightly differently), and also look a little bit different when displayed in an emulator.
What now? Should we trust that Android OS does The Right Thing on actual devices? Is it just the preview that is to blame — a far-from-precise approximation of the real thing whose calculations need not be taken too seriously?