TextView
一、概述
一般用于显示文本信息,本文内容局限API19
extends View
implements ViewTreeObserver.OnPreDrawListener
二、可能用得到的XML属性
Link(匹配超链接)
代码使用
//以下模式可用|串在一起
//匹配网址
android:autoLink="web"
//匹配邮件
android:autoLink="email"
//匹配手机
android:autoLink="phone"\
//匹配地图地址
android:autoLink="map"
//匹配所有
android:autoLink="all"
textView.setAutoLinkMask(Linkify.WEB_URLS);
textView.setAutoLinkMask(Linkify.EMAIL_ADDRESSES);
textView.setAutoLinkMask(Linkify.PHONE_NUMBERS);
textView.setAutoLinkMask(Linkify.MAP_ADDRESSES);
textView.setAutoLinkMask(Linkify.ALL);
//设置超链接是否可点击
android:linksClickable="true"
textView.setLinksClickable(boolean);
//设置超链接字体颜色
android:textColorLink="@color/"
textView.setLinkTextColor(@ColorInt int);
textView.setLinkTextColor(ColorStateList);
看一眼源码
//通过辅助类Linkify,它可以自动的在TextView(或其派生类)中通过RegEx(正则表达式)模式匹配来创建超链接
Linkify.addLinks(s2, mAutoLinkMask);
drawable**(文本对象四个方向的图案绘制)
代码使用
//只能用drawable,使用color无效
android:drawableBottom="@drawable/"
android:drawableEnd="@drawable/"
android:drawableStart="@drawable/"
android:drawableTop="@drawable/"
setCompoundDrawablesWithIntrinsicBounds(int,int,int,int);
setCompoundDrawablesRelativeWithIntrinsicBounds(int,int,int,int);
//绘制图案与文本对象的间距
android:drawablePadding="10dp"
setCompoundDrawablePadding(int);
看一眼源码
通过自定义内置数据封装类Drawables,mShowing储存四个方向的drawable,mDrawablePadding储存padding。
ellipsize、marqueeRepeatLimit(当文本内容过长时,该控件该如何显示)
代码使用
//省略号显示在开头
android:ellipsize="start"
//省略号显示在中间
android:ellipsize="middle"
//省略号显示在结尾
android:ellipsize="end"
//横向跑马灯
android:ellipsize="marquee"
textView.setEllipsize(TextUtils.TruncateAt.START);
textView.setEllipsize(TextUtils.TruncateAt.MIDDLE);
textView.setEllipsize(TextUtils.TruncateAt.END);
textView.setEllipsize(TextUtils.TruncateAt.MARQUEE);
//跑马灯次数2
android:marqueeRepeatLimit="2"
//跑马灯次数无限
android:marqueeRepeatLimit="marquee_forever"
textView.setMarqueeRepeatLimit(2);
textView.setMarqueeRepeatLimit(-1);
看一眼源码
判断是否是跑马灯模式,是否启动跑马灯动画,
//TextView需要在isFocused或者isSelected的情况下才会执行跑马灯
if (textView != null && (textView.isFocused() || textView.isSelected()))
if (mMarquee != null && mMarquee.isRunning()) {
final float dx = -mMarquee.getScroll();
//通过canvas.translate移动画布来实现跑马灯的效果。
canvas.translate(layout.getParagraphDirection(0) * dx, 0.0f);
}
ems(限制单行"字符长度")
代码使用
//单行"字符长度"
android:ems="6"
//单行最长"字符长度"长度
android:minEms="6"
//单行最短"字符长度"长度
android:maxEms="6"
textView.setEms(int);
textView.setMaxEms(int);
textView.setMinEms(int);
看一眼源码
//通过ems长度*单行的行高限制TextView 的整体宽度(android:layout_width="wrap_content"的时候才有效)
if (mMaxWidthMode == EMS) {
width = Math.min(width, mMaxWidth * getLineHeight());
} else {
width = Math.min(width, mMaxWidth);
}
if (mMinWidthMode == EMS) {
width = Math.max(width, mMinWidth * getLineHeight());
} else {
width = Math.max(width, mMinWidth);
}
//返回单行的行高,但是由于float转int,实际会有偏差。
public int getLineHeight() {
return FastMath.round(mTextPaint.getFontMetricsInt(null) * mSpacingMult + mSpacingAdd);
}
这里值得注意的是,根据源码我们可以看出,这里的宽度限制,并不是百度多数说的指限制其多少个中文字符的宽度,实际上是限制多少个行高的宽度,这里的行高受到mSpacingMult和mSpacingAdd的影响,即lineSpacingMultiplierh和lineSpacingExtra。
textStyle、fontFamily、typeface(字体设置)
代码使用
//导入第三方字体库
//下载字体文件(ttf,otf),拷贝字体文件到res/font文件夹下
android:fontFamily="@font/"
Typeface typeface = Typeface.createFromAsset(getAssets(), "fonts/");
textView.setTypeface(typeface);
//粗体
android:textStyle="bold"
//斜体
android:textStyle="italic"
textView.setTypeface(Typeface.DEFAULT_BOLD);
//等宽字体
android:typeface="monospace"
//非衬线字体
android:typeface="sans"
//衬线字体
android:typeface="serif"
textView.setTypeface(Typeface.MONOSPACE);
textView.setTypeface(Typeface.SANS_SERIF);
textView.setTypeface(Typeface.SERIF);
看一眼源码
//直接setTypeface重绘,往下就不看了。
if (mTextPaint.getTypeface() != tf) {
mTextPaint.setTypeface(tf);
if (mLayout != null) {
nullLayouts();
requestLayout();
invalidate();
}
}
gravity(文本内容位置)
代码使用
//导入第三方字体库
//将对象推到其容器的顶部,而不更改其大小
android:gravity="top"
//将对象推到其容器的低部,而不更改其大小
android:gravity="bottom"
//将对象推到其容器的左侧,而不更改其大小。
android:gravity="left"
//将对象推入其容器的右侧,而不更改其大小。
android:gravity="right"
//将对象放置在容器的垂直中心,而不更改其大小。
android:gravity="center_vertical"
//必要的时候增加对象的纵向大小,以完全充满其容器.垂直方向填充
android:gravity="fill_vertical"
//将对象放置在其容器的水平中心,而不改变其大小。
android:gravity="center_horizontal"
//必要的时候增加对象的横向大小,以完全充满其容器.水平方向填充
android:gravity="fill_horizontal"
//将对象在垂直和水平轴上都放在其容器的中心,而不更改其大小。
android:gravity="center"
//必要的时候增加对象的横纵向大小,以完全充满其容器.
android:gravity="fill"
//可以设置为附加选项,以将子项的顶部和/或底部边缘修剪到其容器的边界。剪辑将基于垂直重力:顶部重力将修剪底部边缘,底部重力将修剪顶部边缘,而两者都不将两个边缘都修剪。
android:gravity="clip_vertical"
//可以设置为附加选项,使孩子的左边缘和/或右边缘被裁剪到其容器的边界。剪辑将基于水平重力:左重力将剪辑右边缘,右重力将剪辑左边缘,而两者都不将两个边缘都剪辑。
android:gravity="clip_horizontal"
//将对象推到其容器的开头,而不更改其大小。
android:gravity="start"
//将对象推到其容器的末端,而不更改其大小。
android:gravity="end"
textView.setGravity(Gravity.TOP);
textView.setGravity(Gravity.BOTTOM);
textView.setGravity(Gravity.LEFT);
textView.setGravity(Gravity.RIGHT);
textView.setGravity(Gravity.CENTER_VERTICAL);
textView.setGravity(Gravity.CENTER_HORIZONTAL);
textView.setGravity(Gravity.CENTER);
textView.setGravity(Gravity.START);
textView.setGravity(Gravity.END);
看一眼源码
//CENTER实际等同于CENTER_VERTICAL|CENTER_HORIZONTAL
public static final int CENTER = CENTER_VERTICAL|CENTER_HORIZONTAL;
//以下为fill的实现,我实际测试过程中发现fill和clip都没有官方文档描述中的效果,不建议使用。
public static final int FILL = FILL_VERTICAL|FILL_HORIZONTAL;
public static final int FILL_VERTICAL = TOP|BOTTOM;
public static final int FILL_HORIZONTAL = LEFT|RIGHT;
//相对布局的左堆
public static final int START = RELATIVE_LAYOUT_DIRECTION | LEFT;
//相对布局的右堆
public static final int END = RELATIVE_LAYOUT_DIRECTION | RIGHT;
lineSpacing(文本内容行间距)
代码使用
//增加1.5dp额外的行间距
android:lineSpacingExtra="1.5dp"
//1.5倍文本高度的行距
android:lineSpacingMultiplier="1.5"
textView.setLineSpacing(float, float);
看一眼源码
//第一个参数是额外行距,第二个参数是文本高度的倍数。
public void setLineSpacing(float add, float mult) {
if (mSpacingAdd != add || mSpacingMult != mult) {
mSpacingAdd = add;
mSpacingMult = mult;
if (mLayout != null) {
nullLayouts();
requestLayout();
invalidate();
}
}
}
//行高等于 文本高度乘于文本高度的倍数mSpacingMult加上额外行距mSpacingAdd。
public int getLineHeight() {
return FastMath.round(mTextPaint.getFontMetricsInt(null) * mSpacingMult + mSpacingAdd);
}
lines(文本的行数)
代码使用
//设置文本行数为6行
android:lines="6"
//设置文本的最大显示行数,与width或者layout_width结合使用,超出行数将不显示。
android:maxLines="6"
//设置文本的最小显示行数,与width或者layout_width结合使用,超出行数将继续显示。
android:minLines="6"
//设置文本单行显示
android:singleLine="true"
textView.setLines(int);
textView.setMaxLines(int);
textView.setMinLines(int);
textView.setSingleLine();
textView.setSingleLine(boolean);
看一眼源码
//将mMaximum和mMinimum都等于lines,mMaxMode和mMinMode都设置为LINES。
@android.view.RemotableViewMethod
public void setLines(int lines) {
mMaximum = mMinimum = lines;
mMaxMode = mMinMode = LINES;
requestLayout();
invalidate();
}
shadow(文本的阴影效果)
代码使用
//设置文本行数为6行
//阴影效果的X轴偏移量
android:shadowDx="5.0"
//阴影效果的Y轴偏移量
android:shadowDy="5.0"
//阴影效果的半径
android:shadowRadius="3"
//阴影效果的颜色
android:shadowColor="@color/"
textView.setShadowLayer(float, float, float, int);
看一眼源码
//mShadowRadius对Left、Top、Bottom、Right的影响
@Override
protected int getLeftPaddingOffset() {
return getCompoundPaddingLeft() - mPaddingLeft
+ (int) Math.min(0, mShadowDx - mShadowRadius);
}
@Override
protected int getTopPaddingOffset() {
return (int) Math.min(0, mShadowDy - mShadowRadius);
}
@Override
protected int getBottomPaddingOffset() {
return (int) Math.max(0, mShadowDy + mShadowRadius);
}
@Override
protected int getRightPaddingOffset() {
return -(getCompoundPaddingRight() - mPaddingRight)
+ (int) Math.max(0, mShadowDx + mShadowRadius);
}
这里值得注意的是,根据源码我们可以看出,这里mShadowRadius对Left、Top、Bottom、Right的影响,网上多数对mShadowRadius的描述很模糊,这里或许对mShadowRadius能有一定的理解(不一定对),有点像在Z轴上的偏移,Z轴拉近,阴影成扩散状拉大。
text(文本的内容)
代码使用
//显示文本内容
android:text="你好世界"
//显示string的文本内容
android:text="@string/"
//显示drawable文件的路径
android:text="@drawable/"
//显示color的颜色文本内容,如#BEBEBE
android:text="@color/"
textView.setText(CharSequence);
textView.setText(CharSequence, BufferType);
textView.setText(char[], int, int);
textView.setText(@StringRes int);
textView.setText(@StringRes int, BufferType);
android:textAllCaps="true"
textView.setAllCaps(true);
//设置文本颜色和透明度
android:textColor="@color/"
//设置文本颜色和透明度
android:textColor="#RGB"
//设置文本颜色和透明度
android:textColor="#ARGB"
//设置文本颜色
android:textColor="#rrggbb"
//设置文本颜色和透明度
android:textColor="#aarrggbb"
textView.setAllCaps(true);
看一眼源码
//textAllCaps 转化成全大写是通过toUpperCase实现的
public CharSequence getTransformation(CharSequence source, View view) {
return source != null?source.toString().toUpperCase(this.mLocale):null;
}
textAppearance(文本的文字外观)
代码使用
//设置文本的文字外观
android:textAppearance="@style/"
<style name="MyAppTheme" parent="Theme.AppCompat.Light.DarkActionBar">
//<!-- 设置文本颜色. -->
<item name="android:textColor">#4871A8</item>
//<!-- 被选中文字的底色,默认为蓝色. -->
<item name="android:textColorHighlight">#4871A8</item>
//<!-- 设置提示信息文字的颜色,默认为灰色。与hint一起使用. -->
<item name="android:textColorHint">#4871A8</item>
//<!-- 文字链接的颜色. -->
<item name="android:textColorLink">#4871A8</item>
//<!-- 设置文字水平拉伸,默认为1.0f. -->
<item name="android:textScaleX">1.0</item>
//<!-- 设置文字大小,推荐度量单位”sp”,如”15sp”. -->
<item name="android:textSize">12sp</item>
//<!-- 设置字形[bold(粗体), italic(斜体), bolditalic(又粗又斜)] 可以设置一个或多个,用“|”隔开. -->
<item name="android:textStyle">bold</item>
//<!-- 设置文本字体,必须是以下常量值之一:normal, sans, serif, monospace(等宽字体)]. -->
<item name="android:typeface">normal</item>
//<!-- 设置文本区域的高度,支持度量单位:px(像素)/dp/sp/in/mm(毫米). -->
<item name="android:height">12dp</item>
//<!-- 设置文本区域的最大高度. -->
<item name="android:maxHeight">12dp</item>
//<!-- 设置文本区域的最小高度. -->
<item name="android:minHeight">12dp</item>
//<!-- 设置文本区域的宽度,支持度量单位:px(像素)/dp/sp/in/mm(毫米),与layout_width的区别看这里. -->
<item name="android:width">12dp</item>
//<!-- 设置文本区域的高度,支持度量单位:px(像素)/dp/sp/in/mm(毫米). -->
<item name="android:height">12dp</item>
//<!-- 设置文本区域的最大宽度. -->
<item name="android:maxWidth">12dp</item>
//<!-- 设置文本区域的最小宽度. -->
<item name="android:minWidth">12dp</item>
</style>
看一眼源码
//不看不看了,没啥好看的.
select(文本的选中效果)
代码使用
//文本可选中
android:textIsSelectable="true"
//选中文本的背景色
android:textColorHighlight="#0b0bff"
//当获取焦点的时候选中所有文本
android:selectAllOnFocus="true"
textView.isTextSelectable();
textView.setHighlightColor(@ColorInt int);
textView.setSelectAllOnFocus(boolean);
看一眼源码
//不看不看了,没啥好看的.