並存執行的Service,以媒體轉碼成新格式為例

來源:互聯網
上載者:User

標籤:android   java   service 並存執行   

大家眾所周知,IntentService內建的handler只有一個線程,而AsyncTask又只適合時間至多幾秒的操作,所以我們關注使用ExecutorService建立並存執行。為了確保Service一直保持活躍狀態,需要調用Service.startForeground()方法。由於Service.startForeground()和Service.stopForeground()並不會疊加,所以還需要維護一個內部計數器,用來記錄活躍的任務。一旦計數器為0則調用Service.stopForeground();

在這個例子中,主要介紹怎麼利用Service執行並行的任務,並不是主要講解多媒體格式檔案轉碼的操作,所以轉碼操作都省略,主要實現並存執行。

public class MediaTranscoder extends Service {
private static final int NOTIFICATION_ID = 1001;//定義通知的標識ID
public static final String ACTION_TRANSCODE_MEDIA = "com.liyaunjinglyj.services.TRANSCODE_MEDIA";
public static final String EXTRA_OUTPUT_TYPE = "outputType";//轉碼的類型
private ExecutorService mExecutorService;//定義線程池
private int mRunningJobs = 0;//任務計數器
private final Object mLock = new Object();//鎖
private boolean mIsForeground = false;//標誌是否需要結束Service


@Override
public IBinder onBind(Intent intent) {
return null;
}


@Override
public void onCreate() {
super.onCreate();
this.mExecutorService = Executors.newCachedThreadPool();//緩衝型池子,先查看池中有沒有以前建立的線程,如果有,就reuse.如果沒有,就建一個新的線程加入池中,緩衝型池子通常用於執行一些生存期很短的非同步型任務,因此在一些連線導向的daemon型SERVER中用得不多。能reuse的線程,必須是timeout IDLE內的池中線程,預設timeout是60s,超過這個IDLE時間長度,線程執行個體將被終止及移出池。 注意,放入CachedThreadPool的線程不必擔心其結束,超過TIMEOUT不活動,其會自動被終止。
}


@Override
public int onStartCommand(Intent intent, int flags, int startId) {
String action = intent.getAction();
if (ACTION_TRANSCODE_MEDIA.equals(action)) {
String outputType = intent.getStringExtra(EXTRA_OUTPUT_TYPE);


//啟動新的作業增加計數器
synchronized (mLock) {
TranscodeRunnable transcodeRunnable = new TranscodeRunnable(
intent.getData(), outputType);
mExecutorService.execute(transcodeRunnable);//執行當前線程
mRunningJobs++;//執行緒計數器加1
startForegroundIfNeeded();//建立通知,並保持活躍
}
}
return START_NOT_STICKY;//系統回收資源關閉了當前的Service並不會重新啟動.適合執行一次性操作。
}


@Override
public void onDestroy() {
super.onDestroy();
this.mExecutorService.shutdownNow();//shutdownNow() 方法阻止等待任務啟動並試圖停止當前正在執行的任務
}


private class TranscodeRunnable implements Runnable {
private Uri mInData;
private String mOutputType;


private TranscodeRunnable(Uri inData, String outputType) {
this.mInData = inData;
this.mOutputType = outputType;
}


@Override
public void run() {

//在這裡執行轉碼操作

//轉碼完成後,計數器加1

synchronized (mLock) {
mRunningJobs--;
stopForegroundIfAllDone();
}
}


}


private void stopForegroundIfAllDone() {
if (mRunningJobs == 0 && mIsForeground) {
stopForeground(true);
this.mIsForeground = false;
}
}


private void startForegroundIfNeeded() {
if (!mIsForeground) {
Notification notification = buildNotFication();
startForeground(NOTIFICATION_ID, notification);
this.mIsForeground = true;
}
}


private Notification buildNotFication() {
Notification notification = null;

//在這裡構建通知
return notification;
}


}

並存執行的Service,以媒體轉碼成新格式為例

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.