-
rawQuery doesn't seem to be used in beforeQuery. I assume that's passed just in case a subclass finds it useful?
Perhaps the queryPlan object should be created in doQuery and passed to beforeQuery, it might help to keep it future compatible if other parameters come along later?
Code:
queryPlan = me.beforeQuery({
query: queryString,
forceAll: forceAll,
rawQuery: rawQuery,
combo: me,
cancel: false
});
and:
Code:
beforeQuery: function(queryPlan) {
...
}
A beforeQuery method is a good start but I feel there's potentially a lot of benefit in factoring out the bits inside the local/remote bifurcation, that's where most of the patching tends to happen. Coming up with a decent API for that without exposing too many implementation details may be tricky though.
Nested 'ifs' four levels deep followed by a massive bifurcation... just the indentation waveform is enough to set alarm bells ringing, you don't even have to read the code.
-
Good points. I'll split into doLocalQuery and doRemoteQuery.
-
The new doQuery:
Code:
doQuery: function(queryString, forceAll, rawQuery) {
var me = this,
// Decide if, and how we are going to query the store
queryPlan = me.beforeQuery({
query: queryString || '',
rawQuery: rawQuery,
forceAll: forceAll,
combo: me,
cancel: false
});
// Allow veto.
if (queryPlan === false || queryPlan.cancel) {
return false;
}
// Make sure they aren't using the same value as last time
if (!me.queryCaching || queryPlan.query !== me.lastQuery) {
me.lastQuery = queryPlan.query;
if (me.queryMode === 'local') {
me.doLocalQuery(queryPlan);
} else {
me.doRemoteQuery(queryPlan);
}
}
return true;
},
Each branch (local/remote) has to call afterQuery in its own way because local will be synchronous, and remote could be asynchronous, and will call it in e store load callback.
Much cleaner!
-
Edit: sorry, what I wrote below does not work as expected.
In order to make anyMatch with typeAhead work, I added the following code in doLocalQuery:
Code:
...
// Filter the Store according to the updated filter
me.store.filter();
// Expand after adjusting the filter unless there are no matches
if (me.store.getCount()) {
/* added by me */
me.getPicker().refresh();
/* end added by me */
me.expand();
} else {
me.collapse();
}
...
This has for effect to refresh the picker as I type
-
I solved it. I changed :
Code:
// Create our filter when first needed
if (!me.queryFilter) {
// Create the filter that we will use during typing to filter the Store
me.queryFilter = new Ext.util.Filter({
id: me.id + '-query-filter',
anyMatch: me.anyMatch,
caseSensitive: me.caseSensitive,
root: 'data',
property: me.displayField
});
me.store.addFilter(me.queryFilter, false);
}
To :
Code:
// Create our filter when first needed
if (!me.queryFilter || me.anyMatch) {
// Create the filter that we will use during typing to filter the Store
me.queryFilter = new Ext.util.Filter({
id: me.id + '-query-filter',
anyMatch: me.anyMatch,
caseSensitive: me.caseSensitive,
root: 'data',
property: me.displayField
});
me.store.addFilter(me.queryFilter, false);
}
And now it reacts to anyMatch :)