UNPKG

@openui5/sap.m

Version:

OpenUI5 UI Library sap.m

1,230 lines (1,096 loc) 40.7 kB
/*! * OpenUI5 * (c) Copyright 2009-2023 SAP SE or an SAP affiliate company. * Licensed under the Apache License, Version 2.0 - see LICENSE.txt. */ // Provides control sap.m.P13nDimMeasurePanel. sap.ui.define([ './library', './P13nPanel', './P13nDimMeasureItem', './SearchField', './Table', './Column', './ColumnListItem', './ScrollContainer', './Text', './Select', './ComboBox', './Button', './OverflowToolbar', './OverflowToolbarLayoutData', './OverflowToolbarButton', './ToolbarSpacer', 'sap/ui/core/library', 'sap/ui/model/ChangeReason', 'sap/ui/model/json/JSONModel', 'sap/ui/model/BindingMode', 'sap/ui/core/ResizeHandler', 'sap/ui/core/Item', 'sap/ui/core/InvisibleText', 'sap/ui/core/IconPool', "sap/ui/thirdparty/jquery", "sap/ui/core/Configuration" ], function( library, P13nPanel, P13nDimMeasureItem, SearchField, Table, Column, ColumnListItem, ScrollContainer, Text, Select, ComboBox, Button, OverflowToolbar, OverflowToolbarLayoutData, OverflowToolbarButton, ToolbarSpacer, CoreLibrary, ChangeReason, JSONModel, BindingMode, ResizeHandler, Item, InvisibleText, IconPool, jQuery, Configuration ) { "use strict"; // shortcut for sap.m.OverflowToolbarPriority var OverflowToolbarPriority = library.OverflowToolbarPriority; // shortcut for sap.m.ButtonType var ButtonType = library.ButtonType; // shortcut for sap.m.ToolbarDesign var ToolbarDesign = library.ToolbarDesign; // shortcut for sap.m.ListType var ListType = library.ListType; // shortcut for sap.m.ListMode var ListMode = library.ListMode; // shortcut for sap.m.P13nPanelType var P13nPanelType = library.P13nPanelType; /** * Constructor for a new P13nDimMeasurePanel. * * @param {string} [sId] id for the new control, generated automatically if no id is given * @param {object} [mSettings] initial settings for the new control * @class The P13nDimMeasurePanel control is used to define chart-specific settings like chart type, the visibility, the order and roles of * dimensions and measures for table personalization. * @extends sap.m.P13nPanel * @author SAP SE * @version 1.117.4 * @constructor * @public * @since 1.34.0 * @alias sap.m.P13nDimMeasurePanel */ var P13nDimMeasurePanel = P13nPanel.extend("sap.m.P13nDimMeasurePanel", /** @lends sap.m.P13nDimMeasurePanel.prototype */ { metadata: { library: "sap.m", properties: { /** * Specifies a chart type key. */ chartTypeKey: { type: "string", defaultValue: "" } }, aggregations: { /** * List of columns that has been changed. */ dimMeasureItems: { type: "sap.m.P13nDimMeasureItem", multiple: true, singularName: "dimMeasureItem", bindable: "bindable" }, /** * Internal aggregation for the toolbar content. */ content: { type: "sap.ui.core.Control", multiple: true, singularName: "content", visibility: "hidden" }, /** * Specifies available chart types. */ availableChartTypes: { type: "sap.ui.core.Item", multiple: true, singularName: "availableChartType" } }, events: { // TODO /** * Event raised when one or more <code>DimMeasureItems</code> has been updated. * Aggregation <code>DimMeasureItems</code> should be updated outside... * @since 1.50.0 */ changeDimMeasureItems: {}, /** * Event raised when a <code>ChartType</code> has been updated. * @since 1.50.0 */ changeChartType: {} } }, renderer: { apiVersion: 2, render: function(oRm, oControl){ oRm.openStart("div", oControl); oRm.class("sapMP13nColumnsPanel"); oRm.openEnd(); oControl.getAggregation("content").forEach(function(oChildren){ oRm.renderControl(oChildren); }); oRm.close("div"); } } }); P13nDimMeasurePanel.prototype.init = function() { // The panel is using internal JSON model which is bound to internal sap.m.Table. // When a table item is selected it reflects in the JSON model. When a table item is moved, // we bring the JSON items in the right order and it reflects in the sap.m.Table. // The JSON model is filled based on 'items' aggregation and is updated afterwards // with information like selection and position of an item based on 'dimMeasureItems' aggregation // (the information is taken from the model of aggregation binding. See _updateInternalModel() for more details). // // This update should be done: // * before the panel is rendered first time (onBeforeRendering) - with item sorting // // * after the 'dimMeasureItems' or 'items' aggregation has been changed (via API e.g. addDimMeasureItem or via binding e.g. updateDimMeasureItem) - with item sorting // Note: the JSON model should not be updated during the 'changeDimMeasureItems' event is fired. // // * before getOKPayload is called. getOKPayload is called when the user opens the dialog were other panel is // initially visible and P13nDimMeasurePanel has not yet rendered. For validation the JSON model should be updated - with item sorting // // General note: it is not supposed that control keeps the 'dimMeasureItems' aggregation up-to-date. // * The usual SAPUI5 wide approach is that the control fires an event (here 'changeDimMeasureItems') // and the consumer has to update the model data of the aggregation binding. This is the case where user's interaction, // like set selection or move items, ends up in model data. // * The case where the consumer pushes changes into model data, like e.g. Restore, is done also via binding update. var that = this; this._iLiveChangeTimer = 0; this._iSearchTimer = 0; this._bIgnoreUpdateInternalModel = false; this._bUpdateInternalModel = true; this._bOnAfterRenderingFirstTimeExecuted = false; var oRb = sap.ui.getCore().getLibraryResourceBundle("sap.m"); this.oAvailableRoleTypes = { Dimension: [ { key: "category", text: oRb.getText('COLUMNSPANEL_CHARTROLE_CATEGORY') }, { key: "category2", text: oRb.getText('COLUMNSPANEL_CHARTROLE_CATEGORY2') }, { key: "series", text: oRb.getText('COLUMNSPANEL_CHARTROLE_SERIES') } ], Measure: [ { key: "axis1", text: oRb.getText('COLUMNSPANEL_CHARTROLE_AXIS1') }, { key: "axis2", text: oRb.getText('COLUMNSPANEL_CHARTROLE_AXIS2') }, { key: "axis3", text: oRb.getText('COLUMNSPANEL_CHARTROLE_AXIS3') }, { key: "axis4", text: oRb.getText('COLUMNSPANEL_CHARTROLE_AXIS4') } ] }; var oModel = new JSONModel({ availableChartTypes: [], selectedChartTypeKey: null, items: [], columnKeyOfMarkedItem: undefined, isMoveDownButtonEnabled: undefined, isMoveUpButtonEnabled: undefined, showOnlySelectedItems: undefined, countOfSelectedItems: 0, countOfItems: 0 }); oModel.setDefaultBindingMode(BindingMode.TwoWay); oModel.setSizeLimit(1000); this.setModel(oModel, "$sapmP13nDimMeasurePanel"); this.setType(P13nPanelType.dimeasure); this.setTitle(oRb.getText("CHARTPANEL_TITLE")); this._createTable(); this._createToolbar(); this.setVerticalScrolling(false); var oScrollContainer = new ScrollContainer({ horizontal: false, vertical: true, content: [ this._oTable ], width: '100%', height: '100%' }); this.addAggregation("content", oScrollContainer); // Call-back for handling of resizing // TODO: make sure we optimize calculation and respect margins and borders, use e.g. // jQuery.outerHeight(true) this._fnHandleResize = function() { var bChangeResult = false, iScrollContainerHeightOld, iScrollContainerHeightNew; if (that.getParent) { var $dialogCont = null, iContentHeight, iHeaderHeight; var oParent = that.getParent(); var oToolbar = that._getToolbar(); if (oParent && oParent.$) { $dialogCont = oParent.$("cont"); if ($dialogCont.children().length > 0 && oToolbar.$().length > 0) { iScrollContainerHeightOld = oScrollContainer.$()[0].clientHeight; iContentHeight = $dialogCont.children()[0].clientHeight; iHeaderHeight = oToolbar ? oToolbar.$()[0].clientHeight : 0; iScrollContainerHeightNew = iContentHeight - iHeaderHeight; if (iScrollContainerHeightOld !== iScrollContainerHeightNew) { oScrollContainer.setHeight(iScrollContainerHeightNew + 'px'); bChangeResult = true; } } } } return bChangeResult; }; this._sContainerResizeListener = ResizeHandler.register(oScrollContainer, this._fnHandleResize); }; P13nDimMeasurePanel.prototype.onBeforeRendering = function() { this._updateInternalModel(); // Set marked item initially to the first table item if (!this._getInternalModel().getProperty("/columnKeyOfMarkedItem")) { this._setColumnKeyOfMarkedItem(this._getColumnKeyByTableItem(this._getVisibleTableItems()[0])); } // After each re-render the 'markedTableItem' is re-created. So we have to set the new table item as marked. this._switchMarkedTableItemTo(this._getTableItemByColumnKey(this._getInternalModel().getProperty("/columnKeyOfMarkedItem"))); this._updateControlLogic(); }; P13nDimMeasurePanel.prototype.onAfterRendering = function() { var that = this; // adapt scroll-container very first time to the right size of the browser if (!this._bOnAfterRenderingFirstTimeExecuted) { this._bOnAfterRenderingFirstTimeExecuted = true; window.clearTimeout(this._iLiveChangeTimer); this._iLiveChangeTimer = window.setTimeout(function() { that._fnHandleResize(); // following line is needed to get layout of OverflowToolbar rearranged IF it is used in a dialog that._getToolbar()._resetAndInvalidateToolbar(); }, 0); } }; P13nDimMeasurePanel.prototype.getOkPayload = function() { this._updateInternalModel(); // This is very bad practice. As of SAPUI5 directive it is not supposed that control keeps the 'dimMeasureItems' aggregation up-to-date. // The usual SAPUI5 approach is that the control fires an event ('changeDimMeasureItems') and the consumer has to update the model data // of the aggregation binding. This is the case where user's interaction, like set selection or move items, ends up in model data. // But due to backward compatibility we have to keep it. this._getInternalModel().getProperty("/items").forEach(function(oMItem) { if (this._getDimMeasureItemByColumnKey(oMItem.columnKey)) { // Do not update existing dimMeasureItem as it has been just updated in _updateInternalModel method return; } if (!oMItem.persistentSelected) { // Nothing relevant has been changed as item is not selected return; } // Create a new dimMeasureItem if an item have been changed to 'selected' this.addAggregation("dimMeasureItems", new P13nDimMeasureItem({ columnKey: oMItem.columnKey, visible: oMItem.persistentSelected, index: oMItem.persistentIndex === -1 ? undefined : oMItem.persistentIndex, role: oMItem.role })); }, this); return { // We have to return dimMeasureItems as of the fact that new created or deleted dimMeasureItems are not updated in the model via list // binding. dimMeasureItems: this.getDimMeasureItems(), chartTypeKey: this.getChartTypeKey() }; }; P13nDimMeasurePanel.prototype.exit = function() { ResizeHandler.deregister(this._sContainerResizeListener); this._sContainerResizeListener = null; this._getToolbar().destroy(); this._oTable.destroy(); this._oTable = null; // destroy model and its data if (this._getInternalModel()) { this._getInternalModel().destroy(); } if (this.oInvisibleChartTypeText) { this.oInvisibleChartTypeText.destroy(); this.oInvisibleChartTypeText = null; } window.clearTimeout(this._iLiveChangeTimer); window.clearTimeout(this._iSearchTimer); }; P13nDimMeasurePanel.prototype.addItem = function(oItem) { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } this.addAggregation("items", oItem); return this; }; P13nDimMeasurePanel.prototype.insertItem = function(oItem, iIndex) { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } this.insertAggregation("items", oItem, iIndex); return this; }; P13nDimMeasurePanel.prototype.removeItem = function(oItem) { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } oItem = this.removeAggregation("items", oItem); return oItem; }; P13nDimMeasurePanel.prototype.removeAllItems = function() { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } return this.removeAllAggregation("items"); }; P13nDimMeasurePanel.prototype.destroyItems = function() { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } this.destroyAggregation("items"); return this; }; P13nDimMeasurePanel.prototype.addDimMeasureItem = function(oDimMeasureItem) { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } this.addAggregation("dimMeasureItems", oDimMeasureItem); return this; }; P13nDimMeasurePanel.prototype.insertDimMeasureItem = function(oDimMeasureItem, iIndex) { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } this.insertAggregation("dimMeasureItems", oDimMeasureItem, iIndex); return this; }; P13nDimMeasurePanel.prototype.updateDimMeasureItems = function(sReason) { this.updateAggregation("dimMeasureItems"); if (sReason === ChangeReason.Change && !this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } }; P13nDimMeasurePanel.prototype.removeDimMeasureItem = function(oDimMeasureItem) { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } return this.removeAggregation("dimMeasureItems", oDimMeasureItem); }; P13nDimMeasurePanel.prototype.removeAllDimMeasureItems = function() { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } return this.removeAllAggregation("dimMeasureItems"); }; P13nDimMeasurePanel.prototype.destroyDimMeasureItems = function() { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } this.destroyAggregation("dimMeasureItems"); return this; }; P13nDimMeasurePanel.prototype.setChartTypeKey = function(sChartTypeKey) { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } this.setProperty("chartTypeKey", sChartTypeKey); return this; }; P13nDimMeasurePanel.prototype.addAvailableChartType = function(oAvailableChartType) { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } this.addAggregation("availableChartTypes", oAvailableChartType); return this; }; P13nDimMeasurePanel.prototype.insertAvailableChartType = function(oAvailableChartType, iIndex) { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } this.insertAggregation("availableChartTypes", oAvailableChartType, iIndex); return this; }; P13nDimMeasurePanel.prototype.removeAvailableChartType = function(oAvailableChartType) { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } return this.removeAggregation("availableChartTypes", oAvailableChartType); }; P13nDimMeasurePanel.prototype.removeAllAvailableChartType = function() { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } return this.removeAllAggregation("availableChartTypes"); }; P13nDimMeasurePanel.prototype.destroyAvailableChartType = function() { if (!this._bIgnoreUpdateInternalModel) { this._bUpdateInternalModel = true; } this.destroyAggregation("availableChartTypes"); return this; }; P13nDimMeasurePanel.prototype._notifyChange = function() { var fListener = this.getChangeNotifier(); if (fListener) { fListener(this); } }; P13nDimMeasurePanel.prototype._scrollToSelectedItem = function(oItem) { if (!oItem) { return; } sap.ui.getCore().applyChanges(); if (oItem.getDomRef()) { oItem.focus(); } }; // ------------------------------------------------------------------------------------------------- P13nDimMeasurePanel.prototype._getInternalModel = function() { return this.getModel("$sapmP13nDimMeasurePanel"); }; P13nDimMeasurePanel.prototype._createTable = function() { var oRb = sap.ui.getCore().getLibraryResourceBundle("sap.m"); this._oTable = new Table({ mode: ListMode.MultiSelect, rememberSelections: false, itemPress: jQuery.proxy(this._onItemPressed, this), selectionChange: jQuery.proxy(this._onSelectionChange, this), columns: [ new Column({ vAlign: CoreLibrary.VerticalAlign.Middle, header: new Text({ text: { parts: [ { path: '/countOfSelectedItems' }, { path: '/countOfItems' } ], formatter: function(iCountOfSelectedItems, iCountOfItems) { return oRb.getText('COLUMNSPANEL_SELECT_ALL_WITH_COUNTER', [ iCountOfSelectedItems, iCountOfItems ]); } } }) }), new Column({ vAlign: CoreLibrary.VerticalAlign.Middle, header: new Text({ text: oRb.getText('COLUMNSPANEL_COLUMN_TYPE') }) }), new Column({ vAlign: CoreLibrary.VerticalAlign.Middle, header: new Text({ text: oRb.getText('COLUMNSPANEL_COLUMN_ROLE') }) }) ], items: { path: "/items", templateShareable: false, template: new ColumnListItem({ cells: [ new Text({ text: "{text}" }), new Text({ text: { path: '', formatter: function(oMItem) { if (oMItem.aggregationRole === "Dimension") { return oRb.getText('COLUMNSPANEL_TYPE_DIMENSION'); } if (oMItem.aggregationRole === "Measure") { return oRb.getText('COLUMNSPANEL_TYPE_MEASURE'); } } } }), new Select({ selectedKey: "{role}", items: { path: 'availableRoleTypes', // sorter: [ // new sap.ui.model.Sorter("/text", false) // ], factory: function(sId, oBindingContext) { var oAvailableRoleType = oBindingContext.getObject(); return new Item({ key: oAvailableRoleType.key, text: oAvailableRoleType.text }); } }, change: jQuery.proxy(this._onRoleChange, this) }) ], visible: "{visible}", selected: "{persistentSelected}", tooltip: "{tooltip}", type: ListType.Active }) } }); this._oTable.setModel(this._getInternalModel()); }; /** * @private */ P13nDimMeasurePanel.prototype._createToolbar = function() { var that = this; var oRb = sap.ui.getCore().getLibraryResourceBundle("sap.m"); var oInvisibleChartTypeText = new InvisibleText({ text: oRb.getText('COLUMNSPANEL_CHARTTYPE') }); // set a reference on the instance so it can be later destroyed this.oInvisibleChartTypeText = oInvisibleChartTypeText; var oChartTypeComboBox = new ComboBox({ placeholder: oInvisibleChartTypeText.getText(), selectedKey: { path: '/selectedChartTypeKey' }, ariaLabelledBy: oInvisibleChartTypeText, items: { path: '/availableChartTypes', templateShareable: false, template: new Item({ key: "{key}", text: "{text}" }) }, selectionChange: jQuery.proxy(this._onChartTypeChange, this), layoutData: new OverflowToolbarLayoutData({ priority: OverflowToolbarPriority.NeverOverflow }) }); var oToolbar = new OverflowToolbar(this.getId() + "-toolbar", { design: ToolbarDesign.Auto, content: [ oInvisibleChartTypeText, oChartTypeComboBox, new ToolbarSpacer(), new SearchField(this.getId() + "-searchField", { liveChange: function(oEvent) { var sValue = oEvent.getSource().getValue(), iDelay = (sValue ? 300 : 0); // no delay if value is empty // execute search after user stops typing for 300ms window.clearTimeout(that._iSearchTimer); if (iDelay) { that._iSearchTimer = window.setTimeout(function() { that._onExecuteSearch(); }, iDelay); } else { that._onExecuteSearch(); } }, // execute the standard search search: jQuery.proxy(this._onExecuteSearch, this), layoutData: new OverflowToolbarLayoutData({ minWidth: "12.5rem", maxWidth: "23.077rem", shrinkable: true, priority: OverflowToolbarPriority.NeverOverflow }) }), new Button({ text: { path: '/showOnlySelectedItems', formatter: function(bShowOnlySelectedItems) { return bShowOnlySelectedItems ? oRb.getText('COLUMNSPANEL_SHOW_ALL') : oRb.getText('COLUMNSPANEL_SHOW_SELECTED'); } }, tooltip: { path: '/showOnlySelectedItems', formatter: function(bShowOnlySelectedItems) { return bShowOnlySelectedItems ? oRb.getText('COLUMNSPANEL_SHOW_ALL') : oRb.getText('COLUMNSPANEL_SHOW_SELECTED'); } }, type: ButtonType.Transparent, press: jQuery.proxy(this._onSwitchButtonShowSelected, this), layoutData: new OverflowToolbarLayoutData({ priority: OverflowToolbarPriority.High }) }), new OverflowToolbarButton({ icon: IconPool.getIconURI("collapse-group"), text: oRb.getText('COLUMNSPANEL_MOVE_TO_TOP'), tooltip: oRb.getText('COLUMNSPANEL_MOVE_TO_TOP'), type: ButtonType.Transparent, enabled: { path: '/isMoveUpButtonEnabled' }, press: jQuery.proxy(this.onPressButtonMoveToTop, this), layoutData: new OverflowToolbarLayoutData({ priority: OverflowToolbarPriority.Low, group: 2 }) }), new OverflowToolbarButton({ icon: IconPool.getIconURI("navigation-up-arrow"), text: oRb.getText('COLUMNSPANEL_MOVE_UP'), tooltip: oRb.getText('COLUMNSPANEL_MOVE_UP'), type: ButtonType.Transparent, enabled: { path: '/isMoveUpButtonEnabled' }, press: jQuery.proxy(this.onPressButtonMoveUp, this), layoutData: new OverflowToolbarLayoutData({ priority: OverflowToolbarPriority.High, group: 1 }) }), new OverflowToolbarButton({ icon: IconPool.getIconURI("navigation-down-arrow"), text: oRb.getText('COLUMNSPANEL_MOVE_DOWN'), tooltip: oRb.getText('COLUMNSPANEL_MOVE_DOWN'), type: ButtonType.Transparent, enabled: { path: '/isMoveDownButtonEnabled' }, press: jQuery.proxy(this.onPressButtonMoveDown, this), layoutData: new OverflowToolbarLayoutData({ priority: OverflowToolbarPriority.High, group: 1 }) }), new OverflowToolbarButton({ icon: IconPool.getIconURI("expand-group"), text: oRb.getText('COLUMNSPANEL_MOVE_TO_BOTTOM'), tooltip: oRb.getText('COLUMNSPANEL_MOVE_TO_BOTTOM'), type: ButtonType.Transparent, enabled: { path: '/isMoveDownButtonEnabled' }, press: jQuery.proxy(this.onPressButtonMoveToBottom, this), layoutData: new OverflowToolbarLayoutData({ priority: OverflowToolbarPriority.Low, group: 2 }) }) ] }); oToolbar.setModel(this._getInternalModel()); this.addAggregation("content", oToolbar); }; P13nDimMeasurePanel.prototype.onPressButtonMoveToTop = function() { this._moveMarkedTableItem(this._getMarkedTableItem(), this._getVisibleTableItems()[0]); }; P13nDimMeasurePanel.prototype.onPressButtonMoveUp = function() { var aVisibleTableItems = this._getVisibleTableItems(); this._moveMarkedTableItem(this._getMarkedTableItem(), aVisibleTableItems[aVisibleTableItems.indexOf(this._getMarkedTableItem()) - 1]); }; P13nDimMeasurePanel.prototype.onPressButtonMoveDown = function() { var aVisibleTableItems = this._getVisibleTableItems(); this._moveMarkedTableItem(this._getMarkedTableItem(), aVisibleTableItems[aVisibleTableItems.indexOf(this._getMarkedTableItem()) + 1]); }; P13nDimMeasurePanel.prototype.onPressButtonMoveToBottom = function() { var aVisibleTableItems = this._getVisibleTableItems(); this._moveMarkedTableItem(this._getMarkedTableItem(), aVisibleTableItems[aVisibleTableItems.length - 1]); }; P13nDimMeasurePanel.prototype._onSwitchButtonShowSelected = function() { this._getInternalModel().setProperty("/showOnlySelectedItems", !this._getInternalModel().getProperty("/showOnlySelectedItems")); this._switchVisibilityOfUnselectedModelItems(); this._filterModelItemsBySearchText(); this._scrollToSelectedItem(this._getMarkedTableItem()); this._updateControlLogic(); this._fnHandleResize(); }; P13nDimMeasurePanel.prototype._onExecuteSearch = function() { this._switchVisibilityOfUnselectedModelItems(); this._filterModelItemsBySearchText(); this._updateControlLogic(); }; P13nDimMeasurePanel.prototype._switchVisibilityOfUnselectedModelItems = function() { var bShowOnlySelectedItems = this._isFilteredByShowSelected(); var aMItems = this._getInternalModel().getProperty("/items"); aMItems.forEach(function(oMItem) { if (oMItem.persistentSelected) { oMItem.visible = true; return; } oMItem.visible = !bShowOnlySelectedItems; }); this._getInternalModel().setProperty("/items", aMItems); }; P13nDimMeasurePanel.prototype._getVisibleModelItems = function() { return this._getInternalModel().getProperty("/items").filter(function(oMItem) { return !!oMItem.visible; }); }; P13nDimMeasurePanel.prototype._getVisibleModelItems = function() { return this._getInternalModel().getProperty("/items").filter(function(oMItem) { return !!oMItem.visible; }); }; P13nDimMeasurePanel.prototype._moveMarkedTableItem = function(oTableItemFrom, oTableItemTo) { var oMItemFrom = this._getModelItemByColumnKey(this._getColumnKeyByTableItem(oTableItemFrom)); var oMItemTo = this._getModelItemByColumnKey(this._getColumnKeyByTableItem(oTableItemTo)); var iIndexFrom = this._getModelItemIndexByColumnKey(oMItemFrom.columnKey); var iIndexTo = this._getModelItemIndexByColumnKey(oMItemTo.columnKey); this._moveModelItems(iIndexFrom, iIndexTo); this._scrollToSelectedItem(this._getMarkedTableItem()); this._updateControlLogic(); this._fireChangeDimMeasureItems(); this._notifyChange(); }; /** * Moves model item from <code>iIndexFrom</code> to <code>iIndexTo</code>. * * @param {int} iIndexFrom Model item at this index will be removed. Range: {0, length-1} * @param {int} iIndexTo Model item at this index will be inserted. Range: {0, length-1} * @return {boolean} <code>true</code> if table item has been moved, else <code>false</code> * @private */ P13nDimMeasurePanel.prototype._moveModelItems = function(iIndexFrom, iIndexTo) { var aMItems = this._getInternalModel().getProperty("/items"); if (iIndexFrom < 0 || iIndexTo < 0 || iIndexFrom > aMItems.length - 1 || iIndexTo > aMItems.length - 1) { return false; } // Remove the marking style before table items are updated this._removeStyleOfMarkedTableItem(); // Move items var aModelItems = aMItems.splice(iIndexFrom, 1); aMItems.splice(iIndexTo, 0, aModelItems[0]); // Do not sort after user action as the table should not be sorted once selected items has been rendered // Re-Index the persistentIndex this._updateModelItemsPersistentIndex(aMItems); this._updateCounts(aMItems); this._getInternalModel().setProperty("/items", aMItems); // Set the marking style again after table items are updated this._switchMarkedTableItemTo(this._getMarkedTableItem()); return true; }; P13nDimMeasurePanel.prototype._getModelItemByColumnKey = function(sColumnKey) { var aMItems = this._getInternalModel().getProperty("/items").filter(function(oMItem) { return oMItem.columnKey === sColumnKey; }); return aMItems[0]; }; P13nDimMeasurePanel.prototype._updateCounts = function(aMItems) { var iCountOfItems = 0; var iCountOfSelectedItems = 0; aMItems.forEach(function(oMItem) { iCountOfItems++; if (oMItem.persistentSelected) { iCountOfSelectedItems++; } }); this._getInternalModel().setProperty("/countOfItems", iCountOfItems); this._getInternalModel().setProperty("/countOfSelectedItems", iCountOfSelectedItems); }; P13nDimMeasurePanel.prototype._sortModelItemsByPersistentIndex = function(aModelItems) { // BCP 0020751294 0000593415 2018 var oCollator; var sLanguage = Configuration.getLocale().toString(); try { if (typeof window.Intl !== 'undefined') { oCollator = window.Intl.Collator(sLanguage, { numeric: true }); } } catch (oException) { // this exception can happen if the configured language is not convertible to BCP47 -> getLocale will deliver an exception } // BCP 0020751295 0000514259 2018 aModelItems.forEach(function(oMItem, iIndex) { oMItem.localIndex = iIndex; }); aModelItems.sort(function(a, b) { if (a.persistentSelected === true && (b.persistentSelected === false || b.persistentSelected === undefined)) { return -1; } else if ((a.persistentSelected === false || a.persistentSelected === undefined) && b.persistentSelected === true) { return 1; } else if (a.persistentSelected === true && b.persistentSelected === true) { if (a.persistentIndex > -1 && a.persistentIndex < b.persistentIndex) { return -1; } else if (b.persistentIndex > -1 && a.persistentIndex > b.persistentIndex) { return 1; } else { return a.localIndex - b.localIndex; } } else if ((a.persistentSelected === false || a.persistentSelected === undefined) && (b.persistentSelected === false || b.persistentSelected === undefined)) { return oCollator ? oCollator.compare(a.text, b.text) : a.text.localeCompare(b.text, sLanguage, { numeric: true }); } }); aModelItems.forEach(function(oMItem) { delete oMItem.localIndex; }); }; P13nDimMeasurePanel.prototype._getColumnKeyByTableItem = function(oTableItem) { var iIndex = this._oTable.indexOfItem(oTableItem); if (iIndex < 0) { return null; } return this._oTable.getBinding("items").getContexts(undefined, undefined, undefined, true)[iIndex].getObject().columnKey; }; P13nDimMeasurePanel.prototype._getModelItemIndexByColumnKey = function(sColumnKey) { var iIndex = -1; this._getInternalModel().getData().items.some(function(oMItem, iIndex_) { if (oMItem.columnKey === sColumnKey) { iIndex = iIndex_; return true; } }); return iIndex; }; P13nDimMeasurePanel.prototype._getSelectedModelItems = function() { return this._getInternalModel().getProperty("/items").filter(function(oMItem) { return oMItem.persistentSelected; }); }; P13nDimMeasurePanel.prototype._getVisibleTableItems = function() { return this._oTable.getItems().filter(function(oTableItem) { return oTableItem.getVisible(); }); }; P13nDimMeasurePanel.prototype._getTableItemByColumnKey = function(sColumnKey) { var aContext = this._oTable.getBinding("items").getContexts(); var aTableItems = this._oTable.getItems().filter(function(oTableItem, iIndex) { return aContext[iIndex].getObject().columnKey === sColumnKey; }); return aTableItems[0]; }; P13nDimMeasurePanel.prototype._getToolbar = function() { return sap.ui.getCore().byId(this.getId() + "-toolbar") || null; }; P13nDimMeasurePanel.prototype._getSearchField = function() { return sap.ui.getCore().byId(this.getId() + "-searchField") || null; }; P13nDimMeasurePanel.prototype._getSearchText = function() { var oSearchField = this._getSearchField(); return oSearchField ? oSearchField.getValue() : ""; }; P13nDimMeasurePanel.prototype._isFilteredBySearchText = function() { return !!this._getSearchText().length; }; P13nDimMeasurePanel.prototype._isFilteredByShowSelected = function() { return this._getInternalModel().getData().showOnlySelectedItems; }; P13nDimMeasurePanel.prototype._updateControlLogic = function() { var bIsSearchActive = this._isFilteredBySearchText(); var bShowOnlySelectedItems = this._isFilteredByShowSelected(); var aVisibleTableItems = this._getVisibleTableItems(); // Value in search field has been changed... this._getInternalModel().setProperty("/isMoveUpButtonEnabled", aVisibleTableItems.indexOf(this._getMarkedTableItem()) > 0); this._getInternalModel().setProperty("/isMoveDownButtonEnabled", aVisibleTableItems.indexOf(this._getMarkedTableItem()) > -1 && aVisibleTableItems.indexOf(this._getMarkedTableItem()) < aVisibleTableItems.length - 1); // Switch off the "Select all (n/m)" checkbox if search var oTableCB = sap.ui.getCore().byId(this._oTable.getId() + '-sa'); if (oTableCB) { oTableCB.setEnabled(!bIsSearchActive && !bShowOnlySelectedItems); } }; P13nDimMeasurePanel.prototype._updateModelItemsPersistentIndex = function(aMItems) { var iPersistentIndex = -1; aMItems.forEach(function(oMItem) { oMItem.persistentIndex = -1; if (oMItem.persistentSelected) { iPersistentIndex++; oMItem.persistentIndex = iPersistentIndex; } }); }; P13nDimMeasurePanel.prototype._fireChangeDimMeasureItems = function() { this._bIgnoreUpdateInternalModel = true; // var aMItems = this._getInternalModel().getProperty("/items"); // aMItems.forEach(function(oMItem) { // var oDimMeasureItem = this._getDimMeasureItemByColumnKey(oMItem.columnKey); // if (oDimMeasureItem) { // oDimMeasureItem.setVisible(oMItem.persistentSelected); // oDimMeasureItem.setIndex(oMItem.persistentIndex === -1 ? undefined : oMItem.persistentIndex); // if (oMItem.role !== undefined) { // oDimMeasureItem.setRole(oMItem.role); // } // } // }, this); this.fireChangeDimMeasureItems({ items: this._getInternalModel().getProperty("/items").map(function(oMItem) { return { columnKey: oMItem.columnKey, visible: oMItem.persistentSelected, index: oMItem.persistentIndex === -1 ? undefined : oMItem.persistentIndex, role: oMItem.role }; }) }); this._bIgnoreUpdateInternalModel = false; }; P13nDimMeasurePanel.prototype._fireChangeChartType = function() { this._bIgnoreUpdateInternalModel = true; this.fireChangeChartType({ chartTypeKey: this._getInternalModel().getProperty("/selectedChartTypeKey") }); this._bIgnoreUpdateInternalModel = false; }; P13nDimMeasurePanel.prototype._getDimMeasureItemByColumnKey = function(sColumnKey) { var aDimMeasureItems = this.getDimMeasureItems().filter(function(oDimMeasureItem) { return oDimMeasureItem.getColumnKey() === sColumnKey; }); return aDimMeasureItems[0]; }; P13nDimMeasurePanel.prototype._getMarkedTableItem = function() { return this._getTableItemByColumnKey(this._getInternalModel().getProperty("/columnKeyOfMarkedItem")); }; P13nDimMeasurePanel.prototype._setColumnKeyOfMarkedItem = function(sColumnKey) { this._getInternalModel().setProperty("/columnKeyOfMarkedItem", sColumnKey); }; P13nDimMeasurePanel.prototype._onItemPressed = function(oEvent) { this._switchMarkedTableItemTo(oEvent.getParameter('listItem')); this._updateControlLogic(); }; P13nDimMeasurePanel.prototype._onChartTypeChange = function(oEvent) { this._fireChangeChartType(); this._notifyChange(); }; P13nDimMeasurePanel.prototype._onRoleChange = function(oEvent) { this._fireChangeDimMeasureItems(); this._notifyChange(); }; P13nDimMeasurePanel.prototype._onSelectionChange = function(oEvent) { if (!oEvent.getParameter("selectAll") && oEvent.getParameter("listItems").length === 1) { this._switchMarkedTableItemTo(oEvent.getParameter("listItem")); } this._selectTableItem(); }; P13nDimMeasurePanel.prototype._selectTableItem = function() { this._updateControlLogic(); // No update of model items is needed as it is already up-to-date due to binding // Do not sort after user interaction as the table should not be sorted once selected items has been rendered // Re-Index only the persistentIndex after user interaction var aMItems = this._getInternalModel().getProperty("/items"); this._updateModelItemsPersistentIndex(aMItems); this._updateCounts(aMItems); this._getInternalModel().setProperty("/items", aMItems); this._fireChangeDimMeasureItems(); this._notifyChange(); }; P13nDimMeasurePanel.prototype._switchMarkedTableItemTo = function(oTableItem) { this._removeStyleOfMarkedTableItem(); // When filter is set, the table items are reduced so marked table item can disappear. var sColumnKey = this._getColumnKeyByTableItem(oTableItem); if (sColumnKey) { this._setColumnKeyOfMarkedItem(sColumnKey); oTableItem.addStyleClass("sapMP13nColumnsPanelItemSelected"); } }; /** * Remove highlighting from the current marked table item * * @private */ P13nDimMeasurePanel.prototype._removeStyleOfMarkedTableItem = function() { if (this._getMarkedTableItem()) { this._getMarkedTableItem().removeStyleClass("sapMP13nColumnsPanelItemSelected"); } }; /** * @private */ P13nDimMeasurePanel.prototype._filterModelItemsBySearchText = function() { var sSearchText = this._getSearchText(); // Replace white spaces at begin and end of the searchText. Leave white spaces in between. sSearchText = sSearchText.replace(/(^\s+)|(\s+$)/g, ''); // Escape special characters entered by user sSearchText = sSearchText.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&'); // i = ignore case; g = global; m = multiline var oRegExp = new RegExp(sSearchText, 'igm'); if (!oRegExp) { return; } this._getVisibleModelItems().forEach(function(oMItem) { var oItem = this._getTableItemByColumnKey(oMItem.columnKey); var aCells = oItem.getCells(); oMItem.visible = false; // Search in item text if (aCells[0] && aCells[0].getText().match(oRegExp)) { oMItem.visible = true; } // Search in aggregationRole if (aCells[1] && aCells[1].getText().match(oRegExp)) { oMItem.visible = true; } // Search in role if (aCells[2] && aCells[2].getSelectedItem() && aCells[2].getSelectedItem().getText().match(oRegExp)) { oMItem.visible = true; } // Search in tooltip if (oMItem.tooltip && oMItem.tooltip.match(oRegExp)) { oMItem.visible = true; } }, this); this._getInternalModel().refresh(); }; P13nDimMeasurePanel.prototype._updateInternalModel = function() { if (!this._bUpdateInternalModel) { return; } this._bUpdateInternalModel = false; // Remove the marking style before table items are updated this._removeStyleOfMarkedTableItem(); // Items this._getInternalModel().setProperty("/items", this.getItems().map(function(oItem) { return { columnKey: oItem.getColumnKey(), visible: true, text: oItem.getText(), tooltip: oItem.getTooltip(), aggregationRole: oItem.getAggregationRole(), availableRoleTypes: this.oAvailableRoleTypes[oItem.getAggregationRole()], role: oItem.getRole(), // default value persistentIndex: -1, persistentSelected: undefined }; }, this)); // ChartTypeKey this._getInternalModel().setProperty("/selectedChartTypeKey", this.getChartTypeKey()); // AvailableChartType this._getInternalModel().setProperty("/availableChartTypes", this.getAvailableChartTypes().map(function(oAvailableChartType) { return { key: oAvailableChartType.getKey(), text: oAvailableChartType.getText() }; }, this)); // DimMeasureItems this.getDimMeasureItems().forEach(function(oDimMeasureItem) { var oMItem = this._getModelItemByColumnKey(oDimMeasureItem.getColumnKey()); if (!oMItem) { return; } if (oDimMeasureItem.getIndex() !== undefined) { oMItem.persistentIndex = oDimMeasureItem.getIndex(); } if (oDimMeasureItem.getVisible() !== undefined) { oMItem.persistentSelected = oDimMeasureItem.getVisible(); } if (oDimMeasureItem.getRole() !== undefined) { oMItem.role = oDimMeasureItem.getRole(); } }, this); this._switchVisibilityOfUnselectedModelItems(); this._filterModelItemsBySearchText(); var aMItems = this._getInternalModel().getProperty("/items"); // Sort the table items only by persistentIndex this._sortModelItemsByPersistentIndex(aMItems); this._updateCounts(aMItems); this._getInternalModel().setProperty("/items", aMItems); // Set the marking style again after table items are updated this._switchMarkedTableItemTo(this._getMarkedTableItem()); }; return P13nDimMeasurePanel; });