Эх сурвалжийг харах

Progress bar in details view is successfully updated

David A. Velasco 12 жил өмнө
parent
commit
cfb68a69dd

+ 47 - 24
src/com/owncloud/android/files/services/FileDownloader.java

@@ -20,7 +20,9 @@ package com.owncloud.android.files.services;
 
 
 import java.io.File;
 import java.io.File;
 import java.util.AbstractList;
 import java.util.AbstractList;
+import java.util.HashMap;
 import java.util.Iterator;
 import java.util.Iterator;
+import java.util.Map;
 import java.util.Vector;
 import java.util.Vector;
 import java.util.concurrent.ConcurrentHashMap;
 import java.util.concurrent.ConcurrentHashMap;
 import java.util.concurrent.ConcurrentMap;
 import java.util.concurrent.ConcurrentMap;
@@ -49,7 +51,6 @@ import android.os.Looper;
 import android.os.Message;
 import android.os.Message;
 import android.os.Process;
 import android.os.Process;
 import android.util.Log;
 import android.util.Log;
-import android.widget.ProgressBar;
 import android.widget.RemoteViews;
 import android.widget.RemoteViews;
 
 
 import com.owncloud.android.R;
 import com.owncloud.android.R;
@@ -136,6 +137,7 @@ public class FileDownloader extends Service implements OnDatatransferProgressLis
             DownloadFileOperation newDownload = new DownloadFileOperation(account, file); 
             DownloadFileOperation newDownload = new DownloadFileOperation(account, file); 
             mPendingDownloads.putIfAbsent(downloadKey, newDownload);
             mPendingDownloads.putIfAbsent(downloadKey, newDownload);
             newDownload.addDatatransferProgressListener(this);
             newDownload.addDatatransferProgressListener(this);
+            newDownload.addDatatransferProgressListener((FileDownloaderBinder)mBinder);
             requestedDownloads.add(downloadKey);
             requestedDownloads.add(downloadKey);
             sendBroadcastNewDownload(newDownload);
             sendBroadcastNewDownload(newDownload);
             
             
@@ -165,13 +167,29 @@ public class FileDownloader extends Service implements OnDatatransferProgressLis
         return mBinder;
         return mBinder;
     }
     }
 
 
+
+    /**
+     * Called when ALL the bound clients were onbound.
+     */
+    @Override
+    public boolean onUnbind(Intent intent) {
+        ((FileDownloaderBinder)mBinder).clearListeners();
+        return false;   // not accepting rebinding (default behaviour)
+    }
+
     
     
     /**
     /**
      *  Binder to let client components to perform operations on the queue of downloads.
      *  Binder to let client components to perform operations on the queue of downloads.
      * 
      * 
      *  It provides by itself the available operations.
      *  It provides by itself the available operations.
      */
      */
-    public class FileDownloaderBinder extends Binder {
+    public class FileDownloaderBinder extends Binder implements OnDatatransferProgressListener {
+        
+        /** 
+         * Map of listeners that will be reported about progress of downloads from a {@link FileDownloaderBinder} instance 
+         */
+        private Map<String, OnDatatransferProgressListener> mBoundListeners = new HashMap<String, OnDatatransferProgressListener>();
+        
         
         
         /**
         /**
          * Cancels a pending or current download of a remote file.
          * Cancels a pending or current download of a remote file.
@@ -190,6 +208,11 @@ public class FileDownloader extends Service implements OnDatatransferProgressLis
         }
         }
         
         
         
         
+        public void clearListeners() {
+            mBoundListeners.clear();
+        }
+
+
         /**
         /**
          * Returns True when the file described by 'file' in the ownCloud account 'account' is downloading or waiting to download.
          * Returns True when the file described by 'file' in the ownCloud account 'account' is downloading or waiting to download.
          * 
          * 
@@ -225,22 +248,13 @@ public class FileDownloader extends Service implements OnDatatransferProgressLis
          * @param file          {@link OCfile} of interest for listener. 
          * @param file          {@link OCfile} of interest for listener. 
          */
          */
         public void addDatatransferProgressListener (OnDatatransferProgressListener listener, Account account, OCFile file) {
         public void addDatatransferProgressListener (OnDatatransferProgressListener listener, Account account, OCFile file) {
-            if (account == null || file == null) return;
+            if (account == null || file == null || listener == null) return;
             String targetKey = buildRemoteName(account, file);
             String targetKey = buildRemoteName(account, file);
-            DownloadFileOperation target = null;
-            synchronized (mPendingDownloads) {
-                if (!file.isDirectory()) {
-                    target = mPendingDownloads.get(targetKey);
-                } else {
-                    // nothing to do for directories, right now
-                }
-            }
-            if (target != null) {
-                target.addDatatransferProgressListener(listener);
-            }
+            mBoundListeners.put(targetKey, listener);
         }
         }
         
         
         
         
+        
         /**
         /**
          * Removes a listener interested in the progress of the download for a concrete file.
          * Removes a listener interested in the progress of the download for a concrete file.
          * 
          * 
@@ -249,18 +263,27 @@ public class FileDownloader extends Service implements OnDatatransferProgressLis
          * @param file          {@link OCfile} of interest for listener. 
          * @param file          {@link OCfile} of interest for listener. 
          */
          */
         public void removeDatatransferProgressListener (OnDatatransferProgressListener listener, Account account, OCFile file) {
         public void removeDatatransferProgressListener (OnDatatransferProgressListener listener, Account account, OCFile file) {
-            if (account == null || file == null) return;
+            if (account == null || file == null || listener == null) return;
             String targetKey = buildRemoteName(account, file);
             String targetKey = buildRemoteName(account, file);
-            DownloadFileOperation target = null;
-            synchronized (mPendingDownloads) {
-                if (!file.isDirectory()) {
-                    target = mPendingDownloads.get(targetKey);
-                } else {
-                    // nothing to do for directories, right now
-                }
+            if (mBoundListeners.get(targetKey) == listener) {
+                mBoundListeners.remove(targetKey);
             }
             }
-            if (target != null) {
-                target.removeDatatransferProgressListener(listener);
+        }
+
+
+        @Override
+        public void onTransferProgress(long progressRate) {
+            // old way, should not be in use any more
+        }
+
+
+        @Override
+        public void onTransferProgress(long progressRate, long totalTransferredSoFar, long totalToTransfer,
+                String fileName) {
+            String key = buildRemoteName(mCurrentDownload.getAccount(), mCurrentDownload.getFile());
+            OnDatatransferProgressListener boundListener = mBoundListeners.get(key);
+            if (boundListener != null) {
+                boundListener.onTransferProgress(progressRate, totalTransferredSoFar, totalToTransfer, fileName);
             }
             }
         }
         }
         
         

+ 62 - 12
src/com/owncloud/android/files/services/FileUploader.java

@@ -20,7 +20,9 @@ package com.owncloud.android.files.services;
 
 
 import java.io.File;
 import java.io.File;
 import java.util.AbstractList;
 import java.util.AbstractList;
+import java.util.HashMap;
 import java.util.Iterator;
 import java.util.Iterator;
+import java.util.Map;
 import java.util.Vector;
 import java.util.Vector;
 import java.util.concurrent.ConcurrentHashMap;
 import java.util.concurrent.ConcurrentHashMap;
 import java.util.concurrent.ConcurrentMap;
 import java.util.concurrent.ConcurrentMap;
@@ -33,6 +35,7 @@ import com.owncloud.android.authenticator.AccountAuthenticator;
 import com.owncloud.android.datamodel.FileDataStorageManager;
 import com.owncloud.android.datamodel.FileDataStorageManager;
 import com.owncloud.android.datamodel.OCFile;
 import com.owncloud.android.datamodel.OCFile;
 import com.owncloud.android.files.InstantUploadBroadcastReceiver;
 import com.owncloud.android.files.InstantUploadBroadcastReceiver;
+import com.owncloud.android.files.services.FileDownloader.FileDownloaderBinder;
 import com.owncloud.android.operations.ChunkedUploadFileOperation;
 import com.owncloud.android.operations.ChunkedUploadFileOperation;
 import com.owncloud.android.operations.DownloadFileOperation;
 import com.owncloud.android.operations.DownloadFileOperation;
 import com.owncloud.android.operations.RemoteOperationResult;
 import com.owncloud.android.operations.RemoteOperationResult;
@@ -254,6 +257,7 @@ public class FileUploader extends Service implements OnDatatransferProgressListe
                 }
                 }
                 mPendingUploads.putIfAbsent(uploadKey, newUpload);
                 mPendingUploads.putIfAbsent(uploadKey, newUpload);
                 newUpload.addDatatransferProgressListener(this);
                 newUpload.addDatatransferProgressListener(this);
+                newUpload.addDatatransferProgressListener((FileUploaderBinder)mBinder);
                 requestedUploads.add(uploadKey);
                 requestedUploads.add(uploadKey);
             }
             }
             
             
@@ -291,13 +295,28 @@ public class FileUploader extends Service implements OnDatatransferProgressListe
     public IBinder onBind(Intent arg0) {
     public IBinder onBind(Intent arg0) {
         return mBinder;
         return mBinder;
     }
     }
+    
+    /**
+     * Called when ALL the bound clients were onbound.
+     */
+    @Override
+    public boolean onUnbind(Intent intent) {
+        ((FileDownloaderBinder)mBinder).clearListeners();
+        return false;   // not accepting rebinding (default behaviour)
+    }
+    
 
 
     /**
     /**
      *  Binder to let client components to perform operations on the queue of uploads.
      *  Binder to let client components to perform operations on the queue of uploads.
      * 
      * 
      *  It provides by itself the available operations.
      *  It provides by itself the available operations.
      */
      */
-    public class FileUploaderBinder extends Binder {
+    public class FileUploaderBinder extends Binder implements OnDatatransferProgressListener {
+        
+        /** 
+         * Map of listeners that will be reported about progress of uploads from a {@link FileDownloaderBinder} instance 
+         */
+        private Map<String, OnDatatransferProgressListener> mBoundListeners = new HashMap<String, OnDatatransferProgressListener>();
         
         
         /**
         /**
          * Cancels a pending or current upload of a remote file.
          * Cancels a pending or current upload of a remote file.
@@ -316,6 +335,14 @@ public class FileUploader extends Service implements OnDatatransferProgressListe
         }
         }
         
         
         
         
+        
+        public void clearListeners() {
+            mBoundListeners.clear();
+        }
+
+
+        
+        
         /**
         /**
          * Returns True when the file described by 'file' is being uploaded to the ownCloud account 'account' or waiting for it
          * Returns True when the file described by 'file' is being uploaded to the ownCloud account 'account' or waiting for it
          * 
          * 
@@ -351,22 +378,45 @@ public class FileUploader extends Service implements OnDatatransferProgressListe
          * @param file          {@link OCfile} of interest for listener. 
          * @param file          {@link OCfile} of interest for listener. 
          */
          */
         public void addDatatransferProgressListener (OnDatatransferProgressListener listener, Account account, OCFile file) {
         public void addDatatransferProgressListener (OnDatatransferProgressListener listener, Account account, OCFile file) {
-            if (account == null || file == null) return;
+            if (account == null || file == null || listener == null) return;
             String targetKey = buildRemoteName(account, file);
             String targetKey = buildRemoteName(account, file);
-            UploadFileOperation target = null;
-            synchronized (mPendingUploads) {
-                if (!file.isDirectory()) {
-                    target = mPendingUploads.get(targetKey);
-                } else {
-                    // nothing to do for directories, right now
-                }
+            mBoundListeners.put(targetKey, listener);
+        }
+        
+        
+        
+        /**
+         * Removes a listener interested in the progress of the download for a concrete file.
+         * 
+         * @param listener      Object to notify about progress of transfer.    
+         * @param account       ownCloud account holding the file of interest.
+         * @param file          {@link OCfile} of interest for listener. 
+         */
+        public void removeDatatransferProgressListener (OnDatatransferProgressListener listener, Account account, OCFile file) {
+            if (account == null || file == null || listener == null) return;
+            String targetKey = buildRemoteName(account, file);
+            if (mBoundListeners.get(targetKey) == listener) {
+                mBoundListeners.remove(targetKey);
             }
             }
-            if (target != null) {
-                target.addDatatransferProgressListener(listener);
+        }
+
+
+        @Override
+        public void onTransferProgress(long progressRate) {
+            // old way, should not be in use any more
+        }
+
+
+        @Override
+        public void onTransferProgress(long progressRate, long totalTransferredSoFar, long totalToTransfer,
+                String fileName) {
+            String key = buildRemoteName(mCurrentUpload.getAccount(), mCurrentUpload.getFile());
+            OnDatatransferProgressListener boundListener = mBoundListeners.get(key);
+            if (boundListener != null) {
+                boundListener.onTransferProgress(progressRate, totalTransferredSoFar, totalToTransfer, fileName);
             }
             }
         }
         }
         
         
-        
     }
     }
     
     
     
     

+ 3 - 53
src/com/owncloud/android/ui/activity/FileDetailActivity.java

@@ -73,8 +73,6 @@ public class FileDetailActivity extends SherlockFragmentActivity implements File
     private ServiceConnection mDownloadConnection, mUploadConnection = null;
     private ServiceConnection mDownloadConnection, mUploadConnection = null;
     private FileUploaderBinder mUploaderBinder = null;
     private FileUploaderBinder mUploaderBinder = null;
     private boolean mWaitingToPreview;
     private boolean mWaitingToPreview;
-
-    public ProgressListener mProgressListener;
     
     
 
 
     @Override
     @Override
@@ -151,36 +149,21 @@ public class FileDetailActivity extends SherlockFragmentActivity implements File
 
 
         @Override
         @Override
         public void onServiceConnected(ComponentName component, IBinder service) {
         public void onServiceConnected(ComponentName component, IBinder service) {
-            Fragment fragment = getSupportFragmentManager().findFragmentByTag(FileDetailFragment.FTAG);
-            FileDetailFragment detailsFragment = (fragment instanceof FileDetailFragment) ? (FileDetailFragment) fragment : null;
                 
                 
             if (component.equals(new ComponentName(FileDetailActivity.this, FileDownloader.class))) {
             if (component.equals(new ComponentName(FileDetailActivity.this, FileDownloader.class))) {
                 Log.d(TAG, "Download service connected");
                 Log.d(TAG, "Download service connected");
                 mDownloaderBinder = (FileDownloaderBinder) service;
                 mDownloaderBinder = (FileDownloaderBinder) service;
-                if (detailsFragment != null) {
-                    mProgressListener = new ProgressListener(detailsFragment.getProgressBar());
-                    mDownloaderBinder.addDatatransferProgressListener(
-                            mProgressListener, 
-                            (Account) getIntent().getParcelableExtra(FileDetailFragment.EXTRA_ACCOUNT), 
-                            (OCFile) getIntent().getParcelableExtra(FileDetailFragment.EXTRA_FILE)
-                            );
-                }
             } else if (component.equals(new ComponentName(FileDetailActivity.this, FileUploader.class))) {
             } else if (component.equals(new ComponentName(FileDetailActivity.this, FileUploader.class))) {
                 Log.d(TAG, "Upload service connected");
                 Log.d(TAG, "Upload service connected");
                 mUploaderBinder = (FileUploaderBinder) service;
                 mUploaderBinder = (FileUploaderBinder) service;
-                if (detailsFragment != null) {
-                    mProgressListener = new ProgressListener(detailsFragment.getProgressBar());
-                    mUploaderBinder.addDatatransferProgressListener(
-                            mProgressListener, 
-                            (Account) getIntent().getParcelableExtra(FileDetailFragment.EXTRA_ACCOUNT), 
-                            (OCFile) getIntent().getParcelableExtra(FileDetailFragment.EXTRA_FILE)
-                            );
-                }
             } else {
             } else {
                 return;
                 return;
             }
             }
             
             
+            Fragment fragment = getSupportFragmentManager().findFragmentByTag(FileDetailFragment.FTAG);
+            FileDetailFragment detailsFragment = (fragment instanceof FileDetailFragment) ? (FileDetailFragment) fragment : null;
             if (detailsFragment != null) {
             if (detailsFragment != null) {
+                detailsFragment.listenForTransferProgress();
                 detailsFragment.updateFileDetails(false);   // let the fragment gets the mDownloadBinder through getDownloadBinder() (see FileDetailFragment#updateFileDetais())
                 detailsFragment.updateFileDetails(false);   // let the fragment gets the mDownloadBinder through getDownloadBinder() (see FileDetailFragment#updateFileDetais())
             }
             }
         }
         }
@@ -198,39 +181,6 @@ public class FileDetailActivity extends SherlockFragmentActivity implements File
     };    
     };    
     
     
     
     
-    /**
-     * Helper class responsible for updating the progress bar shown for file uploading or downloading  
-     * 
-     * @author David A. Velasco
-     */
-    private class ProgressListener implements OnDatatransferProgressListener {
-        int mLastPercent = 0;
-        WeakReference<ProgressBar> mProgressBar = null;
-        
-        ProgressListener(ProgressBar progressBar) {
-            mProgressBar = new WeakReference<ProgressBar>(progressBar);
-        }
-        
-        @Override
-        public void onTransferProgress(long progressRate) {
-            // old method, nothing here
-        };
-
-        @Override
-        public void onTransferProgress(long progressRate, long totalTransferredSoFar, long totalToTransfer, String filename) {
-            int percent = (int)(100.0*((double)totalTransferredSoFar)/((double)totalToTransfer));
-            if (percent != mLastPercent) {
-                ProgressBar pb = mProgressBar.get();
-                if (pb != null) {
-                    pb.setProgress(percent);
-                }
-            }
-            mLastPercent = percent;
-        }
-
-    };
-    
-
     @Override
     @Override
     public void onDestroy() {
     public void onDestroy() {
         super.onDestroy();
         super.onDestroy();

+ 64 - 7
src/com/owncloud/android/ui/fragment/FileDetailFragment.java

@@ -137,6 +137,7 @@ public class FileDetailFragment extends SherlockFragment implements
     
     
     private DownloadFinishReceiver mDownloadFinishReceiver;
     private DownloadFinishReceiver mDownloadFinishReceiver;
     private UploadFinishReceiver mUploadFinishReceiver;
     private UploadFinishReceiver mUploadFinishReceiver;
+    public ProgressListener mProgressListener;
     
     
     private Handler mHandler;
     private Handler mHandler;
     private RemoteOperation mLastRemoteOperation;
     private RemoteOperation mLastRemoteOperation;
@@ -160,6 +161,7 @@ public class FileDetailFragment extends SherlockFragment implements
         mAccount = null;
         mAccount = null;
         mStorageManager = null;
         mStorageManager = null;
         mLayout = R.layout.file_details_empty;
         mLayout = R.layout.file_details_empty;
+        mProgressListener = null;
     }
     }
     
     
     
     
@@ -176,6 +178,7 @@ public class FileDetailFragment extends SherlockFragment implements
         mAccount = ocAccount;
         mAccount = ocAccount;
         mStorageManager = null; // we need a context to init this; the container activity is not available yet at this moment 
         mStorageManager = null; // we need a context to init this; the container activity is not available yet at this moment 
         mLayout = R.layout.file_details_empty;
         mLayout = R.layout.file_details_empty;
+        mProgressListener = null;
     }
     }
     
     
     
     
@@ -211,6 +214,8 @@ public class FileDetailFragment extends SherlockFragment implements
             mView.findViewById(R.id.fdOpenBtn).setOnClickListener(this);
             mView.findViewById(R.id.fdOpenBtn).setOnClickListener(this);
             mView.findViewById(R.id.fdRemoveBtn).setOnClickListener(this);
             mView.findViewById(R.id.fdRemoveBtn).setOnClickListener(this);
             //mView.findViewById(R.id.fdShareBtn).setOnClickListener(this);
             //mView.findViewById(R.id.fdShareBtn).setOnClickListener(this);
+            ProgressBar progressBar = (ProgressBar)mView.findViewById(R.id.fdProgressBar);
+            mProgressListener = new ProgressListener(progressBar);
         }
         }
         
         
         updateFileDetails(false);
         updateFileDetails(false);
@@ -261,6 +266,7 @@ public class FileDetailFragment extends SherlockFragment implements
         if (mFile != null && mFile.isAudio()) {
         if (mFile != null && mFile.isAudio()) {
             bindMediaService();
             bindMediaService();
         }
         }
+        listenForTransferProgress();
     }
     }
     
     
     @Override
     @Override
@@ -307,6 +313,7 @@ public class FileDetailFragment extends SherlockFragment implements
                 mMediaController = null;
                 mMediaController = null;
             }
             }
         }
         }
+        leaveTransferProgress();
     }
     }
     
     
     
     
@@ -1099,16 +1106,66 @@ public class FileDetailFragment extends SherlockFragment implements
             }
             }
         }
         }
     }
     }
+    
+    
+    public void listenForTransferProgress() {
+        if (mProgressListener != null) {
+            if (mContainerActivity.getFileDownloaderBinder() != null) {
+                mContainerActivity.getFileDownloaderBinder().addDatatransferProgressListener(mProgressListener, mAccount, mFile);
+            }
+            if (mContainerActivity.getFileUploaderBinder() != null) {
+                mContainerActivity.getFileUploaderBinder().addDatatransferProgressListener(mProgressListener, mAccount, mFile);
+            }
+        }
+    }
+    
+    
+    public void leaveTransferProgress() {
+        if (mProgressListener != null) {
+            if (mContainerActivity.getFileDownloaderBinder() != null) {
+                mContainerActivity.getFileDownloaderBinder().removeDatatransferProgressListener(mProgressListener, mAccount, mFile);
+            }
+            if (mContainerActivity.getFileUploaderBinder() != null) {
+                mContainerActivity.getFileUploaderBinder().removeDatatransferProgressListener(mProgressListener, mAccount, mFile);
+            }
+        }
+    }
 
 
 
 
-    public ProgressBar getProgressBar() {
-        View v = getView();
-        if (v != null) {
-            return (ProgressBar) v.findViewById(R.id.fdProgressBar);
-        } else {
-            return null;
+    
+    /**
+     * Helper class responsible for updating the progress bar shown for file uploading or downloading  
+     * 
+     * @author David A. Velasco
+     */
+    private class ProgressListener implements OnDatatransferProgressListener {
+        int mLastPercent = 0;
+        WeakReference<ProgressBar> mProgressBar = null;
+        
+        ProgressListener(ProgressBar progressBar) {
+            mProgressBar = new WeakReference<ProgressBar>(progressBar);
         }
         }
-    }
+        
+        @Override
+        public void onTransferProgress(long progressRate) {
+            // old method, nothing here
+        };
+
+        @Override
+        public void onTransferProgress(long progressRate, long totalTransferredSoFar, long totalToTransfer, String filename) {
+            int percent = (int)(100.0*((double)totalTransferredSoFar)/((double)totalToTransfer));
+            if (percent != mLastPercent) {
+                ProgressBar pb = mProgressBar.get();
+                if (pb != null) {
+                    pb.setProgress(percent);
+                    pb.postInvalidate();
+                }
+            }
+            mLastPercent = percent;
+        }
+
+    };
+    
 
 
 
 
 }
 }