应用Loader

206 阅读4分钟



整个思路:先遍历当前所有的应用,获取每一个应用的信息,包括:包名,类名,图标,应用名称。然后读取指定路径下的配置文件,比较配置文件中的包名和当前所有应用的包名是否一致,一致则添加到list集合中,用listView通过适配器显示。
dvr_selector.xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/LinearLayout1"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="@android:color/black"
    android:paddingLeft="10dp"
    android:paddingRight="10dp"
    android:orientation="vertical" >

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_weight="1" >

        <ListView
            android:id="@+id/listView"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:choiceMode="singleChoice"
            android:divider="?android:attr/listDivider"
            android:dividerHeight="3px" >

        </ListView>
    </LinearLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content">
        <Button
            android:id="@+id/btnCancel"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:onClick="onClickView"
            android:text="@string/cancel" />

        <Button
            android:id="@+id/btnConfirm"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:onClick="onClickView"
            android:text="@string/confirm" />

    </LinearLayout>

</LinearLayout>

app_list_item.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="horizontal">

    <ImageView
        android:id="@+id/list_ico"
        android:layout_width="72px"
        android:layout_height="72px" />

    <LinearLayout
        android:layout_width="wrap_content"
        android:layout_height="match_parent"
        android:layout_weight="1"
        android:orientation="vertical">

        <TextView
            android:id="@+id/list_text"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:gravity="center_vertical"
            android:textAppearance="?android:attr/textAppearanceLarge" />
    </LinearLayout>

    <RadioButton
        android:id="@+id/list_select"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center_vertical"
        android:clickable="false"
        android:focusable="false" />

</LinearLayout>

DvrSelector.java

package android.car.app.dvr_selector.activity;

import android.app.Activity;
import android.app.ActivityOptions;
import android.car.app.dvr_selector.R;
import android.car.utils.FileUtils;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.ListView;
import android.widget.RadioButton;
import android.widget.TextView;

import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;

public class DvrSelector extends Activity {
    private static final String TAG = "DvrSelector";

    private ListView mListView;
    private boolean mEnterBySetting = false;

    private ArrayList<AppInfo> mAppInfos = new ArrayList<AppInfo>();
    private GpsAppListAdapter mAdapter;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.dvr_selector);

        initUI();
    }

    static class AppInfo {
        String packageName;
        Drawable icon;
        String lable;
        String processName;
        String activityName;
        ComponentName compName;

        static AppInfo make(String packageName, String processName,
                            String activityName, String lable, Drawable icon) {

            AppInfo info = new AppInfo();
            info.packageName = packageName;
            info.processName = processName;
            info.activityName = activityName;
            info.lable = lable;
            info.icon = icon;
            info.compName = new ComponentName(packageName, activityName);
            return info;
        }

        @Override
        public String toString() {
            return "AppInfo [packageName=" + packageName + ", icon=" + icon
                    + ", lable=" + lable + ", activityName=" + activityName
                    + "]";
        }
    }

    private void initUI() {
        mListView = (ListView) findViewById(R.id.listView);

        loadAppList();

        mAdapter = new GpsAppListAdapter(this);
        mAdapter.setAppInfoList(mAppInfos);
        mListView.setAdapter(mAdapter);

        mListView.setOnItemClickListener(new OnItemClickListener() {
            public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
                mAdapter.setSelected(position);
            }
        });
    }

    public void onClickView(View v) {
        switch (v.getId()) {
            case R.id.btnConfirm:
                enterApp();

                break;
            case R.id.btnCancel:
                finish();
                break;
        }
    }

    private void enterApp() {
        int pos = mAdapter.getSelected();
        if (pos >= 0 && pos < mAdapter.getCount()) {
            AppInfo info = mAppInfos.get(pos);

            Log.i(TAG, "enterApp: lable=" + info.lable);
            Log.i(TAG, "enterApp: packageName=" + info.packageName);
            Log.i(TAG, "enterApp: activityName=" + info.activityName);

            PackageInfo packageInfo;
            try {
                packageInfo = getPackageManager().getPackageInfo(info.packageName, 0);
            } catch (PackageManager.NameNotFoundException e) {
                packageInfo = null;
                e.printStackTrace();
                return;
            }

            Intent resolveIntent = new Intent(Intent.ACTION_MAIN, null);
            resolveIntent.addCategory(Intent.CATEGORY_LAUNCHER);
            resolveIntent.setPackage(packageInfo.packageName);
            List<ResolveInfo> resolveinfoList = getPackageManager().queryIntentActivities(resolveIntent, 0);
            ResolveInfo resolveinfo = resolveinfoList.iterator().next();
            if (resolveinfo != null) {
                String packageName = resolveinfo.activityInfo.packageName;
                String _classname = resolveinfo.activityInfo.name;

                try {
                    ComponentName componet = new ComponentName(info.packageName, _classname);
                    Intent intent = new Intent(Intent.ACTION_MAIN);
                    intent.setComponent(componet);
                    intent.addCategory(Intent.CATEGORY_LAUNCHER);

                    startActivityForResultSafely(null, intent, 15, null);
                } catch (Exception e) {
                    e.printStackTrace();
                    return;
                }
            }

            finish();
        }
    }

    public boolean startActivityForResultSafely(View v, Intent intent, int requestCode, Object tag) {
        intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
        try {
            boolean useLaunchAnimation = (v != null) &&
                    !intent.hasExtra("com.android.launcher3.intent.extra.shortcut.INGORE_LAUNCH_ANIMATION");
            if (useLaunchAnimation) {
                ActivityOptions opts = ActivityOptions.makeScaleUpAnimation(v, 0, 0,
                        v.getMeasuredWidth(), v.getMeasuredHeight());
                startActivityForResult(intent, requestCode, opts.toBundle());
            } else {
                startActivityForResult(intent, requestCode);
            }
            return true;
        } catch (SecurityException e) {
            Log.e(TAG, "Launcher does not have the permission to launch " + intent +
                    ". Make sure to create a MAIN intent-filter for the corresponding activity " +
                    "or use the exported attribute for this activity. "
                    + "tag=" + tag + " intent=" + intent, e);
        }
        return false;
    }


    class GpsAppListAdapter extends BaseAdapter {

        ArrayList<AppInfo> mAppInfos;
        Context mContext;
        LayoutInflater mInflater;
        int mSelectedPos = -1;

        class ViewHolder {
            ImageView icon;
            TextView text;
            RadioButton select;
        }

        public GpsAppListAdapter(Context context) {
            mContext = context;
            mInflater = LayoutInflater.from(context);
        }

        public void setAppInfoList(ArrayList<AppInfo> appInfos) {
            mAppInfos = appInfos;
        }

        public void setSelected(int pos) {
            if (mSelectedPos != pos) {
                mSelectedPos = pos;
                notifyDataSetChanged();
            }
        }

        public int getSelected() {
            return mSelectedPos;
        }

        public int getCount() {
            return mAppInfos != null ? mAppInfos.size() : 0;
        }

        public Object getItem(int position) {
            if (mAppInfos != null && position >= 0
                    && position < mAppInfos.size()) {
                return mAppInfos.get(position);
            }
            return null;
        }

        public long getItemId(int position) {
            return position;
        }

        public View getView(int position, View convertView, ViewGroup parent) {
            ViewHolder holder;

            if (convertView == null) {
                convertView = mInflater.inflate(R.layout.app_list_item, null);
                holder = new ViewHolder();

                holder.icon = (ImageView) convertView
                        .findViewById(R.id.list_ico);
                holder.text = (TextView) convertView
                        .findViewById(R.id.list_text);
                holder.select = (RadioButton) convertView
                        .findViewById(R.id.list_select);

                convertView.setTag(holder);// 绑定ViewHolder对象
            } else {
                holder = (ViewHolder) convertView.getTag();
            }

            /* 设置TextView显示的内容,即我们存放在动态数组中的数据 */
            AppInfo info = mAppInfos.get(position);

            holder.icon.setImageDrawable(info.icon);
            holder.text.setText(info.lable);
            holder.select.setChecked(mSelectedPos == position);

            return convertView;
        }
    }

    static final HashSet<String> sWhiteList = new HashSet<>();
    static final String DVR_WHITE_LIST_FILE = "/system/ziqi/dvr_selector_white_list.conf";

    static {
        initBlackWhiteList();
    }

    static void readListFromFile(HashSet<String> set, String filePath) {
        try {
            String cfg = FileUtils.readTextFile(new File(filePath), 0, null);
            if (cfg != null) {
                String[] items = cfg.split("\n");
                for (String i : items) {
                    if (!i.startsWith("#")) {
                        set.add(i.trim());
                    }
                }
            }
        } catch (IOException e) {
            Log.e(TAG, "Open config file fail! " + e.getMessage());
        }
    }

    static void initBlackWhiteList() {
        sWhiteList.add("com.ankai.cardvr");
        readListFromFile(sWhiteList, DVR_WHITE_LIST_FILE);
    }

    private void loadAppList() {
        mAppInfos.clear();
        PackageManager pm = getPackageManager();
        Intent intent = new Intent(Intent.ACTION_MAIN);
        intent.addCategory(Intent.CATEGORY_LAUNCHER);

        List<ResolveInfo> apps = pm.queryIntentActivities(intent, 0);

        int number = 0;
        for (ResolveInfo info : apps) {
            String pkgName = info.activityInfo.packageName;

            Log.i(TAG, "loadAppList: pkgName=" + pkgName);

            boolean isInWhite = sWhiteList.contains(pkgName);
            if (isInWhite) {
                number++;

                Log.d(TAG, "[" + number + "]" + info.activityInfo);

                mAppInfos.add(AppInfo.make(
                        info.activityInfo.packageName,
                        info.activityInfo.processName,
                        info.activityInfo.name,
                        info.activityInfo.loadLabel(pm).toString(),
                        info.activityInfo.loadIcon(pm)));
            }
        }
    }

}

readTextFile():

public static String readTextFile(File file, int max, String ellipsis) throws IOException {
    FileInputStream input = new FileInputStream(file);

    String var8;
    try {
        long size = file.length();
        int length;
        if(max <= 0 && (size <= 0L || max != 0)) {
            byte[] last;
            if(max >= 0) {
                ByteArrayOutputStream contents = new ByteArrayOutputStream();
                last = new byte[1024];

                do {
                    length = input.read(last);
                    if(length > 0) {
                        contents.write(last, 0, length);
                    }
                } while(length == last.length);

                String var18 = contents.toString();
                return var18;
            }

            boolean rolled = false;
            last = null;
            byte[] data = null;

            int len;
            do {
                if(last != null) {
                    rolled = true;
                }

                byte[] tmp = last;
                last = data;
                data = tmp;
                if(tmp == null) {
                    data = new byte[-max];
                }

                len = input.read(data);
            } while(len == data.length);

            String var19;
            if(last == null && len <= 0) {
                var19 = "";
                return var19;
            }

            if(last == null) {
                var19 = new String(data, 0, len);
                return var19;
            }

            if(len > 0) {
                rolled = true;
                System.arraycopy(last, len, last, 0, last.length - len);
                System.arraycopy(data, 0, last, last.length - len, len);
            }

            if(ellipsis != null && rolled) {
                var19 = ellipsis + new String(last);
                return var19;
            }

            var19 = new String(last);
            return var19;
        }

        if(size > 0L && (max == 0 || size < (long)max)) {
            max = (int)size;
        }

        byte[] data = new byte[max + 1];
        length = input.read(data);
        if(length <= 0) {
            var8 = "";
            return var8;
        }

        if(length <= max) {
            var8 = new String(data, 0, length);
            return var8;
        }

        if(ellipsis != null) {
            var8 = new String(data, 0, max) + ellipsis;
            return var8;
        }

        var8 = new String(data, 0, max);
    } finally {
        input.close();
    }

    return var8;
}