好的,所以我正在开发一个Android程序,它将列出您在历史记录中复制的内容。我曾经有一个活动这样做,但我希望即使活动不在后台运行,它也能工作,所以我正在开发一个服务来获取用户复制的数据,并调用一个活动方法来处理它并在应用程序中列出。这是我的服务:
公共类操作扩展服务 {
private static int NOTIFY_ID = 1;
ClipData.Item item;
String newText;
ClipboardManager clipboard;
Context context = this;
ArrayList<String> operationVals = new ArrayList<String>();
@Override
public IBinder onBind(Intent arg0) {
return null;
}
@Override
public void onCreate() {
NotificationCompat.Builder tasker =
new NotificationCompat.Builder(this)
.setSmallIcon(R.drawable.appicon)
.setContentTitle("Copy Data Recorder")
.setOngoing(true)
.setContentText("Recording copied data");
Intent copyAction = new Intent(this, MainActivity.class);
PendingIntent pendAction = PendingIntent.getActivity(this, 0, copyAction, 0);
tasker.setContentIntent(pendAction);
NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
notificationManager.notify(NOTIFY_ID, tasker.build());
}
@Override
public void onStart(Intent intent, int startId) {}
@Override
public void onDestroy() {}
@Override
public int onStartCommand(Intent intent, int flags, int startId){
clipboard = (ClipboardManager)
getSystemService(Context.CLIPBOARD_SERVICE);
clipboard.addPrimaryClipChangedListener(new OnPrimaryClipChangedListener() {
public void onPrimaryClipChanged() {
ClipData clip = clipboard.getPrimaryClip();
try {
item = clip.getItemAt(0);
} catch (Exception e) {
}
newText = item.coerceToText(context).toString();
operationVals.add(newText);
try {
MainActivity messager = new MainActivity();
messager.doIt(operationVals);
} catch (Exception e) {
System.out.println("Exception Error: " + e);
}
}
});
return START_STICKY;
}
}
基本上,每次,它都会获取复制的内容,将其添加到字符串数组列表"operationVals"中,并调用主要活动的 doIt(( 方法。 doIt(( 遍历数组,检查哪些复制的数据是新的,并将其添加到名为"ets"的 EditText 对象的数组列表中,这些对象在打开应用程序活动时显示。在这里:
public void doIt(ArrayList values( {
for (String element : values) {
if (ets.size() != 0) {
for (int i = 0; i < ets.size(); i++) {
String element2 = ets.get(i).getText().toString();
if (element2.equals(element)) {
values.remove(i);
}
}
}
}
if (values.size() != 0) {
for (String newText : values) {
/* If the size is zero and we currently have no items, this one should
be immediately added.*/
if (ets.size() == 0) {
ets.add(new EditText(context)); //Adds EditText field
ets.get(ets.size() - 1).setText(newText); //Sets newText string in EditText that was created
linearlayout.addView(ets.get(ets.size() - 1)); //Adds element to view
contentSpace.add(ets.get(ets.size() - 1).getText().toString());
} else if (ets.size() != 0) {
oldText = ets.get(ets.size() - 1).getText().toString();
// Checks that new copied data is different from previous data and does not contain only spaces
if (!newText.equals(oldText) && newText.trim().length() > 0 && oldText.trim().length() > 0) {
ets.add(new EditText(context)); //Adds EditText field
ets.get(ets.size() - 1).setText(newText); //Sets newText string in EditText that was created
linearlayout.addView(ets.get(ets.size() - 1)); //Adds element to view
contentSpace.add(ets.get(ets.size() - 1).getText().toString());
} else if (oldText.trim().length() == 0) {
for (int i = 0; i < ets.size(); i++) {
if (ets.get(i).getText().toString().equals(oldText)) {
oldText = oldText.trim();
ets.get(ets.size() - 1).setText(newText);
}
}
} else {
}
}
}
}
}
但是,我对其进行了测试,事情似乎进展顺利,直到我的服务调用doIt((,程序开始检查ets并向其中添加元素,并且我得到了一个NullPointerException。似乎 ets 已被正确声明和初始化,并且我的活动显然已被创建(该服务在主活动的 onStart(( 中启动(。如果有人能帮助我解决这个问题,我将不胜感激。谢谢。
代码中存在多个问题:
-
你不能像这样实例化一个活动:MainActivity messager = new MainActivity((;活动只能通过使用Intents(Intent.startActivity 系列方法(来启动(或激活(。
-
您应该使用广播接收器或信使来处理服务和活动之间的通信。
-
考虑以下情况:当您向活动发送数据,但活动处于后台并处于停止状态时(当活动处于后台时,将调用 Activity.onPause 和 Activity.onStop(。在这种情况下,您可以再次调用 Intent.startActivity,但设置了标志FLAG_ACTIVITY_REORDER_TO_FRONT,这将导致活动被置于前台(如果已存在活动的新实例,则不会重新创建活动的新实例(
-
请考虑将您在 Service.onStartCommand 中设置的逻辑移动到 Service.onCreate,因为每次调用 Context.startService 方法时都会调用 Service.onStartCommand,并且每次都会覆盖以前的设置。