Android笔记(五十九)Android总结:四大组件——Service篇
什么是服务?
服务(service)是Android中实现程序后台运行的解决方案,适用于去执行那些不需要和用户交互并且还需要长期运行的任务。服务的运行不依赖于任何用户界面。
服务运行在主线程中,所以在service不能用来做一些耗时操作。
服务的用法
1.新建一个继承自Service的类,并实现其抽象方法
2.构建一个Intent
3.使用startService(intent)启动服务
4.使用stopService(intent)停止服务
服务在创建的时候会调用其onCreate()方法,而在每次启动服务的时候都会调用onStartCommand()方法,在服务销毁的时候会调用onDestroy()方法。
Service和Activity的通信
在现实编程中,我们除了要开启关闭Service之外,我们往往还需要获取Service执行的步骤、进度等等,这就需要Service和Activity之间进行通信。
想要Activity和Service之间进行通信,需要使用bindService()和unbindService()方法启动、关闭Service。
bindService()方法有三个参数,分别是:
1.service:通过Intent指定要启动的Service
2.conn:一个ServiceConnection对象,该对用用于监听访问者与Service之间的连接情况。当访问者与Service之间连接成功时将回调该ServiceConnection的onServiceConnectioned方法,当Service所在的宿主进程终止,导致Service与访问者之间断开连接的时回调该ServiceConnection的onServiceDesconnected方法
3.flags:指定绑定时是否自动创建Service(如果该Service还没有创建)。可指定为0(不自动创建),BIND_AUTO_CREATE(自动创建)。
Activity传值给Service
MainActivity.java
package com.example.servicedemo; import com.example.servicedemo.MyService.MyBinder; import android.app.Activity;
import android.content.ComponentName;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.IBinder;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView; public class MainActivity extends Activity implements OnClickListener { private Button start_service_button, stop_service_button, bind_service_button, unbind_service_button,
pass_on_message;
private TextView tvOut; private Intent intent; private MyBinder myBinder; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main); start_service_button = (Button) findViewById(R.id.start_service_button);
stop_service_button = (Button) findViewById(R.id.stop_service_button);
bind_service_button = (Button) findViewById(R.id.bind_service_button);
unbind_service_button = (Button) findViewById(R.id.unbind_service_button);
pass_on_message = (Button) findViewById(R.id.pass_on_message);
tvOut = (TextView) findViewById(R.id.tvOut); start_service_button.setOnClickListener(this);
stop_service_button.setOnClickListener(this);
bind_service_button.setOnClickListener(this);
unbind_service_button.setOnClickListener(this);
pass_on_message.setOnClickListener(this);
} @Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.start_service_button:
start();
break;
case R.id.stop_service_button:
stop();
break;
case R.id.bind_service_button:
bind();
break;
case R.id.unbind_service_button:
unbind();
break;
case R.id.pass_on_message:
passOnMessage();
break; }
} // 传递数据
private void passOnMessage() {
myBinder.setData("BBBBB"); } // 解除绑定Service
private void unbind() {
Intent intent = new Intent(this, MyService.class);
Log.d("TTTT", "===========点击了unbind按钮============");
unbindService(conn);
} // 绑定启动service
private void bind() {
Intent intent = new Intent(this, MyService.class);
Log.d("TTTT", "===========点击了bind按钮============");
bindService(intent, conn, BIND_AUTO_CREATE);
} // 使用stopService关闭Service
private void stop() {
Intent intent = new Intent(this, MyService.class);
Log.d("TTTT", "===========点击了stop按钮============");
stopService(intent);
} // 使用startService启动Service
private void start() {
Intent intent = new Intent(this, MyService.class);
Log.d("TTTT", "===========点击了start按钮============");
startService(intent); } ServiceConnection conn = new ServiceConnection() { @Override
public void onServiceDisconnected(ComponentName name) {
// TODO Auto-generated method stub } @Override
public void onServiceConnected(ComponentName name, IBinder service) {
myBinder = (MyBinder) service; }
};
}
MyService.java
package com.example.servicedemo; import android.app.Service;
import android.content.Intent;
import android.os.Binder;
import android.os.IBinder;
import android.util.Log; public class MyService extends Service { private String data = "AAAAA"; @Override
public IBinder onBind(Intent intent) {
Log.d("TTTT", "IBind方法运行了...");
return new MyBinder();
} @Override
public void onCreate() {
Log.d("TTTT", "onCreate方法运行了...");
new Thread(new Runnable() {
@Override
public void run() {
int j = 0; for (int i = 0; i < 30; i++) {
try {
j++; String str = j + ":" + data;
Log.d("TTTT", str); Thread.sleep(1000 * 1);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}).start();
super.onCreate();
} @Override
public void onStart(Intent intent, int startId) {
// TODO Auto-generated method stub
super.onStart(intent, startId);
Log.d("TTTT", "onStart方法运行了...");
} @Override
public int onStartCommand(Intent intent, int flags, int startId) { Log.d("TTTT", "onStartCommand方法运行了..."); return super.onStartCommand(intent, flags, startId);
} @Override
public void onDestroy() {
super.onDestroy();
Log.d("TTTT", "onDestroy方法运行了...");
} @Override
public boolean onUnbind(Intent intent) {
Log.d("TTTT", "onUnbind方法运行了...");
return super.onUnbind(intent);
} public class MyBinder extends Binder {
public void setData(String str) {
data = str;
} public MyService getService() {
return MyService.this;
}
}
}
activity_main.xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.example.servicedemo.MainActivity" > <TextView
android:id="@+id/tvOut"
android:layout_width="match_parent"
android:layout_height="wrap_content" /> <Button
android:id="@+id/start_service_button"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="开启服务" /> <Button
android:id="@+id/stop_service_button"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="关闭服务" /> <Button
android:id="@+id/bind_service_button"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="绑定服务" /> <Button
android:id="@+id/unbind_service_button"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="解除绑定" /> <Button
android:id="@+id/pass_on_message"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="传递数据" /> </LinearLayout>
Service传值给Activity
MainActivity.java
package com.example.passupmessageforservice; import com.example.passupmessageforservice.MyService.Callback;
import com.example.passupmessageforservice.MyService.MyBinder; import android.app.Activity;
import android.content.ComponentName;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.Handler;
import android.os.IBinder;
import android.os.Message;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView; public class MainActivity extends Activity implements OnClickListener { private Button bt_bindService, bt_unbindService, bt_sync;
private TextView showtext;
private EditText et_str; private Intent intent; private MyBinder myBinder; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main); initView(); bt_bindService.setOnClickListener(this);
bt_unbindService.setOnClickListener(this);
bt_sync.setOnClickListener(this);
} // 初始化view组件
private void initView() {
bt_bindService = (Button) findViewById(R.id.bt_bindService);
bt_unbindService = (Button) findViewById(R.id.bt_unbindService);
bt_sync = (Button) findViewById(R.id.bt_sync);
showtext = (TextView) findViewById(R.id.showtext);
et_str = (EditText) findViewById(R.id.et_str);
} // 响应点击事件
@Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.bt_bindService:
bind();
break;
case R.id.bt_unbindService:
unbind();
break;
case R.id.bt_sync:
sync();
break;
}
} // 绑定服务
private void bind() {
Log.d("TTTT", "=========执行bind方法=========");
intent = new Intent(this, MyService.class);
bindService(intent, conn, BIND_AUTO_CREATE);
} // 解除绑定
private void unbind() {
Log.d("TTTT", "=========执行unbind方法=========");
unbindService(conn);
} // 同步数据方法
private void sync() {
myBinder.setData(et_str.getText().toString());
} ServiceConnection conn = new ServiceConnection() { @Override
public void onServiceDisconnected(ComponentName name) {
Log.d("TTTT", "=========执行onServiceDisconnected方法========="); } @Override
public void onServiceConnected(ComponentName name, IBinder service) {
Log.d("TTTT", "=========执行onServiceConnected方法=========");
myBinder = (MyBinder) service;
myBinder.getService().setCallback(new Callback() { public void change(String str) {
Log.d("TTTT", "~~~~~");
Message msg = new Message();
msg.obj = str;
handler.sendMessage(msg);
}
});
}
}; Handler handler = new Handler() {
public void handleMessage(android.os.Message msg) {
String str = (String) msg.obj;
showtext.setText(str);
};
}; }
MyService.java
package com.example.passupmessageforservice; import android.app.Service;
import android.content.Intent;
import android.os.Binder;
import android.os.IBinder;
import android.util.Log; public class MyService extends Service { private String logStr = "AAAA"; private Callback callback = null; private boolean status = false; @Override
public IBinder onBind(Intent intent) {
Log.d("TTTT", "~~~~~~~~~~~~执行onBind方法~~~~~~~~~~~~");
return new MyBinder();
} @Override
public boolean onUnbind(Intent intent) {
Log.d("TTTT", "~~~~~~~~~~~~执行onUnbind方法~~~~~~~~~~~~");
status = true;
return super.onUnbind(intent);
} @Override
public void onCreate() {
super.onCreate(); new Thread(new Runnable() {
@Override
public void run() {
for (int i = 0; i < 15; i++) {
if (!status) { if (callback != null) {
callback.change(i + ":" + logStr);
Log.d("TTTT", "================================");
} try {
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
}).start(); Log.d("TTTT", "~~~~~~~~~~~~执行onCreate方法~~~~~~~~~~~~");
} @Override
public int onStartCommand(Intent intent, int flags, int startId) {
Log.d("TTTT", "~~~~~~~~~~~~执行onStartCommand方法~~~~~~~~~~~~");
return super.onStartCommand(intent, flags, startId);
} @Override
public void onDestroy() { Log.d("TTTT", "~~~~~~~~~~~~执行onDestroy方法~~~~~~~~~~~~");
super.onDestroy();
} public class MyBinder extends Binder {
public void setData(String str) {
logStr = str;
} public MyService getService() {
return MyService.this;
}
} public interface Callback {
void change(String str);
} public Callback getCallback() {
return callback;
} public void setCallback(Callback callback) {
this.callback = callback;
} }
activity_main.xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.example.passupmessageforservice.MainActivity" > <EditText
android:id="@+id/et_str"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="输入要传入的文字" /> <Button
android:id="@+id/bt_bindService"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="绑定服务" /> <Button
android:id="@+id/bt_unbindService"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="解除绑定" /> <Button
android:id="@+id/bt_sync"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="同步数据" /> <TextView
android:id="@+id/showtext"
android:layout_width="match_parent"
android:layout_height="wrap_content" /> </LinearLayout>
Service的生命周期
Service的生命周期,从创建到销毁,有两条不同的路径。
直接启动
使用startService()启动Service,初次启动会先调用onCreate()方法,然后调用onStartCommand()方法,创建Service之后,之后不会再调用onCreate()方法
这种Service可以无限的运行下去,必须调用stopSelf()方法或者其他组件调用stopService()方法来停止它
停止时会调用其onDestroy()方法来销毁这个Service
绑定启动
被绑定的Service是当其他组件调用bindService来创建的
初次绑定会调用onCreate()方法,之后便不会再调用
紧接着会调用onBind()方法
当别的组件调用unbindService()时候,会调用Service的unbind方法,紧接着调用onDestroy()方法。

Android笔记(五十九)Android总结:四大组件——Service篇的更多相关文章
- Android笔记(六十九) 仿微信界面(一)
		综合之前的Fragment和自定义组件的知识,实现微信界面 MainActivity.java package cn.lixyz.test; import android.app.Acti ... 
- Android笔记(十九) Android中的Fragment
		通常我们使用Activity来展示界面,但是在手机上界面可能显示的很好看,但在平板上,因为平板的屏幕非常大,手机的界面放在平板上可能会出现控件被拉长.控件之间间距变大等问题.为了更好的体验效果,在Ac ... 
- Android笔记二十四.Android基于回调的事件处理机制
		假设说事件监听机制是一种托付式的事件处理,那么回调机制则与之相反,对于基于回调的事件处理模型来说,事件源和事件监听器是统一的,或者说事件监听器全然消失了,当用户在GUI控件上激发某个事件时,控 ... 
- Android笔记(六十六) android中的动画——XML文件定义属性动画
		除了直接在java代码中定义动画之外,还可以使用xml文件定义动画,以便重用. 如果想要使用XML来编写动画,首先要在res目录下面新建一个animator文件夹,所有属性动画的XML文件都应该存放在 ... 
- Android笔记(六十四) android中的动画——补间动画(tweened animation)
		补间动画就是只需要定义动画开始和结束的位置,动画中间的变化由系统去补齐. 补间动画由一下四种方式: 1.AplhaAnimation——透明度动画效果 2.ScaleAnimation ——缩放动画效 ... 
- Android笔记(十) Android中的布局——表格布局
		TableLayout运行我们使用表格的方式来排列控件,它的本质依然是线性布局.表格布局采用行.列的形式来管理控件,TableLayout并不需要明确的声明包含多少行多少列,而是通过添加TableRo ... 
- 论文阅读笔记五十九:Res2Net: A New Multi-scale Backbone Architecture(CVPR2019)
		论文原址:https://arxiv.org/abs/1904.01169 摘要 视觉任务中多尺寸的特征表示十分重要,作为backbone的CNN的对尺寸表征能力越强,性能提升越大.目前,大多数多尺寸 ... 
- Android Studio(五):修改Android Studio项目包名
		Android Studio相关博客: Android Studio(一):介绍.安装.配置 Android Studio(二):快捷键设置.插件安装 Android Studio(三):设置Andr ... 
- Android实训案例(六)——四大组件之一BroadcastReceiver的基本使用,拨号,短信,SD卡,开机,应用安装卸载监听
		Android实训案例(六)--四大组件之一BroadcastReceiver的基本使用,拨号,短信,SD卡,开机,应用安装卸载监听 Android中四大组件的使用时重中之重,我这个阶段也不奢望能把他 ... 
随机推荐
- 学习使用Lombok生成代码
			一.介绍 Lombok官网:https://projectlombok.org/ Lombok的功能简单一点说,就是可以帮我们生成一些代码,这些代码并不是在源码(source code)体现出来的,而 ... 
- matlab学习笔记10_5 通用字符串操作和比较函数
			一起来学matlab-matlab学习笔记10 10_5 通用字符串操作和比较函数 觉得有用的话,欢迎一起讨论相互学习~Follow Me 参考书籍 <matlab 程序设计与综合应用>张 ... 
- xshell修改配色方案为白色
- k8s-RC副本机制
			一.libeness probe的三种检测机制 HTTP GET:对容器的IP(指定的端口和路径)执行HTTP GET请求,收到响应并返回状态码不代表错误(2xx/3xx),成功 TCP socket ... 
- svn客户端清空账号信息的两种方法
			1.直接删除配置 C:\Users\Administrator\AppData\Roaming\Subversion\auth 一般在这个文件夹下 2.svn的设置里清空 
- [转帖]Latch
			Latch (转) http://blog.csdn.net/tianlesoftware/article/details/5263238 2013-05-24 15:33:09 huashanlun ... 
- Apache ZooKeeper在Kafka中的角色 - 监控和配置
			1.目标 今天,我们将看到Zookeeper在Kafka中的角色.本文包含Kafka中需要ZooKeeper的原因.我们可以说,ZooKeeper是Apache Kafka不可分割的一部分.在了解Zo ... 
- PHP 可变参数
			<?php //php 可变参数 function concatenate( ...$strings): string { $string = ''; //此时的strings 是一个数组 fo ... 
- Java线程的等待与唤醒完整示例代码
			项目结构: 资源类: 输入线程: 输出线程: 测试: 人妖问题发生: 线程安全问题的解决方法: 调用Object的wait()和notify()方法时需注意:必须是锁对象方可调用,否则将抛出无效的监 ... 
- Build step 'Send files or execute commands over SSH' changed build result to UNSTABLE
			删除logs文件夹日志即可 
