1 项目演示:
2 代码演示:
1)MainActivity类代码:
MainActivity类代码:
package com.example.phoneinteceptor_one;
import java.util.ArrayList;
import java.util.List;
import android.app.Activity;
import android.app.AlertDialog;
import android.content.DialogInterface;
import android.content.Intent;
import android.os.Bundle;
import android.text.Editable;
import android.text.TextWatcher;
import android.view.ContextMenu;
import android.view.ContextMenu.ContextMenuInfo;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.AdapterView.AdapterContextMenuInfo;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.BaseAdapter;
import android.widget.Button;
import android.widget.CheckBox;
import android.widget.CompoundButton;
import android.widget.CompoundButton.OnCheckedChangeListener;
import android.widget.EditText;
import android.widget.ListView;
import android.widget.TextView;
import android.widget.Toast;
import com.example.bean.BlackInfo;
import com.example.db.BlackInfoDao;
/**
* 主界面
1. 查询所有黑名单的列表并显示
2. 在查询输入框中输入关键字时, 显示所有匹配的黑名单列表
3. 在添加界面, 点击确认将信息保存到数据库表, 并回到主界面显示最新的列表
4. 长按某个黑名单项显示删除/修改的上下文菜单
点击删除的菜单项删除选定的黑名单, 并显示最新的列表
选中一些黑名单后项后, 点击删除按钮, 提示删除所有选中的黑名单
选中全选则所有黑名单选中, 否则都不选中
点击修改的上下文菜单项进入修改界面, 并显示选中的黑名单信息
在修改界面, 修改信息后, 点击确定修改表中对应的数据, 回到主界面显示新列表
*/
public class MainActivity extends Activity implements OnItemClickListener, OnClickListener, OnCheckedChangeListener {
private ListView lv_black_list;
private List<BlackInfo> data;
private BlackInfoDao blackInfoDao;
private BlackAdapter adapter;
private EditText atv_black_list_search;
private Button btn_black_list_delete;
private CheckBox cb_black_list_selectall;
//内部类---实现监听文本框的输入查询的内容时刻监听
private TextWatcher watcher = new TextWatcher() {
@Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
}
@Override
public void beforeTextChanged(CharSequence s, int start, int count,
int after) {
}
//在内容改变之后 就回调
@Override
public void afterTextChanged(Editable s) {
//获取输入的数据
String key = s.toString();
//查询要查询的列表数据--赋值给data
data = blackInfoDao.getBlacks(key);
//更新列表
lv_black_list.setAdapter(adapter);
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//获取显示的listview id
lv_black_list = (ListView) findViewById(R.id.lv_black_list);
btn_black_list_delete = (Button) findViewById(R.id.btn_black_list_delete);
cb_black_list_selectall = (CheckBox) findViewById(R.id.cb_black_list_selectall);
btn_black_list_delete.setOnClickListener(this);
//实现点击item事件方法
lv_black_list.setOnItemClickListener(this);
//需要数据 --集合数据--数据的初始化
blackInfoDao = new BlackInfoDao(this);
cb_black_list_selectall.setOnCheckedChangeListener(this);
// data = new DataSource().getAllBlacks();
data = blackInfoDao.getAll();//从数据库里面取数据
// BaseAdapter
//创建一个适配器--是一个抽象类 定义一个类去继承他
adapter = new BlackAdapter();
//显示设置数据到适配器
lv_black_list.setAdapter(adapter);
atv_black_list_search = (EditText) findViewById(R.id.atv_black_list_search);
//监听atv_black_list_search数据的改变
atv_black_list_search.addTextChangedListener(watcher);
//实现长按住一个item 弹出一个对话框 出来 是否删除还是取消-当前的activiet就是这类型的this
lv_black_list.setOnCreateContextMenuListener(this);
}
//lv_black_list.setOnCreateContextMenuListener(this);
//实现长按住一个item 默认的回调的方法1
@Override
public void onCreateContextMenu(ContextMenu menu, View v,
ContextMenuInfo menuInfo) {
super.onCreateContextMenu(menu, v, menuInfo);
//获取poistion
AdapterContextMenuInfo contextMenuInfo = (AdapterContextMenuInfo) menuInfo;
int position = contextMenuInfo.position;
//ItemId 不能一样menu.add(position, ItemId, 1, "更新");
menu.add(position, 1, 1, "更新");
menu.add(position, 2, 1, "删除");
}
//实现长按住一个item 默认的回调的方法2--获取是点击的删除还是更新
@Override
public boolean onContextItemSelected(MenuItem item) {
//获取点击的向
int itemId = item.getItemId();
if(itemId==1) {//更新
} else if(itemId==2) {//删除
//获取poistion
int position = item.getGroupId();
blackInfoDao.delete(data.get(position).get_id());
data.remove(position);//移除位置标号
adapter.notifyDataSetChanged();//通知更新界面
}
return super.onContextItemSelected(item);
}
//实现点击添加按钮 实现跳转到添加页面去
public void startAdd(View view){
int resultCode=1;
//startActivity(new Intent(this,BlackAddActivity.class));
//为了实现到添加数据成功之后--返回来更新列比列表的信息 所有--
startActivityForResult(new Intent(this,BlackAddActivity.class),resultCode);
}
//实现点击退出按钮
public void exit(View view){
finish();
}
//当添加界面返回时调用----完数据之后 就返回来---
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent intent) {
//回调方法--requestCode请求码--resultCode结果码
if(requestCode==1 && resultCode==2){
//都满足--就更新就界面
data = blackInfoDao.getAll();
//去更新感应最新的数据
lv_black_list.setAdapter(adapter);
}
}
class BlackAdapter extends BaseAdapter {
//巧妙之处
private String[] types = {"电话+短信","电话","短信"};
@Override
public int getCount() { // 数据集合中数据的个数
return data.size();
}
@Override
public Object getItem(int position) {// 返回指定下标的数据对象
return data.get(position);
}
@Override
public long getItemId(int position) {// 这个不重要
return position;
}
// 此方法最关键
// 根据指定的下标返回将要显示的item中的一个View对象
// 返回的View对象中必须包含显示的数据--包含对应的数据
@Override
public View getView(int position, View convertView, ViewGroup parent) {
//加载item的布局文件--打气筒
convertView = View.inflate(MainActivity.this, R.layout.black_item, null);
//设置对应的数据到对应的视图中
TextView number =(TextView) convertView.findViewById(R.id.tv_item_number);
TextView name =(TextView) convertView.findViewById(R.id.tv_item_name);
TextView type =(TextView) convertView.findViewById(R.id.tv_item_type);
//获取当前位置的数据 返回的是的一个对象
BlackInfo info = data.get(position);
//把数据放到按键中去
number.setText(info.getNumber());
name.setText(info.getName());
//巧妙的地方就在这
type.setText(types[info.getType()]);
//返回
return convertView;
}
}
//实现点击item向 回调方法
@Override
public void onItemClick(AdapterView<?> arg0, View view, int poisoion, long arg3) {
CheckBox box = (CheckBox) view.findViewById(R.id.cb_item_black);//点击复选框
box.toggle();//切换选中状态
//弹出对话框
Toast.makeText(this,data.get(poisoion).getNumber(),0).show();
}
@Override
public void onClick(View v) {
if (v == btn_black_list_delete) {
List<Integer> selectIds = new ArrayList<Integer>();
for (BlackInfo blackNumber : data) {
if (blackNumber.isChecked()) {
selectIds.add(blackNumber.get_id());
}
}
if (selectIds.size() == 0) {
Toast.makeText(this, "请选择要删除的项", 0).show();
} else {
showDeleteDialog(selectIds);
}
}
}
private void showDeleteDialog(final List<Integer> selectIds) {
new AlertDialog.Builder(this)
.setTitle("黑名单删除")
.setMessage("你确认删除选中项吗?")
.setPositiveButton(R.string.confirm,
new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog,
int which) {
blackInfoDao.deleteBlacks(selectIds);
List<BlackInfo> list = blackInfoDao
.getAll();
list.addAll(list);
adapter.notifyDataSetChanged();
}
}).setNegativeButton(R.string.cancel, null).show();
}
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
for (BlackInfo blackNumber : data) {
blackNumber.setChecked(isChecked);
}
adapter.notifyDataSetChanged();
}
}
2)BlackAddActivity类代码:
package com.example.phoneinteceptor_one;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.RadioButton;
import android.widget.RadioGroup;
import android.widget.RadioGroup.OnCheckedChangeListener;
import android.widget.Toast;
import com.example.bean.BlackInfo;
import com.example.db.BlackInfoDao;
public class BlackAddActivity extends Activity {
public Button btn_black_add_cancel;
private BlackInfoDao blackInfoDao;
private BlackInfo info = new BlackInfo();
private EditText et_black_add_number;
private EditText et_black_add_name;
private RadioGroup rg_black_add_actions;
//内部类--点击复选框的监听事件
private OnCheckedChangeListener listener = new OnCheckedChangeListener () {
@Override
public void onCheckedChanged(RadioGroup group, int checkedId) {
//这是checkedId是你选择的RadioButton的id
RadioButton rb =(RadioButton) group.findViewById(checkedId);
String tog = (String)rb.getTag(); //0 1 2
//Log.d("BlackAddActivity","togtogtogtogtog=="+tog);
info.setType(Integer.parseInt(tog)); //转换成整形设置到实例
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_black_add);
//实例化义务逻辑实例
blackInfoDao = new BlackInfoDao(this);
et_black_add_number = (EditText) findViewById(R.id.et_black_add_number);
et_black_add_name = (EditText) findViewById(R.id.et_black_add_name);
rg_black_add_actions = (RadioGroup) findViewById(R.id.rg_black_add_actions);
//实现点击复选框的监听事件
rg_black_add_actions.setOnCheckedChangeListener(listener);
//点击取消时 实现回到主界面
findViewById(R.id.btn_black_add_cancel).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
//回到上一个界面--干掉自己
finish();
}
});
}
//实现点击确认 保存数据到数据库
public void saveBlackInfo(View view){
//验证数据是否输入合法
String number = et_black_add_number.getText().toString().trim();
if(number.length()==0){
Toast.makeText(this, "电话号码不能为空", 0).show();
return ;
}
info.setNumber(number);
//name
String name = et_black_add_name.getText().toString().trim();
if(number.length()==0){
name = number;//不指定名称 就把你的号码 赋值给你的名称
// Toast.makeText(this, "必须指定号码", 0).show();
}
info.setName(name);
//保存数据到表里面
blackInfoDao.add(info);
//设置一个返回的结果码、-给要返回的界面一个结果码--以便标识出来
int resultCode = 2;
setResult(resultCode);
//返回到上一个界面--通知上一个界面 更新列表
finish();//所谓的是自己干掉自己
Toast.makeText(this, "添加成功!", 0).show();
}
}
3)AndroidManifest.xml权限配置:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.phoneinteceptor_one"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="8"
android:targetSdkVersion="18" />
<!-- 接收短信广播的权限 -->
<uses-permission android:name="android.permission.RECEIVE_SMS"/>
<!-- 读取短信内容的权限 -->
<uses-permission android:name="android.permission.READ_SMS"/>
<!-- 接收开机广播的权限 -->
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<!-- 读取电话状态的权限 -->
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<!-- 打/挂电话的权限 -->
<uses-permission android:name="android.permission.CALL_PHONE" />
<application
android:allowBackup="true"
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:theme="@android:style/Theme.Light.NoTitleBar" >
<activity
android:name="com.example.phoneinteceptor_one.MainActivity"
android:label="@string/app_name" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name="com.example.phoneinteceptor_one.BlackAddActivity"
android:label="@string/title_activity_black_add" >
</activity>
<!--注册一个广播接收器 SmsReceiver 优先级0==100 优先级设置为最大值 短信-->
<receiver android:name="com.example.receiver.SmsReceiver">
<intent-filter android:priority="1000">
<action android:name="android.provider.Telephony.SMS_RECEIVED"/>
</intent-filter>
</receiver>
<!-- 注册一个广播接收器 BootReceiver 开机服务-->
<receiver android:name="com.example.receiver.BootReceiver">
<intent-filter android:priority="1000">
<action android:name="android.intent.action.BOOT_COMPLETED"/>
</intent-filter>
</receiver>
<service android:name="com.example.receiver.ListenerPhoneService"></service>
</application>
</manifest>
4)代码结构:
说明:部分代码没上传--此代码仅供参考………