Фильтрация локальной сетки EXT JS 5 с пейджингом на стороне клиента

Я хочу добавить фильтр в свою сетку, которая выгружается локально.

Проблема, с которой я столкнулся, заключается в том, что эта реализация фильтрует только текущую страницу сетки, а не все данные хранилища, связанные с сеткой.

Есть ли обходной путь с использованием фильтра на прокси? или каким-либо образом заставить его фильтровать полные данные магазина.

Заранее спасибо.

Ниже представлена ​​моя сетка:

Ext.define('MyApp.view.grid.FAQGrid', {
    extend: 'Ext.grid.Panel',

    xtype: 'faqQuesGrid',   
    store: 'faqQuestionsStore',
    title: 'FAQ',

    columnLines: true,
    stripeRows: true,

    columns: {
        defaults:
        {
            resizable: false
        },
        items:
        [{
            header: 'Title',
            dataIndex: 'title',
            width: '77%'
        },
        {
            header: 'Category',
            dataIndex: 'categoriesName',
            width: '10%',
            renderer: function(value) {
                return '<a href="#">' + value + '</a>';
            }
        },
        {
            header: 'Published Date',
            dataIndex: 'publishedDate',
            width: '11.5%'
        }]
    },

    plugins: [{
        ptype: 'rowexpander',
        pluginId: 'faqRowId',

        rowBodyTpl: new Ext.XTemplate (
            '<p><b>Question: </b> {question}</p>',
            '<p><br/><b>Answer: </b>',
                '<tpl if="writtenAnswer">',
                    '{writtenAnswer}',
                '</tpl>',
                '<tpl if="videoAnswer">',
                    '{videoAnswer}',
                '</tpl>',
            '</p>',
             '<p><br/><i><b>Posted on</b> {publishedDate} | <b>Filed Under</b>: {categoriesName}</i></p>',
            '<tpl if="searchTagsName">',
                '<p><i><b>Tags</b>: ',
                    '<tpl for="searchTagsName">',
                        '{.};',
                    '</tpl>',
                '</i></p>',
            '</tpl>' 
        )
    }],

    tools:
    [{
        xtype: 'button',
        text: 'Expand All',
        itemId: 'expandButtonId',
        iconAlign: 'left',
        style: 'margin: 5px'
    },{
        xtype: 'button',
        text: 'Collapse All',
        itemId: 'collapseButtonId',
        iconAlign: 'left',
        style: 'margin: 5px'
    },{
        xtype: 'textfield',
        itemId: 'searchItem',
        allowBlank: false,
        emptyText: 'Search FAQ',
        style: 'margin: 5px'
    },{
        baseCls: 'search-icon',
        itemId: 'searchIconId',
        height: 20,
        iconAlign: 'right',
        tooltip: 'Search Grid',
        style: 'margin: 5px'
    }],

    dockedItems: 
    [{
        xtype: 'pagingtoolbar',
        dock: 'bottom',
        store: 'faqQuestionsStore',
        itemId: 'faqPagingToolbarId',
        displayInfo: true,
        displayMsg: 'Displaying questions {0} - {1} of {2}',
        emptyMsg: "No questions to display",
    }],

    listeners: {
        cellclick : function(grid, rowIndex, cellIndex, record, e) {
            if(cellIndex == 2){
                var clickedDataIndex = grid.headerCt.getGridColumns()[cellIndex].dataIndex;
                var clickedCellValue = record.get(clickedDataIndex);
                MyApp.app.getController('MyApp.controller.CategoriesController').getCategoryQuestions(clickedCellValue);
            }
        }
    }
});

Магазин:

Ext.define('MyApp.store.FAQQuestionsStore', {
    extend: 'Ext.data.Store',
    model: 'MyApp.model.QuestionsModel',
    requires: [
            'MyApp.model.QuestionsModel'
            ],

    storeId: 'faqQuestionsStore',
    autoLoad: false,
    remoteSort: true,
    remoteFilter: false,

    pageSize: 25,

    proxy: {
        type: 'memory',
        enablePaging: true,

        reader: {
            type: 'json'
        }
    }   
});

Я выполняю фильтрацию, как показано ниже:

this.control({
            'faqQuesGrid #searchItem':{
                change: this.filterQuestions
            }
}); 

filterQuestions: function(textfield) {
        var grid = textfield.up('panel');
        var store = grid.getStore();
        if(store != null) {
            //clear filters first
            store.remoteFilter = false;
            store.clearFilter(true);

            var filters = new Array();

            //add filter to filter array
            if(textfield.isValid()){
                var searchTxt = textfield.getValue();

                //create filter and add to filters array
                var questionFilter = {
                    property: 'question',
                    anyMatch: true,
                    caseSensitive: false,
                    value   : searchTxt
                };

                filters.push(questionFilter);
            } else{
                 store.read();
            } 
            //else condition is necessary to populate the grid correctly when a search query is removed

            //add filters to store
            if(filters.length > 0){
                store.addFilter(filters);
            }
        }
    },

//to remove any filters added when we leave this page to prevent issues with other page functionality
deactivate: function(){
                    var store = Ext.getStore('faqQuesStore');
                    if(store != null){
                        store.clearFilter();
                    }

                }

person Kartik    schedule 27.10.2014    source источник
comment
Вам нужно установить remoteFilter: true.   -  person Evan Trimboli    schedule 27.10.2014
comment
Привет Эван, Спасибо за решение. Если установить для remoteFilter значение true, возможно локальное разбиение по страницам и фильтрация. Однако, как я понял из документов API, эта конфигурация устанавливается как true для операций на стороне сервера. Не могли бы вы кратко объяснить это? Спасибо   -  person Kartik    schedule 27.10.2014
comment
Фильтрация происходит удаленно в прокси. Он действует как сервер. Локальная фильтрация означает фильтрацию в магазине. Удаленный означает, что он обрабатывается прокси.   -  person Evan Trimboli    schedule 28.10.2014
comment
хорошо .. Это объясняет это.   -  person Kartik    schedule 28.10.2014
comment
@Evan - я обновил Sencha с 5.0.0 до 5.1.3, и это решение не работает. Похоже, когда remoteFilter: true, я не могу применить локальный фильтр к моему магазину..   -  person Kartik    schedule 16.09.2016
comment
Я понял. Переход на 5.0.1 заставил его работать как раньше.   -  person Kartik    schedule 23.09.2016


Ответы (1)


Как упомянул Эван Тримболи в комментариях к вашему вопросу, вы должны установить remoteFilter: true для хранилища, чтобы фильтровать весь набор данных с использованием прокси-сервера памяти.

Фильтрация происходит «удаленно» в прокси. Он действует как сервер. Локальная фильтрация означает фильтрацию в магазине. Удаленный означает, что он обрабатывается прокси.

Хочу отметить, что Ext.data.proxy.Memory.read используйте Ext.util.Filter.createFilterFn для создания функции фильтра на основе переданного Ext.util.Filter[] (со значением свойства конфиги):

// Filter the resulting array of records 
if (filters && filters.length) {
    // Total will be updated by setting records 
    resultSet.setRecords(records = Ext.Array.filter(records, Ext.util.Filter.createFilterFn(filters)));
    resultSet.setTotal(records.length);
}

Итак, если вы хотите использовать другую логику фильтра, вы можете переопределить метод чтения прокси-сервера memroy и использовать пользовательскую функцию для создания функции фильтра. Проверьте, например, этот ответ.

person Sergey Novikov    schedule 07.07.2017