LOGO OA教程 ERP教程 模切知识交流 PMS教程 CRM教程 开发文档 其他文档  
 
网站管理员

android仿QQ聊天,带表情,可翻页,带翻页拖动缓冲

admin
2013年2月25日 17:48 本文热度 5857

如题,这是公司项目的一个功能模块,先上个效果图:




其次大致说说原理:


1,首先判断输入的字符,是否包含表情的文字,比如   这个表情对应的文件名为 emoji_1.png,它对应的文字描述 : [可爱],如果我们在输出的是输出这么一句话:老婆,我想你了。  那么我们对应的根本文字就是:老婆,我想你了[可爱]。




2,具体的转换过程就是用正则表达式比配文字中是否含有[xxx]这类的文字,如果有,那么我们就根据拿到的[xxx]找到它对应的资源文件id,当然这其中有一个关系表,看你怎么处理这个关系了。最后将其用SpannableString替换成文字,表面上显示有图片,其实TextView里的text依然是:老婆,我想你了[可爱]。这个过程明白么?




下面贴上DEMO工程的结构:




再贴上几个重要的类:





[java]


  1. package com.example.facedemo;  

  2.   

  3. import java.util.ArrayList;  

  4. import java.util.HashMap;  

  5. import java.util.List;  

  6. import java.util.regex.Matcher;  

  7. import java.util.regex.Pattern;  

  8.   

  9. import android.content.Context;  

  10. import android.graphics.Bitmap;  

  11. import android.graphics.BitmapFactory;  

  12. import android.text.Spannable;  

  13. import android.text.SpannableString;  

  14. import android.text.TextUtils;  

  15. import android.text.style.ImageSpan;  

  16. import android.util.Log;  

  17.   

  18. /** 

  19.  *  

  20.  ******************************************  

  21.  * @author 廖乃波 

  22.  * @文件名称 : FaceConversionUtil.java 

  23.  * @创建时间 : 2013-1-27 下午02:34:09 

  24.  * @文件描述 : 表情轉換工具 

  25.  ******************************************  

  26.  */  

  27. public class FaceConversionUtil {  

  28.   

  29.     /** 每一页表情的个数 */  

  30.     private int pageSize = 20;  

  31.   

  32.     private static FaceConversionUtil mFaceConversionUtil;  

  33.   

  34.     /** 保存于内存中的表情HashMap */  

  35.     private HashMap emojiMap = new HashMap();  

  36.   

  37.     /** 保存于内存中的表情集合 */  

  38.     private List emojis = new ArrayList();  

  39.   

  40.     /** 表情分页的结果集合 */  

  41.     public List> emojiLists = new ArrayList>();  

  42.   

  43.     private FaceConversionUtil() {  

  44.   

  45.     }  

  46.   

  47.     public static FaceConversionUtil getInstace() {  

  48.         if (mFaceConversionUtil == null) {  

  49.             mFaceConversionUtil = new FaceConversionUtil();  

  50.         }  

  51.         return mFaceConversionUtil;  

  52.     }  

  53.   

  54.     /** 

  55.      * 得到一个SpanableString对象,通过传入的字符串,并进行正则判断 

  56.      *  

  57.      * @param context 

  58.      * @param str 

  59.      * @return 

  60.      */  

  61.     public SpannableString getExpressionString(Context context, String str) {  

  62.         SpannableString spannableString = new SpannableString(str);  

  63.         // 正则表达式比配字符串里是否含有表情,如: 我好[开心]啊   

  64.         String zhengze = "\\[[^\\]]+\\]";  

  65.         // 通过传入的正则表达式来生成一个pattern   

  66.         Pattern sinaPatten = Pattern.compile(zhengze, Pattern.CASE_INSENSITIVE);  

  67.         try {  

  68.             dealExpression(context, spannableString, sinaPatten, 0);  

  69.         } catch (Exception e) {  

  70.             Log.e("dealExpression", e.getMessage());  

  71.         }  

  72.         return spannableString;  

  73.     }  

  74.   

  75.     /** 

  76.      * 添加表情 

  77.      *  

  78.      * @param context 

  79.      * @param imgId 

  80.      * @param spannableString 

  81.      * @return 

  82.      */  

  83.     public SpannableString addFace(Context context, int imgId,  

  84.             String spannableString) {  

  85.         if (TextUtils.isEmpty(spannableString)) {  

  86.             return null;  

  87.         }  

  88.         Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(),  

  89.                 imgId);  

  90.         bitmap = Bitmap.createScaledBitmap(bitmap, 3535true);  

  91.         ImageSpan imageSpan = new ImageSpan(context, bitmap);  

  92.         SpannableString spannable = new SpannableString(spannableString);  

  93.         spannable.setSpan(imageSpan, 0, spannableString.length(),  

  94.                 Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);  

  95.         return spannable;  

  96.     }  

  97.   

  98.     /** 

  99.      * 对spanableString进行正则判断,如果符合要求,则以表情图片代替 

  100.      *  

  101.      * @param context 

  102.      * @param spannableString 

  103.      * @param patten 

  104.      * @param start 

  105.      * @throws Exception 

  106.      */  

  107.     private void dealExpression(Context context,  

  108.             SpannableString spannableString, Pattern patten, int start)  

  109.             throws Exception {  

  110.         Matcher matcher = patten.matcher(spannableString);  

  111.         while (matcher.find()) {  

  112.             String key = matcher.group();  

  113.             // 返回第一个字符的索引的文本匹配整个正则表达式,ture 则继续递归   

  114.             if (matcher.start() < start) {  

  115.                 continue;  

  116.             }  

  117.             String value = emojiMap.get(key);  

  118.             if (TextUtils.isEmpty(value)) {  

  119.                 continue;  

  120.             }  

  121.             int resId = context.getResources().getIdentifier(value, "drawable",  

  122.                     context.getPackageName());  

  123.             // 通过上面匹配得到的字符串来生成图片资源id,下边的方法可用,但是你工程混淆的时候就有事了,你懂的。不是我介绍的重点   

  124.             // Field field=R.drawable.class.getDeclaredField(value);   

  125.             // int resId=Integer.parseInt(field.get(null).toString());   

  126.             if (resId != 0) {  

  127.                 Bitmap bitmap = BitmapFactory.decodeResource(  

  128.                         context.getResources(), resId);  

  129.                 bitmap = Bitmap.createScaledBitmap(bitmap, 5050true);  

  130.                 // 通过图片资源id来得到bitmap,用一个ImageSpan来包装   

  131.                 ImageSpan imageSpan = new ImageSpan(bitmap);  

  132.                 // 计算该图片名字的长度,也就是要替换的字符串的长度   

  133.                 int end = matcher.start() + key.length();  

  134.                 // 将该图片替换字符串中规定的位置中   

  135.                 spannableString.setSpan(imageSpan, matcher.start(), end,  

  136.                         Spannable.SPAN_INCLUSIVE_EXCLUSIVE);  

  137.                 if (end < spannableString.length()) {  

  138.                     // 如果整个字符串还未验证完,则继续。。   

  139.                     dealExpression(context, spannableString, patten, end);  

  140.                 }  

  141.                 break;  

  142.             }  

  143.         }  

  144.     }  

  145.   

  146.     public void getFileText(Context context) {  

  147.         ParseData(FileUtils.getEmojiFile(context), context);  

  148.     }  

  149.   

  150.     /** 

  151.      * 解析字符 

  152.      *  

  153.      * @param data 

  154.      */  

  155.     private void ParseData(List data, Context context) {  

  156.         if (data == null) {  

  157.             return;  

  158.         }  

  159.         ChatEmoji emojEentry;  

  160.         try {  

  161.             for (String str : data) {  

  162.                 String[] text = str.split(",");  

  163.                 String fileName = text[0]  

  164.                         .substring(0, text[0].lastIndexOf("."));  

  165.                 emojiMap.put(text[1], fileName);  

  166.                 int resID = context.getResources().getIdentifier(fileName,  

  167.                         "drawable", context.getPackageName());  

  168.   

  169.                 if (resID != 0) {  

  170.                     emojEentry = new ChatEmoji();  

  171.                     emojEentry.setId(resID);  

  172.                     emojEentry.setCharacter(text[1]);  

  173.                     emojEentry.setFaceName(fileName);  

  174.                     emojis.add(emojEentry);  

  175.                 }  

  176.             }  

  177.             int pageCount = (int) Math.ceil(emojis.size() / 20 + 0.1);  

  178.   

  179.             for (int i = 0; i < pageCount; i++) {  

  180.                 emojiLists.add(getData(i));  

  181.             }  

  182.         } catch (Exception e) {  

  183.             e.printStackTrace();  

  184.         }  

  185.     }  

  186.   

  187.     /** 

  188.      * 获取分页数据 

  189.      *  

  190.      * @param page 

  191.      * @return 

  192.      */  

  193.     private List getData(int page) {  

  194.         int startIndex = page * pageSize;  

  195.         int endIndex = startIndex + pageSize;  

  196.   

  197.         if (endIndex > emojis.size()) {  

  198.             endIndex = emojis.size();  

  199.         }  

  200.         // 不这么写,会在viewpager加载中报集合操作异常,我也不知道为什么   

  201.         List list = new ArrayList();  

  202.         list.addAll(emojis.subList(startIndex, endIndex));  

  203.         if (list.size() < pageSize) {  

  204.             for (int i = list.size(); i < pageSize; i++) {  

  205.                 ChatEmoji object = new ChatEmoji();  

  206.                 list.add(object);  

  207.             }  

  208.         }  

  209.         if (list.size() == pageSize) {  

  210.             ChatEmoji object = new ChatEmoji();  

  211.             object.setId(R.drawable.face_del_icon);  

  212.             list.add(object);  

  213.         }  

  214.         return list;  

  215.     }  

  216. }  
下边是表情布局,带输入框的,这样可以多个地方使用,就不不会使用太多多余代码。


[java]




  1. package com.example.facedemo;  

  2.   

  3. import java.util.ArrayList;  

  4. import java.util.List;  

  5.   

  6. import android.content.Context;  

  7. import android.graphics.Color;  

  8. import android.graphics.drawable.ColorDrawable;  

  9. import android.support.v4.view.ViewPager;  

  10. import android.support.v4.view.ViewPager.OnPageChangeListener;  

  11. import android.text.SpannableString;  

  12. import android.text.TextUtils;  

  13. import android.util.AttributeSet;  

  14. import android.view.Gravity;  

  15. import android.view.View;  

  16. import android.view.View.OnClickListener;  

  17. import android.view.ViewGroup;  

  18. import android.widget.AdapterView;  

  19. import android.widget.AdapterView.OnItemClickListener;  

  20. import android.widget.EditText;  

  21. import android.widget.GridView;  

  22. import android.widget.ImageView;  

  23. import android.widget.LinearLayout;  

  24. import android.widget.RelativeLayout;  

  25.   

  26. /** 

  27.  *  

  28.  ****************************************** 

  29.  * @author 廖乃波 

  30.  * @文件名称    :  FaceRelativeLayout.java 

  31.  * @创建时间    : 2013-1-27 下午02:34:17 

  32.  * @文件描述    : 带表情的自定义输入框 

  33.  ****************************************** 

  34.  */  

  35. public class FaceRelativeLayout extends RelativeLayout implements  

  36.         OnItemClickListener, OnClickListener {  

  37.   

  38.     private Context context;  

  39.   

  40.     /** 表情页的监听事件 */  

  41.     private OnCorpusSelectedListener mListener;  

  42.   

  43.     /** 显示表情页的viewpager */  

  44.     private ViewPager vp_face;  

  45.   

  46.     /** 表情页界面集合 */  

  47.     private ArrayList pageViews;  

  48.   

  49.     /** 游标显示布局 */  

  50.     private LinearLayout layout_point;  

  51.   

  52.     /** 游标点集合 */  

  53.     private ArrayList pointViews;  

  54.   

  55.     /** 表情集合 */  

  56.     private List> emojis;  

  57.   

  58.     /** 表情区域 */  

  59.     private View view;  

  60.   

  61.     /** 输入框 */  

  62.     private EditText et_sendmessage;  

  63.   

  64.     /** 表情数据填充器 */  

  65.     private List faceAdapters;  

  66.   

  67.     /** 当前表情页 */  

  68.     private int current = 0;  

  69.   

  70.     public FaceRelativeLayout(Context context) {  

  71.         super(context);  

  72.         this.context = context;  

  73.     }  

  74.   

  75.     public FaceRelativeLayout(Context context, AttributeSet attrs) {  

  76.         super(context, attrs);  

  77.         this.context = context;  

  78.     }  

  79.   

  80.     public FaceRelativeLayout(Context context, AttributeSet attrs, int defStyle) {  

  81.         super(context, attrs, defStyle);  

  82.         this.context = context;  

  83.     }  

  84.   

  85.     public void setOnCorpusSelectedListener(OnCorpusSelectedListener listener) {  

  86.         mListener = listener;  

  87.     }  

  88.   

  89.     /** 

  90.      * 表情选择监听 

  91.      *  

  92.      * @author naibo-liao 

  93.      * @时间: 2013-1-15下午04:32:54 

  94.      */  

  95.     public interface OnCorpusSelectedListener {  

  96.   

  97.         void onCorpusSelected(ChatEmoji emoji);  

  98.   

  99.         void onCorpusDeleted();  

  100.     }  

  101.   

  102.     @Override  

  103.     protected void onFinishInflate() {  

  104.         super.onFinishInflate();  

  105.         emojis = FaceConversionUtil.getInstace().emojiLists;  

  106.         onCreate();  

  107.     }  

  108.   

  109.     private void onCreate() {  

  110.         Init_View();  

  111.         Init_viewPager();  

  112.         Init_Point();  

  113.         Init_Data();  

  114.     }  

  115.   

  116.     @Override  

  117.     public void onClick(View v) {  

  118.         switch (v.getId()) {  

  119.         case R.id.btn_face:  

  120.             // 隐藏表情选择框   

  121.             if (view.getVisibility() == View.VISIBLE) {  

  122.                 view.setVisibility(View.GONE);  

  123.             } else {  

  124.                 view.setVisibility(View.VISIBLE);  

  125.             }  

  126.             break;  

  127.         case R.id.et_sendmessage:  

  128.             // 隐藏表情选择框   

  129.             if (view.getVisibility() == View.VISIBLE) {  

  130.                 view.setVisibility(View.GONE);  

  131.             }  

  132.             break;  

  133.   

  134.         }  

  135.     }  

  136.   

  137.     /** 

  138.      * 隐藏表情选择框 

  139.      */  

  140.     public boolean hideFaceView() {  

  141.         // 隐藏表情选择框   

  142.         if (view.getVisibility() == View.VISIBLE) {  

  143.             view.setVisibility(View.GONE);  

  144.             return true;  

  145.         }  

  146.         return false;  

  147.     }  

  148.   

  149.     /** 

  150.      * 初始化控件 

  151.      */  

  152.     private void Init_View() {  

  153.         vp_face = (ViewPager) findViewById(R.id.vp_contains);  

  154.         et_sendmessage = (EditText) findViewById(R.id.et_sendmessage);  

  155.         layout_point = (LinearLayout) findViewById(R.id.iv_image);  

  156.         et_sendmessage.setOnClickListener(this);  

  157.         findViewById(R.id.btn_face).setOnClickListener(this);  

  158.         view = findViewById(R.id.ll_facechoose);  

  159.   

  160.     }  

  161.   

  162.     /** 

  163.      * 初始化显示表情的viewpager 

  164.      */  

  165.     private void Init_viewPager() {  

  166.         pageViews = new ArrayList();  

  167.         // 左侧添加空页   

  168.         View nullView1 = new View(context);  

  169.         // 设置透明背景   

  170.         nullView1.setBackgroundColor(Color.TRANSPARENT);  

  171.         pageViews.add(nullView1);  

  172.   

  173.         // 中间添加表情页   

  174.   

  175.         faceAdapters = new ArrayList();  

  176.         for (int i = 0; i < emojis.size(); i++) {  

  177.             GridView view = new GridView(context);  

  178.             FaceAdapter adapter = new FaceAdapter(context, emojis.get(i));  

  179.             view.setAdapter(adapter);  

  180.             faceAdapters.add(adapter);  

  181.             view.setOnItemClickListener(this);  

  182.             view.setNumColumns(7);  

  183.             view.setBackgroundColor(Color.TRANSPARENT);  

  184.             view.setHorizontalSpacing(1);  

  185.             view.setVerticalSpacing(1);  

  186.             view.setStretchMode(GridView.STRETCH_COLUMN_WIDTH);  

  187.             view.setCacheColorHint(0);  

  188.             view.setPadding(5050);  

  189.             view.setSelector(new ColorDrawable(Color.TRANSPARENT));  

  190.             view.setLayoutParams(new LayoutParams(LayoutParams.FILL_PARENT,  

  191.                     LayoutParams.WRAP_CONTENT));  

  192.             view.setGravity(Gravity.CENTER);  

  193.             pageViews.add(view);  

  194.         }  

  195.   

  196.         // 右侧添加空页面   

  197.         View nullView2 = new View(context);  

  198.         // 设置透明背景   

  199.         nullView2.setBackgroundColor(Color.TRANSPARENT);  

  200.         pageViews.add(nullView2);  

  201.     }  

  202.   

  203.     /** 

  204.      * 初始化游标 

  205.      */  

  206.     private void Init_Point() {  

  207.   

  208.         pointViews = new ArrayList();  

  209.         ImageView imageView;  

  210.         for (int i = 0; i < pageViews.size(); i++) {  

  211.             imageView = new ImageView(context);  

  212.             imageView.setBackgroundResource(R.drawable.d1);  

  213.             LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(  

  214.                     new ViewGroup.LayoutParams(LayoutParams.WRAP_CONTENT,  

  215.                             LayoutParams.WRAP_CONTENT));  

  216.             layoutParams.leftMargin = 10;  

  217.             layoutParams.rightMargin = 10;  

  218.             layoutParams.width = 8;  

  219.             layoutParams.height = 8;  

  220.             layout_point.addView(imageView, layoutParams);  

  221.             if (i == 0 || i == pageViews.size() - 1) {  

  222.                 imageView.setVisibility(View.GONE);  

  223.             }  

  224.             if (i == 1) {  

  225.                 imageView.setBackgroundResource(R.drawable.d2);  

  226.             }  

  227.             pointViews.add(imageView);  

  228.   

  229.         }  

  230.     }  

  231.   

  232.     /** 

  233.      * 填充数据 

  234.      */  

  235.     private void Init_Data() {  

  236.         vp_face.setAdapter(new ViewPagerAdapter(pageViews));  

  237.   

  238.         vp_face.setCurrentItem(1);  

  239.         current = 0;  

  240.         vp_face.setOnPageChangeListener(new OnPageChangeListener() {  

  241.   

  242.             @Override  

  243.             public void onPageSelected(int arg0) {  

  244.                 current = arg0 - 1;  

  245.                 // 描绘分页点   

  246.                 draw_Point(arg0);  

  247.                 // 如果是第一屏或者是最后一屏禁止滑动,其实这里实现的是如果滑动的是第一屏则跳转至第二屏,如果是最后一屏则跳转到倒数第二屏.   

  248.                 if (arg0 == pointViews.size() - 1 || arg0 == 0) {  

  249.                     if (arg0 == 0) {  

  250.                         vp_face.setCurrentItem(arg0 + 1);// 第二屏 会再次实现该回调方法实现跳转.   

  251.                         pointViews.get(1).setBackgroundResource(R.drawable.d2);  

  252.                     } else {  

  253.                         vp_face.setCurrentItem(arg0 - 1);// 倒数第二屏   

  254.                         pointViews.get(arg0 - 1).setBackgroundResource(  

  255.                                 R.drawable.d2);  

  256.                     }  

  257.                 }  

  258.             }  

  259.   

  260.             @Override  

  261.             public void onPageScrolled(int arg0, float arg1, int arg2) {  

  262.   

  263.             }  

  264.   

  265.             @Override  

  266.             public void onPageScrollStateChanged(int arg0) {  

  267.   

  268.             }  

  269.         });  

  270.   

  271.     }  

  272.   

  273.     /** 

  274.      * 绘制游标背景 

  275.      */  

  276.     public void draw_Point(int index) {  

  277.         for (int i = 1; i < pointViews.size(); i++) {  

  278.             if (index == i) {  

  279.                 pointViews.get(i).setBackgroundResource(R.drawable.d2);  

  280.             } else {  

  281.                 pointViews.get(i).setBackgroundResource(R.drawable.d1);  

  282.             }  

  283.         }  

  284.     }  

  285.   

  286.     @Override  

  287.     public void onItemClick(AdapterView arg0, View arg1, int arg2, long arg3) {  

  288.         ChatEmoji emoji = (ChatEmoji) faceAdapters.get(current).getItem(arg2);  

  289.         if (emoji.getId() == R.drawable.face_del_icon) {  

  290.             int selection = et_sendmessage.getSelectionStart();  

  291.             String text = et_sendmessage.getText().toString();  

  292.             if (selection > 0) {  

  293.                 String text2 = text.substring(selection - 1);  

  294.                 if ("]".equals(text2)) {  

  295.                     int start = text.lastIndexOf("[");  

  296.                     int end = selection;  

  297.                     et_sendmessage.getText().delete(start, end);  

  298.                     return;  

  299.                 }  

  300.                 et_sendmessage.getText().delete(selection - 1, selection);  

  301.             }  

  302.         }  

  303.         if (!TextUtils.isEmpty(emoji.getCharacter())) {  

  304.             if (mListener != null)  

  305.                 mListener.onCorpusSelected(emoji);  

  306.             SpannableString spannableString = FaceConversionUtil.getInstace()  

  307.                     .addFace(getContext(), emoji.getId(), emoji.getCharacter());  

  308.             et_sendmessage.append(spannableString);  

  309.         }  

  310.   

  311.     }  

  312. }  
接下来是聊天数据填充器的


[java]




  1. package com.example.facedemo;  

  2.   

  3. import android.content.Context;  

  4.   

  5. import android.text.SpannableString;  

  6. import android.view.LayoutInflater;  

  7. import android.view.View;  

  8. import android.view.ViewGroup;  

  9.   

  10. import android.widget.BaseAdapter;  

  11. import android.widget.TextView;  

  12.   

  13. import java.util.List;  

  14.   

  15. /** 

  16.  *  

  17.  ****************************************** 

  18.  * @author 廖乃波 

  19.  * @文件名称    :  ChatMsgAdapter.java 

  20.  * @创建时间    : 2013-1-27 下午02:33:16 

  21.  * @文件描述    : 消息数据填充起 

  22.  ****************************************** 

  23.  */  

  24. public class ChatMsgAdapter extends BaseAdapter {  

  25.   

  26.     public static interface IMsgViewType {  

  27.         int IMVT_COM_MSG = 0;  

  28.         int IMVT_TO_MSG = 1;  

  29.     }  

  30.   

  31.     private List coll;  

  32.     private LayoutInflater mInflater;  

  33.     private Context context;  

  34.     public ChatMsgAdapter(Context context, List coll) {  

  35.         this.coll = coll;  

  36.         mInflater = LayoutInflater.from(context);  

  37.         this.context = context;  

  38.     }  

  39.   

  40.     public int getCount() {  

  41.         return coll.size();  

  42.     }  

  43.   

  44.     public Object getItem(int position) {  

  45.         return coll.get(position);  

  46.     }  

  47.   

  48.     public long getItemId(int position) {  

  49.         return position;  

  50.     }  

  51.   

  52.     public int getItemViewType(int position) {  

  53.         ChatMsgEntity entity = coll.get(position);  

  54.   

  55.         if (entity.getMsgType()) {  

  56.             return IMsgViewType.IMVT_COM_MSG;  

  57.         } else {  

  58.             return IMsgViewType.IMVT_TO_MSG;  

  59.         }  

  60.   

  61.     }  

  62.   

  63.     public int getViewTypeCount() {  

  64.         return 2;  

  65.     }  

  66.   

  67.     public View getView(int position, View convertView, ViewGroup parent) {  

  68.   

  69.         ChatMsgEntity entity = coll.get(position);  

  70.         boolean isComMsg = entity.getMsgType();  

  71.   

  72.         ViewHolder viewHolder = null;  

  73.         if (convertView == null) {  

  74.             if (isComMsg) {  

  75.                 convertView = mInflater.inflate(  

  76.                         R.layout.chatting_item_msg_text_left, null);  

  77.             } else {  

  78.                 convertView = mInflater.inflate(  

  79.                         R.layout.chatting_item_msg_text_right, null);  

  80.             }  

  81.   

  82.             viewHolder = new ViewHolder();  

  83.             viewHolder.tvSendTime = (TextView) convertView  

  84.                     .findViewById(R.id.tv_sendtime);  

  85.             viewHolder.tvContent = (TextView) convertView  

  86.                     .findViewById(R.id.tv_chatcontent);  

  87.             viewHolder.isComMsg = isComMsg;  

  88.   

  89.             convertView.setTag(viewHolder);  

  90.         } else {  

  91.             viewHolder = (ViewHolder) convertView.getTag();  

  92.         }  

  93.   

  94.         viewHolder.tvSendTime.setText(entity.getDate());  

  95.         SpannableString spannableString = FaceConversionUtil.getInstace().getExpressionString(context, entity.getText());  

  96.         viewHolder.tvContent.setText(spannableString);  

  97.   

  98.         return convertView;  

  99.     }  

  100.   

  101.     class ViewHolder {  

  102.         public TextView tvSendTime;  

  103.         public TextView tvContent;  

  104.         public boolean isComMsg = true;  

  105.     }  

  106.   

  107. }  


最开始要读取的表情配置文件


[java]




  1. package com.example.facedemo;  

  2.   

  3. import java.io.BufferedReader;  

  4. import java.io.IOException;  

  5. import java.io.InputStream;  

  6. import java.io.InputStreamReader;  

  7. import java.util.ArrayList;  

  8. import java.util.List;  

  9.   

  10. import android.content.Context;  

  11.   

  12. /** 

  13.  *  

  14.  ****************************************** 

  15.  * @author 廖乃波 

  16.  * @文件名称    :  FileUtils.java 

  17.  * @创建时间    : 2013-1-27 下午02:35:09 

  18.  * @文件描述    : 文件工具类 

  19.  ****************************************** 

  20.  */  

  21. public class FileUtils {  

  22.     /** 

  23.      * 读取表情配置文件 

  24.      *  

  25.      * @param context 

  26.      * @return 

  27.      */  

  28.     public static List getEmojiFile(Context context) {  

  29.         try {  

  30.             List list = new ArrayList();  

  31.             InputStream in = context.getResources().getAssets().open("emoji");  

  32.             BufferedReader br = new BufferedReader(new InputStreamReader(in,  

  33.                     "UTF-8"));  

  34.             String str = null;  

  35.             while ((str = br.readLine()) != null) {  

  36.                 list.add(str);  

  37.             }  

  38.   

  39.             return list;  

  40.         } catch (IOException e) {  

  41.             e.printStackTrace();  

  42.         }  

  43.         return null;  

  44.     }  

  45. }  
下边这个是表情翻页的数据填充,用的是viewpager,每一页填充的是一个gridview





[java]


  1. package com.example.facedemo;  

  2.   

  3. import java.util.List;  

  4.   

  5. import android.support.v4.view.PagerAdapter;  

  6. import android.support.v4.view.ViewPager;  

  7. import android.view.View;  

  8. /** 

  9.  *  

  10.  ****************************************** 

  11.  * @author 廖乃波 

  12.  * @文件名称    :  ViewPagerAdapter.java 

  13.  * @创建时间    : 2013-1-27 下午02:35:27 

  14.  * @文件描述    : ViewPager 数据填充器,切记做其他操作!!!只填充View!!!! 

  15.  ****************************************** 

  16.  */  

  17. public class ViewPagerAdapter extends PagerAdapter {  

  18.   

  19.     private List pageViews;  

  20.   

  21.     public ViewPagerAdapter(List pageViews) {  

  22.         super();  

  23.         this.pageViews=pageViews;  

  24.     }  

  25.   

  26.     // 显示数目   

  27.     @Override  

  28.     public int getCount() {  

  29.         return pageViews.size();  

  30.     }  

  31.   

  32.     @Override  

  33.     public boolean isViewFromObject(View arg0, Object arg1) {  

  34.         return arg0 == arg1;  

  35.     }  

  36.   

  37.     @Override  

  38.     public int getItemPosition(Object object) {  

  39.         return super.getItemPosition(object);  

  40.     }  

  41.   

  42.     @Override  

  43.     public void destroyItem(View arg0, int arg1, Object arg2) {  

  44.         ((ViewPager)arg0).removeView(pageViews.get(arg1));  

  45.     }  

  46.   

  47.     /*** 

  48.      * 获取每一个item�?类于listview中的getview 

  49.      */  

  50.     @Override  

  51.     public Object instantiateItem(View arg0, int arg1) {  

  52.         ((ViewPager)arg0).addView(pageViews.get(arg1));  

  53.         return pageViews.get(arg1);  

  54.     }  

  55. }  
最后呢,是表情的配置文件,你想怎么搞都行,我就这么搞的


[java]




  1. emoji_1.png,[可爱]  

  2. emoji_2.png,[笑脸]  

  3. emoji_3.png,[囧]  

  4. emoji_4.png,[生气]  

  5. emoji_5.png,[鬼脸]  

  6. emoji_6.png,[花心]  

  7. emoji_7.png,[害怕]  

  8. emoji_8.png,[我汗]  

  9. emoji_9.png,[尴尬]  

  10. emoji_10.png,[哼哼]  

  11. emoji_11.png,[忧郁]  

  12. emoji_12.png,[呲牙]  

  13. emoji_13.png,[媚眼]  

  14. emoji_14.png,[累]  

  15. emoji_15.png,[苦逼]  

  16. emoji_16.png,[瞌睡]  

  17. emoji_17.png,[哎呀]  

  18. emoji_18.png,[刺瞎]  

  19. emoji_19.png,[哭]  

  20. emoji_20.png,[激动]  

  21. emoji_21.png,[难过]  

  22. emoji_22.png,[害羞]  

  23. emoji_23.png,[高兴]  

  24. emoji_24.png,[愤怒]  

  25. emoji_25.png,[亲]  

  26. emoji_26.png,[飞吻]  

  27. emoji_27.png,[得意]  

  28. emoji_28.png,[惊恐]  

  29. emoji_29.png,[口罩]  

  30. emoji_30.png,[惊讶]  

  31. emoji_31.png,[委屈]  

  32. emoji_32.png,[生病]  

  33. emoji_33.png,[红心]  

  34. emoji_34.png,[心碎]  

  35. emoji_35.png,[玫瑰]  

  36. emoji_36.png,[花]  

  37. emoji_37.png,[外星人]  

  38. emoji_38.png,[金牛座]  

  39. emoji_39.png,[双子座]  

  40. emoji_40.png,[巨蟹座]  

  41. emoji_41.png,[狮子座]  

  42. emoji_42.png,[处女座]  

  43. emoji_43.png,[天平座]  

  44. emoji_44.png,[天蝎座]  

  45. emoji_45.png,[射手座]  

  46. emoji_46.png,[摩羯座]  

  47. emoji_47.png,[水瓶座]  

  48. emoji_48.png,[白羊座]  

  49. emoji_49.png,[双鱼座]  

  50. emoji_50.png,[星座]  

  51. emoji_51.png,[男孩]  

  52. emoji_52.png,[女孩]  

  53. emoji_53.png,[嘴唇]  

  54. emoji_54.png,[爸爸]  

  55. emoji_55.png,[妈妈]  

  56. emoji_56.png,[衣服]  

  57. emoji_57.png,[皮鞋]  

  58. emoji_58.png,[照相]  

  59. emoji_59.png,[电话]  

  60. emoji_60.png,[石头]  

  61. emoji_61.png,[胜利]  

  62. emoji_62.png,[禁止]  

  63. emoji_63.png,[滑雪]  

  64. emoji_64.png,[高尔夫]  

  65. emoji_65.png,[网球]  

  66. emoji_66.png,[棒球]  

  67. emoji_67.png,[冲浪]  

  68. emoji_68.png,[足球]  

  69. emoji_69.png,[小鱼]  

  70. emoji_70.png,[问号]  

  71. emoji_71.png,[叹号]  

  72. emoji_179.png,[顶]  

  73. emoji_180.png,[写字]  

  74. emoji_181.png,[衬衫]  

  75. emoji_182.png,[小花]  

  76. emoji_183.png,[郁金香]  

  77. emoji_184.png,[向日葵]  

  78. emoji_185.png,[鲜花]  

  79. emoji_186.png,[椰树]  

  80. emoji_187.png,[仙人掌]  

  81. emoji_188.png,[气球]  

  82. emoji_189.png,[炸弹]  

  83. emoji_190.png,[喝彩]  

  84. emoji_191.png,[剪子]  

  85. emoji_192.png,[蝴蝶结]  

  86. emoji_193.png,[机密]  

  87. emoji_194.png,[铃声]  

  88. emoji_195.png,[女帽]  

  89. emoji_196.png,[裙子]  

  90. emoji_197.png,[理发店]  

  91. emoji_198.png,[和服]  

  92. emoji_199.png,[比基尼]  

  93. emoji_200.png,[拎包]  

  94. emoji_201.png,[拍摄]  

  95. emoji_202.png,[铃铛]  

  96. emoji_203.png,[音乐]  

  97. emoji_204.png,[心星]  

  98. emoji_205.png,[粉心]  

  99. emoji_206.png,[丘比特]  

  100. emoji_207.png,[吹气]  

  101. emoji_208.png,[口水]  

  102. emoji_209.png,[对]  

  103. emoji_210.png,[错]  

  104. emoji_211.png,[绿茶]  

  105. emoji_212.png,[面包]  

  106. emoji_213.png,[面条]  

  107. emoji_214.png,[咖喱饭]  

  108. emoji_215.png,[饭团]  

  109. emoji_216.png,[麻辣烫]  

  110. emoji_217.png,[寿司]  

  111. emoji_218.png,[苹果]  

  112. emoji_219.png,[橙子]  

  113. emoji_220.png,[草莓]  

  114. emoji_221.png,[西瓜]  

  115. emoji_222.png,[柿子]  

  116. emoji_223.png,[眼睛]  

  117. emoji_224.png,[好的]  
忘了布局文件,哇哈哈

 







[html]


  1. <?xml version="1.0" encoding="utf-8"?>  

  2. <com.example.facedemo.FaceRelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"  

  3.     android:id="@+id/FaceRelativeLayout"  

  4.     android:layout_width="fill_parent"  

  5.     android:layout_height="wrap_content" >  

  6.   

  7.     <RelativeLayout  

  8.         android:id="@+id/rl_input"  

  9.         android:layout_width="fill_parent"  

  10.         android:layout_height="wrap_content"  

  11.         android:background="@drawable/chat_footer_bg" >  

  12.   

  13.         <ImageButton  

  14.             android:id="@+id/btn_face"  

  15.             android:layout_width="40dip"  

  16.             android:layout_height="40dip"  

  17.             android:layout_alignParentLeft="true"  

  18.             android:layout_centerVertical="true"  

  19.             android:layout_marginLeft="8dip"  

  20.             android:background="@drawable/chat_send_btn"  

  21.             android:src="@drawable/ib_face" />  

  22.   

  23.         <Button  

  24.             android:id="@+id/btn_send"  

  25.             android:layout_width="60dp"  

  26.             android:layout_height="40dp"  

  27.             android:layout_alignParentRight="true"  

  28.             android:layout_centerVertical="true"  

  29.             android:layout_marginRight="10dp"  

  30.             android:background="@drawable/chat_send_btn"  

  31.             android:text="发送" />  

  32.   

  33.         <EditText  

  34.             android:id="@+id/et_sendmessage"  

  35.             android:layout_width="fill_parent"  

  36.             android:layout_height="40dp"  

  37.             android:layout_centerVertical="true"  

  38.             android:layout_marginLeft="8dp"  

  39.             android:layout_marginRight="10dp"  

  40.             android:layout_toLeftOf="@id/btn_send"  

  41.             android:layout_toRightOf="@id/btn_face"  

  42.             android:background="@drawable/login_edit_normal"  

  43.             android:singleLine="true"  

  44.             android:textSize="18sp" />  

  45.     </RelativeLayout>  

  46.   

  47.     <RelativeLayout  

  48.         android:id="@+id/ll_facechoose"  

  49.         android:layout_width="fill_parent"  

  50.         android:layout_height="124dip"  

  51.         android:layout_below="@id/rl_input"  

  52.         android:background="#f6f5f5"  

  53.         android:visibility="gone" >  

  54.   

  55.         <android.support.v4.view.ViewPager  

  56.             android:id="@+id/vp_contains"  

  57.             android:layout_width="match_parent"  

  58.             android:layout_height="match_parent" >  

  59.         </android.support.v4.view.ViewPager>  

  60.   

  61.         <LinearLayout  

  62.             android:id="@+id/iv_image"  

  63.             android:layout_width="match_parent"  

  64.             android:layout_height="wrap_content"  

  65.             android:layout_alignParentBottom="true"  

  66.             android:layout_marginBottom="6dip"  

  67.             android:gravity="center"  

  68.             android:orientation="horizontal" >  

  69.         </LinearLayout>  

  70.     </RelativeLayout>  

  71.   

  72. </com.example.facedemo.FaceRelativeLayout>  

该文章在 2013/2/25 17:48:16 编辑过
关键字查询
相关文章
正在查询...
点晴ERP是一款针对中小制造业的专业生产管理软件系统,系统成熟度和易用性得到了国内大量中小企业的青睐。
点晴PMS码头管理系统主要针对港口码头集装箱与散货日常运作、调度、堆场、车队、财务费用、相关报表等业务管理,结合码头的业务特点,围绕调度、堆场作业而开发的。集技术的先进性、管理的有效性于一体,是物流码头及其他港口类企业的高效ERP管理信息系统。
点晴WMS仓储管理系统提供了货物产品管理,销售管理,采购管理,仓储管理,仓库管理,保质期管理,货位管理,库位管理,生产管理,WMS管理系统,标签打印,条形码,二维码管理,批号管理软件。
点晴免费OA是一款软件和通用服务都免费,不限功能、不限时间、不限用户的免费OA协同办公管理系统。
Copyright 2010-2024 ClickSun All Rights Reserved