2011-06-19 43 views
1

我遇到以下問題:FileObserver不會對變化做出反應

在我的Activity中,我有一個列表視圖,列出了外部文件目錄的內容。 我想任何一種變化中的內容發生儘快更新列表,所以我必須:

public class FileAdapter implements ListAdapter { 
    private File mDirectory; 
    private FileObserver mFileObserver; 
    private DataSetObservable mDataSetObservable; 

    public FileAdapter() { 
    super(); 
    this.mDirectory = 
     new ContextWrapper(ImportList.this).getExternalFilesDir(null); 
     if (this.mDirectory != null) { 
      this.mFileObserver = 
       new FileObserver(this.mDirectory.getAbsolutePath()) { 
        @Override 
        public void onEvent(int event, String path) { 
         new Handler().post(new Runnable() { 
          public void run() { 
           FileAdapter.this.mDataSetObservable.notifyChanged(); 
          } 
         }); 
        } 
       }; 
     } 
     this.mDataSetObservable = new DataSetObservable(); 
    } 
    public void startWatching() { 
     this.mFileObserver.startWatching(); 
    } 

    public void stopWatching() { 
     this.mFileObserver.stopWatching(); 
    } 

    public boolean areAllItemsEnabled() { 
     return true; 
    } 

    public boolean isEnabled(int position) { 
     return true; 
    } 

    public int getCount() { 
     return this.mDirectory == null ? 0 : this.mDirectory.listFiles().length; 
    } 

    public Object getItem(int arg0) { 
     return this.mDirectory.listFiles()[arg0]; 
    } 

    public long getItemId(int position) { 
     return position; 
    } 

    public int getItemViewType(int position) { 
     return 0; 
    } 

    public View getView(int position, View convertView, ViewGroup parent) { 
     ItemView itemView; 
     if (convertView == null) { 
      itemView = new ItemView(ImportList.this, 1); 
     } else { 
      itemView = (ItemView) convertView; 
     } 
     File file = (File) this.getItem(position); 
     itemView.setValue(0, file.getName()); 
     return itemView; 
    } 

    public int getViewTypeCount() { 
     return 1; 
    } 

    public boolean hasStableIds() { 
     return false; 
    } 

    public boolean isEmpty() { 
     return this.getCount() < 1; 
    } 

    public void registerDataSetObserver(DataSetObserver observer) { 
     this.mDataSetObservable.registerObserver(observer); 
    } 

    public void unregisterDataSetObserver(DataSetObserver observer) { 
     this.mDataSetObservable.unregisterObserver(observer); 
    } 

    public String getPath() { 
     return this.mDirectory == null ? 
      ImportList.this.getResources().getString(R.string.no_external_files) : 
      this.mDirectory.getAbsolutePath(); 
    } 
} 

作爲一個內部類我的活動

,並以我的onCreate我做的:

this.mFileBrowser = (ListView) this.findViewById(R.id.listview_filebrowser); 
.... 
this.mFileAdapter = new FileAdapter(); 
this.mFileBrowser.setAdapter(this.mFileAdapter); 

而在的onResume()我做的:

this.mFileAdapter.startWatching(); 

所以,按照我的理解,這應該例如,一旦從外部文件目錄中刪除一個文件,就會導致我的ListView自動重新加載。 但它不起作用!

+1

有一點需要注意......文件查找顯示文檔對於通過子目錄遞歸查看的更改是不正確的..他們只能在目標目錄中看到。 – DJC

回答

0

正如DJC所說,fileobserver不是遞歸的。如果你在google上進行了很好的搜索,你會發現一個很好的RecursiveFileObserver類。然而,我對它做的一件事是線程startWatching方法,因爲它需要永遠設置,特別是對於複雜的目錄樹,所以我建議將它線程化,以便不綁定UI線程。

2

另一件需要注意的事情是,不支持爲同一路徑創建多個FileObserver實例,並可能導致一些競爭條件。所以如果有可能這個代碼可能被多次調用同一個目錄,你可能會遇到問題。

相關問題