【问题标题】:content resolver notifyChange() not working内容解析器 notifyChange() 不起作用
【发布时间】:2014-08-19 09:36:43
【问题描述】:

我已经设置了一个片段来使用 CursorLoader 从自定义内容提供程序中提取数据。

问题是当我使用内容解析器更新 SQLite 表中的记录时,游标不会刷新,即 getContext().getContentResolver().notifyChange(myUri, null) 无效。我必须退出片段并再次打开它才能看到变化。

我认为问题在于加载程序没有观察到我用来更新行的 URI:

  • 创建加载器的URI -content://com.myapp.provider/MyTable/Set/22
  • 更新行的URI -content://com.myapp.provider/MyTable/167

167 标识表中的唯一行。 22 标识表中的一组行。 有没有办法告诉加载器第 167 行在集合 22 中,所以它应该重置光标?

这里是代码,以防它更清晰:

在 Fragment 中创建 CursorLoader:

@Override
public Loader<Cursor> onCreateLoader(int arg0, Bundle queryBundle) {
    CursorLoader cursorLoader = new CursorLoader(getActivity(), Uri.parse("content://com.myapp.provider/MyTable/Set/22"), myProjection, null, null, null);
    return cursorLoader;
}

点击片段中的按钮:

mContext.getContentResolver().update("content://com.myapp.provider/MyTable/167", values, null, null);

内容提供者类:

private static final String AUTHORITY = "com.myapp.provider";
private static final String TABLE_PATH = "MyTable";
public static final String CONTENT_URI_BASEPATH = "content://" + AUTHORITY + "/" + TABLE_PATH;

private static final int URITYPE_TABLE = 1;
private static final int URITYPE_SINGLE_SET = 2;
private static final int URITYPE_SINGLE_ROW = 3;

private static final UriMatcher sUriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
static{
    sUriMatcher.addURI(AUTHORITY, TABLE_PATH,URITYPE_TABLE);
    sUriMatcher.addURI(AUTHORITY, TABLE_PATH + "/Set/#", URITYPE_SINGLE_SET);
    sUriMatcher.addURI(AUTHORITY, TABLE_PATH + "/#", URITYPE_SINGLE_ROW);
    }

@Override
public int update(Uri myUri, ContentValues values, String selection, String[] selectionArgs){
    int rowCount = 0;
    String id;
    SQLiteDatabase db = localDB.getWritableDatabase();
    int uriType = sUriMatcher.match(myUri);

    switch(uriType){
    case URITYPE_SINGLE_ROW :
    id = uri.getLastPathSegment();
        //selection and selectionArgs are ignored since the URI itself identifies a unique row. 
        rowCount = db.update(MyTable.TABLE_NAME, values, MyTable.COLUMN_ID + " = ?", new String[] {id});
    }

    getContext().getContentResolver().notifyChange(myUri, null);
    return rowCount;
}

【问题讨论】:

    标签: android android-contentprovider


    【解决方案1】:

    我也有类似的问题,找到了solution here

    简而言之,我需要在我的内容提供者的query() 方法返回的光标上调用setNotificationUri(ContentResolver cr, Uri uri)

    【讨论】:

      【解决方案2】:

      解决方案是在正在观察的 Uri 上调用 notifyChange(),即在集合上而不是在行上。

      为了实现这一点,我们需要做一些改变:

      1. 在调用更新时在 URI 中包含设置 ID:

        mContext.getContentResolver().update("content://com.myapp.provider/MyTable/Set/22/167", values, null, null);
        
      2. 将单行的URI模式从“/#”更改为“/Set/#/#”

        private static final UriMatcher sUriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
        static{
        sUriMatcher.addURI(AUTHORITY, TABLE_PATH,URITYPE_TABLE);
        sUriMatcher.addURI(AUTHORITY, TABLE_PATH + "/Set/#", URITYPE_SINGLE_SET);
        sUriMatcher.addURI(AUTHORITY, TABLE_PATH + "/Set/#/#", URITYPE_SINGLE_ROW);
        }
        
      3. 然后在更新函数中,构造一个需要通知的新Uri:

        List<String> pathSegments = uri.getPathSegments();
        String mySetID = pathSegments.get(2); 
        Uri mySetUri = Uri.parse("content://" + AUTHORITY + "/" + TABLE_PATH + "/Set/" + mySetID);
        getContext().getContentResolver().notifyChange(mySetUri, null);
        

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2012-08-06
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-01-28
        • 1970-01-01
        相关资源
        最近更新 更多