package com.partynetwork.iparty.imessage;
import java.io.File;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Collections;
import java.util.Date;
import java.util.List;
import org.jivesoftware.smack.Chat;
import org.jivesoftware.smack.MessageListener;
import org.jivesoftware.smack.XMPPConnection;
import org.jivesoftware.smack.XMPPException;
import org.jivesoftware.smack.packet.Message;
import org.jivesoftware.smack.packet.Message.Type;
import android.app.Activity;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.database.Cursor;
import android.graphics.Bitmap;
import android.net.Uri;
import android.os.Bundle;
import android.os.Handler;
import android.os.Handler.Callback;
import android.provider.MediaStore;
import android.provider.MediaStore.Images.Media;
import android.text.Editable;
import android.text.TextWatcher;
import android.text.format.DateFormat;
import android.view.KeyEvent;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.WindowManager;
import android.view.View.OnKeyListener;
import android.view.View.OnTouchListener;
import android.view.inputmethod.InputMethodManager;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageButton;
import android.widget.LinearLayout;
import android.widget.TextView;
import android.widget.Toast;
import com.baidu.mobstat.StatService;
import com.lidroid.xutils.util.LogUtils;
import com.openfire.manager.XmppConnection;
import com.partynetwork.dataprovider.util.ActionUtil.user;
import com.partynetwork.dataprovider.util.BitmapUtil;
import com.partynetwork.dataprovider.util.OpenfireUtil;
import com.partynetwork.dataprovider.util.T;
import com.partynetwork.dataprovider.util.TimeUtil;
import com.partynetwork.iparty.R;
import com.partynetwork.iparty.app.AppContext;
import com.partynetwork.iparty.app.AppException;
import com.partynetwork.iparty.app.entities.CommonUser;
import com.partynetwork.iparty.app.entities.IMessage;
import com.partynetwork.iparty.app.manager.MessageManager;
import com.partynetwork.iparty.app.manager.UserManager;
import com.partynetwork.iparty.app.util.StringUtils;
import com.partynetwork.iparty.imessage.RecordStatus.RecordListener;
import com.partynetwork.myview.mylistview.XListView;
import com.partynetwork.myview.mylistview.XListView.IXListViewListener;
public class ChatActivity extends Activity implements OnTouchListener,
IXListViewListener, OnKeyListener, TextWatcher, OnClickListener,
Callback {
public static String WITH_USER = "withUser";
public static final int SELECT_PICTURE = 100;// 相片
public static final int SELECT_CAMER = 101;// 拍照
private String imagePath;// 本次生成的路径
private String filePath;// 最后选择的图片地址
private int voiceTime;// 录音时长
private InputMethodManager imm;// 输入法管理
private WindowManager.LayoutParams params;
private boolean isFaceShow = false;
private boolean isMoreShow = false;
private TextView titieName;
private ChatAdapter adapter;
private XListView mMsgListView;
/************************************************ 底部控件 */
private ImageButton voiceBtn;// 录音,文字功能选择
private Button recarder;// 录音按钮
private EditText msgEt;// 消息输入文本框
private ImageButton faceBtn;// 表情
private Button sendBtn;// 发送按钮
private ImageButton moreBtn;// 更多功能
/************************************************ 功能面板 */
private LinearLayout faceOutLayout;//
private LinearLayout faceLinearLayout;// 表情功能按钮
private LinearLayout moreLinearLayout;// 更多功能布局
private LinearLayout recardStatusLayout;// 录音状态布局
private FacePageInit facePageInit;
private MorePageInit morePageInit;
private RecordStatus recordStatus;
private CommonUser mFromUser;// 聊天对象
private String withUser;// 聊天对象用户名
private Chat chat;// 聊天链接
private XmppConnection xmppConnection;
private XMPPConnection connection;
private List<IMessage> message_pool = new ArrayList<IMessage>();// 聊天数据集合
private Handler mHandler;// 更新界面的Handler
// 更多功能面板的功能监听
private MorePageListener morePageListener = new MorePageListener() {
public void click(int position) {
switch (position) {
case 0:
// 照片
Intent intent = new Intent(Intent.ACTION_GET_CONTENT, null);
intent.setType("image/*");
ChatActivity.this
.startActivityForResult(intent, SELECT_PICTURE);
break;
case 1:
// 拍照
Intent intent2 = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
imagePath = BitmapUtil.getImagePath();
Uri uri = Uri.fromFile(new File(imagePath));
intent2.putExtra(MediaStore.EXTRA_OUTPUT, uri);
ChatActivity.this.startActivityForResult(intent2, SELECT_CAMER);
break;
default:
break;
}
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
withUser = getIntent().getStringExtra(WITH_USER);
// System.out.println("withUser=========="+withUser);
setContentView(R.layout.chat_main);
initView();
initData();
}
@Override
protected void onResume() {
List<IMessage> list = MessageManager.getInstance(this)
.getMessageListByFrom(withUser, 1, 10);
if (list != null) {
message_pool.removeAll(message_pool);
message_pool.addAll(list);
}
if (null != message_pool && message_pool.size() > 0) {
Collections.sort(message_pool);
refreshMessage();
}
IntentFilter filter = new IntentFilter();
filter.addAction(OpenfireConstant.NEW_MESSAGE_ACTION);
registerReceiver(receiver, filter);
StatService.onResume(this);
super.onResume();
}
@Override
protected void onPause() {
unregisterReceiver(receiver);
StatService.onPause(this);
MessageManager.getInstance(this).updateStatusByFrom(withUser);
super.onPause();
}
protected List<IMessage> getMessages() {
return message_pool;
}
private void initView() {
imm = (InputMethodManager) getSystemService(INPUT_METHOD_SERVICE);
titieName = (TextView) this.findViewById(R.id.chat_title_name);
findViewById(R.id.chat_title_back).setOnClickListener(this);
mMsgListView = (XListView) findViewById(R.id.msg_listView);
mMsgListView.setOnTouchListener(this);
mMsgListView.setPullLoadEnable(false);
mMsgListView.setPullRefreshEnable(false);
mMsgListView.setXListViewListener(this);
voiceBtn = (ImageButton) this.findViewById(R.id.voice_btn);
voiceBtn.setOnClickListener(this);
recarder = (Button) this.findViewById(R.id.recarder);
msgEt = (EditText) this.findViewById(R.id.msg_et);
msgEt.setOnKeyListener(this);
msgEt.addTextChangedListener(this);
msgEt.setOnTouchListener(this);
sendBtn = (Button) this.findViewById(R.id.send_btn);
sendBtn.setOnClickListener(this);
moreBtn = (ImageButton) findViewById(R.id.more_btn);
moreBtn.setOnClickListener(this);
faceBtn = (ImageButton) findViewById(R.id.face_btn);
faceBtn.setOnClickListener(this);
faceOutLayout = (LinearLayout) findViewById(R.id.face_out_ll);
faceLinearLayout = (LinearLayout) findViewById(R.id.face_ll);
moreLinearLayout = (LinearLayout) findViewById(R.id.more_ll);
recardStatusLayout = (LinearLayout) findViewById(R.id.record_status);
}
private void initData() {
mHandler = new Handler(this);
params = getWindow().getAttributes();// 触摸ListView隐藏表情和输入法
new Thread() {
@Override
public void run() {
// 获得聊天对象
//XmppConnection.getInstance().login(user, password);
System.out.println("获得聊天对象");
xmppConnection = XmppConnection.getInstance();
System.out.println("聊天xmppConnection = XmppConnection.getInstance()");
connection = xmppConnection.getConnection();
System.out.println("聊天connection = xmppConnection.getConnection();");
chat = connection.getChatManager().createChat(OpenfireUtil.getJidByName(withUser), null);
System.out.println("获取登陆用户");
// 获取登陆用户
mFromUser = UserManager.getInstance(ChatActivity.this)
.getUserbyId(OpenfireUtil.getUserNameByJid(withUser));
// 触摸ListView隐藏表情和输入法
adapter = new ChatAdapter(ChatActivity.this, message_pool);
mHandler.sendEmptyMessage(1);// 刷新
}
}.start();
}
/**
* 发送消息
*
* @param messageContent
* @throws Exception
*/
protected void sendMessage(String messageContent, int contentType)
throws XMPPException {
if (StringUtils.isEmpty(messageContent)) {
return;
}
String time = TimeUtil.date2Str(Calendar.getInstance(),
OpenfireConstant.MS_FORMART);
Message message = new Message();
message.setProperty(IMessage.KEY_TIME, time);
message.setProperty(IMessage.CONTENT_TYPE, contentType);
message.setBody(messageContent);
chat.sendMessage(message);
IMessage newMessage = new IMessage();
newMessage.setState(1);
newMessage.setWithUser(OpenfireUtil.getUserNameByJid(withUser));
newMessage.setIsCome(0);
newMessage.setContent(messageContent);
newMessage.setContentType(contentType);
newMessage.setTime(time);
if (contentType == IMessage.VOICE) {
newMessage.setVoiceTime(voiceTime);
voiceTime = 0;
}
message_pool.add(newMessage);
MessageManager.getInstance(this).saveIMessage(newMessage);
chat.addMessageListener(new MessageListener() {
@Override
public void processMessage(Chat arg0, Message arg1) {
if (arg1.getType() == Type.error) {
T.showLong(ChatActivity.this, "消息发送失败!");
LogUtils.i(arg1.toString());
IMessage newMessage = new IMessage();
newMessage.setState(1);
newMessage.setWithUser(withUser);
newMessage.setIsCome(0);
newMessage.setContent(arg1.getBody());
newMessage.setContentType(StringUtils.toInt(arg1.getProperty(IMessage.CONTENT_TYPE).toString(),0));
newMessage.setTime(arg1.getProperty(IMessage.CONTENT_TYPE).toString());
MessageManager.getInstance(ChatActivity.this)
.delLastChatWithSb(newMessage);
}
}
});
mHandler.sendEmptyMessage(0);
}
protected void refreshMessage() {
if (adapter == null) {
return;
}
adapter.setList(message_pool);
adapter.refreshList();
mMsgListView.setSelection(message_pool.size() - 1);
}
/**
* 广播接收消息
*/
private BroadcastReceiver receiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
String action = intent.getAction();
if (OpenfireConstant.NEW_MESSAGE_ACTION.equals(action)) {
IMessage message = intent
.getParcelableExtra(IMessage.IMMESSAGE_KEY);
if (message.getWithUser().equals(withUser)) {
MessageManager.getInstance(ChatActivity.this).updateStatus(
message);
message_pool.add(message);
mHandler.sendEmptyMessage(0);
// NoticeManager.getInstance(ChatActivity.this)
// .updateStatusByFrom(to, Notice.READ);
}
}
}
};
@Override
public void onRefresh() {
List<IMessage> newMsgList = new ArrayList<IMessage>();
newMsgList = MessageManager.getInstance(this).getMessageListByFrom(
withUser, message_pool.size(), 10);
if (newMsgList != null && newMsgList.size() > 0) {
message_pool.addAll(newMsgList);
Collections.sort(message_pool);
mHandler.sendEmptyMessage(0);
}
mMsgListView.stopRefresh();
}
@Override
public void onLoadMore() {
}
@Override
public boolean onTouch(View v, MotionEvent event) {
switch (v.getId()) {
case R.id.msg_listView:
imm.hideSoftInputFromWindow(msgEt.getWindowToken(), 0);
hideFace();
hideMore();
break;
case R.id.msg_et:
imm.showSoftInput(msgEt, 0);
hideFace();
hideMore();
break;
default:
break;
}
return false;
}
@Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
if (keyCode == KeyEvent.KEYCODE_BACK) {
if (params.softInputMode == WindowManager.LayoutParams.SOFT_INPUT_STATE_VISIBLE
|| isFaceShow) {
faceOutLayout.setVisibility(View.GONE);
isFaceShow = false;
// imm.showSoftInput(msgEt, 0);
return true;
}
}
return false;
}
@Override
public void beforeTextChanged(CharSequence s, int start, int count,
int after) {
}
@Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
}
@Override
public void afterTextChanged(Editable s) {
if (s.length() > 0) {
moreBtn.setVisibility(View.GONE);
sendBtn.setVisibility(View.VISIBLE);
sendBtn.setEnabled(true);
} else {
moreBtn.setVisibility(View.VISIBLE);
sendBtn.setVisibility(View.GONE);
sendBtn.setEnabled(false);
}
}
@Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.send_btn:
String message = msgEt.getText().toString();
if ("".equals(message)) {
Toast.makeText(ChatActivity.this, "不能为空", Toast.LENGTH_SHORT)
.show();
} else {
try {
message=new String(message.getBytes(), "UTF-8");
sendMessage(message, IMessage.TEXT);
msgEt.setText("");
} catch (Exception e) {
T.showShort(this, "信息发送失败");
msgEt.setText(message);
}
closeInput();
}
break;
case R.id.face_btn:
if (!isFaceShow) {
imm.hideSoftInputFromWindow(msgEt.getWindowToken(), 0);
try {
Thread.sleep(80);// 解决此时会黑一下屏幕的问题
} catch (InterruptedException e) {
e.printStackTrace();
}
showFace();
} else {
hideFace();
}
break;
case R.id.chat_title_back:
finish();
break;
case R.id.voice_btn:
// 音频按钮
showOrHideRecarder();
break;
case R.id.more_btn:
if (!isMoreShow) {
imm.hideSoftInputFromWindow(msgEt.getWindowToken(), 0);
try {
Thread.sleep(80);// 解决此时会黑一下屏幕的问题
} catch (InterruptedException e) {
e.printStackTrace();
}
showMore();
} else {
hideMore();
}
break;
default:
break;
}
}
private void showMore() {
if (isFaceShow) {
hideFace();
}
if (morePageInit == null) {
morePageInit = new MorePageInit(this, moreLinearLayout,
morePageListener);
}
isMoreShow = true;
moreLinearLayout.setVisibility(View.VISIBLE);
}
private void hideMore() {
if (morePageInit == null) {
morePageInit = new MorePageInit(this, moreLinearLayout,
morePageListener);
}
isMoreShow = false;
moreLinearLayout.setVisibility(View.GONE);
}
private void showFace() {
if (isMoreShow) {
hideMore();
}
if (facePageInit == null) {
facePageInit = new FacePageInit(this, faceLinearLayout, msgEt);
}
isFaceShow = true;
faceOutLayout.setVisibility(View.VISIBLE);
}
private void hideFace() {
if (facePageInit == null) {
facePageInit = new FacePageInit(this, faceLinearLayout, msgEt);
}
isFaceShow = false;
faceOutLayout.setVisibility(View.GONE);
}
// 显示录音操作
private void showOrHideRecarder() {
// 隐藏软键盘
imm.hideSoftInputFromWindow(msgEt.getWindowToken(), 0);
// 隐藏表情
hideFace();
if (voiceBtn.getTag() == null) {
showRecareder();
} else {
hideRecareder();
}
}
private RecordListener recordListener = new RecordListener() {
@Override
public void recordEnd(File amrFile, final int voiceTime) {
final List<File> lists = new ArrayList<File>();
lists.add(amrFile);
new Thread() {
public void run() {
android.os.Message msg = new android.os.Message();
try {
AppContext ac = (AppContext) getApplication();
List<String> lis = ac.upFiles4Url(lists);
ChatActivity.this.voiceTime = voiceTime;
msg.what = 2;// 成功
msg.obj = lis;
} catch (AppException e) {
e.printStackTrace();
msg.what = -1;
msg.obj = e;
}
mHandler.sendMessage(msg);
}
}.start();
}
};
// 显示录制操作选项
private void showRecareder() {
voiceBtn.setTag(1);
voiceBtn.setImageResource(R.drawable.chat_bottombar_keybord);
msgEt.setVisibility(View.GONE);
faceBtn.setVisibility(View.GONE);
moreBtn.setVisibility(View.VISIBLE);
sendBtn.setVisibility(View.GONE);
recarder.setVisibility(View.VISIBLE);
if (recordStatus == null) {
recordStatus = new RecordStatus(this, recarder, recordListener);
recarder.setOnTouchListener(recordStatus);
recardStatusLayout.addView(recordStatus);
}
recardStatusLayout.setVisibility(View.VISIBLE);
}
// 隐藏录制操作选项
private void hideRecareder() {
voiceBtn.setTag(null);
voiceBtn.setImageResource(R.drawable.chat_bottombar_voice);
faceBtn.setVisibility(View.VISIBLE);
recarder.setVisibility(View.GONE);
msgEt.setVisibility(View.VISIBLE);
if (msgEt.length() > 0) {
moreBtn.setVisibility(View.GONE);
sendBtn.setVisibility(View.VISIBLE);
} else {
moreBtn.setVisibility(View.VISIBLE);
sendBtn.setVisibility(View.GONE);
}
recardStatusLayout.setVisibility(View.GONE);
}
/**
*
* 关闭键盘事件
*
* @update 2012-7-4 下午2:34:34
*/
public void closeInput() {
InputMethodManager inputMethodManager = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
if (inputMethodManager != null && this.getCurrentFocus() != null) {
inputMethodManager.hideSoftInputFromWindow(this.getCurrentFocus()
.getWindowToken(), InputMethodManager.HIDE_NOT_ALWAYS);
}
}
@Override
public boolean handleMessage(android.os.Message msg) {
switch (msg.what) {
case 0:
// 刷新视图
refreshMessage();
break;
case 1:
// 设置聊天对象
if (mFromUser != null) {
titieName.setText(mFromUser.getUserName());
}
mMsgListView.setAdapter(adapter);
mMsgListView.setSelection(adapter.getCount() - 1);
break;
case 2:
// 语音成功
List<String> lis = (List<String>) msg.obj;
if (lis != null) {
for (String str : lis) {
try {
ChatActivity.this.sendMessage(str, IMessage.VOICE);
} catch (XMPPException e) {
AppException.im(e).makeToast(ChatActivity.this);
}
}
}
break;
case 3:
// 图片
List<String> lis2 = (List<String>) msg.obj;
if (lis2 != null) {
for (String str : lis2) {
try {
ChatActivity.this.sendMessage(str, IMessage.PICTURE);
} catch (XMPPException e) {
AppException.im(e).makeToast(ChatActivity.this);
}
}
}
break;
case -1:
AppException e = (AppException) msg.obj;
e.makeToast(ChatActivity.this);
break;
default:
break;
}
return false;
}
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
Object object = null;
// 选择照片的返回结果
filePath = null;
if (data == null && requestCode == SELECT_CAMER) {
filePath = imagePath;
} else if (resultCode == Activity.RESULT_OK) {
switch (requestCode) {
case SELECT_PICTURE:
// 相册
Uri uri = data.getData();
String[] proj = { MediaStore.Images.Media.DATA };
Cursor cursor = this.managedQuery(uri, proj, null, null, null);
int column_index = cursor
.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);
cursor.moveToFirst();
filePath = cursor.getString(column_index);
break;
case SELECT_CAMER:
// 相机拍照
if (data.getData() != null) {
// 根据返回的URI获取对应的SQLite信息
Cursor cursor2 = this.getContentResolver().query(
data.getData(), null, null, null, null);
if (cursor2.moveToFirst()) {
filePath = cursor2.getString(cursor2
.getColumnIndex(Media.DATA));// 获取绝对路径
}
cursor2.close();
} else {// 三星 小米(小米手机不会自动存储DCIM... 这点让哥又爱又恨...)
object = (Bitmap) (data.getExtras() == null ? null : data
.getExtras().get("data"));
Bitmap bitmap = object == null ? null : (Bitmap) object;
if (bitmap != null) {
try {
filePath = BitmapUtil.saveImg(bitmap, DateFormat
.format("yyyyMMddhhmmss", new Date())
.toString());
} catch (Exception e) {
e.printStackTrace();
}
}
}
filePath = !filePath.equals("") ? filePath : getRealFilePath();
break;
default:
break;
}
} else {
Toast.makeText(this, "请重新选择图片", Toast.LENGTH_SHORT).show();
}
if (!StringUtils.isEmpty(filePath)) {
final List<File> lists = new ArrayList<File>();
lists.add(new File(filePath));
new Thread() {
public void run() {
android.os.Message msg = new android.os.Message();
try {
AppContext ac = (AppContext) getApplication();
List<String> lis = ac.upFiles4Url(lists);
msg.what = 3;// 成功
msg.obj = lis;
} catch (AppException e) {
e.printStackTrace();
msg.what = -1;
msg.obj = e;
}
mHandler.sendMessage(msg);
}
}.start();
}
}
/**
* 获取系统默认存储真实文件路径 两个路径 一个是最后一张所拍图片路径
* (由于设置了存储路径所以DCIM中会存储两张一模一样的图片,所以在此获取两张图片路径以便于缩放处理后全部删除)
*
* @param filePath
* @return
*/
protected String getRealFilePath() {
String filePath = "";
// MediaStore.Images.Media.EXTERNAL_CONTENT_URI
// content://media/external/images/media
Cursor cursor = this.getContentResolver().query(
MediaStore.Images.Media.EXTERNAL_CONTENT_URI, null, null, null,
Media.DATE_MODIFIED + " desc");
if (cursor.moveToNext()) {
/**
* _data:文件的绝对路径 Media.DATA='_data'
*/
filePath = cursor.getString(cursor.getColumnIndex(Media.DATA));
}
return filePath;
}
public interface MorePageListener {
public abstract void click(int position);
}
}