I am looking to change the color of the header by directly click on the header and
also if column is selected through a click on a list of fields..
For the first task I tried css:
.jimu-widget-attributetable .dgrid-header .dgrid-selected {
background-color: rgb(34, 228, 34)
}
but it doesn't seem to be working.
Solved! Go to Solution.
So there is no way you can stop event propagation. What is puzzling is that by just clicking the select box the second time for another field, it triggers refresh, even though no filtering is done. I changed my script so no filtering is performed after you click on the select, for the second field, and it still refreshes the map. Why?I just try to understand the mechanics of it.Does it has to do that the select is inside the toolbar? THanks.
That must be some side effect from how you have your dropdown event wired up. Here is how mine is setup:
createToolbar: function() {
var toolbar = new Toolbar({}, html.create("div"))
....
this.refreshButton = new Button({
label: this.nls.refresh,
showLabel: true,
iconClass: "esriAttributeTableRefreshImage",
onClick: lang.hitch(this, this.refresh)
});
toolbar.addChild(this.refreshButton);
//Add filter functionality
this.filterFieldDD = new Select({
value: "",
onChange: lang.hitch(this, this.filterFieldChanged),
intermediateChanges: true
});
html.addClass(this.filterFieldDD.domNode, 'filter-field-select');
toolbar.addChild(this.filterFieldDD);
this.thetextbox = new TextBox({
value: "",
placeHolder: "type in your filter value",
onChange: lang.hitch(this, this.filterTextChanged),
intermediateChanges: true
});
html.addClass(this.thetextbox.domNode, 'filter-textbox');
toolbar.addChild(this.thetextbox);
//End add filter functionallity
....
filterFieldChanged: function(field) {
query('.dgrid-header th').forEach(function(th){
if(html.hasClass(th, 'field-' + field)){
html.addClass(th, 'th-selected');
}else{
html.removeClass(th, 'th-selected');
}
});
filter_name = field;
},
filterTextChanged: function(value) {
if (value.length >= 3 && filter_name) {
var partsObj = {
"expr": "UPPER(" + filter_name + ") LIKE '%" + value.toUpperCase() + "%'",
"parts": []
};
this.setFilterObj(partsObj);
this.clearSelection(false);
this.startQuery();
this.emit('apply-filter', {
layerInfoId: this.layerInfo.id,
expr: partsObj.expr
});
}
if(value === ""){
this.setFilterObj(null);
this.clearSelection(false);
this.startQuery();
this.emit('apply-filter', {
layerInfoId: this.layerInfo.id,
expr: null
});
}
},
Oh. Here is how I populate the dropdown.
queryExecute: function(oFields, recordCounts, exceededLimit, results, nExtent) {
var data = [];
var store = null;
var columns = {};
if (!this.domNode) {
return;
}
// mixin porperty of field to result.fields
this.filterFieldDD.innerHTML = '';
results.fields = this._processExecuteFields(this.layer.fields, oFields);
results.fields.map(lang.hitch(this, function(fld, indx){
if(fld.type !== 'esriFieldTypeOID'){
this.filterFieldDD.options[this.filterFieldDD.options.length] = new Option(fld.alias, fld.name);
}
}));
....
So like I said in my previous post, I am not sure about the soundness of your workflow, but here is how to maintain the css rule on the header after a filter refresh. Add lines 2 -10 to the changeToolbarStatus function.
changeToolbarStatus: function() {
if(filter_name && filter_name !== ""){
query('.dgrid-header th').forEach(function(th){
if(html.hasClass(th, 'field-' + filter_name)){
html.addClass(th, 'th-selected');
}else{
html.removeClass(th, 'th-selected');
}
});
}
//selected/all option
....
Lefteris,
This is what I am liking now (cleaner UI/UX feel). Filter icon does not get applied till the table is actually filtered and it persists when the table is refreshed.
define([
...
'dijit/form/TextBox',
"dijit/form/Select",
'dijit/ToolbarSeparator'
], function(
...
TextBox,
Select,
ToolbarSeparator
) {
createToolbar: function() {
var toolbar = new Toolbar({}, html.create("div"));
....
this.refreshButton = new Button({
label: this.nls.refresh,
showLabel: true,
iconClass: "esriAttributeTableRefreshImage",
onClick: lang.hitch(this, this.refresh)
});
toolbar.addChild(this.refreshButton);
//my quick filter additions
var sep = new ToolbarSeparator();
toolbar.addChild(sep);
html.place("<div class='quickFilterLabel'>Quick Filter: </div>", sep.domNode, "after");
this.filterFieldDD = new Select({
value: "",
onChange: lang.hitch(this, this.filterFieldChanged),
intermediateChanges: true
});
html.addClass(this.filterFieldDD.domNode, 'filter-field-select');
toolbar.addChild(this.filterFieldDD);
this.thetextbox = new TextBox({
value: "",
placeHolder: "type in your filter value",
onChange: lang.hitch(this, this.filterTextChanged),
intermediateChanges: true
});
html.addClass(this.thetextbox.domNode, 'filter-textbox');
toolbar.addChild(this.thetextbox);
this.clearFilterButton = new Button({
label: "Clear Filter",
showLabel: true,
iconClass: "esriAttributeTableFilterImage",
onClick: lang.hitch(this, this.clearFilter)
});
toolbar.addChild(this.clearFilterButton);
//end my quick filter additions
....
changeToolbarStatus: function() {
//my quick filter additions
query('.esriAttributeTableFilterFieldImage').forEach(function(node){
html.destroy(node);
});
if (this.thetextbox.value.length >= 3 && this.filter_name) {
var header = query('.dgrid-header th.field-' + this.filter_name + '>div')[0];
var tip = "Filter SQL: " + this._filterObj.expr;
html.place('<div class="esriAttributeTableFilterFieldImage" role="presentation" title="' + tip + '"></div>',header, "first");
}
//end my quick filter additons
//selected/all option
if (!this.tableCreated) {
//dgrid not created, set initial state
if (this._relatedQuery) {
//if RELATIONSHIPTABLE mode, show "Show All Records"
this.showSelectedRecordsMenuItem.set('disabled', false);
this.showSelectedRecordsMenuItem.set('label', this.nls.showAllRecords);
} else {
this.showSelectedRecordsMenuItem.set('disabled', true);
}
this.showRelatedRecordsMenuItem.set('disabled', true);
this.matchingCheckBox.set('disabled', true);
this.filterMenuItem.set('disabled', true);
this.toggleColumnsMenuItem.set('disabled', true);
if (!this.hideExportButton) {
this.exportCSVMenuItem.set('disabled', true);
}
this.zoomButton.set('disabled', true);
return;
}
//now dgid is created
var selectionRows = this.getSelectedRows();
if (this.showSelected) {
//if this.showSelected is true, means we are in selected mode
//now we need to show "Show All Records"
this.showSelectedRecordsMenuItem.set('label', this.nls.showAllRecords);
} else {
this.showSelectedRecordsMenuItem.set('label', this.nls.showSelectedRecords);
}
if (this.tableCreated && selectionRows && selectionRows.length > 0 &&
this.layer && this.layer.objectIdField) {
this.showSelectedRecordsMenuItem.set('disabled', false);
this.clearSelectionButton.set('disabled', false);
} else {
this.showSelectedRecordsMenuItem.set('disabled', true);
this.clearSelectionButton.set('disabled', true);
}
//my quick filter additons
if(this.tableCreated && this._filterObj){
this.clearFilterButton.set('disabled', false);
}else{
this.clearFilterButton.set('disabled', true);
}
//end my quick filter additons
...
//my quick filter additons
filterFieldChanged: function(field) {
this.filter_name = field;
},
filterTextChanged: function(value) {
if (value.length >= 3 && this.filter_name) {
var partsObj = {
"expr": "UPPER(" + this.filter_name + ") LIKE '%" + value.toUpperCase() + "%'",
"parts": []
};
this.setFilterObj(partsObj);
this.clearSelection(false);
this.startQuery();
this.emit('apply-filter', {
layerInfoId: this.layerInfo.id,
expr: partsObj.expr
});
}
},
clearFilter: function() {
this.thetextbox.set("value", '');
this.setFilterObj(null);
this.clearSelection(false);
this.startQuery();
this.emit('apply-filter', {
layerInfoId: this.layerInfo.id,
expr: null
});
},
//end my quick filter additons
queryExecute: function(oFields, recordCounts, exceededLimit, results, nExtent) {
var data = [];
var store = null;
var columns = {};
if (!this.domNode) {
return;
}
// mixin porperty of field to result.fields
results.fields = this._processExecuteFields(this.layer.fields, oFields);
//my quick filter additons
this.filterFieldDD.innerHTML = '';
results.fields.map(lang.hitch(this, function(fld, indx){
if(fld.type !== 'esriFieldTypeOID'){
this.filterFieldDD.options[this.filterFieldDD.options.length] = new Option(fld.alias, fld.name);
}
}));
//end my quick filter additons
...
.jimu-widget-attributetable .filter-textbox {
height: 24px;
line-height: 24px;
margin: 0 0.3em;
}
.claro .dijitInputContainer {
line-height: 20px;
}
.claro .dijitTextBox .dijitInputInner {
height: 20px;
line-height: 20px !important;
}
.claro .dijitTextBox .dijitPlaceHolder {
font-size: 12px;
height: 22px;
}
.jimu-widget-attributetable .filter-field-select {
height: 24px;
line-height: 24px;
margin: 0 0.3em;
min-width: 120px;
}
.esriAttributeTableFilterFieldImage{
background-image: url("../images/filter.png");
width: 13px;
height: 13px;
float: left;
margin: 1px 9px 0 5px;
}
.quickFilterLabel {
display:inline-block;
margin: 0 2px 0 5px;
line-height: 22px;
}
Robert, I'd like to thank you for your time and effort to assist me with this effort.
I finally realized why the map kept refreshing when I was clicking on the column header at first, then at the select drop down. Because of stupidity, I didn't realized that by initializing the textbox, every time I was selecting another field, I was re-initiating the query of the fields.
this.thetextbox.set("value", "")
What I should have done is that I could keep this line but also use
if(filter_name && filter_name !== ""){
...............................
Anyway, your code is very helpful to understand, among other things, of how to change the default stylesheetsof WAB widgets for a target element.