I manage to create a working CursorWrapper
, but get stuck when I want to use my ContentProvider
across processes.
These posts even show how to implement the CrossProcessCursor
interface, notably the hard and undocumented fillWindow()
method:
The problem is that I can think only of an implementation of fillWindow()
that deals with a cursor with either all columns containing Blobs, or Strings, or ..., but not a mix of those, as a real-world cursor is bound to have. The real issue here is a lack of a getType()
function (exists only from v11 on), or a getRaw()
/putRaw()
that would just copy binary without complaining. How do you deal with this without incurring unwanted conversions in your returned cursor values?
I've implemented it as follows for now, but it does not feel like the right thing to do or robust:
/**
* Copy data from cursor to CursorWindow
* @param position start position of data
* @param window
*/
public void fillWindow(int position, CursorWindow window) {
if (position < 0 || position > getCount()) {
return;
}
window.acquireReference();
try {
int oldpos = this.getPosition();
this.moveToPosition(position - 1);
window.clear();
window.setStartPosition(position);
int columnNum = getColumnCount();
window.setNumColumns(columnNum);
while (moveToNext() && window.allocRow()) {
for (int i = 0; i < columnNum; i++) {
//int type = getType(i);//only from v11 on
try {
String field7 = getString(i);
if (field7 != null) {
try {
if (!window.putLong(new Long(field7), this.getPosition(), i)) {
if (!window.putDouble(new Double(field7), this.getPosition(), i)) {
if (!window.putString(field7, this.getPosition(), i)) {
window.freeLastRow();
break;
}
}
}
} catch (NumberFormatException e) {
try {
if (!window.putDouble(new Double(field7), this.getPosition(), i)) {
if (!window.putString(field7, this.getPosition(), i)) {
window.freeLastRow();
break;
}
}
} catch (NumberFormatException e1) {
if (!window.putString(field7, this.getPosition(), i)) {
window.freeLastRow();
break;
}
}
}
} else {
if (!window.putNull(this.getPosition(), i)) {
window.freeLastRow();
break;
}
}
} catch (SQLiteException e7) {
try {
byte[] field1 = getBlob(i);
if (field1 != null) {
if (!window.putBlob(field1, this.getPosition(), i)) {
window.freeLastRow();
break;
}
} else {
if (!window.putNull(this.getPosition(), i)) {
window.freeLastRow();
break;
}
}
} catch (SQLiteException e1) {
throw e1;
}
}
}
}
this.moveToPosition(oldpos);
} catch (IllegalStateException e){
// simply ignore it
} finally {
window.releaseReference();
}
}