Tia*_*tos 16 android alignment multiline android-constraintlayout
我有三个TextViews "hi","x"和"Hello World"我想在Hello World文本底部对齐(即hi_x_World)。你好世界仅仅是一个线,但两者layout_width并layout_height设置为wrap_content。
它们具有不同的字体大小,因此即使我可以轻松对齐文本视图框的底部,文本本身也不会对齐。
我发现了一个不同的 XML 参数app:layout_constraintBaseline_toBaselineOf="@+id/text,它在 TextView 中只有一行时有效。但是,当我有 2 行或更多行(如在 Hello World TextView 中)时,考虑的基线在“Hello”而不是“World”中。
有什么方法可以更改设置以考虑单词“World”而不是“Hello”下方的基线?
第二个更新:这是查看从这个Stack Overflow 答案中获取的第一个解决方案的另一种方式,该解决方案也适用于ConstraintLayout。此解决方案使用自定义TextView。自定义的TextView返回文本的最后一行的基线的TextView从getBaseline()函数,而不是这是默认动作第一行的基线。这是一个很好的、干净的解决方案 (IMO),它考虑了多行TextViews以及重力等。
BaselineLastLineTextView 的 Kotlin 版本
class BaselineLastLineTextView @JvmOverloads constructor(
context: Context, attrs: AttributeSet? = null
) : AppCompatTextView(context, attrs) {
override fun getBaseline(): Int {
val layout = layout ?: return super.getBaseline()
val baselineOffset = super.getBaseline() - layout.getLineBaseline(0)
return baselineOffset + layout.getLineBaseline(layout.lineCount - 1)
}
}
Run Code Online (Sandbox Code Playgroud)
第一次更新:这是对我下面的答案的更新,它仍然是一个有效的解决方案 (IMO)。这是一种替代方法,不涉及任何 Java/Kotlin 代码,只需使用 XML 即可完成。
创建一个不可见的wrap_content TextView,其字体大小与“Hello World!”相同。文本视图。(根据实际布局,您可能还需要考虑填充和边距。)将这个新视图限制在“Hello World!”的底部,制作它invisible并将内容设置为保证仅占一行的简短内容。这将为您提供一个目标视图,该视图与“Hello World!”的最后一行具有相同的基线。看法。
将“hi”和“x”的基线约束到新invisible视图。所有视图现在将共享相同的基线并且无需编码。
<androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/layout"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<TextView
android:id="@+id/hiddenView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="A"
android:textSize="50sp"
android:visibility="invisible"
app:layout_constraintBottom_toBottomOf="@id/helloView"
app:layout_constraintEnd_toEndOf="parent" />
<TextView
android:id="@+id/hiView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="hi"
android:textSize="46sp"
app:layout_constraintBaseline_toBaselineOf="@id/hiddenView"
app:layout_constraintEnd_toStartOf="@+id/xView"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="@id/helloView" />
<TextView
android:id="@+id/xView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="x"
android:textSize="36sp"
app:layout_constraintBaseline_toBaselineOf="@id/hiddenView"
app:layout_constraintEnd_toStartOf="@+id/helloView"
app:layout_constraintStart_toEndOf="@+id/hiView"
app:layout_constraintTop_toTopOf="@id/helloView" />
<TextView
android:id="@+id/helloView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Hello\nWorld!"
android:textSize="50sp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@+id/xView"
app:layout_constraintTop_toTopOf="parent" />
<Button
android:id="@+id/button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="24dp"
android:onClick="onClick"
android:text="Adjust Base Lines"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/helloView" />
</androidx.constraintlayout.widget.ConstraintLayout>
Run Code Online (Sandbox Code Playgroud)
第一个答案:如另一个答案中所述,仅使用ConstraintLayout约束无法做到这一点。您将需要求助于程序化解决方案。
每个TextView 中都有一个StaticLayout,它可以揭示一些关于文本排版的信息。通过参考静态布局,可以在适当的视图中添加填充以使基线对齐。
在这个演示中,三个TextViews只是将它们的顶部对齐。最初,视图如下所示:
单击按钮时,将计算基线位置并将填充添加到 "hi" 和 "x" TextViews的顶部。
细节会因实现而异,但这是通用技术。
主活动.kt
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
}
fun onClick(view: View) {
button.isEnabled = false
// Get the StaticLayout from the TextView
val layout = helloView.layout
// Get the base line location for last line of Hello World! TextView, "hi" and "x"
val helloBaseLIne = layout.getLineBaseline(layout.lineCount - 1)
val hiBaseLine = hiView.layout.getLineBaseline(0)
val xBaseLine = xView.layout.getLineBaseline(0)
// Shift "hi" and "x" down so base lines match that of hello world!
hiView.updatePadding(top = helloBaseLIne - hiBaseLine)
xView.updatePadding(top = helloBaseLIne - xBaseLine)
}
}
Run Code Online (Sandbox Code Playgroud)
活动_main.xml
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:id="@+id/layout"
android:layout_height="match_parent"
tools:context=".MainActivity">
<TextView
android:id="@+id/hiView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="hi"
android:textSize="46sp"
app:layout_constraintTop_toTopOf="@id/helloView"
app:layout_constraintEnd_toStartOf="@+id/xView"
app:layout_constraintStart_toStartOf="parent"/>
<TextView
android:id="@+id/xView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="x"
android:textSize="36sp"
app:layout_constraintTop_toTopOf="@id/helloView"
app:layout_constraintEnd_toStartOf="@+id/helloView"
app:layout_constraintStart_toEndOf="@+id/hiView" />
<TextView
android:id="@+id/helloView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Hello\nWorld!"
android:textSize="50sp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@+id/xView"
app:layout_constraintTop_toTopOf="parent" />
<Button
android:id="@+id/button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="24dp"
android:text="Adjust Base Lines"
android:onClick="onClick"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/helloView" />
</androidx.constraintlayout.widget.ConstraintLayout>
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
2891 次 |
| 最近记录: |