Ext.define('uas.AppController', { extend: 'Ext.app.ViewController', alias: 'controller.app', privates: { dynamicViews: {} }, init: function () { this.onLaunch(); this.control({ 'dynamicform': { boxready: 'onViewInitEvent' }, 'tab': { activate: 'onTabChangeEvent' }, 'button': { click: 'onButtonClickEvent' }, 'menuitem': { click: 'onMenuItemClickEvent' }, 'grouplist': { itemclick: 'onListItemClickEvent' }, 'field': { change: 'onFieldChangeEvent' }, 'searchfield': { search: 'onFieldSearchEvent', labelclick: 'onFieldLabelClickEvent' }, 'gridpanel': { selectionchange: 'onGridSelectionChangeEvent', paging: 'onPagingEvent', schemechange: 'onSchemeChangeEvent', cellclick: 'onGridCellClickEvent', itemdblclick: 'onGridItemDbClickEvent' } }); }, /** * 单页应用启动 */ onLaunch() { var me = this; Ext.Ajax.promise({ url: '/api/web/launch', headers: me.getRequestHeader() }).then(function (res) { var actions = res.data.actions; if (actions) { actions.forEach(action => { me.invokeAction(me, action); }); } }).catch(function (e) { console.error(e); me.showToast(null, [(e ? e.message : null) || '出现错误']); }).finally(function () { Ext.getBody().removeCls('launching'); }); }, /** * 执行后端动作指令 * * @param {*} action */ invokeAction: function (trigger, action) { var me = this; if (action.type == 'invokeMethod') { var methodName = action.params.methodName, args = action.params.args, viewId = action.params.viewId; if (me[methodName]) { me[methodName].apply(me, [trigger, args, viewId]); } else { console.error('Unknown action ', action); } } else if (action.type == 'invokeCmpMethod') { var itemId = action.params.itemId, methodName = action.params.methodName, args = action.params.args, viewId = action.params.viewId, view = me.dynamicViews[viewId], cmp = view.down('#' + itemId); if (cmp && cmp[methodName]) { cmp[methodName].apply(cmp, args); } else { console.error('Unknown item method', action); } } }, setUuid: function (trigger, args) { this.uuid = args[0]; sessionStorage.setItem("uuid", this.uuid); }, getUuid: function () { var me = this, uuid = me.uuid; if (!uuid) { me.uuid = uuid = sessionStorage.getItem("uuid"); } return uuid; }, getRequestHeader: function () { var me = this, uuid = me.getUuid(); if (uuid) { return { uuid: uuid }; } return null; }, setTitle: function (trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view && view.setTitle) { view.setTitle(args[0]); } }, /** * 打开视图 * * @param {*} args */ addView: function (trigger, args) { var me = this, viewConfig = args[0], cacheId = viewConfig.viewName + "_" + viewConfig.viewType, dataStr = localStorage.getItem(cacheId); if (dataStr) { // TODO 考虑版本 var metadata = JSON.parse(dataStr); me.addDynamicForm(trigger, viewConfig, metadata); } else { me.loadViewMetadata(viewConfig).then(function (res) { var metadata = res.data; localStorage.setItem(cacheId, JSON.stringify(metadata)); me.addDynamicForm(trigger, viewConfig, metadata); }).catch(function (e) { console.error(e); me.showToast(trigger, [(e ? e.message : null) || '出现错误']); }); } }, /** * 获取视图元数据 * * @param {*} viewConfig */ loadViewMetadata: function (viewConfig) { var me = this; return Ext.Ajax.promise({ url: '/api/web/view', headers: me.getRequestHeader(), params: { viewId: viewConfig.viewId } }); }, addDynamicForm: function (trigger, viewConfig, viewMetadata) { var me = this; // 主视图 if (viewConfig.openType == 'page') { me.setMainContent(viewConfig, viewMetadata); } else if (viewConfig.openType == 'card') { me.addCard(viewConfig, viewMetadata); } else if (viewConfig.openType == 'floating') { me.addFloating(trigger, viewConfig, viewMetadata); } else if (viewConfig.openType == 'window') { me.addWindow(viewConfig, viewMetadata); } }, setMainContent: function (viewConfig, viewMetadata) { if (viewConfig.title) { document.title = viewConfig.title; } var me = this, viewport = me.getView(); viewport.removeAll(); viewport.add(Ext.apply(viewMetadata, { xtype: 'dynamicform', viewId: viewConfig.viewId, formId: viewConfig.viewName, height: window.innerHeight })); me.dynamicViews[viewConfig.viewId] = viewport; }, addCard: function (viewConfig, viewMetadata) { var me = this, mainTabPanel = me.getView().down('tabpanel'); var card = mainTabPanel.insert(mainTabPanel.items.length + 1, { iconCls: viewMetadata.iconCls, title: viewConfig.title, closable: viewConfig.closable, items: [Ext.apply(viewMetadata, { xtype: 'dynamicform', viewId: viewConfig.viewId, formId: viewConfig.viewName })] }); mainTabPanel.setActiveTab(card); me.dynamicViews[viewConfig.viewId] = card; }, addFloating: function (trigger, viewConfig, viewMetadata) { var me = this, cacheId = viewConfig.viewName + "_" + viewConfig.viewType, panel = trigger[cacheId]; if (panel) { if (!panel.isExpanded) { panel.expand(); } else { panel.collapse(); } } else { panel = Ext.create('uas.panel.Floating', { scope: trigger, items: [Ext.apply(viewMetadata, { xtype: 'dynamicform', viewId: viewConfig.viewId, formId: viewConfig.viewName })] }); panel.expand(); trigger[cacheId] = panel; me.dynamicViews[viewConfig.viewId] = panel; } }, /** * 打开窗口 * * @param {*} viewConfig * @param {*} viewMetadata */ addWindow: function (viewConfig, viewMetadata) { var win = Ext.create('Ext.window.Window', { autoShow: true, closeAction: 'destroy', width: viewConfig.width || '60%', height: viewConfig.height || '80%', renderTo: Ext.getBody(), title: viewConfig.title, ui: 'form', scrollable: true, layout: 'fit', items: [Ext.apply(viewMetadata, { xtype: 'dynamicform', viewId: viewConfig.viewId, formId: viewConfig.viewName })] }); this.dynamicViews[viewConfig.viewId] = win; }, close: function (trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { view.close(); } }, clearState: function (trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { view.down('dynamicform').clearState(); } }, bindData: function(trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { var vm = view.down('dynamicform').getViewModel(), key = args[0], value = args[1]; vm.set(key, value); } }, updateHeadData: function(trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { var vm = view.down('dynamicform').getViewModel(), headName = args[0], headData = args[1]; data = vm.get(headName) || {}; data = Ext.Object.merge(data, headData); // 服务端推送的字段数据,无需标记dirty Ext.Object.each(headData, function(field, value){ var item = view.down('#' + headName + "_" + field); if (item) { item.originalValue = value; } }); vm.set(headName, data); } }, setStoreData: function(trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { var vm = view.down('dynamicform').getViewModel(), storeId = args[0], store = vm.get(storeId), data = args[1] || []; if (!store) { store = new Ext.data.Store(); vm.set(storeId, store); } store.loadData(data); } }, addStoreData: function(trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { var vm = view.down('dynamicform').getViewModel(), storeId = args[0], store = vm.get(storeId), data = args[1] || {}; if (!store) { store = new Ext.data.Store(); vm.set(storeId, store); } store.add(data); } }, insertStoreData: function(trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { var vm = view.down('dynamicform').getViewModel(), storeId = args[0], store = vm.get(storeId), rowIndex = args[1], data = args[2] || {}; if (!store) { store = new Ext.data.Store(); vm.set(storeId, store); } store.add(rowIndex, data); } }, updateStoreData: function(trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { var vm = view.down('dynamicform').getViewModel(), storeId = args[0], store = vm.get(storeId), rowIndex = args[1], data = args[2]; if (store) { var record = store.getAt(rowIndex); if (record && data) { Ext.Object.each(data, function(k, v){ record.set(k, v); }); } } } }, removeStoreData: function(trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { var vm = view.down('dynamicform').getViewModel(), storeId = args[0], store = vm.get(storeId), rowIndex = args[1]; if (store) { store.removeAt(rowIndex); } } }, setListSchemes: function(trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { view.down('gridpanel').setSchemes(args[0]); } }, setListColumns: function(trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { view.down('gridpanel').reconfigure(args[0]); } }, setListData: function(trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { var data = args[0], page = args[1], grid = view.down('gridpanel'), store = grid.getStore(); if (page) { store.totalCount = page.totalCount; store.pageSize = page.pageSize; store.currentPage = page.currentPage; } store.loadData(data); } }, showToast: function (trigger, args, viewId) { Ext.toast({ html: args[0], closable: false, align: 't', slideDUration: 400, autoCloseDelay: 5000, autoClose: true, maxWidth: 400 }); }, updateState: function(trigger, args, viewId) { var me = this, view = me.dynamicViews[viewId]; if (view) { var stateMap = args[0]; Ext.Object.each(stateMap, function(itemId, states){ var item = view.down('#' + itemId); if (item) { Ext.Object.each(states, function(prop, val){ if (prop == 'disabled') { item.setDisabled && item.setDisabled(val); } else if (prop == 'editable') { item.setEditable && item.setEditable(val); } else if (prop == 'hidden') { item.hidden && item.hidden(val); } else if (prop == 'required') { item.setRequired && item.setRequired(val); } else if (prop == 'value') { item.setValue && item.setValue(val); } else if (prop == 'options') { // 下拉框store item.setOptions && item.setOptions(val); } }); } }); } }, setActive: function(trigger, args, viewId) { var me = this, mainTabPanel = me.getView().down('tabpanel'), view = me.dynamicViews[viewId]; mainTabPanel.setActiveTab(view); }, /** * 查找并执行动态服务 * * @param {触发动作的组件} trigger */ handleEvent: function (trigger, event, args) { var me = this, view = (trigger.xtype == 'dynamicform' ? trigger : trigger.up('dynamicform')), viewId = view.viewId; if (Ext.isArray(trigger.actions)) { trigger.actions.forEach(action => { me.invokeAction(trigger, action); }); } else { view.mask('请稍等...'); Ext.Ajax.payload({ url: '/api/web/event', headers: me.getRequestHeader(), params: { viewId: viewId, itemId: trigger.itemId, event: event, args: args } }).then(function (res) { var actions = res.data.actions; if (actions) { actions.forEach(action => { me.invokeAction(trigger, action); }); } }).catch(function (e) { console.error(e); me.showToast(trigger, [(e ? e.message : null) || '出现错误']); }).finally(function () { view.isMasked() && view.unmask(); }); } }, onViewInitEvent: function (form) { this.handleEvent(form, 'initialize'); }, onTabChangeEvent: function (tab) { var me = this, card = tab.card; if (card.eventArgs && !card.items.length) { // tab activate 1th me.handleEvent(card, 'tabInit', card.eventArgs); } }, onButtonClickEvent: function (btn) { var me = this, operation = btn.operation; if (operation) { var data = btn.up('dynamicform').getViewModel().getData(); me.handleEvent(btn, 'click', [operation, data]); } }, onMenuItemClickEvent: function (item) { var me = this, operation = item.operation; if (operation) { var view = item.up('dynamicform'); if (item.valid && !view.isValid()) { view.showError(); return; } me.handleEvent(item, 'menuItemClick', [operation, view.getValues(true)]); } }, onListItemClickEvent: function (view, record) { var me = this; me.handleEvent(view, 'itemClick', [view.getItemValue(record)]); }, onFieldChangeEvent: function (field) { if (field.fireChangeEvent) { var args; if (field.bind) { args = field.bind.value.stub.path.split("."); } else { args = [field.ownerCt.grid.entity, field.name]; } args.push(field.getValue()); this.handleEvent(field, 'change', args); } }, onFieldSearchEvent: function (field) { var args; if (field.bind) { args = field.bind.value.stub.path.split("."); } else { args = [field.ownerCt.grid.entity, field.name]; } args.push(field.getValue()); // 点击搜索基础资料列表 this.handleEvent(field, 'fieldSearch', args); }, onFieldLabelClickEvent: function (field) { var args; if (field.bind) { args = field.bind.value.stub.path.split("."); } else { args = [field.ownerCt.grid.entity, field.name]; } args.push(field.getValue()); // 点击label查看基础资料列表/表单 this.handleEvent(field, 'fieldView', args); }, onGridSelectionChangeEvent: function (selModel, selected) { var grid = selModel.view.ownerCt, lastSelectedIndex = null, selectedIndex = []; if (selected.length) { lastSelectedIndex = selModel.view.store.indexOf(selModel.lastSelected); selected.forEach(function (select) { selectedIndex.push(selModel.view.store.indexOf(select)); }) } this.handleEvent(grid, 'selectionChange', [grid.entity, lastSelectedIndex, selectedIndex]); }, onPagingEvent: function (grid, pageParam) { this.handleEvent(grid, 'paging', [grid.entity, pageParam]); }, onSchemeChangeEvent: function (grid, selectedIndex) { this.handleEvent(grid, 'schemeChange', [grid.entity, selectedIndex]); }, onGridCellClickEvent: function(grid, cell, cellIndex, record, row, rowIndex, e) { var me = this, column = e.position.column, rowIdx = e.position.rowIdx, colIdx = e.position.colIdx; if (column.enableCellEvent) { me.handleEvent(grid, 'cellClick', [grid.entity, column.dataIndex, rowIdx, colIdx]); } }, onGridItemDbClickEvent: function(grid, record, row, index) { this.handleEvent(grid, 'itemDbClick', [grid.entity, index]); } });