ExtJS - Grid multiple value filter in same column - checkbox

Needed help in filtering grid with multiple values.
I am trying to create a menucheckitem with many phone value.
And filter the grid based on the phone Checked.
By using below code, i am able to filter grid based on single value.
store.filter([{
property: 'type',
value: value
}]);
Now i wanted to filter grid, even if i select many phone checkBoxs.
I tried using store.filterBy(). But, not working properly, i do not know what i am doing wrong.
var test = ["111-222-333","111-222-334","111-222-335"]
store.filterBy(function(record, val){
return test.indexOf(record.get('phone')) != -1
}
});
This filters the first value only i.e. "111-222-333" value only.. Not filtering all other value in test.
find sample code in here -
https://fiddle.sencha.com/#view/editor&fiddle/2ll7

So i forked your fiddle, remade it and i think i have achieved what you wanted. First of all your definition of menucheckitem in bbar was kind of strange. I think you needed a list of phones which would be checkboxes, but the list is depends on the store records, so it needs to be build dynamically (as i did it in afterrender). Actually this must be inside of store's load event, but in example it didn't fire(maybe bcz it is a memory type of store). Anyway when you copy the code you'll need to put all of the afterrender content inside the store load event.
FIDDLE
Ext.application({
name: 'Fiddle',
launch: function () {
Ext.create('Ext.grid.Panel', {
title: 'Simpsons',
store: {
fields: ['name', 'email', 'phone', 'type'],
data: [{
name: 'Marge',
email: 'marge#simpsons.com',
phone: '111-222-334',
type: 'Foo'
}, {
name: 'Homer',
email: 'homer#simpsons.com',
phone: '111-222-333',
type: 'Foo'
}, {
name: 'Marge',
email: 'marge#simpsons.com',
phone: '111-222-334',
type: 'Foo'
}, {
name: 'Bart',
email: 'bart#simpsons.com',
phone: '111-222-335',
type: 'Bar'
}, {
name: 'Bart',
email: 'bart#simpsons.com',
phone: '111-222-335',
type: 'Bar'
}, {
name: 'Lisa',
email: 'lisa#simpsons.com',
phone: '111-222-336',
type: 'Bar'
}]
},
columns: [{
text: 'Name',
dataIndex: 'name'
}, {
text: 'Email',
dataIndex: 'email'
}, {
text: 'Phone',
dataIndex: 'phone'
}, {
text: 'Type',
dataIndex: 'type'
}],
listeners: {
afterrender: function (grid) {
var store = grid.store;
var phones = store.getData().items.map(function (r) { //get the phones
return r.get('phone');
});
var phonesFiltered = [];
phones.forEach(function (p) { //filter them to make records unique
if (!phonesFiltered.includes(p)) {
phonesFiltered.push(p);
}
});
var items = [];
phonesFiltered.forEach(function (p) { //create `menucheckitem` items with phone names and attaching `checkchange` event
items.push({
xtype: 'menucheckitem',
text: p,
listeners: {
checkchange: function (checkbox, checked, eOpts) {
var menu = checkbox.up('menu');
var filterPhones = [];
menu.items.items.forEach(function (c) { //get all checked `menucheckitem`-s
if (c.checked) {
filterPhones.push(c.text);
}
});
var store = checkbox.up('grid').store;
store.clearFilter();
if (filterPhones.length > 0) {
store.filterBy(function (record) {
return this.filterPhones.indexOf(record.get('phone')) !== -1;
}, {
filterPhones: filterPhones
});
}
}
}
});
});
//
Ext.getCmp('toolbarId').add({
xtype: 'menu',
// height: 120,
floating: false,
items: items
});
}
},
bbar: {
xtype: 'toolbar',
height: 200,
id: 'toolbarId'
},
renderTo: Ext.getBody()
});
}
});

Related

ExtJs - Checkbox selection model, disable checkbox per row and lose clearing all the selections

I have a grid with a checkbox selection model.
There are some rows that not be selectable, based on a value in a field. It's work.
My problem is that clearing all the selections by clicking the checkbox in the column header doesn't work.
On this link I see that costa was faced the same problem as me: ExtJs - Checkbox selection model, disable checkbox per row.
This listener is worked, but it's break checkbox clearing.
Code:
xtype: 'grid',
border: false,
selModel: {
selType: 'checkboxmodel',
listeners: {
beforeselect: function(grid, record) {
if (!record.get('supplier')) {
return false;
}
}
}
colums:[
....
],
....
Does anyone have an idea how to do this?
Thank you.
The header checkbox is checked only if all the records are checked. In your case it is impossible to check all the records => header checkbox will be never checked => it is impossible to uncheck.
To implement new logic, you can extend the checkbox model and write your own one with custom logic (by overriding the updateHeaderState method). Something like this:
Ext.define('CustomCheckboxModel', {
alias: 'selection.custom_checkboxmodel',
extend: 'Ext.selection.CheckboxModel',
allowDeselect: true,
updateHeaderState: function () {
// check to see if all records are selected
var me = this,
store = me.store,
storeCount = store.getCount(),
views = me.views,
hdSelectStatus = true,
selectedCount = 0,
selected, len, i;
if (!store.isBufferedStore && storeCount > 0) {
selected = me.selected;
hdSelectStatus = true;
store.each(function (record) {
if (!record.get('supplier')) {
return true;
}
var found = false;
for (i = 0, len = selected.getCount(); i < len; ++i) {
if (record.getId() == selected.getAt(i).id) {
found = true;
break;
}
}
if (!found) {
hdSelectStatus = found;
return false;
}
}, this);
}
if (views && views.length) {
me.column.setHeaderStatus(hdSelectStatus);
}
},
});
Ext.application({
name: 'Fiddle',
launch: function () {
var store = Ext.create('Ext.data.Store', {
fields: ['name', 'email', 'phone'],
data: [{
name: 'Lisa',
email: 'lisa#simpsons.com',
phone: '555-111-1224',
supplier: true
}, {
name: 'Bart',
email: 'bart#simpsons.com',
phone: '555-222-1234',
supplier: false
}, {
name: 'Homer',
email: 'homer#simpsons.com',
phone: '555-222-1244',
supplier: true
}, {
name: 'Marge',
email: 'marge#simpsons.com',
phone: '555-222-1254',
supplier: false
}]
});
Ext.create('Ext.grid.Panel', {
title: 'Simpsons',
store: store,
columns: [{
text: 'Name',
dataIndex: 'name'
}, {
text: 'Email',
dataIndex: 'email',
flex: 1
}, {
text: 'Phone',
dataIndex: 'phone'
}, {
xtype: 'checkcolumn',
text: 'Supplier',
dataIndex: 'supplier'
}],
height: 400,
renderTo: Ext.getBody(),
selModel: {
selType: 'custom_checkboxmodel',
listeners: {
beforeselect: function (selectionCheckboxModel, record, index, eOpts) {
console.log(record);
if (!record.get('supplier')) {
return false;
}
return true;
}
}
}
});
}
});

ExtJS 7 How to select grid row on rightclick

I'd like to both open a context menu and select the right-clicked row in a ExtJS 7 modern grid. The context menu works with the code below. However, I cannot find a way to select the row. The grid.getSelectionModel() seems to be no longer available in ExtJS 7.
// Listener in my Ext.app.ViewController manages to update and show context menu but not to select the row.
onContextMenu: function (e) {
const grid = this.getView();
const target = e.getTarget(grid.itemSelector);
if (target) {
e.stopEvent();
const item = Ext.getCmp(target.id);
if (item) {
// Would like to select row here with something like grid.getSelectionModel().selectRow(rowindex);
this.updateMenu(item.getRecord(), item.el, e);
}
}
}
Have a look at the following fiddle sample (Modern toolkit 7.3.1)
Ext.application({
name: 'Fiddle',
launch: function () {
const menu = new Ext.menu.Menu({
items: [{
text: 'Menu Item 1'
}, {
text: 'Menu Item 2'
}]
});
Ext.Viewport.add({
xclass: 'Ext.grid.Grid',
store: Ext.create('Ext.data.Store', {
fields: ['name', 'email', 'phone'],
data: [{
name: 'Lisa',
email: 'lisa#simpsons.com',
phone: '555-111-1224'
}, {
name: 'Bart',
email: 'bart#simpsons.com',
phone: '555-222-1234'
}]
}),
columns: [{
text: 'Name',
dataIndex: 'name',
width: 200
}, {
text: 'Email',
dataIndex: 'email',
width: 250
}, {
text: 'Phone',
dataIndex: 'phone',
width: 120
}],
listeners: {
childcontextmenu: function (grid, location) {
const {
record,
event
} = location;
grid.deselectAll();
grid.setSelection(record);
menu.showAt(event.getX(), event.getY());
event.stopEvent()
}
}
})
}
});

Ext.grid.column.Check click event to the CheckBox itself not the whole cell area

Is there any to way to restrict check column action to only check box and restrict to the cell area. sample code for check column which i have copied from docs.
var store = Ext.create('Ext.data.Store', {
fields: ['name', 'email', 'phone', 'active'],
data: [{
name: 'Lisa',
email: 'lisa#simpsons.com',
phone: '555-111-1224',
active: true
}, {
name: 'Bart',
email: 'bart#simpsons.com',
phone: '555-222-1234',
active: true
}, {
name: 'Homer',
email: 'homer#simpsons.com',
phone: '555-222-1244',
active: false
}, {
name: 'Marge',
email: 'marge#simpsons.com',
phone: '555-222-1254',
active: true
}]
});
Ext.create('Ext.grid.Panel', {
title: 'Simpsons',
height: 200,
width: 400,
renderTo: Ext.getBody(),
store: store,
columns: [{
text: 'Name',
dataIndex: 'name'
}, {
text: 'Email',
dataIndex: 'email',
flex: 1
}, {
text: 'Phone',
dataIndex: 'phone'
}, {
xtype: 'checkcolumn',
text: 'Active',
dataIndex: 'active'
}]
});
Kindly help me on this.
This solution will work on every version of ExtJS from 4.2.0 to 4.2.6.
Ext.define('CheckColumn', {
override: 'Ext.grid.column.' + (!!Ext.grid.column.Check ? 'Check': 'CheckColumn'),
processEvent: function(type, view, cell, recordIndex, cellIndex, e, record, row) {
var me = this,
key = type === 'keydown' && e.getKey(),
mousedown = type == 'mousedown';
if (mousedown && !Ext.fly(e.getTarget()).hasCls('x-grid-checkcolumn')) {
return !me.stopSelection;
}
me.callParent([type, view, cell, recordIndex, cellIndex, e, record, row]);
}
});
Based on Guiherme lopes answer I have applied the fix in beforecheckchange.
beforecheckchange: function(me , rowIndex , checked , record , e , eOpts){
if(!Ext.fly(e.getTarget()).hasCls('x-grid-checkcolumn')){
return false;
}
return true;
}

Set a renderer for a column with a click of a button

I want to create a button that when I click on it, it will set a renderer for a column on my grid. I'm looking through the API for columns http://docs.sencha.com/extjs/5.1/5.1.1-apidocs/#!/api/Ext.grid.column.Column
and I do not see a method that says setRenderer, how can I achieve this?
Edit: I do not want to set it when I create the column ( i know there is a property to set the renderer)
You could try simply changing the renderer, no need for a setRenderer
Ext.create('Ext.data.Store', {
storeId: 'simpsonsStore',
fields:[ 'name', 'email', 'phone'],
data: [
{ name: 'Lisa', email: 'lisa#simpsons.com', phone: '555-111-1224' },
{ name: 'Bart', email: 'bart#simpsons.com', phone: '555-222-1234' },
{ name: 'Homer', email: 'homer#simpsons.com', phone: '555-222-1244' },
{ name: 'Marge', email: 'marge#simpsons.com', phone: '555-222-1254' }
]
});
Ext.create('Ext.grid.Panel', {
title: 'Simpsons',
store: Ext.data.StoreManager.lookup('simpsonsStore'),
columns: [
{ text: 'Name', dataIndex: 'name',
renderer: function (value) {
return value + ' Simpson';
}},
{ text: 'Email', dataIndex: 'email', flex: 1 },
{ text: 'Phone', dataIndex: 'phone' }
],
height: 400,
width: 400,
renderTo: Ext.getBody(),
bbar: [{
text: 'Change First Column Renderer',
handler: function(b) {
var grid = b.up('grid'),
columns = grid.getColumnManager().getColumns(),
column = columns[0];
column.renderer = function(value) {
return value === 'Lisa' ? 'L Simpson' : value;
}
grid.view.refreshView();
}
}]
});
Fiddle: https://fiddle.sencha.com/#fiddle/1a5e

ExtJS Gridpanel selected rows

I am design ExtJs Gridpanel with Checkboxes...
How to get checked records for save the data
Use getSelections to get all selected records and getSelected to get the first record.
var selected = checkBoxSelectionModelObj.getSelections();
for (var i = 0; i < selected.length; i++)
{
alert(selected[i].data.code);
}
In ExtJs docs provide method to get selected record in grid grid.getSelection(). You can refer ExtJs docs
I have create small demo to show you, how it work. Sencha fiddle example
var store = Ext.create('Ext.data.Store', {
fields: ['name', 'email', 'phone'],
data: [{
name: 'Lisa',
email: 'lisa#simpsons.com',
phone: '555-111-1224'
}, {
name: 'Bart',
email: 'bart#simpsons.com',
phone: '555-222-1234'
}, {
name: 'Homer',
email: 'homer#simpsons.com',
phone: '555-222-1244'
}, {
name: 'Marge',
email: 'marge#simpsons.com',
phone: '555-222-1254'
}, {
name: 'AMargeia',
email: 'marge#simpsons.com',
phone: '555-222-1254'
}]
});
Ext.create('Ext.grid.Panel', {
title: 'Simpsons',
store: store,
id: 'testGrid',
columns: [{
text: 'Name',
dataIndex: 'name'
}, {
text: 'Email',
dataIndex: 'email',
flex: 1
}, {
text: 'Phone',
dataIndex: 'phone'
}],
height: 200,
width: 400,
renderTo: Ext.getBody(),
selModel: {
checkOnly: false,
injectCheckbox: 'last',
mode: 'SIMPLE'
},
selType: 'checkboxmodel',
buttons: [{
text: 'Select All',
handler: function () {
Ext.getCmp('testGrid').getSelectionModel().selectAll();
}
}, {
text: 'Deselect All',
handler: function () {
Ext.getCmp('testGrid').getSelectionModel().deselectAll();
}
},{
text:'Print Selected Recod',
handler:function(){
var selection = Ext.getCmp('testGrid').getSelection();
if(selection.length){
let name='';
selection.map(item=>{
name+=item.get('name')+'<br>';
});
Ext.Msg.alert('Selected Record',name);
}else{
Ext.Msg.alert('Error','Please select record');
}
}
}]
});

Resources