11

I'v은 Contentprovide를 생성하고이 같은 갱신() 메소드의 구현 : 어떻게 나의 appwidget에contentprovider 변경을 관찰하는 방법은 무엇입니까? 안드로이드

@Override 
    public int update(Uri uri, ContentValues values, String selection, 
     String[] selectionArgs) { 
     final SQLiteDatabase db = mHelper.getWritableDatabase(); 
     int count = db.update(InslideDB.FOLDER_TABLE, values, selection, selectionArgs); 

     /* To notify the observer */ 
     this.getContext().getContentResolver().notifyChange(URI, null); 
     return count; 
} 

를 통보받을 수 있습니까? 감사! 나는 마지막으로

class DataProviderObserver extends ContentObserver { 
    private AppWidgetManager mAppWidgetManager; 
    private ComponentName mComponentName; 

    DataProviderObserver(AppWidgetManager mgr, ComponentName cn, Handler h) { 
     super(h); 
     mAppWidgetManager = mgr; 
     mComponentName = cn; 
    } 

    @Override 
    public void onChange(boolean selfChange) { 
     super.onChange(selfChange); //NOTE: Have to call this. dwy. 

     // The data has changed, so notify the widget that the collection view needs to be updated. 
     // In response, the factory's onDataSetChanged() will be called which will requery the 
     // cursor for the new data. 

     Log.d("PresenterWidgetProvider", "--------------------Date Changed"); 

     mAppWidgetManager.notifyAppWidgetViewDataChanged(
       mAppWidgetManager.getAppWidgetIds(mComponentName), R.id.inslide_grid); 
    } 
} 


public class PresenterWidgetProvider extends AppWidgetProvider{ 

    private static final String AUTHORITY = "com.apps.slide"; 

    static final Uri CONTENT_URI = Uri.parse("content://" + AUTHORITY + "/folder"); 

    public static final String EXTRA_INSLIDE_PATH = "EXTRA_WIDGET_PATH"; 
    private static HandlerThread sWorkerThread; 
    private static Handler sWorkerQueue; 
    private static DataProviderObserver sDataObserver; 

    public PresenterWidgetProvider() { 

     // Start the worker thread to update Content Provider. 
     sWorkerThread = new HandlerThread("PresenterWidgetProvider worker"); 
     sWorkerThread.start(); 
     sWorkerQueue = new Handler(sWorkerThread.getLooper()); 

    } 

    @Override 
    public void onEnabled(Context context) { 
     // Register for external updates to the data to trigger an update of the widget. When using 
     // content providers, the data is often updated via a background service, or in response to 
     // user interaction in the main app. To ensure that the widget always reflects the current 
     // state of the data, we must listen for changes and update ourselves accordingly. 
     final ContentResolver r = context.getContentResolver(); 
     if (sDataObserver == null) { 
      final AppWidgetManager mgr = AppWidgetManager.getInstance(context); 
      final ComponentName cn = new ComponentName(context, PresenterWidgetProvider.class); 
      sDataObserver = new DataProviderObserver(mgr, cn, sWorkerQueue); 
      r.registerContentObserver(CONTENT_URI, true, sDataObserver); 
      Log.d("PresenterWidgetProvider", "--------------------onEnabled. sDataObserver = " + sDataObserver); 
     } 
    } 

그래서 :

나는이 리졸버하지만 로그 (-------------------- 날짜 변경) 인쇄를 시도하고있다 4 단계로 그것을 해결 :

  1. 는) (삭제) (컨텐트 프로 바이더의 UPDAT() 삽입에 콜백을 this.getContext().getContentResolver().notifyChange(URI, null);

를 추가합니다.

  1. 새로운 Observer와 새로운 Thread를 작성하여 처리하십시오.

  2. Observer의 onChange()에서 notifyAppWidgetViewDataChanged()를 호출하십시오.

  3. 위젯을 삭제하고 새 위젯을 배치하십시오.

그렇습니다.

+1

공유해 주셔서 감사합니다. 장치를 다시 시작한 후에는 onEnabled가 다시 호출되지 않기 때문에 관찰자를 onEnabled에 등록하는 것만으로는 충분하지 않다고 생각합니다. 나는 그것을 onReceive에 넣었습니다. – mtotschnig

답변

15

ContentObserver 클래스를 사용할 수 있습니다. 해당 클래스를 구현하고 getContentResolver().registerContentObserver() 메서드를 사용하여 관찰자를 등록하면됩니다.

+0

@Ctristian 감사합니다! 그리고 ContentObserver를 사용했지만 콜백 onChange()를 호출하지 않았습니다. 질문에 대한 코드를 업데이트했습니다. Observer를 사용하는 방법과 위젯을 업데이트하는 방법에 대해 약간 혼란스러워합니다. 다시 한 번 감사드립니다! – herbertD

+2

'AppWidgetProvider' 내부에 관찰자를 등록 할 수 없다고 생각합니다. 대신,'AppWidgetProvider'에서 서비스를 시작하고 거기서 당신의'ContentObserver '를 등록하십시오. – Cristian

+0

나는 그것을 해결했다. 전체 코드는 위에 업데이트되었습니다. 고맙습니다. – herbertD

관련 문제