原创地址:http://www.cnblogs.com/nokiaguy/archive/2010/04/29/1723497.html

《Android/OPhone 开发完全讲义》目录

源代码下载


在本例中要实现一个可以在文本前方添加一个 图像(可以是任何Android系统支持的图像格式)的TextView组件。在编写代码之前,先看一下Android组件的配置代码。

< TextView android:id ="@+id/textview1" android:layout_width ="fill_parent"
android:layout_height
="wrap_content" android:text ="textview1" />

在构造方法中可以通过AttributeSet接口的相应getter方法来读取指定的属性值,如果 在配置属性时指定了命名空间,需要在使用getter方法获得属性值时指定这个命名空间,如果未指定命名空间,则将命名空间设为null即可。

IconTextView是本例要编写的组件类,该类从TextView继承,在onDraw方法中将TextView中的文本后移,并在文本的前方添加了一个图像,该图像的资源ID通过mobile:iconSrc属性来指定。IconTextView类的代码如下:

package net.blogjava.mobile.widget;

import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Rect;
import android.util.AttributeSet;
import android.widget.TextView;

public class IconTextView extends TextView
{
// 命名空间的值
private final Stringnamespace = " http://net.blogjava.mobile " ;
// 保存图像资源ID的变量
private int resourceId = 0 ;
private Bitmapbitmap;
public IconTextView(Contextcontext,AttributeSetattrs)
{
super (context,attrs);
// getAttributeResourceValue方法用来获得组件属性的值,在 本例中需要通过该方法的第1个参数指
// 定命名空间的值。该方法的第2个参数表示组件属性名(不包括命名空间名称),第3个 参数表示默
// 认值,也就是如果该属性不存在,则返回第3个参数指定的值
resourceId = attrs.getAttributeResourceValue(namespace, " iconSrc " , 0 );
if (resourceId > 0 )
// 如果成功获得图像资源的ID,装载这个图像资源,并创建Bitmap对象
bitmap = BitmapFactory.decodeResource(getResources(),resourceId);
}
@Override
protected void onDraw(Canvascanvas)
{
if (bitmap != null )
{
// 从原图上截取图像的区域,在本例中为整个图像
Rectsrc = new Rect();
// 将截取的图像复制到bitmap上的目标区域,在本例中与复制区域相同
Recttarget = new Rect();
src.left
= 0 ;
src.top
= 0 ;
src.right
= bitmap.getWidth();
src.bottom
= bitmap.getHeight();
int textHeight = ( int )getTextSize();
target.left
= 0 ;
// 计算图像复制到目标区域的纵坐标。由于TextView组件的文本内容并不是
// 从最顶端开始绘制的,因此,需要重新计算绘制图像的纵坐标
target.top = ( int )((getMeasuredHeight() - getTextSize()) / 2 ) + 1 ;
target.bottom
= target.top + textHeight;
// 为了保证图像不变形,需要根据图像高度重新计算图像的宽度
target.right = ( int )(textHeight * (bitmap.getWidth() / ( float )bitmap.getHeight()));
// 开始绘制图像
canvas.drawBitmap(bitmap,src,target,getPaint());
// 将TextView中的文本向右移动一定的距离(在本例中移动了图像宽度加2个象素 点的位置)
canvas.translate(target.right + 2 , 0 );
}
super .onDraw(canvas);
}
}

在编写上面代码时需要注意如下3点:
1. 需要指定命名空间的值。该值将在<LinearLayout>标签的xmlns:mobile属性中定义。
2. 如果在配置组件的属性时指定了命名空间,需要在AttributeSet 接口的相应getter方法中的第1个参数指定命名空间的值,而第2个参数只需指定不带命名空间的属性名即可。
3. TextView类中的onDraw方法一定要在translate方法后面执行,否则系统不会移动TextView中的文本。
<!--[endif]-->

运行本实例后,将显示如图1所示的效果。

注意:虽然很多人认为组件的属性必须以android命名空间开头,该命名空间的值必须是http://schemas.android.com/apk/res/android。实际上,只是命名空间的值必须是http://schemas.android.com/apk/res/android而已,命名空间的名称可以是任何值,如下面的代码所示:

<? xmlversion="1.0"encoding="utf-8" ?>
<!-- 将android换成了abcd -->
< LinearLayout xmlns:abcd ="http://schemas.android.com/apk/res/android"
abcd:orientation
="vertical" abcd:layout_width ="fill_parent"
abcd:layout_height
="fill_parent" >

</ LinearLayout >

更多相关文章

  1. Android(安卓)下的EXIF
  2. [置顶] Android(安卓)Paint之 setXfermode PorterDuffXfermode
  3. Android(安卓)项目开发建议标准规范
  4. android values-v11和values-v14文件夹是干啥的?
  5. android获取空间的宽度高度 的方法
  6. Android(安卓)资源文件的命名规则
  7. Android的layout_weight属性释疑(全面讲解)
  8. Android(安卓)Studio 布局中引用自定义属性不提示的问题
  9. android图像绘制(六)——获取本地图片或拍照图片

随机推荐

  1. android studio 自用快捷键方案
  2. Android自定义view绘制顺序及相关原理
  3. Activity的架构设计
  4. android 制造假数据
  5. Android中Handler原理
  6. Android(安卓)使用SWIG生成Jni代码
  7. android studio ,gradle 导入项目 常见错
  8. android color 透明度列表
  9. Android(安卓)new Message()和Message.ob
  10. Createing Dialogs/创建对话框