如何禁用 TextView 中的自动换行?
How to disable automatic line breaking in TextView?
我有一个 TextView
,其中包含 60 个字符的随机字符串。
该字符串是一个单词,不包含任何空格。
问题是在某些字符后(例如 @, &, %
)我得到一个我不想要的自动换行符。
我想要的结果是每一行都被填满,并且没有随机换行符。
我已经尝试设置 breakStrategy
和更新 hyphenationFrequency
,但这没有帮助。
如何防止这种情况发生?
更新:感谢@Darkman,这是我编写的解决方案。它检查在没有换行符的情况下一行可以容纳多少个字符,并在末尾附加 \n
。
请注意,对于我的用例,字符串没有空格,我使用的是等宽字体。
fun TextView.toNonBreakingString(text: String?): String {
if (text == null) return ""
val container = parent as? ViewGroup ?: return text
val lineWidth = (container.width - container.paddingStart - container.paddingEnd).toFloat()
val maxCharsInOneLine = paint.breakText(text, 0, text.length, true, lineWidth, null)
if (maxCharsInOneLine == 0) return text
val sb = StringBuilder()
var currentLine = 1
var end = 0
for (i in 0..text.count() step maxCharsInOneLine) {
end = currentLine * maxCharsInOneLine
if (end > text.length) end = text.length
sb.append(text.subSequence(i, end))
sb.append("\n")
currentLine = currentLine.inc()
}
if (end < text.length) {
val remainingChars = text.length - end
sb.append(text.takeLast(remainingChars))
}
return sb.toString()
}
如果您的 API 等级是 26+,那么您可以使用下面的 XML 标签来设置 android 中的理由。
android:justificationMode="inter_word"
或者您可以使用 this GitHub 库来完成所有 API 关卡
我知道这个解决方案有点奇怪,但如果有什么不满意的地方,或者如果您在不久的将来没有找到任何解决方案,那么您可以使用:
<HorizontalScrollView
android:fillViewport="true"
android:scrollbars="none"
android:layout_width="match_parent"
android:layout_height="wrap_content"
>
<TextView
android:id="@+id/file_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:maxLines="1"
android:textStyle="bold"
android:text="@string/file_name"
android:textColor="?attr/primaryText"/>
</HorizontalScrollView>
实现所需结果的一种方法是使用 monospace
字体、左重力和一点点编程。
<TextView
android:layout_height="wrap_content"
android:layout_width="200dp"
android:text="akAOCYMKIpVmSwhHtWS%fBFK7eWi%19a590344gZqGQtkTcRv^1lFqH#F@Lhr"
android:gravity="left"
android:background="#708BCD"
android:id="@+id/tv"
android:textSize="20sp"
android:typeface="monospace"/>
//Note :: Auto-updated
public final void wrapText(final TextView textView, final String text)
{
final float textSize = (textView.getTextSize() / 250F) * 150F;
final int textLen = text.length();
final int columns = (int)(textView.getWidth() / textSize);
final int lines = (int)((float) textLen / columns);
final StringBuilder sb = new StringBuilder(textLen + lines);
for(int i=0, n=0; i < textLen; i+=columns, ++n) {
sb.append(text.subSequence(i, Math.min(textLen, i + columns)));
if(n<lines) sb.append("\n");
}
textView.setText(sb.toString());
}
或
//Note :: Auto-updated
public final void wrapText(final TextView textView)
{
final float textSize = (textView.getTextSize() / 250F) * 150F;
final CharSequence text = textView.getText();
final int textLen = text.length();
final int columns = (int)(textView.getWidth() / textSize);
final int lines = (int)((float) textLen / columns);
final StringBuilder sb = new StringBuilder(textLen + lines);
for(int i=0, n=0; i < textLen; i+=columns, ++n) {
sb.append(text.subSequence(i, Math.min(textLen, i + columns)));
if(n<lines) sb.append("\n");
}
textView.setText(sb.toString());
}
或
// Note :: Self-update
public final String wrapText(final TextView textView, final String text)
{
final float textSize = (textView.getTextSize() / 250F) * 150F;
final int textLen = text.length();
final int columns = (int)(textView.getWidth() / textSize);
final int lines = (int)((float) textLen / columns);
final StringBuilder sb = new StringBuilder(textLen + lines);
for(int i=0, n=0; i < textLen; i+=columns, ++n) {
sb.append(text.subSequence(i, Math.min(textLen, i + columns)));
if(n<lines) sb.append("\n");
}
return sb.toString();
}
// Implementation:
// textView.setText(wrapText(textView, "akAOCYMKIpVmSwhHtWS%fBFK7eWi%19a590344gZqGQtkTcRv^1lFqH#F@Lhr"));
并且您需要在测量布局后调用其中一种方法。这意味着在 onCreate()
、onCreateView()
或类似的东西之外。
我有一个 TextView
,其中包含 60 个字符的随机字符串。
该字符串是一个单词,不包含任何空格。
问题是在某些字符后(例如 @, &, %
)我得到一个我不想要的自动换行符。
我想要的结果是每一行都被填满,并且没有随机换行符。
我已经尝试设置 breakStrategy
和更新 hyphenationFrequency
,但这没有帮助。
如何防止这种情况发生?
更新:感谢@Darkman,这是我编写的解决方案。它检查在没有换行符的情况下一行可以容纳多少个字符,并在末尾附加 \n
。
请注意,对于我的用例,字符串没有空格,我使用的是等宽字体。
fun TextView.toNonBreakingString(text: String?): String {
if (text == null) return ""
val container = parent as? ViewGroup ?: return text
val lineWidth = (container.width - container.paddingStart - container.paddingEnd).toFloat()
val maxCharsInOneLine = paint.breakText(text, 0, text.length, true, lineWidth, null)
if (maxCharsInOneLine == 0) return text
val sb = StringBuilder()
var currentLine = 1
var end = 0
for (i in 0..text.count() step maxCharsInOneLine) {
end = currentLine * maxCharsInOneLine
if (end > text.length) end = text.length
sb.append(text.subSequence(i, end))
sb.append("\n")
currentLine = currentLine.inc()
}
if (end < text.length) {
val remainingChars = text.length - end
sb.append(text.takeLast(remainingChars))
}
return sb.toString()
}
如果您的 API 等级是 26+,那么您可以使用下面的 XML 标签来设置 android 中的理由。
android:justificationMode="inter_word"
或者您可以使用 this GitHub 库来完成所有 API 关卡
我知道这个解决方案有点奇怪,但如果有什么不满意的地方,或者如果您在不久的将来没有找到任何解决方案,那么您可以使用:
<HorizontalScrollView
android:fillViewport="true"
android:scrollbars="none"
android:layout_width="match_parent"
android:layout_height="wrap_content"
>
<TextView
android:id="@+id/file_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:maxLines="1"
android:textStyle="bold"
android:text="@string/file_name"
android:textColor="?attr/primaryText"/>
</HorizontalScrollView>
实现所需结果的一种方法是使用 monospace
字体、左重力和一点点编程。
<TextView
android:layout_height="wrap_content"
android:layout_width="200dp"
android:text="akAOCYMKIpVmSwhHtWS%fBFK7eWi%19a590344gZqGQtkTcRv^1lFqH#F@Lhr"
android:gravity="left"
android:background="#708BCD"
android:id="@+id/tv"
android:textSize="20sp"
android:typeface="monospace"/>
//Note :: Auto-updated
public final void wrapText(final TextView textView, final String text)
{
final float textSize = (textView.getTextSize() / 250F) * 150F;
final int textLen = text.length();
final int columns = (int)(textView.getWidth() / textSize);
final int lines = (int)((float) textLen / columns);
final StringBuilder sb = new StringBuilder(textLen + lines);
for(int i=0, n=0; i < textLen; i+=columns, ++n) {
sb.append(text.subSequence(i, Math.min(textLen, i + columns)));
if(n<lines) sb.append("\n");
}
textView.setText(sb.toString());
}
或
//Note :: Auto-updated
public final void wrapText(final TextView textView)
{
final float textSize = (textView.getTextSize() / 250F) * 150F;
final CharSequence text = textView.getText();
final int textLen = text.length();
final int columns = (int)(textView.getWidth() / textSize);
final int lines = (int)((float) textLen / columns);
final StringBuilder sb = new StringBuilder(textLen + lines);
for(int i=0, n=0; i < textLen; i+=columns, ++n) {
sb.append(text.subSequence(i, Math.min(textLen, i + columns)));
if(n<lines) sb.append("\n");
}
textView.setText(sb.toString());
}
或
// Note :: Self-update
public final String wrapText(final TextView textView, final String text)
{
final float textSize = (textView.getTextSize() / 250F) * 150F;
final int textLen = text.length();
final int columns = (int)(textView.getWidth() / textSize);
final int lines = (int)((float) textLen / columns);
final StringBuilder sb = new StringBuilder(textLen + lines);
for(int i=0, n=0; i < textLen; i+=columns, ++n) {
sb.append(text.subSequence(i, Math.min(textLen, i + columns)));
if(n<lines) sb.append("\n");
}
return sb.toString();
}
// Implementation:
// textView.setText(wrapText(textView, "akAOCYMKIpVmSwhHtWS%fBFK7eWi%19a590344gZqGQtkTcRv^1lFqH#F@Lhr"));
并且您需要在测量布局后调用其中一种方法。这意味着在 onCreate()
、onCreateView()
或类似的东西之外。