问题描述
我有一个TextView,可在其中显示数据库中的文本,其中可以包含项目符号点:
我的TextView位于带有LinearLayout的ScrollView中,没有什么特别之处:
<TextView
android:id="@+id/textview_quiz_infotext"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:scrollbars="vertical"
tools:text="- This is the text" />
当文本超过一行时,我想添加与第一行相同的间距。 所以看起来像这样:
是否有可能实现这种行为?
解决方法
我也在尝试做同样的事情。我使用RecyclerView和适配器对其进行了尝试,然后找到了本文。下面的文章是在android中实现项目符号列表的最佳方法。 https://itnext.io/un-ordered-lists-on-android-20defac6b156
,我设法在旧项目中一次解决了这个问题。想法是先对文本进行一些预处理,以便在文本中仅包含项目符号定界符,并根据您的情况假设项目符号定界符为“-” 。然后提取每个项目符号行,并使用 BulletSpan (https://developer.android.com/reference/android/text/style/BulletSpan)进行渲染,或者,如果需要更多自定义来呈现自己的项目符号,则可以使用 LeadingMarginSpan ({ {3}})为您提供了使用其 drawLeadingMargin 方法绘制自定义项目符号点的灵活性。就我而言,我制作了以下Bullet Util类:
public class BulletUtil {
public enum BulletStyle{
Style1("•","\u2022"),Style2("●","\u25CF"),Style3("○","\u25CB"),Style4("▪","\u25AA"),Style5("■","\u25A0"),Style6("□","\u25A1"),Style7("►","\u25BA");
private String symbol;
private String code;
private BulletStyle(String symbol,String code){
this.symbol = symbol;
this.code = code;
}
public String getCode() {
return code;
}
}
/**
* Creates Leading Margin Spans {@link LeadingMarginSpan} based on a gap width and a color integer.*
* @param originText the original Text
* @param bulletDelimiter the bullet delimiter
* @param bulletGapWidth the distance,in pixels,between the bullet point and the paragraph.
* @param bulletColor the bullet point color,as a color integer.
* @param bulletStyle the bullet style
* @return CharSequence with BulletSpans
*/
public static CharSequence addLeadingBullets(String originText,String bulletDelimiter,int bulletGapWidth,@ColorInt int bulletColor,BulletStyle bulletStyle) {
return createLeadingMarginSpans(bulletGapWidth,bulletColor,getBulletList(originText,bulletDelimiter),bulletStyle);
}
/**
* Creates Bullet Spans {@link BulletSpan} based on a gap width and a color integer.*
* @param originText the original Text
* @param bulletDelimiter the bullet delimiter
* @param bulletGapWidth the distance,as a color integer.
* @return CharSequence with BulletSpans
*/
public static CharSequence addBullets(String originText,@ColorInt int bulletColor) {
return createBulletSpans(bulletGapWidth,bulletDelimiter));
}
/**
* Retrieves Bullet List based on a Bullet Delimiter
* @param text the Text
* @param bulletDelimiter the bullet delimiter
* @return List<String> the bullet List
*/
public static List<String> getBulletList(String text,String bulletDelimiter){
List<String> bulletLines = Arrays.asList(text.split(bulletDelimiter));
List<String> bulletList = new ArrayList<>();
if(bulletLines!=null && bulletLines.size()>0){
for(int i=0; i<bulletLines.size(); i++){
String bulletLine = bulletLines.get(i);
if(!TextUtils.isEmpty(bulletLine)){
bulletList.add(bulletLine);
}
}
}
return bulletList;
}
/**
* Creates Bullet Spans {@link BulletSpan} based on a gap width and a color integer.
*
* @param bulletGapWidth the distance,between the bullet point and the paragraph.
* @param bulletColor the bullet point color,as a color integer.
* @param bulletList the bullet List lines
*/
public static CharSequence createBulletSpans(int bulletGapWidth,@NonNull List<String> bulletList) {
SpannableStringBuilder sbb = new SpannableStringBuilder();
for(int i=0; i<bulletList.size(); i++){
CharSequence bulletLine = bulletList.get(i) + (i < bulletList.size()-1 ? "\n" : "");
Spannable spannable = new SpannableString(bulletLine);
BulletSpan bulletSpan = new BulletSpan(bulletGapWidth,bulletColor);
spannable.setSpan(bulletSpan,spannable.length(),Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
sbb.append(spannable);
}
return sbb;
}
/**
* Creates Bullet LeadingMarginSpans {@link LeadingMarginSpan} based on a gap width and a color integer.
*
* @param bulletGapWidth the distance,as a color integer.
* @param bulletList the bullet List lines
* @param bulletStyle the bullet enum Style
*/
public static CharSequence createLeadingMarginSpans(int bulletGapWidth,@NonNull List<String> bulletList,BulletStyle bulletStyle) {
SpannableStringBuilder sbb = new SpannableStringBuilder();
for(int i=0; i<bulletList.size(); i++){
CharSequence bulletLine = bulletList.get(i) + (i < bulletList.size()-1 ? "\n" : "");
Spannable spannable = new SpannableString(bulletLine);
String bulletPointStyle = bulletStyle.getCode();
LeadingMarginSpan bulletLeadingMarginSpan = new LeadingMarginSpan()
{
@Override
public int getLeadingMargin(boolean first) {
return bulletPointStyle.length()*bulletGapWidth;
}
@Override
public void drawLeadingMargin(Canvas c,Paint p,int x,int dir,int top,int baseline,int bottom,CharSequence text,int start,int end,boolean first,Layout layout) {
if (first) {
Paint.Style orgStyle = p.getStyle();
p.setStyle(Paint.Style.FILL);
p.setColor(bulletColor);
c.drawText(bulletPointStyle + " ",bottom - p.descent(),p);
p.setColor(Color.BLACK);
p.setStyle(orgStyle);
}
}
};
spannable.setSpan(bulletLeadingMarginSpan,Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
sbb.append(spannable);
}
return sbb;
}
}
我使用 BulletSpan 像下面这样称呼它:
String text = "- Enhanced base performance. - Lightweight headband enhances comfort and adds durability - Easy to adjust headband ensures optimum fit and comfort - 2 metre-long cable";
bulletTextView.setText(BulletUtil.addBullets(text,"- ",100,getResources().getColor(android.R.color.holo_red_dark)));
或使用 LeadingMarginSpan :
String text = "- Enhanced base performance. - Lightweight headband enhances comfort and adds durability - Easy to adjust headband ensures optimum fit and comfort - 2 metre-long cable";
bulletTextView.setText(BulletUtil.addLeadingBullets(text,getResources().getColor(android.R.color.black),BulletUtil.BulletStyle.Style2));
我在上述示例中使用了您的示例数据。