`
zdpeng
  • 浏览: 126605 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

android 通过Service和Receiver来监听网络状态

 
阅读更多

注:本内容部分来自网络

 

需要在Activity中得到网络状态,就是需要在接收到网络状态改变的广播的时候,要能够与Activity进行交互,通知Activity当前的网络状态,这就需要写一个Service,并且绑定到Activity,把广播监听到的实时的网络状态返回给Activity。

package com.yooeee.ziyoutong.service;

import java.util.Date;
import java.util.Timer;
import java.util.TimerTask;

import android.app.Service;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.net.ConnectivityManager;
import android.net.NetworkInfo;
import android.net.NetworkInfo.State;
import android.os.Binder;
import android.os.IBinder;
import android.util.Log;

public class ReceiveMsgService extends Service
{// 实时监听网络状态改变
	private BroadcastReceiver mReceiver = new BroadcastReceiver()
	{
		@Override
		public void onReceive(Context context, Intent intent)
		{
			String action = intent.getAction();
			if (action.equals(ConnectivityManager.CONNECTIVITY_ACTION))
			{
				Timer timer = new Timer();
				timer.schedule(new QunXTask(getApplicationContext()), new Date());
			}
		}
	};

	public interface GetConnectState
	{
		public void GetState(boolean isConnected); // 网络状态改变之后,通过此接口的实例通知当前网络的状态,此接口在Activity中注入实例对象
	}

	private GetConnectState onGetConnectState;

	public void setOnGetConnectState(GetConnectState onGetConnectState)
	{
		this.onGetConnectState = onGetConnectState;
	}

	private Binder binder = new MyBinder();
	private boolean isContected = true;

	@Override
	public IBinder onBind(Intent intent)
	{
		return binder;
	}

	@Override
	public void onCreate()
	{// 注册广播
		IntentFilter mFilter = new IntentFilter();
		mFilter.addAction(ConnectivityManager.CONNECTIVITY_ACTION); // 添加接收网络连接状态改变的Action
		registerReceiver(mReceiver, mFilter);
	}

	class QunXTask extends TimerTask
	{
		private Context context;

		public QunXTask(Context context)
		{
			this.context = context;
		}

		@Override
		public void run()
		{
			if (isNetworkConnected(context) || isWifiConnected(context))
			{
				isContected = true;
			}
			else
			{
				isContected = false;
			}
			if (onGetConnectState != null)
			{
				onGetConnectState.GetState(isContected); // 通知网络状态改变
				Log.i("mylog", "通知网络状态改变:" + isContected);
			}
		}

		/*
		 * 判断是3G否有网络连接
		 */
		private boolean isNetworkConnected(Context context)
		{
			if (context != null)
			{
				ConnectivityManager mConnectivityManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
				NetworkInfo mNetworkInfo = mConnectivityManager.getActiveNetworkInfo();
				if (mNetworkInfo != null)
				{
					return mNetworkInfo.isAvailable();
				}
			}
			return false;
		}

		/*
		 * 判断是否有wifi连接
		 */
		private boolean isWifiConnected(Context context)
		{
			if (context != null)
			{
				ConnectivityManager mConnectivityManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
				NetworkInfo mWiFiNetworkInfo = mConnectivityManager.getNetworkInfo(ConnectivityManager.TYPE_WIFI);
				if (mWiFiNetworkInfo != null)
				{
					return mWiFiNetworkInfo.isAvailable();
				}
			}
			return false;
		}
	}

	public class MyBinder extends Binder
	{
		public ReceiveMsgService getService()
		{
			return ReceiveMsgService.this;
		}
	}

	@Override
	public void onDestroy()
	{
		super.onDestroy();
		unregisterReceiver(mReceiver); // 删除广播
	}
}
 

接下来在Activity中,绑定服务

public class MainActivity extends Activity  {

	protected String TAG = "mylog";
	ReceiveMsgService receiveMsgService;
	private boolean conncetState = true; // 记录当前连接状态,因为广播会接收所有的网络状态改变wifi/3g等等,所以需要一个标志记录当前状态

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		// TODO Auto-generated method stub
		super.onCreate(savedInstanceState);
		setContentView(R.layout.page_main);
				
		bind();


	}

	private void bind() {
		Intent intent = new Intent(MainActivity.this, ReceiveMsgService.class);
		bindService(intent, serviceConnection, Context.BIND_AUTO_CREATE);
	}

	private ServiceConnection serviceConnection = new ServiceConnection() {
		@Override
		public void onServiceDisconnected(ComponentName name) {
		}

		@Override
		public void onServiceConnected(ComponentName name, IBinder service) {
			receiveMsgService = ((ReceiveMsgService.MyBinder) service)
					.getService();
			receiveMsgService.setOnGetConnectState(new GetConnectState() { // 添加接口实例获取连接状态
						@Override
						public void GetState(boolean isConnected) {
							if (conncetState != isConnected) { // 如果当前连接状态与广播服务返回的状态不同才进行通知显示
								conncetState = isConnected;
								if (conncetState) {// 已连接
									handler.sendEmptyMessage(1);
								} else {// 未连接
									handler.sendEmptyMessage(2);
								}
							}
						}
					});
		}
	};
	
	private void unbind() {
		if (receiveMsgService != null ) {
			unbindService(serviceConnection);
			Log.i("mylog", "执行unbind()");
		}
	}

	Handler handler = new Handler() {
		public void handleMessage(Message msg) {

			switch (msg.what) {
			case 1:// 已连接
				Toast.makeText(MainActivity.this, "网络已经连接" ,Toast.LENGTH_LONG).show();
				break;
			case 2:// 未连接
				Toast.makeText(MainActivity.this, "网络未连接" ,Toast.LENGTH_LONG).show();
				break;
			default:
				break;
			}
			;
		};

	};
	
	@Override
	protected void onDestroy()
	{
		// TODO Auto-generated method stub
		super.onDestroy();
		unbind();
	}
	
	
}

 

 

当然也可以直接在Activity中注册一个广播,在接收到广播之后进行判断,这种情况就稍简单些,Activity可以直接访问到广播中的一些变量;最后,需要添加一些权限:

<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />    
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />

 

 单纯用广播来监控网络状态,前提是不需要与Activity通信

private ConnectivityManager connectivityManager;
   
private NetworkInfo info;

        @Override
	public void onReceive(Context context, Intent intent) {
		// TODO Auto-generated method stub
		String action = intent.getAction();
        if (action.equals(ConnectivityManager.CONNECTIVITY_ACTION)) {
            Log.d("mylog", "网络状态已经改变");
            connectivityManager = (ConnectivityManager)context.getSystemService(context.CONNECTIVITY_SERVICE);
            info = connectivityManager.getActiveNetworkInfo();  
            if(info != null && info.isAvailable()) {
                String name = info.getTypeName();
                Log.d("mylog", "当前网络名称:" + name);
            } else {
                Log.d("mylog", "没有可用网络");
            }
        }
		
	}

 

如果分别需要得到3G和WIFI连接方式如下:

 

ConnectivityManager connectMgr = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);

//3G		
NetworkInfo mobNetInfo = connectMgr.getNetworkInfo(ConnectivityManager.TYPE_MOBILE);
//WIFI
NetworkInfo wifiNetInfo = connectMgr.getNetworkInfo(ConnectivityManager.TYPE_WIFI);

 

最后别忘了在XML中注册广播,当然也可以在代码中注册广播。

 

<receiver
            android:name="com.yooeee.freepass.service.NetworkReceiver"
            android:label="NetworkConnection" >
            <intent-filter>
                <action android:name="android.net.conn.CONNECTIVITY_CHANGE" />
                <action android:name="android.intent.action.USER_PRESENT" />
            </intent-filter>
        </receiver>

 

 

分享到:
评论
2 楼 云上太阳 2015-02-02  
写的挺好的嘛, 回调机制都用了。。。
1 楼 ponos 2015-01-12  

相关推荐

    Android网络音乐播放器 源码下载

    安卓四大组件之Activity,Service, Broacast Receiver分别实现界面的展示,后台播放和下载,组件之间通信; HttpURLConnection实现歌曲,专辑图片,歌词的搜索; 多线程下载-多个线程分割下载任务提高下载效率并结合...

    android应用程序开机启动

    下面就是一个简单的开机启动的广播receiver"&gt;Android应用程序可以实现开机时启动相关应用 如service等 Android系统在开机启动时会发出一个系统广播&quot;android intent action BOOT COMPLETED&quot; 在接收到这个...

    Android监听来电和去电的实现方法

    本文实例讲述了Android监听来电和去电的实现方法。分享给大家供大家参考,具体如下: 要监听android打电话和接电话,只需下面2步骤 第一步,写一个Receiver继承自BroadcastReceiver import android.app.Service; ...

    疯狂Android讲义源码

     2.7.2 使用监听器来监听菜单事件 136  2.7.3 创建复选菜单项和单选菜单项 137  2.7.4 设置与菜单项关联的Activity 140  2.7.5 上下文菜单 141  2.8 本章小结 143  第3章 事件处理 144  3.1 Android的事件...

    Android开发应用实战详解源代码

    2.8.2 使用broadcast receiver监听广播 2.8.3 android本地广播 2.9 小结 第3章 设备界面演练 3.1 文字标签处理 3.2 改变屏幕窗口元素的背景颜色 3.3 改变textview的文字颜色 3.4 实现textview文字的替换 3.5 获取...

    疯狂Android讲义.part2

    2.7.2 使用监听器来监听菜单事件 136 2.7.3 创建复选菜单项和单选菜单项 137 2.7.4 设置与菜单项关联的Activity 140 2.7.5 上下文菜单 141 2.8 本章小结 143 第3章 事件处理 144 3.1 Android的事件处理 145 3.2 基于...

    疯狂Android讲义.part1

    2.7.2 使用监听器来监听菜单事件 136 2.7.3 创建复选菜单项和单选菜单项 137 2.7.4 设置与菜单项关联的Activity 140 2.7.5 上下文菜单 141 2.8 本章小结 143 第3章 事件处理 144 3.1 Android的事件处理 145 3.2 基于...

    Android开发艺术探索

    第11章 Android的线程和线程池 / 391 11.1 主线程和子线程 / 392 11.2 Android中的线程形态 / 392 11.2.1 Async Task / 392 11.2.2 Async Task的工作原理 / 395 11.2.3 Handler Thread / 402 11.2.4 ...

    android开发艺术探索高清完整版PDF

    316 9.1 四大组件的运行状态 / 316 9.2 Activity的工作过程 / 318 9.3 Service的工作过程 / 336 9.3.1 Service的启动过程 / 336 9.3.2 Service的绑定过程 / 344 9.4 Broadcast Receiver的工作过程 / 352 9.4.1...

    android 面试2

    对于activity和service来说,它指定了请求的操作名称和待操作数据的URIIntent对象可以显式的指定一个目标component。如果这样的话,android会找到这个component(基于manifest文件中的声明)并激活它。但如果一个...

    Android ScreenLockReceiver监听锁屏功能示例

    本文实例讲述了Android ScreenLockReceiver监听锁屏功能。分享给大家供大家参考,具体如下: 监听屏幕锁屏状态(注册接受者–执行业务–注销接受者) public class AppLockService extends Service { private ...

    Android开发资料合集-World版!

    9.13、调用ANDROID INSTALLER 安装和卸载程序 215 9.14、后台监控应用程序包的安装&卸载 216 9.15、显示应用详细列表 224 9.16、寻找应用 224 9.17、注册一个BROADCASTRECEIVER 225 9.18、打开另一程序 225 9.19、...

    Android 开发技巧

    0、ANDROID常用类库说明 6 1、ANDROID文件系统与应用程序架构 7 1.1、ANDROID 文件系统 7 1.2、ANDROID应用程序架构 9 2、ANDROID应用程序结构 11 2.1、ACTIVITY 12 2.1.1、概述 12 2.1.2、Activity的生命周期 15 ...

    安卓应用实现之音乐播放器

    界面的上半部显示正在播放的歌曲信息。...播放完当前歌曲,自动切换到下一曲。 使用service进行音乐播放。使用BroadcastReceiver将歌曲信息传输到...main Activity中的broadcast receiver将会监听从service传回来的广播。

    浅析Android手机卫士sim卡绑定

    获取TelephonyManager对象,通过getSystemService(TELEPHONY_SERVICE) 调用TelephonyManager对象的getSimSerialNumber()方法,得到String类型的序列号 把序列号保存在SharedPreences里面 需要加权限 android....

Global site tag (gtag.js) - Google Analytics