Не удалось вызвать runOnUiThread в потоке изнутри службы
Я хотел сделать услугу, которая будет проверять мои SMS каждые 20 секунд, если есть какие-то непрочитанные SMS-сообщения, а затем отправить их на мой сайт, а затем пометить как прочитанные для публикации данных на веб-сайт. Я использовал asynctask, и он отлично работал, когда я пытался вручную (с помощью нажатия кнопки типа)
но в боковом сервисе я не могу определить
runOnUiThread(new Runnable() {
@Override
public void run() { new MyAsyncTask().execute(sender,time,message);}
});
он не может идентифицировать и просит меня определить runOnUiThread
Есть ли способ вызвать мою асинтексу из того места, где я звоню ниже кода
public class TestService extends Service {
String sender = null;
String time = null;
String message = null;
@Override
public IBinder onBind(Intent intent) {
// TODO: Return the communication channel to the service.
throw new UnsupportedOperationException("Not yet implemented");
}
@Override
public void onCreate() {
Toast.makeText(getApplicationContext(), "Service Created", 1).show();
super.onCreate();
}
@Override
public void onDestroy() {
Toast.makeText(getApplicationContext(), "Service Destroy", 1).show();
super.onDestroy();
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
Toast.makeText(getApplicationContext(), "Service Running ", 1).show();
new Thread(new Runnable() {
public void run() {
ContentValues values = new ContentValues();
Uri mSmsinboxQueryUri = Uri.parse("content://sms/inbox");
String[] columns = new String[] { "_id", "thread_id",
"address", "person", "date", "body", "type" };
Cursor cursor1 = getContentResolver().query(mSmsinboxQueryUri,
null, "read=0", null, null);
DateFormat formatter = new SimpleDateFormat(
"dd/MM/yyyy hh:mm:ss.SSS");
Calendar calendar = Calendar.getInstance();
if (cursor1.getCount() > 0) {
cursor1.moveToFirst();
do {
// Retrieving sender number
sender = (cursor1.getString(cursor1
.getColumnIndex(columns[2])).toString());
// Retriving time of reception
long ms = cursor1.getLong(cursor1
.getColumnIndex(columns[4]));
calendar.setTimeInMillis(ms);
time = formatter.format(calendar.getTime()).toString();
// Retriving the message body
message = (cursor1.getString(cursor1
.getColumnIndex(columns[5])).toString());
runOnUiThread(new Runnable() {
@Override
public void run() {
new MyAsyncTask()
.execute(sender, time, message);
}
});
} while (cursor1.moveToNext());// end of while
}// end of if
// set as read
values.put("read", true);
getContentResolver().update(Uri.parse("content://sms/inbox"),
values, null, null);
}
}).start();
return super.onStartCommand(intent, flags, startId);
}
private class MyAsyncTask extends AsyncTask<String, Integer, Double> {
@Override
protected Double doInBackground(String... params) {
postData(params[0], params[1], params[2]);
return null;
}
protected void onPostExecute(Double result) {
// pb.setVisibility(View.GONE);
Toast.makeText(getApplicationContext(), "command sent",
Toast.LENGTH_LONG).show();
}
protected void onProgressUpdate(Integer... progress) {
// pb.setProgress(progress[0]);
}
public void postData(String sender, String time, String message) {
// Create a new HttpClient and Post Header
HttpClient httpclient = new DefaultHttpClient();
HttpPost httppost = new HttpPost(
"http://www.mysite.co.nf/reciever.php");
try {
// Add your data
List<NameValuePair> nameValuePairs =
new ArrayList<NameValuePair>();
nameValuePairs.add(new BasicNameValuePair("sender", sender));
nameValuePairs.add(new BasicNameValuePair("time", time));
nameValuePairs.add(new BasicNameValuePair("message", message));
httppost.setEntity(new UrlEncodedFormEntity(nameValuePairs));
// Execute HTTP Post Request
HttpResponse response = httpclient.execute(httppost);
} catch (ClientProtocolException e) {} catch (IOException e) {}
}
}
}
Ответы
Ответ 1
Service
не имеет метода, называемого runOnUiThread()
. Вы предполагаете, что метод из Activity
также определен для a Service
, но это не так.
Решение, просто определите метод, который делает именно это. Здесь упрощенный пример, остальная часть вашего кода останется без изменений.
import android.os.Handler;
public class TestService extends Service {
Handler handler;
@Override
public void onCreate() {
// Handler will get associated with the current thread,
// which is the main thread.
handler = new Handler();
super.onCreate();
}
private void runOnUiThread(Runnable runnable) {
handler.post(runnable);
}
}
Для получения дополнительной информации см. документы для обработчика. Он использовал, чтобы сбрасывать некоторую работу на конкретный поток. В этом случае Handler
ассоциируется с потоком пользовательского интерфейса, так как поток пользовательского интерфейса всегда вызывает Service.onCreate()
.