編輯:關於Android編程
* Activity的singleTask的啟動模式
* 界面跳轉的基本實現
* 前台Service的基本介紹和實現
* SharedPreference的簡單用法
在XHL應用程序中去調用MPos應用程序,借助MPos的一些界面完成特殊的功能。
(1)創建名為XHL的應用程序
(2)創建名為MPos的應用程序
1.創建名為XHL的應用程序的界面
如下是XHL的主界面
public class MainActivity extends AppCompatActivity {
//要調用app的包名 + 類名
private static String MOSPACKAGE = "zlll.bg.com.example.cn.application";
private static String MPOSCLASSNAME = "zlll.bg.com.example.cn.application.WelcomeActivity";
private static String MPOSCLASSNAME2 = "zlll.bg.com.example.cn.application.MainActivity"
//要調用app的服務
private static String SERVICENAME = "zl.com.example.cn.myapplication.service.MainService";
//如下是本應用的包名
private static String PACKAGE = "zl.com.example.cn.myapplication";
private Button open,exit;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
open = (Button) findViewById(R.id.open);
exit = (Button) findViewById(R.id.exit);
}
@Override
protected void onResume() {
super.onResume();
//這裡通過判斷某個服務是否正在運行來設定按鈕的狀態
if(Utils.isServiceWork(MainActivity.this,SERVICENAME)) {
open.setEnabled(false);
exit.setEnabled(true);
}else{
open.setEnabled(true);
exit.setEnabled(false);
}
public void btn(View view){
//首先判斷調用的apk是否安裝
boolean isAlive = Utils.isInstall(MainActivity.this,MOSPACKAGE);
if(isAlive){
Intent intent = new Intent(Intent.ACTION_MAIN);//設置action
intent.addCategory(Intent.CATEGORY_LAUNCHER);//設置category
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);//設置singleTask啟動模式
ComponentName cn = new ComponentName(MOSPACKAGE,MPOSCLASSNAME );//封裝了包名 + 類名
//設置數據
intent.putExtra("package",PACKAGE);
intent.putExtra("className",CLASSNAME);
intent.putExtra("isOnLineSign", true);
intent.setComponent(cn);
startActivity(intent);
}else{
Toast.makeText(MainActivity.this, "沒有找到對應的應用程序", Toast.LENGTH_SHORT).show();
}
}
public void exit(View view){
Toast.makeText(MainActivity.this, "退出調用的的應用程序", Toast.LENGTH_SHORT).show();
Intent intent = new Intent("com.bocs.mpos.home");//設置action
intent.putExtra("isExit", true); //設置數據
intent.setClassName(MOSPACKAGE, MPOSCLASSNAME2);//內部調用了ComponentName組件
startActivity(intent);
}
}
如下是工具類
public class Utils {
/**根據包名判斷某個應用程序是否安裝方法*/
public static boolean isInstall(Context context , String packageName) {
if (packageName == null || "".equals(packageName))
return false;
try {
ApplicationInfo info = context.getPackageManager().getApplicationInfo(
packageName, PackageManager.GET_UNINSTALLED_PACKAGES);
return true;
} catch (PackageManager.NameNotFoundException e) {
return false;
}
}
/**判斷某個進程是否正在運行的方法*/
public static boolean isProcessWork(Context context,String runningPackage) {
ActivityManager mActivityManager = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);
List listOfProcesses = mActivityManager.getRunningAppProcesses();
for (ActivityManager.RunningAppProcessInfo process : listOfProcesses) {
if (process.processName.contains(runningPackage)) {
return true;
}
}
return false;
}
/** 判斷某個服務是否正在運行的方法*/
public static boolean isServiceWork(Context mContext, String serviceName) {
boolean isWork = false;
ActivityManager myAM = (ActivityManager) mContext.getSystemService(Context.ACTIVITY_SERVICE);
List myList = myAM.getRunningServices(40);
if (myList.size() <= 0) {
return false;
}
for (int i = 0; i < myList.size(); i++) {
String mName = myList.get(i).service.getClassName().toString();
if (mName.equals(serviceName)) {
isWork = true;
break;
}
}
return isWork;
}
}
如下是在AnroidManifest.xml中配置
如下是的界面代碼
如下圖
2.創建名為MPos的應用程序
首先建立一個全局的集合用於管理Activity的ExitApplication,記得在AndroidManifest.xml中配置
public class ExitApplication extends Application {
private static List activityList = new ArrayList();
public static void remove(Activity activity) {
activityList.remove(activity);
}
public static void add(Activity activity) {
activityList.add(activity);
}
//銷毀掉所有的activity
public static void exitApplication() {
for (Activity activity : activityList) {
activity.finish();
}
android.os.Process.killProcess(android.os.Process.myPid());//直接殺掉當前應用進程
}
創建一個可以管理所有Activity的基類 – BaseActivity
public class BaseActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
ExitApplication.add(this);
}
@Override
protected void onDestroy() {
super.onDestroy();
ExitApplication.remove(this);
}
}
接下來寫界面代碼 – WelcomeActivity
public class WelcomeActivity extends BaseActivity {
//定義SP引用,用於簡單地保存數據
private SharedPreferences userHis;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_welcome);
userHis = getSharedPreferences("user_histroy", 0);
}
@Override
protected void onResume() {
super.onResume();
//行業應用調用時,參數是不為空的
if (getIntent() != null) {
SharedPreferences.Editor editor = userHis.edit();
if (!isEmpty(getIntent().getStringExtra("package"))) {
editor.putString("package", getIntent().getStringExtra("package"));
}
if (!isEmpty(getIntent().getStringExtra("className"))) {
editor.putString("className", getIntent().getStringExtra("className"));
}
editor.putBoolean("isOnLineSign", getIntent().getBooleanExtra("isOnLineSign", false));//在線簽到的標志
editor.commit();
}
//模擬耗時操作
new Thread(){
@Override
public void run() {
try {
Thread.sleep(1000);
//啟動Activity
Intent intent = new Intent(WelcomeActivity.this,MainActivity.class);
startActivity(intent);
//啟動服務
Intent serviceIntent = new Intent(WelcomeActivity.this, MainService.class);
startService(serviceIntent);
finish();//當前界面finish
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}.start();
}
//判空方法
public static boolean isEmpty(String content) {
return content == null || "".equals(content) || "null".equals(content);
}
}
接下來寫界面代碼 – MainActivity
public class MainActivity extends BaseActivity {
SharedPreferences userHis;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
userHis = getSharedPreferences("user_histroy", 0);
}
@Override
protected void onResume() {
super.onResume();
//如果標志位是true,那麼退出應用程序,調回到行業應用
if (getIntent().getBooleanExtra("isExit",false)) {
if (!isEmpty(userHis.getString("package", ""))) {
Intent intent = new Intent();
//通過ConponentName調回到指定的界面
ComponentName cn = new ComponentName("zl.com.example.cn.myapplication",
"zl.com.example.cn.myapplication.MainActivity");
intent.setComponent(cn);
startActivity(intent);
userHis.edit().remove("package").commit();
userHis.edit().remove("className").commit();
userHis.edit().remove("isExit").commit();
//退出服務
Intent updateIntent = new Intent(MainActivity.this, MainService.class);
stopService(updateIntent);
//退出程序
ExitApplication.exitApplication();
}
}
//如果標志位是true,返回到行業應用
if (userHis.getBoolean("isOnLineSign", false)) {
Toast.makeText(MainActivity.this, "返回XHL", Toast.LENGTH_SHORT).show();
Intent intent = new Intent();
Bundle bundle = new Bundle();
bundle.putBoolean("login_exit", true);
intent.putExtras(bundle);
ComponentName cn = new ComponentName("zl.com.example.cn.myapplication",
"zl.com.example.cn.myapplication.MainActivity");
intent.setComponent(cn);
startActivity(intent);
//移除這個標志,為了點擊MPos的圖標不調回到XHL中
userHis.edit().remove("isOnLineSign").commit();
}
}
public static boolean isEmpty(String content) {
return content == null || "".equals(content) || "null".equals(content);
}
}
如下是在AnroidManifest.xml中配置
MainService的代碼如下
public class MainService extends Service{
@Nullable
@Override
public IBinder onBind(Intent intent) {
return null;
}
@Override
public void onCreate() {
super.onCreate();
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
//這裡只是簡單的定義了一個通知,開啟前台Service
startForeground(startId,new Notification());
return super.onStartCommand(intent, flags, startId);
}
@Override
public void onDestroy() {
super.onDestroy();
stopForeground(true);//關閉前台服務
}
如下圖
Activity的singleTask的啟動模式
standard:標准模式
舉個例子:
現在棧的情況為:A B C D ,在D這個Activity中通過Intent跳轉到D,那麼棧的情況為:A B C D D
描述:每次啟動一個activity,都會創建一個實例,不管這個實例是否已經存在。
singleTask:棧內復用模式
舉個例子:
(1)目前任務棧S1中的情況為ABC,這個時候Activity D以singleTask模式請求啟動,其所需任務棧為S2,由於S2和D的實例並不存在,所以系統會先創建任務棧S2,然後再創建D的實例並將其入棧到S2。
(2)假設D所需的任務棧為S1,由於S1已經存在,所以直接創建D的實例將其入棧到S1。
(3)假設D所需的任務棧為S1,當前任務棧S1情況為ADBC,此時D並不會重新創建,系統把D切換到棧頂,同時它具有clearTop的效果,最後S1的情況為AD。
描述:在這種模式下,只要Activity在一個棧中存在,多次啟動此Activity都不會重新創建實例。
兩種設置Activity的啟動模式:
(1) intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); – 代碼中
(2) android:launchMode=”singleTask” – AndroidManifest的Activity中
APP間界面交互的基本實現
在Android中如果要詳細的描述一個組件我們需要知道該組件的所在的應用包名和類名
,我們可以使用ComponentName來封裝一個組件的應用包名和組件的類名。
常見的用法:
Intent intent = new Intent();
intent .setComponent(new ComponentName(String packageName,String activityName));
startActivity(intent );
前台Service的基本介紹和實現
如果你希望Service可以一直保持運行狀態,而不會由於系統內存不足的原因導致被回收,考慮使用前台Service。
前台Service和普通Service最大的區別在於它會一直有一個正在運行的圖標在系統的狀態欄顯示
只需要在onStartCommand裡面調用 startForeground,然後再onDestroy裡面調用stopForeground即可
SharedPreference的簡單用法
SharePreferences是用來存儲一些簡單配置信息的一種機制,創建的存儲文件保存在/data/data//shares_prefs文件夾下
插入數據 – Editor.putxxxx方法
獲取數據 – Editor.getxxxx方法
刪除數據 – Editor.remove方法。
清空所有數據 –Editor.clear方法
在一個比較坑的需求裡,一段文字右上角需要追加一個圓形紅點。最右側有個金額,紅點動態隨著文字移動,然後各種擺布局,一下午坑死我了。後來果斷放棄。然後就想試試直接自定義vie
1. 工具包文件 2. build-signer.xml文件<project name="jarsigner" def
自定義開關控件 Android自定義控件一般有三種方式 1、繼承Android固有的控件,在Android原生控件的基礎上,進行添加功能和邏輯。 2、繼承Vie
前一章我們學習了FM的自動調頻,接下來我們就看看FM手動調頻是如何進行的。如果不清楚FM自動調頻的過程,請打開超鏈接查看FM搜索頻率流程。 首先來看一下流程圖: 2.滑