1

ユーザーがいくつかの番組をダウンロードできるラジオアプリケーションを作成しています。

ユーザーがオーディオ プレーヤーのダウンロード ボタンをクリックすると、番組が として DB に追加されSavedShowます。

ユーザーは でSavedShowインスタンスの状態を確認できます。SavedShowsFragmentこれListViewには、保存されたショーのリストが表示されます。

の各行にはListView、保存されたショーのタイトル、その状態 ( NOT_STARTED/DOWNLOADING/PAUSED/DOWNLOADED/ERROR)、ダウンロードを一時停止、再開、またはダウンロードされている場合はファイルを再生するためのProgressBaraがあります。Button

リストの各項目を my にバインドする方法も、アダプターDownloadServiceからリスナーを実装する方法もわかりません。DownloadService

基本的に、私は各行に次のことを望みます:

  • DownloadTask.onProgressUpdate私のから進行状況を取得しますDownloadService
  • DownloadServiceダウンロードが完了したとき、またはエラーが発生したときに によって通知される
  • からメソッドを呼び出しますDownloadService(たとえば、ファイルのダウンロード中にボタンをクリックすると、ダウンロードを一時停止します)

誰でも助けることができますか?

保存済みショーフラグメント

public class SavedShowsFragment extends Fragment {

    private DownloadService mDownloadService;
    private boolean mBoundToDownloadService = false;

    private ListView mListView;

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {

        return inflater.inflate(R.layout.saved_show_list, container, false);
    }

    @Override
    public void onActivityCreated (Bundle savedInstanceState){
        super.onActivityCreated(savedInstanceState);
    }

    private void setSavedShowList(){

        mListView = (ListView) getView().findViewById(R.id.listview);   

        SavedShowAdapter adapter = new SavedShowAdapter(getActivity(), MyApplication.dbHelper.getSavedShowList());
        mListView.setAdapter(adapter); 
    }

    @Override
    public void onCreate (Bundle savedInstanceState){

        super.onCreate(savedInstanceState);

        // start services

        Intent intent = new Intent(getActivity(), DownloadService.class);
        getActivity().startService(intent);
    }

    @Override
    public void onResume() {         
        super.onResume();

        setSavedShowList();

        // bind service

        Intent intent = new Intent(getActivity(), StreamService.class);
        getActivity().bindService(intent, mDownloadServiceConnection, Context.BIND_AUTO_CREATE);

    }

    @Override
    public void onPause() {

        // unbind service

        if (mBoundToDownloadService) {
            getActivity().unbindService(mDownloadServiceConnection);
        }

        super.onPause();
    }   

    private ServiceConnection mDownloadServiceConnection = new ServiceConnection() {

        @Override
        public void onServiceConnected(ComponentName className, IBinder service) {          

            /*
             * Get service instance
             */

            DownloadServiceBinder binder = (DownloadServiceBinder) service;
            mDownloadService = binder.getService();         
            mBoundToDownloadService = true;

            /*
             * Start download for NOT_STARTED saved show
             */

            for(SavedShow savedShow : MyRadioApplication.dbHelper.getSavedShowList()){

                if(savedShow.getState()==SavedShow.State.NOT_STARTED){
                    mDownloadService.downLoadFile(savedShow.getId());
                }           
            }

        }

        @Override
        public void onServiceDisconnected(ComponentName arg0) {
            mBoundToDownloadService = false;
        }
    };  

}

保存されたShowAdapter

public class SavedShowAdapter extends ArrayAdapter<SavedShow> { 

    private LayoutInflater mLayoutInflater;

    static class ViewHolder {
        TextView title, status;
        ProgressBar progressBar;
        Button downloadStateBtn;
    }


    public SavedShowAdapter(Context context, List<SavedShow> saved_show_list) {
        super(context, 0, saved_show_list);     
        mLayoutInflater = (LayoutInflater) context.getSystemService( Context.LAYOUT_INFLATER_SERVICE );
    }


    @Override
    public View getView(final int position, View convertView, ViewGroup parent) {

        ViewHolder holder;
        View v = convertView;

        if (v == null) {

            v = mLayoutInflater.inflate(R.layout.podcast_list_item, parent, false);

            holder = new ViewHolder();

            holder.title = (TextView)v.findViewById(R.id.title);
            holder.status = (TextView)v.findViewById(R.id.status);
            holder.progressBar = (ProgressBar)v.findViewById(R.id.progress_bar);
            holder.downloadStateBtn = (Button)v.findViewById(R.id.btn_download_state);

            v.setTag(holder);
        } else {
            holder = (ViewHolder) v.getTag();
        }

        holder.downloadStateBtn.setTag(position);

        // TODO set button state according to item state

        holder.downloadStateBtn.setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {

                int position = (Integer) v.getTag();

                    // TODO call DownloadService method (download or pause) according to the state
            }
        });

        //holder.title.setText(getItem(position).getTitle());

        // do a publish progress listener for progress bar

        return v;
    }
} 

ダウンロードサービス

public class DownloadService extends Service {

    private static final int MAX_DOWNLOAD_TASKS = 10;

    private final IBinder mBinder = new DownloadServiceBinder();

    private class MaxDownloadsException extends Exception
    {

        private static final long serialVersionUID = 6859017750734917253L;

        public MaxDownloadsException()
        {
            super(getResources().getString(R.string.max_downloads));
        }
    }

    private List<DownloadTask> mTaskList= new ArrayList<DownloadTask>();

    private void addTaskToList(DownloadTask task) throws MaxDownloadsException {

        if(mTaskList.size() < MAX_DOWNLOAD_TASKS+1){
            mTaskList.add(task);
        }
        else{
            throw new MaxDownloadsException(); 
        }
    }

    private void removeTaskToList(DownloadTask task) {

        mTaskList.remove(task);

        // if no more tasks, stop service

        if(mTaskList.size() == 0){
            stopSelf();
        }

    }

    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {

        return START_NOT_STICKY;
    }

    /*
     * Binding-related methods
     */

    public class DownloadServiceBinder extends Binder {
        DownloadService getService() {
            return DownloadService.this;
        }
    }

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

    public void downLoadFile(long savedShowId){

        new DownloadTask().execute(savedShowId);

    }

    private class DownloadTask extends AsyncTask<Long, Integer, Void> {

        private SavedShow savedShow;

        private int contentLength;

        @Override
        protected Void doInBackground(Long... params) {

            savedShow = MyApplication.dbHelper.getSavedShow(params[0]);

            int contentLength;

            HttpURLConnection connection = null;
            BufferedInputStream in = null;

            try {               

                URL url = new URL(savedShow.getUrl());  

                connection = (HttpURLConnection) url.openConnection();

                long fileLength = new File(getFilesDir(), savedShow.getFilename()).length();

                FileOutputStream outputStream = openFileOutput(savedShow.getFilename(), MODE_PRIVATE | MODE_APPEND);

                int downloaded = 0;             
                contentLength = connection.getContentLength();

                // If there is already a file with that filename,
                // add 'Range' property in header                       

                if(fileLength != 0){
                    connection.setRequestProperty("Range", "bytes=" + fileLength + "-");
                }       

                in = new BufferedInputStream(connection.getInputStream());

                //BufferedOutputStream out = new BufferedOutputStream(outputStream, 1024);

                byte[] data = new byte[1024];
                int x = 0;

                while ((x = in.read(data, 0, 1024)) >= 0) {
                    outputStream.write(data, 0, x);
                    downloaded += x;
                    publishProgress((int) (downloaded));
                }
            } catch (IOException e) {               
                MyApplication.dbHelper.updateSavedShowError(savedShow.getId(), e.toString());

            }
            finally{
                try {
                    in.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
                if(connection != null){
                    connection.disconnect();
                }
            }
            return null;        

        }

        @Override
        protected void onProgressUpdate(Integer... values) {
            super.onProgressUpdate(values);

            // How can I pass values to SavedShowAdapter's items?
        }

        @Override
        protected void onPostExecute(Void nothing) {
            super.onPostExecute(nothing);

            // TODO remove task

            // How can I notify SavedShowAdapter's items?
        }
    }
}
4

2 に答える 2

0

既にサービスにバインドされているようです。デフォルトのバインダーを継承して好きなメソッドを実装したり、メッセンジャーを作成してメッセージをやり取りしたりできます。どちらの方法も API ガイドで説明されています。よく読んで、各方法の長所と短所を十分に理解してください。

http://developer.android.com/guide/components/bound-services.html

于 2013-07-14T11:05:12.527 に答える