会话详情页


listview条目布局

TableLayout是一行几列的意思
  1. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
  2. android:layout_width="match_parent"
  3. android:layout_height="wrap_content"
  4. android:orientation="vertical" >
  5. <!-- android:shrinkColumns="0" 压缩第0列,当第0列的内容过多时,不至于将其他列的内容,挤出屏幕 -->
  6. <TableLayout
  7. android:id="@+id/tl_receive"
  8. android:layout_width="match_parent"
  9. android:shrinkColumns="0"
  10. android:layout_height="wrap_content" >
  11. <TableRow android:layout_height="wrap_content" >
  12. <TextView
  13. android:id="@+id/tv_msg_receive"
  14. android:layout_width="wrap_content"
  15. android:layout_height="wrap_content"
  16. android:background="@drawable/receive_msg_bubble"
  17. android:text="asdfasdfasdfasdfasdfsdfadfadfasdfasfsdfadffad" />
  18. <TextView
  19. android:id="@+id/tv_date_receive"
  20. android:layout_width="wrap_content"
  21. android:layout_height="match_parent"
  22. android:gravity="bottom"
  23. android:text="2014/10/10" />
  24. </TableRow>
  25. </TableLayout>
  26. <!-- android:shrinkColumns="1" 压缩第0列,当第0列的内容过多时,不至于将其他列的内容,挤出屏幕 -->
  27. <TableLayout
  28. android:id="@+id/tl_send"
  29. android:layout_width="match_parent"
  30. android:shrinkColumns="1"
  31. android:layout_height="wrap_content" >
  32. <TableRow android:layout_height="wrap_content"
  33. android:gravity="right">
  34. <TextView
  35. android:id="@+id/tv_date_send"
  36. android:layout_width="wrap_content"
  37. android:layout_height="match_parent"
  38. android:gravity="bottom"
  39. android:text="2014/10/10" />
  40. <TextView
  41. android:id="@+id/tv_msg_send"
  42. android:layout_width="wrap_content"
  43. android:layout_height="wrap_content"
  44. android:background="@drawable/send_msg_bubble"
  45. android:text="sfsdfadadsadsfasdfadfffad" />
  46. </TableRow>
  47. </TableLayout>
  48. <!-- 另一种实现 方式 -->
  49. <!-- <LinearLayout
  50. android:layout_width="match_parent"
  51. android:layout_height="wrap_content"
  52. android:gravity="right"
  53. >
  54. <LinearLayout
  55. android:layout_width="wrap_content"
  56. android:layout_height="wrap_content"
  57. >
  58. <TextView
  59. android:layout_width="wrap_content"
  60. android:layout_height="match_parent"
  61. android:gravity="bottom"
  62. android:text="2014/10/10" />
  63. <TextView
  64. android:layout_width="0dp"
  65. android:layout_height="wrap_content"
  66. android:layout_weight="2"
  67. android:background="@drawable/send_msg_bubble"
  68. android:text="asdfdf" />
  69. </LinearLayout>
  70. </LinearLayout> -->
  71. </LinearLayout>
代码:
  1. public class ConversationDetail extends Activity implements OnClickListener{
  2. /**
  3. *联系人的电话号码
  4. */
  5. private String address;
  6. private Context ctx;
  7. private ListView listView;
  8. private EditText inputMsg;
  9. @Override
  10. protected void onCreate(Bundle savedInstanceState) {
  11. super.onCreate(savedInstanceState);
  12. ctx = this;
  13. address = getIntent().getStringExtra("address");
  14. if(address == null){
  15. throw new RuntimeException("联系人是空,我不知道显示哪个会话记录");
  16. }
  17. setContentView(R.layout.activity_conversation_detail);
  18. init();
  19. listView = (ListView) findViewById(R.id.lv_conversation_detail);
  20. adapter = new MyListAdapter(this, null);
  21. listView.setAdapter(adapter);
  22. //设置listView条目之间的分隔线为null ,即,不要分隔线
  23. listView.setDivider(null);
  24. prepareData();
  25. }
  26. private void prepareData() {
  27. MyQueryHandler
    1. public class MyQueryHandler extends AsyncQueryHandler{
    2. public MyQueryHandler(ContentResolver cr) {
    3. super(cr);
    4. }
    5. @Override
    6. protected void onQueryComplete(int token, Object cookie, Cursor cursor) {
    7. System.out.println("onQueryComplete : token:"+token);
    8. System.out.println("onQueryComplete : cookie:"+cookie);
    9. Tools.printCursor(cursor);
    10. if(cookie!=null && cookie instanceof CursorAdapter){
    11. CursorAdapter adapter = (CursorAdapter) cookie;
    12. // 给adapter 设置新的cursor
    13. adapter.changeCursor(cursor);
    14. }
    15. if(cursorChangedListener!=null){
    16. cursorChangedListener.onCursorChanged(token, cookie, cursor);
    17. }
    18. }
    19. public IOnCursorChangedListener getCursorChangedListener() {
    20. return cursorChangedListener;
    21. }
    22. public void setOnCursorChangedListener(IOnCursorChangedListener cursorChangedListener) {
    23. this.cursorChangedListener = cursorChangedListener;
    24. }
    25. private IOnCursorChangedListener cursorChangedListener;
    26. /**
    27. * 声明,cursor改变时的监听接口
    28. * @author Administrator
    29. *
    30. */
    31. public interface IOnCursorChangedListener{
    32. void onCursorChanged(int token, Object cookie, Cursor cursor);
    33. }
    34. }
    //回调接口写法:这样就把adapter有回传回来了
  28. MyQueryHandler myQueryHandler = new MyQueryHandler(getContentResolver());
  29. myQueryHandler.setOnCursorChangedListener(new MyQueryHandler.IOnCursorChangedListener() {
  30. @Override
  31. /**
  32. * 当adapter 获得 cursor 的时候,回调此方法
  33. */
  34. public void onCursorChanged(int token, Object cookie, Cursor cursor) {
  35. // 让listview 显示最后一行
  36. listView.setSelection(adapter.getCount()-1);
  37. }
  38. });
  39. myQueryHandler.startQuery(99, adapter, MyConstants.URI_SMS, projection, " address="+address, null, " date ");
  40. }
  41. /**
  42. * 显示会话详情,所需要的列
  43. */
  44. private String[] projection={
  45. "_id","body","date","type"
  46. };
  47. /**
  48. * 短信内容所在列的索引值 为 1
  49. */
  50. private final int INDEX_BODY = 1;
  51. private final int INDEX_DATE = 2;
  52. private final int INDEX_TYPE = 3;
  53. private void init() {
  54. TextView title = (TextView) findViewById(R.id.tv_title_conversation_detail);
  55. String name = Tools.findNameByNumber(ctx, address);
  56. if(name !=null){ // 有此联系人
  57. title.setText(name);
  58. }else{ // 无此联系人
  59. title.setText(address);
  60. }
  61. findViewById(R.id.btn_back).setOnClickListener(this);
  62. findViewById(R.id.btn_ok).setOnClickListener(this);
  63. inputMsg = (EditText) findViewById(R.id.et_input_msg_conversation_detail);
  64. }
  65. @Override
  66. /**
  67. * 响应按钮的点击事件
  68. */
  69. public void onClick(View v) {
  70. switch (v.getId()) {
  71. case R.id.btn_back: // 后退按钮
  72. finish();
  73. break;
  74. case R.id.btn_ok: // 确定按钮
  75. //先判断输入的是否有内容,
  76. //如果有内容的话,就将内容以短信的形式发送出去,
  77. String msg = inputMsg.getText().toString();
  78. if(TextUtils.isEmpty(msg.trim())){
  79. Toast.makeText(ctx, "请输入短信内容", 0).show();
  80. return ;
  81. }
  82. // 发送短信
  83. Tools.sendMessage(ctx,msg,address);
  84. //清空输入框
  85. inputMsg.setText("");
  86. // 隐藏输入法键盘
  87. InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
  88. // 隐藏输入法的 API
  89. imm.toggleSoftInput(0, InputMethodManager.HIDE_NOT_ALWAYS);
  90. break;
  91. }
  92. }
  93. private MyListAdapter adapter;
  94. private class MyListAdapter extends CursorAdapter{
  95. public MyListAdapter(Context context, Cursor c) {
  96. super(context, c);
  97. }
  98. @Override
  99. /**
  100. * 当内容发生改变的时候,回调此方法
  101. */
  102. protected void onContentChanged() {
  103. // super 里面,做了重新查询的动作
  104. super.onContentChanged();
  105. // 让listView 显示最后一行
  106. listView.setSelection(getCount()-1);
  107. }
  108. @Override
  109. public View newView(Context context, Cursor cursor, ViewGroup parent) {
  110. View view =View.inflate(ctx, R.layout.list_item_conversation_detail, null);
  111. ViewHolder vh = new ViewHolder();
  112. vh.tlReceive = (TableLayout) view.findViewById(R.id.tl_receive);
  113. vh.msgReceive = (TextView) view.findViewById(R.id.tv_msg_receive);
  114. vh.dateReceive = (TextView) view.findViewById(R.id.tv_date_receive);
  115. vh.tlSend = (TableLayout) view.findViewById(R.id.tl_send);
  116. vh.msgSend = (TextView) view.findViewById(R.id.tv_msg_send);
  117. vh.dateSend = (TextView) view.findViewById(R.id.tv_date_send);
  118. view.setTag(vh);
  119. return view;
  120. }
  121. @Override
  122. public void bindView(View view, Context context, Cursor cursor) {
  123. ViewHolder vh = (ViewHolder) view.getTag();
  124. // 给listView条目设置内容
  125. int type = cursor.getInt(INDEX_TYPE);// 获得短信类型
  126. String text = cursor.getString(INDEX_BODY);//获得短信内容
  127. long when = cursor.getLong(INDEX_DATE);// 获得日期
  128. String dateStr = DateFormat.getDateFormat(ctx).format(when);
  129. if(type == MyConstants.TYPE_RECEIVE){ // 接收到的短信
  130. vh.tlReceive.setVisibility(View.VISIBLE);
  131. vh.tlSend.setVisibility(View.GONE);
  132. //设置短信内容
  133. vh.msgReceive.setText(text);
  134. //设置日期
  135. vh.dateReceive.setText(dateStr);
  136. }else{
  137. vh.tlReceive.setVisibility(View.GONE);
  138. vh.tlSend.setVisibility(View.VISIBLE);
  139. //设置短信内容
  140. vh.msgSend.setText(text);
  141. vh.dateSend.setText(dateStr);
  142. }
  143. }
  144. }
  145. private class ViewHolder {
  146. public TableLayout tlReceive;
  147. public TextView msgReceive;
  148. public TextView dateReceive;
  149. public TableLayout tlSend;
  150. public TextView msgSend;
  151. public TextView dateSend;
  152. }
  153. }

4.TableLayout、回调接口的更多相关文章

  1. Android回调接口的写法

    方法一: 定义一个接口,里面写想要对外提供的方法,在逻辑层方法的参数里传递进去,让在需要的时候调接口里的方法. 实例一: public class SmsUtils { public interfac ...

  2. Android中回调接口的使用

    MainActivity如下: package cn.testcallback; import android.os.Bundle; import android.app.Activity; /** ...

  3. 手势识别官方教程(2)识别常见手势用GestureDetector+手势回调接口/手势抽象类

    简介 GestureDetector识别手势. GestureDetector.OnGestureListener是识别手势后的回调接口.GestureDetector.SimpleOnGesture ...

  4. 使用回调接口实现ActiveX控件和它的容器程序的通讯

    本文阅读基础:有一定的C++基础知识(了解继承.回调函数),对MFC的消息机制有一定了解,对COM的基础知识有一定了解,对ActiveX控件有一定了解. 一. 前言 ActiveX控件和它的容器程序如 ...

  5. 【Android 应用开发】 自定义组件 宽高适配方法, 手势监听器操作组件, 回调接口维护策略, 绘制方法分析 -- 基于 WheelView 组件分析自定义组件

    博客地址 : http://blog.csdn.net/shulianghan/article/details/41520569 代码下载 : -- GitHub : https://github.c ...

  6. Spring Boot启动过程及回调接口汇总

    Spring Boot启动过程及回调接口汇总 链接: https://www.itcodemonkey.com/article/1431.html 来自:chanjarster (Daniel Qia ...

  7. C#POST 支付宝/微信回调接口

    一般支付宝/微信的回调接口都会返回xml格式,下面是调用类似这种接口的办法: public async Task<string> GetData() { string requestUrl ...

  8. vue回调接口

    1.微博回调接口 1.1oauth/urls.py 中添加路由 urlpatterns = [ path('weibo/callback/', views.OauthWeiboCallback.as_ ...

  9. Android中添加监听回调接口的方法

    在Android中,我们经常会添加一些监听回调的接口供别的类来回调,比如自定义一个PopupWindow,需要让new这个PopupWindow的Activity来监听PopupWindow中的一些组 ...

随机推荐

  1. 《剑指Offer》第20题(Java实现):定义栈的数据结构,请在该类型中实现一个能够得到栈中所含最小元素的min函数(时间复杂度应为O(1))。

    一.题目描述 定义栈的数据结构,请在该类型中实现一个能够得到栈中所含最小元素的min函数(时间复杂度应为O(1)). 二.思路解析 首先定义一个Integer类型的栈,记为stack,此栈用来完成数据 ...

  2. java调用本地播放器播放视频文件。调用本地播放器不能播放指定文件的说明。

    public class OpenExe extends HttpServlet { //打开本地播放器并播放视频 public static void openExe(String file) { ...

  3. svn如何根据提交日志信息回退版本

    问题场景: 1 记得提交的日志信息中包含openssl,但是不记得这次提交的版本号revesion,是svn初始化后中间的某次提交: 2 svn环境的操作系统平台为Fedora, 即命令行下:而且sv ...

  4. VB 性能优化点

    1.将Single,Double和Currency类型的变量替换为Integer或Long类型的变量:10倍 2.避免使用变体: 慢:Dim FSO as object     Set FSO = N ...

  5. Django使用第三方模块django-password-reset重置密码

    网上关于django第三方模块django-password-reset重置密码的几篇博客有一个严重的bug 见博客:https://blog.csdn.net/qq_42820268/article ...

  6. pandas 读写 Excel 格式的数据

    import pandas as pd #读入数据: df = pd.read_excel('data_in.xlsx') #导出数据: writer = pd.ExcelWriter('data_o ...

  7. canvas用数组方式做出下雨效果

    效果图 1.做出canvas画布和声明一个用来存储雨滴的数组 var c=document.getElementById('myCanvas'); var ctx= c.getContext('2d' ...

  8. Layui使用table展示数据

    今天在Layui官网拿了一个table表格数据展示的源码,研究遇到了很多问题,最后才把数据展示出来,和大家分享下. 源码地址:https://www.layui.com/demo/table/oper ...

  9. asp:DropDownList 使用

    <asp:DropDownList ID="DropDownList1" runat="server" onchange="return My_ ...

  10. 使用Jmeter进行http接口做功能、性能测试

    在测试移动APP时,会有很多接口需要做测试,我在这里介绍一下对HTTP接口做功能.性能的测试.首先我们会从开发人员拿到接口数据.     一.测试需求描述 1. 本次测试的接口为http服务端接口 2 ...