[英]Android service thread making web request is blocking UI
首先,我將解釋當前的情況。 我在2個服務中有2個不同的線程(從USB端口服務讀取並進行Web請求服務)。 我在我的活動的onCreate中啟動它們,例如:
serialServiceIntent = new Intent(NDKSerialActivity.this, SerialService.class);
startService(serialServiceIntent);
webServiceIntent = new Intent(NDKSerialActivity.this, RecordWebService.class);
startService(webServiceIntent);
串行服務沒有什么問題,但是在RecordWebService中,當我發出請求時,gui會停止,直到響應到來為止。
代碼是這樣的:
public class RecordWebService extends Service
{
public static final String SERVER_ADDRESS = "http://192.168.1.100:8080/MobilHM/rest";
private static final String TAG = RecordWebService.class.getSimpleName();
private RecordWebThread recordWebThread;
@Override
public void onStart(Intent intent, int startId)
{
super.onStart(intent, startId);
recordWebThread = new RecordWebThread(true);
recordWebThread.start();
}
@Override
public void onDestroy()
{
super.onDestroy();
Log.i(TAG, "RecordWebService Destroyed");
}
@Override
public IBinder onBind(Intent intent)
{
return null;
}
}
和
public class RecordWebThread extends Thread
{
private static final String TAG = RecordWebThread.class.getSimpleName();
public boolean always;
public RecordWebThread(boolean always)
{
this.always = always;
}
@Override
public void run()
{
PatientRecord patientRecord = new PatientRecord();
while (always)
{
RestClient restClient = new RestClient(RecordWebService.SERVER_ADDRESS + "/hello");
try
{
restClient.execute(RequestMethod.GET);
}
catch (Exception e1)
{
Log.e(TAG, "", e1);
}
Log.i(TAG, "Server Response Code:->" + restClient.getResponseCode());
Log.i(TAG, "Server Response:->" + restClient.getResponse());
try
{
sleep(4 * 1000);
}
catch (InterruptedException e)
{
Log.e(TAG, "Web service interrupted", e);
}
}
}
}
我也嘗試刪除睡眠部分並使線程與計時器和計時器任務一起運行,例如:
public void sendRecord()
{
scanTask = new TimerTask()
{
public void run()
{
handler.post(new Runnable()
{
public void run()
{
RestClient restClient = new RestClient(RecordWebService.SERVER_ADDRESS + "/hello");
try
{
restClient.execute(RequestMethod.GET);
}
catch (Exception e1)
{
Log.e(TAG, "", e1);
}
Log.i(TAG, "Server Response Code:->" + restClient.getResponseCode());
Log.i(TAG, "Server Response:->" + restClient.getResponse());
}
});
}
};
t.schedule(scanTask, 1000, 4000);
}
但沒有運氣,當談到restClient.execute時,我的gui掛起了。
您可以在http://www.giantflyingsaucer.com/blog/?p=1462上找到RestClient.java 。
如何使我的請求不阻止我的GUI線程?
編輯:
public void sendRecord()
{
scanTask = new TimerTask()
{
public void run()
{
RestClient restClient = new RestClient(RecordWebService.SERVER_ADDRESS + "/hello");
try
{
restClient.execute(RequestMethod.GET);
}
catch (Exception e1)
{
Log.e(TAG, "", e1);
}
Log.i(TAG, "Server Response Code:->" + restClient.getResponseCode());
Log.i(TAG, "Server Response:->" + restClient.getResponse());
}
};
t.schedule(scanTask, 1000, 4000);
}
沒有處理程序,我在我的活動的onCreate中調用此方法,但仍然ui掛起。
或者,您可以使用IntentService來為您處理線程問題。
這是一個示例類:
public class MyService extends IntentService {
public MyService() {
super("MyService");
}
public MyService(String name) {
super(name);
}
@Override
protected void onHandleIntent(Intent arg0) {
//Do what you want
}
}
然后,您只需致電:
Intent intent = new Intent(getApplicationContext(),MyService.class);
startService(intent);
編輯:
要每4秒重復一次相同的操作,您應該執行以下操作:
PendingIntent serviceIntent= PendingIntent.getService(context,
0, new Intent(context, MyService.class), 0);
long firstTime = SystemClock.elapsedRealtime();
AlarmManager am = (AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
long intervalInSec = 4;
am.setRepeating(AlarmManager.ELAPSED_REALTIME, firstTime, intervalInSec*1000, serviceIntent)
;
接下來是代碼(二維版本):創建線程,並要求UI線程進行一些網絡交互。 只是在執行請求時排除handler.post(...)
。 稍后,您可以將其用於簡單的可運行狀態,以使用請求結果更新UI。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.