@adaptabletools/adaptable 20.2.0 → 20.2.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (66) hide show
  1. package/base.css +7 -7
  2. package/base.css.map +1 -1
  3. package/index.css +7 -7
  4. package/index.css.map +1 -1
  5. package/package.json +1 -1
  6. package/src/AdaptableOptions/QuickSearchOptions.d.ts +1 -1
  7. package/src/AdaptableOptions/StateOptions.d.ts +60 -15
  8. package/src/AdaptableState/Common/AdaptableColumn.d.ts +4 -0
  9. package/src/AdaptableState/FormatColumnState.d.ts +11 -6
  10. package/src/AdaptableState/LayoutState.d.ts +16 -2
  11. package/src/AdaptableState/QuickSearchState.d.ts +5 -5
  12. package/src/Api/Implementation/ColumnApiImpl.js +4 -2
  13. package/src/Api/Implementation/LayoutHelpers.d.ts +3 -0
  14. package/src/Api/Implementation/LayoutHelpers.js +76 -40
  15. package/src/Api/Implementation/QuickSearchApiImpl.d.ts +2 -2
  16. package/src/Api/Implementation/QuickSearchApiImpl.js +4 -4
  17. package/src/Api/Implementation/StateApiImpl.d.ts +1 -0
  18. package/src/Api/Implementation/StateApiImpl.js +6 -5
  19. package/src/Api/Internal/ColumnInternalApi.d.ts +1 -0
  20. package/src/Api/Internal/ColumnInternalApi.js +5 -0
  21. package/src/Api/Internal/FormatColumnInternalApi.d.ts +1 -1
  22. package/src/Api/Internal/FormatColumnInternalApi.js +8 -8
  23. package/src/Api/QuickSearchApi.d.ts +2 -2
  24. package/src/Api/StateApi.d.ts +9 -0
  25. package/src/Redux/ActionsReducers/QuickSearchRedux.d.ts +4 -4
  26. package/src/Redux/ActionsReducers/QuickSearchRedux.js +7 -7
  27. package/src/Redux/Store/AdaptableReduxLocalStorageEngine.js +14 -18
  28. package/src/Redux/Store/AdaptableStore.d.ts +2 -0
  29. package/src/Redux/Store/AdaptableStore.js +13 -5
  30. package/src/Redux/Store/Interface/IAdaptableStore.d.ts +1 -0
  31. package/src/Redux/Store/Interface/IStorageEngine.d.ts +4 -4
  32. package/src/Redux/Store/buildAdaptableStateFunctionConfig.d.ts +3 -0
  33. package/src/Redux/Store/buildAdaptableStateFunctionConfig.js +9 -0
  34. package/src/Utilities/ExpressionFunctions/observableExpressionFunctions.js +1 -1
  35. package/src/Utilities/Helpers/StyleHelper.d.ts +1 -1
  36. package/src/Utilities/Helpers/StyleHelper.js +11 -0
  37. package/src/Utilities/Services/LicenseService/index.js +1 -1
  38. package/src/Utilities/license/decode.js +1 -1
  39. package/src/View/CalculatedColumn/Wizard/CalculatedColumnExpressionWizardSection.js +1 -3
  40. package/src/View/Components/EntityRulesEditor/index.js +3 -3
  41. package/src/View/Components/ExpressionWizard.js +1 -1
  42. package/src/View/Components/StyleComponent.d.ts +1 -0
  43. package/src/View/Components/StyleComponent.js +2 -1
  44. package/src/View/Export/Wizard/ReportRowsWizardSection.js +1 -1
  45. package/src/View/GridFilter/GridFilterExpressionEditor.js +1 -1
  46. package/src/View/Layout/Wizard/sections/ColumnsSection.js +27 -8
  47. package/src/View/Layout/Wizard/sections/GridFilterSection.js +1 -1
  48. package/src/View/Layout/Wizard/sections/RowGroupingSection.js +4 -4
  49. package/src/View/License/LicenseWatermark.js +1 -1
  50. package/src/View/NamedQuery/Wizard/NamedQueryExpressionWizardSection.js +1 -1
  51. package/src/View/QuickSearch/QuickSearchInput.js +3 -2
  52. package/src/View/QuickSearch/QuickSearchPopup.d.ts +1 -1
  53. package/src/View/QuickSearch/QuickSearchPopup.js +7 -4
  54. package/src/agGrid/AdaptableAgGrid.js +22 -11
  55. package/src/agGrid/AgGridAdapter.js +6 -1
  56. package/src/agGrid/AgGridColumnAdapter.d.ts +1 -0
  57. package/src/agGrid/AgGridColumnAdapter.js +39 -17
  58. package/src/agGrid/AgGridExportAdapter.js +22 -10
  59. package/src/env.js +2 -2
  60. package/src/layout-manager/src/LayoutManagerModel.d.ts +17 -4
  61. package/src/layout-manager/src/index.d.ts +1 -1
  62. package/src/layout-manager/src/index.js +61 -18
  63. package/src/metamodel/adaptable.metamodel.d.ts +43 -16
  64. package/src/metamodel/adaptable.metamodel.js +1 -1
  65. package/src/types.d.ts +2 -2
  66. package/tsconfig.esm.tsbuildinfo +1 -1
@@ -1 +1 @@
1
- import{LicenseDisablePersistence as e,LicenseShowWatermark as a}from"../../../Redux/ActionsReducers/InternalRedux";import{PopupShowAlert as t}from"../../../Redux/ActionsReducers/PopupRedux";import i from"../../ObjectFactory";import s from"lodash/clamp";import{LicenseDocsLink as o}from"../../Constants/DocumentationLinkConstants";import{decode as n,GENERIC_APP_NAME as r}from"../../license/decode";import{shouldLogThankYouMessage as l}from"./shouldLogThankYouMessage";const c="sales@adaptabletools.com",p=10,d=864e5;export var LicenseValidityType;!function(e){e.INVALID_LICENSE="INVALID_LICENSE",e.NO_LICENSE="NO_LICENSE",e.NON_PRODUCTION_VALID="NON_PRODUCTION_VALID",e.NON_PRODUCTION_EXPIRED_IN_SCOPE="NON_PRODUCTION_EXPIRED_IN_SCOPE",e.NON_PRODUCTION_EXPIRED_OUT_OF_SCOPE="NON_PRODUCTION_EXPIRED_OUT_OF_SCOPE",e.COMMERCIAL_VALID="COMMERCIAL_VALID",e.COMMERCIAL_EXPIRED_IN_SCOPE="COMMERCIAL_EXPIRED_IN_SCOPE",e.COMMERCIAL_EXPIRED_OUT_OF_SCOPE="COMMERCIAL_EXPIRED_OUT_OF_SCOPE"}(LicenseValidityType||(LicenseValidityType={}));const h=()=>"undefined"!=typeof window?window.location.origin:"",E=()=>{const e=h(),[a,t,i]=Array.from(/(https):\/\/\d+\-\d+\-\d+\-(sandpack\.codesandbox\.io)/g.exec(e)||[]);return"https"===t&&"sandpack.codesandbox.io"===i},I=()=>{const e=h(),[a,t,i]=Array.from(/(https):\/\/\S+(\.csb\.app)/g.exec(e)||[]);return"https"===t&&".csb.app"===i},_=()=>{const e=h(),[a,t,i]=Array.from(/(https):\/\/\S+(\.adaptabletools\.com)/g.exec(e)||[]);return"https"===t&&".adaptabletools.com"===i};export class LicenseService{constructor(e,a,t){this.adaptable=e,this.licenseKey=a,this.packageDetails=t,this.adaptable=e,this.adaptable.api.eventApi.on("AdaptableReady",(()=>{requestAnimationFrame((()=>{this.adaptable.isDestroyed||this.init()}))}))}init(){let e=null;if(this.licenseKey)try{e=n(this.licenseKey)}catch(a){e=a}E()||I()||_()||this.handleLicenseValidation(e,this.getValidityType(e,this.packageDetails))}getValidityType(e,a){if(!e)return LicenseValidityType.NO_LICENSE;if(e instanceof Error)return LicenseValidityType.INVALID_LICENSE;const t=new Date(a.publishedAt),i=new Date(e.end),s=i<new Date,o=e.trial;let n=null;return n=s?i>t?o?LicenseValidityType.NON_PRODUCTION_EXPIRED_IN_SCOPE:LicenseValidityType.COMMERCIAL_EXPIRED_IN_SCOPE:o?LicenseValidityType.NON_PRODUCTION_EXPIRED_OUT_OF_SCOPE:LicenseValidityType.COMMERCIAL_EXPIRED_OUT_OF_SCOPE:o?LicenseValidityType.NON_PRODUCTION_VALID:LicenseValidityType.COMMERCIAL_VALID,n}handleLicenseValidation(e,a){const t=new Date;t.setHours(0,0,0,0);let i=0;e instanceof Error||!e?.end||(i=Math.floor((e?.end?.getTime()-t.getTime())/d),i=s(i,0,1/0));let n="",h="";!e||e instanceof Error||!e.appName||e.appName==r||(n=e.appName,h=" for application [APP_NAME]");const E=(e,a=o,t=c,s=i,r=n)=>e.replace("[LINK]",a).replace("[EMAIL]",t).replace("[APP_NAME]",r).replace("[DAYS]",`${s}`);switch(a){case"NO_LICENSE":case"NON_PRODUCTION_EXPIRED_OUT_OF_SCOPE":this.adaptable.logger.consoleLogByMessageType(E("This instance of AdapTable does not have a license, and some functionality has therefore been removed. In order to use a fully-featured version of AdapTable, please contact [EMAIL]. You can learn more about the different AdapTable license options at [LINK]."),"Error"),this.showNotification("No AdapTable License found."),this.showWatermark("This instance of AdapTable does not have a license, and some functionality has therefore been removed."),this.disableStatePersistence();break;case"INVALID_LICENSE":this.adaptable.logger.consoleLogByMessageType(E("This instance of AdapTable seems to use a corrupted License, and some functionality has therefore been removed. In order to use a fully-featured version of AdapTable, please contact [EMAIL]. You can learn more about the different AdapTable license options at [LINK]."),"Error"),this.showNotification("Corrupted AdapTable License found."),this.showWatermark("This instance of AdapTable has a corrupted License, and some functionality has therefore been removed."),this.disableStatePersistence();break;case"NON_PRODUCTION_VALID":this.adaptable.logger.consoleLogByMessageType(E("This AdapTable trial license expires in [DAYS] days. Please contact [EMAIL] to upgrade to a commercial version of AdapTable. You can learn more about the different AdapTable license options at [LINK]."),"Info");break;case"NON_PRODUCTION_EXPIRED_IN_SCOPE":this.adaptable.logger.consoleLogByMessageType(E("This AdapTable trial license has now expired. Please contact [EMAIL] to upgrade to a commercial version of AdapTable. You can learn more about the different AdapTable license options at [LINK]."),"Warning"),this.showWatermark("AdapTable License has expired");break;case"COMMERCIAL_VALID":if(i<=p)this.adaptable.logger.consoleLogByMessageType(E(`This AdapTable license${h} expires in [DAYS] days. Please contact [EMAIL] to renew (giving you access to Support and Updates)`),"Info");else try{l()&&this.adaptable.logger.consoleLogByMessageType(E(`Thank you for using a valid AdapTable license${h}. Your license will expire in [DAYS] days.`),"Info")}catch(e){}break;case"COMMERCIAL_EXPIRED_IN_SCOPE":this.adaptable.logger.consoleLogByMessageType(E(`This AdapTable license${h} has expired. Please contact [EMAIL] if you wish to renew (giving you access to Support and Updates)`),"Warning");break;case"COMMERCIAL_EXPIRED_OUT_OF_SCOPE":this.adaptable.logger.consoleLogByMessageType(E(`This AdapTable license${h} has expired. Adaptable version was published after the license expired. Please contact [EMAIL] if you wish to renew your license.`),"Error"),this.showNotification("Adaptable License has expired"),this.showWatermark("Adaptable License has expired")}}showNotification(e){this.adaptable.api.internalApi.dispatchReduxAction(t({alertType:"generic",header:"License Error",message:e,alertDefinition:i.CreateInternalAlertDefinitionForMessages("Error")}))}showWatermark(e){this.adaptable.api.internalApi.dispatchReduxAction(a(e))}disableStatePersistence(){this.adaptable.api.internalApi.dispatchReduxAction(e())}destroy(){}}
1
+ import{LicenseDisablePersistence as e,LicenseShowWatermark as a}from"../../../Redux/ActionsReducers/InternalRedux";import{PopupShowAlert as t}from"../../../Redux/ActionsReducers/PopupRedux";import i from"../../ObjectFactory";import s from"lodash/clamp";import{LicenseDocsLink as o}from"../../Constants/DocumentationLinkConstants";import{decode as n,GENERIC_APP_NAME as r}from"../../license/decode";import{shouldLogThankYouMessage as l}from"./shouldLogThankYouMessage";const c="sales@adaptabletools.com",p=10,d=864e5;export var LicenseValidityType;!function(e){e.INVALID_LICENSE="INVALID_LICENSE",e.NO_LICENSE="NO_LICENSE",e.NON_PRODUCTION_VALID="NON_PRODUCTION_VALID",e.NON_PRODUCTION_EXPIRED_IN_SCOPE="NON_PRODUCTION_EXPIRED_IN_SCOPE",e.NON_PRODUCTION_EXPIRED_OUT_OF_SCOPE="NON_PRODUCTION_EXPIRED_OUT_OF_SCOPE",e.COMMERCIAL_VALID="COMMERCIAL_VALID",e.COMMERCIAL_EXPIRED_IN_SCOPE="COMMERCIAL_EXPIRED_IN_SCOPE",e.COMMERCIAL_EXPIRED_OUT_OF_SCOPE="COMMERCIAL_EXPIRED_OUT_OF_SCOPE"}(LicenseValidityType||(LicenseValidityType={}));const h=()=>"undefined"!=typeof window?window.location.origin:"",E=()=>{const e=h(),[a,t,i]=Array.from(/(https):\/\/\d+\-\d+\-\d+\-(sandpack\.codesandbox\.io)/g.exec(e)||[]);return"https"===t&&"sandpack.codesandbox.io"===i},I=()=>{const e=h(),[a,t,i]=Array.from(/(https):\/\/\S+(\.csb\.app)/g.exec(e)||[]);return"https"===t&&".csb.app"===i},_=()=>{const e=h(),[a,t,i]=Array.from(/(https):\/\/\S+(\.adaptabletools\.com)/g.exec(e)||[]);return"https"===t&&".adaptabletools.com"===i};export class LicenseService{constructor(e,a,t){this.adaptable=e,this.licenseKey=a,this.packageDetails=t,this.adaptable=e,this.adaptable.api.eventApi.on("AdaptableReady",()=>{requestAnimationFrame(()=>{this.adaptable.isDestroyed||this.init()})})}init(){let e=null;if(this.licenseKey)try{e=n(this.licenseKey)}catch(a){e=a}E()||I()||_()||this.handleLicenseValidation(e,this.getValidityType(e,this.packageDetails))}getValidityType(e,a){if(!e)return LicenseValidityType.NO_LICENSE;if(e instanceof Error)return LicenseValidityType.INVALID_LICENSE;const t=new Date(a.publishedAt),i=new Date(e.end),s=i<new Date,o=e.trial;let n=null;return n=s?i>t?o?LicenseValidityType.NON_PRODUCTION_EXPIRED_IN_SCOPE:LicenseValidityType.COMMERCIAL_EXPIRED_IN_SCOPE:o?LicenseValidityType.NON_PRODUCTION_EXPIRED_OUT_OF_SCOPE:LicenseValidityType.COMMERCIAL_EXPIRED_OUT_OF_SCOPE:o?LicenseValidityType.NON_PRODUCTION_VALID:LicenseValidityType.COMMERCIAL_VALID,n}handleLicenseValidation(e,a){const t=new Date;t.setHours(0,0,0,0);let i=0;e instanceof Error||!e?.end||(i=Math.floor((e?.end?.getTime()-t.getTime())/d),i=s(i,0,1/0));let n="",h="";!e||e instanceof Error||!e.appName||e.appName==r||(n=e.appName,h=" for application [APP_NAME]");const E=(e,a=o,t=c,s=i,r=n)=>e.replace("[LINK]",a).replace("[EMAIL]",t).replace("[APP_NAME]",r).replace("[DAYS]",`${s}`);switch(a){case"NO_LICENSE":case"NON_PRODUCTION_EXPIRED_OUT_OF_SCOPE":this.adaptable.logger.consoleLogByMessageType(E("This instance of AdapTable does not have a license, and some functionality has therefore been removed. In order to use a fully-featured version of AdapTable, please contact [EMAIL]. You can learn more about the different AdapTable license options at [LINK]."),"Error"),this.showNotification("No AdapTable License found."),this.showWatermark("This instance of AdapTable does not have a license, and some functionality has therefore been removed."),this.disableStatePersistence();break;case"INVALID_LICENSE":this.adaptable.logger.consoleLogByMessageType(E("This instance of AdapTable seems to use a corrupted License, and some functionality has therefore been removed. In order to use a fully-featured version of AdapTable, please contact [EMAIL]. You can learn more about the different AdapTable license options at [LINK]."),"Error"),this.showNotification("Corrupted AdapTable License found."),this.showWatermark("This instance of AdapTable has a corrupted License, and some functionality has therefore been removed."),this.disableStatePersistence();break;case"NON_PRODUCTION_VALID":this.adaptable.logger.consoleLogByMessageType(E("This AdapTable trial license expires in [DAYS] days. Please contact [EMAIL] to upgrade to a commercial version of AdapTable. You can learn more about the different AdapTable license options at [LINK]."),"Info");break;case"NON_PRODUCTION_EXPIRED_IN_SCOPE":this.adaptable.logger.consoleLogByMessageType(E("This AdapTable trial license has now expired. Please contact [EMAIL] to upgrade to a commercial version of AdapTable. You can learn more about the different AdapTable license options at [LINK]."),"Warning"),this.showWatermark("AdapTable License has expired");break;case"COMMERCIAL_VALID":if(i<=p)this.adaptable.logger.consoleLogByMessageType(E(`This AdapTable license${h} expires in [DAYS] days. Please contact [EMAIL] to renew (giving you access to Support and Updates)`),"Info");else try{l()&&this.adaptable.logger.consoleLogByMessageType(E(`Thank you for using a valid AdapTable license${h}. Your license will expire in [DAYS] days.`),"Info")}catch(e){}break;case"COMMERCIAL_EXPIRED_IN_SCOPE":this.adaptable.logger.consoleLogByMessageType(E(`This AdapTable license${h} has expired. Please contact [EMAIL] if you wish to renew (giving you access to Support and Updates)`),"Warning");break;case"COMMERCIAL_EXPIRED_OUT_OF_SCOPE":this.adaptable.logger.consoleLogByMessageType(E(`This AdapTable license${h} has expired. Adaptable version was published after the license expired. Please contact [EMAIL] if you wish to renew your license.`),"Error"),this.showNotification("Adaptable License has expired"),this.showWatermark("Adaptable License has expired")}}showNotification(e){this.adaptable.api.internalApi.dispatchReduxAction(t({alertType:"generic",header:"License Error",message:e,alertDefinition:i.CreateInternalAlertDefinitionForMessages("Error")}))}showWatermark(e){this.adaptable.api.internalApi.dispatchReduxAction(a(e))}disableStatePersistence(){this.adaptable.api.internalApi.dispatchReduxAction(e())}destroy(){}}
@@ -1 +1 @@
1
- import{compute_string as e}from"./hashing";const t=()=>new Error("Invalid License");export const GENERIC_APP_NAME="GenericAdaptableApp";export const fieldsToLicenseDetails=e=>{const r=e.reduce(((e,t)=>(e.set(t.name,t.value),e)),new Map),a={start:new Date(r.get("StartDate")),end:new Date(r.get("EndDate")),owner:r.get("Owner"),appName:r.get("AppName")||GENERIC_APP_NAME,timestamp:r.get("TS")?Number(r.get("TS")):0,trial:"true"===r.get("Trial"),ref:r.get("Ref")??""};if(!(a.start&&a.end&&a.owner&&"boolean"==typeof a.trial&&a.ref))throw t();return a};export const decode=r=>{let a="",n=r.split("|").map((e=>{let[t,r]=e.split("=");return"C"===t&&(a=r),{name:t,value:r}}));if(!a)throw t();const o=a.split(",").reverse(),s=o.pop();o.forEach(((r,a)=>{const o=n[a];if(e(o.value)!==r)throw t()}));const p=[...n];p.pop();const i=p.map((e=>`${e.name}=${e.value}`)).join("|");if(e(i)!==s)throw t();return n=n.map((e=>({...e,value:decodeURI(e.value)}))),fieldsToLicenseDetails(n)};
1
+ import{compute_string as e}from"./hashing";const t=()=>new Error("Invalid License");export const GENERIC_APP_NAME="GenericAdaptableApp";export const fieldsToLicenseDetails=e=>{const r=e.reduce((e,t)=>(e.set(t.name,t.value),e),new Map),a={start:new Date(r.get("StartDate")),end:new Date(r.get("EndDate")),owner:r.get("Owner"),appName:r.get("AppName")||GENERIC_APP_NAME,timestamp:r.get("TS")?Number(r.get("TS")):0,trial:"true"===r.get("Trial"),ref:r.get("Ref")??""};if(!(a.start&&a.end&&a.owner&&"boolean"==typeof a.trial&&a.ref))throw t();return a};export const decode=r=>{let a="",n=r.split("|").map(e=>{let[t,r]=e.split("=");return"C"===t&&(a=r),{name:t,value:r}});if(!a)throw t();const o=a.split(",").reverse(),s=o.pop();o.forEach((r,a)=>{const o=n[a];if(e(o.value)!==r)throw t()});const p=[...n];p.pop();const i=p.map(e=>`${e.name}=${e.value}`).join("|");if(e(i)!==s)throw t();return n=n.map(e=>({...e,value:decodeURI(e.value)})),fieldsToLicenseDetails(n)};
@@ -52,9 +52,7 @@ export const CalculatedColumnExpressionWizardSection = (props) => {
52
52
  return 'quantileAggregatedScalar';
53
53
  }
54
54
  };
55
- const columns = api.columnApi
56
- .getQueryableColumns()
57
- .filter((c) => !c.isGeneratedPivotResultColumn);
55
+ const columns = api.columnApi.internalApi.getQueryableColumnsForUIEditor();
58
56
  return (React.createElement(Tabs, { autoFocus: false, height: "100%" },
59
57
  React.createElement(Tabs.Tab, null, Humanize(props.expressionType)),
60
58
  React.createElement(Tabs.Content, null, (() => {
@@ -147,13 +147,13 @@ export const EntityRulesEditor = (props) => {
147
147
  React.createElement(EntityRulePredicatesEditor, { enablePredicateColumnId: props.enablePredicateColumnId, data: data, descriptions: descriptions, predicateDefs: filteredPredicateDefs, getPredicateDefsForColId: props.getPredicateDefsForColId, onChange: props.onChange }))) : null,
148
148
  showBoolean ? (React.createElement(QueryTab, { showRadio: showRadioButtons, value: "BooleanExpression", type: type, label: "Boolean" })) : null,
149
149
  showBoolean ? (React.createElement(Tabs.Content, { "data-name": "BooleanExpression", value: 'BooleanExpression' }, (() => {
150
- const editor = (React.createElement(ExpressionEditor, { type: 'boolean', module: module, value: data.Rule?.BooleanExpression, onChange: setBooleanExpression, initialData: initialData, columns: api.columnApi.getQueryableColumns(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api, showQueryBuilder: props.showQueryBuilder }));
150
+ const editor = (React.createElement(ExpressionEditor, { type: 'boolean', module: module, value: data.Rule?.BooleanExpression, onChange: setBooleanExpression, initialData: initialData, columns: api.columnApi.internalApi.getQueryableColumnsForUIEditor(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api, showQueryBuilder: props.showQueryBuilder }));
151
151
  return props.showQueryBuilder ? React.createElement(Panel, null, editor) : editor;
152
152
  })())) : null,
153
153
  showObservable ? (React.createElement(QueryTab, { showRadio: showRadioButtons, value: "ObservableExpression", type: type, label: "Observable" })) : null,
154
154
  showObservable ? (React.createElement(Tabs.Content, { "data-name": "ObservableExpression", value: 'ObservableExpression' },
155
- React.createElement(ExpressionEditor, { type: 'observable', module: module, value: data.Rule?.ObservableExpression, onChange: setReactiveExpression, initialData: initialData, columns: api.columnApi.getQueryableColumns(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api }))) : null,
155
+ React.createElement(ExpressionEditor, { type: 'observable', module: module, value: data.Rule?.ObservableExpression, onChange: setReactiveExpression, initialData: initialData, columns: api.columnApi.internalApi.getQueryableColumnsForUIEditor(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api }))) : null,
156
156
  showAggregation ? (React.createElement(QueryTab, { showRadio: showRadioButtons, value: "AggregatedBooleanExpression", type: type, label: "Aggregated Boolean" })) : null,
157
157
  showAggregation ? (React.createElement(Tabs.Content, { "data-name": "AggregatedBooleanExpression", value: 'AggregatedBooleanExpression' },
158
- React.createElement(ExpressionEditor, { type: 'aggregatedBoolean', module: module, value: data.Rule?.AggregatedBooleanExpression, onChange: setAggregationExpression, initialData: initialData, columns: api.columnApi.getQueryableColumns(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api }))) : null)));
158
+ React.createElement(ExpressionEditor, { type: 'aggregatedBoolean', module: module, value: data.Rule?.AggregatedBooleanExpression, onChange: setAggregationExpression, initialData: initialData, columns: api.columnApi.internalApi.getQueryableColumnsForUIEditor(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api }))) : null)));
159
159
  };
@@ -27,7 +27,7 @@ export class ExpressionWizard extends React.Component {
27
27
  render() {
28
28
  const initialData = useMemo(() => this.props.api.internalApi.getQueryPreviewData(), []);
29
29
  return (React.createElement(React.Fragment, null,
30
- React.createElement(ExpressionEditor, { type: 'boolean', module: NamedQueryModuleId, value: this.state.expression, onChange: this.handleCustomExpressionChange, initialData: initialData, columns: this.props.api.columnApi.getQueryableColumns(), fields: this.props.api.expressionApi.internalApi.getAvailableFields(), namedQueries: this.props.api.namedQueryApi.getNamedQueries(), api: this.props.api }),
30
+ React.createElement(ExpressionEditor, { type: 'boolean', module: NamedQueryModuleId, value: this.state.expression, onChange: this.handleCustomExpressionChange, initialData: initialData, columns: this.props.api.columnApi.internalApi.getQueryableColumnsForUIEditor(), fields: this.props.api.expressionApi.internalApi.getAvailableFields(), namedQueries: this.props.api.namedQueryApi.getNamedQueries(), api: this.props.api }),
31
31
  ' ',
32
32
  React.createElement(Flex, { flexDirection: "row", padding: 1, marginBottom: 2, marginLeft: 1, alignItems: "center", "data-name": "expression-wizard-save-option" },
33
33
  React.createElement(CheckBox, { marginLeft: 2, disabled: !this.isValidExpression(), marginBottom: 2, checked: this.state.saveToNamedQueries, onChange: (checked) => this.setState({
@@ -8,6 +8,7 @@ export interface StyleComponentProps extends React.ClassAttributes<StyleComponen
8
8
  api: AdaptableApi;
9
9
  headless?: boolean;
10
10
  hidePreview?: boolean;
11
+ headerText?: string;
11
12
  Style: AdaptableStyle;
12
13
  showFontSizeAs?: 'radio' | 'dropdown';
13
14
  UpdateStyle: (style: AdaptableStyle) => void;
@@ -44,10 +44,11 @@ export class StyleComponent extends React.Component {
44
44
  }
45
45
  render() {
46
46
  const Cmp = this.props.headless ? Box : Panel;
47
+ const headerText = this.props.headerText ?? 'Style';
47
48
  const cmpProps = this.props.headless
48
49
  ? {}
49
50
  : {
50
- header: 'Style',
51
+ header: headerText,
51
52
  margin: 2,
52
53
  'data-name': 'style-component',
53
54
  };
@@ -70,5 +70,5 @@ export const ReportRowsWizardSection = (props) => {
70
70
  BooleanExpression,
71
71
  },
72
72
  });
73
- }, initialData: initialData, columns: api.columnApi.getQueryableColumns(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api })))));
73
+ }, initialData: initialData, columns: api.columnApi.internalApi.getQueryableColumnsForUIEditor(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api })))));
74
74
  };
@@ -88,7 +88,7 @@ export const GridFilterExpressionEditor = (props) => {
88
88
  },
89
89
  } },
90
90
  React.createElement(Flex, { height: "100%", flexDirection: "column" },
91
- React.createElement(ExpressionEditor, { ...expressionEditorProps, type: 'boolean', module: GridFilterModuleId, value: expression, onChange: (expression) => setExpression(expression), initialData: initialData, columns: api.columnApi.getQueryableColumns(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api }),
91
+ React.createElement(ExpressionEditor, { ...expressionEditorProps, type: 'boolean', module: GridFilterModuleId, value: expression, onChange: (expression) => setExpression(expression), initialData: initialData, columns: api.columnApi.internalApi.getQueryableColumnsForUIEditor(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api }),
92
92
  React.createElement(Flex, { flexDirection: "row", padding: 1, alignItems: "center" },
93
93
  props.onDismiss && (React.createElement(SimpleButton, { margin: 1, variant: "text", "data-name": "action-close", onClick: () => {
94
94
  props.onDismiss();
@@ -22,6 +22,7 @@ import { ReorderDraggable } from '../../../Components/ReorderDraggable';
22
22
  import { AdaptableFormControlTextClear } from '../../../Components/Forms/AdaptableFormControlTextClear';
23
23
  import { sortColumnIdsByOrder } from '../../../../layout-manager/src/sortColumnIdsByOrder';
24
24
  import HelpBlock from '../../../../components/HelpBlock';
25
+ import { AG_GRID_SELECTION_COLUMN } from '../../../../Utilities/Constants/GeneralConstants';
25
26
  const PropertyOrderText = (props) => (React.createElement(Text, { fontWeight: 600, fontSize: 2 }, props.children));
26
27
  const columnTypes = {
27
28
  default: {
@@ -195,6 +196,7 @@ export const ColumnsSection = (props) => {
195
196
  const adaptable = useAdaptable();
196
197
  const { data: layout } = useOnePageAdaptableWizardContext();
197
198
  const [searchInputValue, setSearchInputValue] = React.useState('');
199
+ let hasSelectionColumn = false;
198
200
  const allColumns = adaptable.api.columnApi
199
201
  .getUIAvailableColumns()
200
202
  .filter((col) => {
@@ -204,7 +206,23 @@ export const ColumnsSection = (props) => {
204
206
  return !col.isGeneratedRowGroupColumn;
205
207
  })
206
208
  // if the current Layout is a PivotLayout, then we also filter out current Pivot Result Columns
207
- .filter((col) => !col.isGeneratedPivotResultColumn);
209
+ .filter((col) => !col.isGeneratedPivotResultColumn)
210
+ // also we need to filter out selection column
211
+ .filter((col) => {
212
+ const result = !col.isGeneratedSelectionColumn;
213
+ if (!result) {
214
+ hasSelectionColumn = true;
215
+ }
216
+ return result;
217
+ });
218
+ const onChange = (data) => {
219
+ if (hasSelectionColumn &&
220
+ Array.isArray(data.TableColumns) &&
221
+ !data.TableColumns.includes(AG_GRID_SELECTION_COLUMN)) {
222
+ data.TableColumns.unshift(AG_GRID_SELECTION_COLUMN);
223
+ }
224
+ props.onChange(data);
225
+ };
208
226
  // however, changes in RowGroupedColumns done in the previous step
209
227
  // are reflected into the layout, so we use the latest layout.RowGroupedColumns
210
228
  // to create new columns
@@ -261,7 +279,7 @@ export const ColumnsSection = (props) => {
261
279
  ColumnVisibility[colId] = false;
262
280
  }
263
281
  });
264
- props.onChange({
282
+ onChange({
265
283
  ...layout,
266
284
  TableColumns: columnIds,
267
285
  ColumnVisibility,
@@ -300,14 +318,14 @@ export const ColumnsSection = (props) => {
300
318
  return shouldInclude;
301
319
  });
302
320
  }
303
- props.onChange({
321
+ onChange({
304
322
  ...layout,
305
323
  TableColumns: TableColumns,
306
324
  ColumnVisibility,
307
325
  });
308
326
  };
309
327
  const handlePinChange = (columnId, pinning) => {
310
- props.onChange({
328
+ onChange({
311
329
  ...layout,
312
330
  ColumnPinning: {
313
331
  ...layout.ColumnPinning,
@@ -316,7 +334,7 @@ export const ColumnsSection = (props) => {
316
334
  });
317
335
  };
318
336
  const handleColumnNameChange = (columnId, headerName) => {
319
- props.onChange({
337
+ onChange({
320
338
  ...layout,
321
339
  ColumnHeaders: {
322
340
  ...layout.ColumnHeaders,
@@ -325,7 +343,7 @@ export const ColumnsSection = (props) => {
325
343
  });
326
344
  };
327
345
  const handleColumnWidthChange = (columnId, width) => {
328
- props.onChange({
346
+ onChange({
329
347
  ...layout,
330
348
  ColumnWidths: {
331
349
  ...layout.ColumnWidths,
@@ -334,7 +352,8 @@ export const ColumnsSection = (props) => {
334
352
  });
335
353
  };
336
354
  const visibleIds = layout.TableColumns.filter((colId) => {
337
- return layout.ColumnVisibility?.[colId] !== false;
355
+ return (layout.ColumnVisibility?.[colId] !== false &&
356
+ adaptable.api.columnApi.isSelectionColumn(colId) === false);
338
357
  });
339
358
  const toLabel = (colId) => adaptable.api.columnApi.getFriendlyNameForColumnId(colId, layout);
340
359
  const toIdentifier = (colId) => colId;
@@ -373,7 +392,7 @@ export const ColumnsSection = (props) => {
373
392
  noSelectionLabel: `No Columns Selected`,
374
393
  onChange: handleColumnsChange,
375
394
  onSelectAll: () => {
376
- props.onChange({
395
+ onChange({
377
396
  ...layout,
378
397
  ColumnVisibility: {},
379
398
  TableColumns: ColumnOrderAllColumns.map((col) => col.columnId),
@@ -32,6 +32,6 @@ export const GridFilterSection = (props) => {
32
32
  Expression: expression,
33
33
  },
34
34
  });
35
- }, initialData: initialData, columns: api.columnApi.getQueryableColumns().filter((c) => !c.isGeneratedPivotResultColumn), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api }));
35
+ }, initialData: initialData, columns: api.columnApi.internalApi.getQueryableColumnsForUIEditor(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api }));
36
36
  return React.createElement("div", null, expressionEditorContent);
37
37
  };
@@ -19,8 +19,8 @@ export const RowGroupingSectionSummary = () => {
19
19
  React.createElement(Tag, null, "Row Grouping is not available in Tree Grids")));
20
20
  }
21
21
  return (React.createElement(Box, { display: 'flex', flexDirection: 'row' }, layout.RowGroupedColumns?.length ? (layout.RowGroupedColumns.map((columnId) => {
22
- return (React.createElement(Box, { mb: 2, mr: 2 },
23
- React.createElement(Tag, { key: columnId }, adaptable.api.columnApi.getFriendlyNameForColumnId(columnId))));
22
+ return (React.createElement(Box, { key: columnId, mb: 2, mr: 2 },
23
+ React.createElement(Tag, null, adaptable.api.columnApi.getFriendlyNameForColumnId(columnId))));
24
24
  })) : (React.createElement(Tag, null, "No Row Grouping"))));
25
25
  };
26
26
  export const RowGroupBehaviorSection = (props) => {
@@ -39,8 +39,8 @@ export const RowGroupBehaviorSection = (props) => {
39
39
  }
40
40
  onChange(newLayout);
41
41
  } },
42
- React.createElement(TypeRadio, { value: "always-collapsed", text: "All Collapsed", description: "Always open Layout with all Grouped Rows collapsed" }),
43
- React.createElement(TypeRadio, { value: "always-expanded", text: "All Expanded", description: "Always open Layout with all Grouped Rows expanded" }),
42
+ React.createElement(TypeRadio, { value: "always-collapsed", text: "All Collapsed", description: "Layout opens with all Grouped Rows always collapsed" }),
43
+ React.createElement(TypeRadio, { value: "always-expanded", text: "All Expanded", description: "Layout opens with all Grouped Rows always expanded" }),
44
44
  React.createElement(TypeRadio, { value: "expanded", text: "Mostly Expanded", description: "Layout opens with all Grouped rows expanded, other than those collapsed when Layout last displayed" }),
45
45
  React.createElement(TypeRadio, { value: "collapsed", text: "Mostly Collapsed", description: "Layout opens with all Grouped rows collapsed, other than those expanded when Layout last displayed" }))));
46
46
  };
@@ -1 +1 @@
1
- import*as e from"react";import{Logo as t}from"../../components/Logo";import{Flex as r}from"rebass";const o={border:"1px solid var(--ab-color-error)",padding:"5px",fontWeight:600,margin:"5px",fontSize:"14px",alignItems:"center",color:"var(--ab-color-text-on-defaultbackground)",background:"var(--ab-color-defaultbackground)"},n=e=>{const t=[["display","none"],["opacity","0"],["position","absolute"],["position","fixed"],["position","relative"],["visibility","hidden"]];for(const[r,o]of t)if(e.style[r]===o)return!1;return!0};export const LicenseWatermark=i=>{const l=e.useRef(null);return e.useEffect((()=>{const e=setInterval((()=>{l.current?.isConnected||alert("It is not allowed to remove the Adaptable watermark."),n(l.current)||alert("It is not allowed to modify the Adaptable watermark."),l?.current?.style&&(l.current.style.border=o.border,l.current.style.padding=o.padding,l.current.style.fontWeight=`${o.fontWeight}`,l.current.style.margin=o.margin,l.current.style.fontSize=o.fontSize,l.current.style.color=o.color,l.current.style.background=o.background,l.current.style.display="flex",l.current.style.position="static",l.current.style.opacity="1",l.current.style.visibility="visible")}),5e3);return()=>clearTimeout(e)}),[]),e.createElement(r,{style:o,ref:l},e.createElement(t,{style:{marginRight:10}}),e.createElement("div",null,i.children))};
1
+ import*as e from"react";import{Logo as t}from"../../components/Logo";import{Flex as r}from"rebass";const o={border:"1px solid var(--ab-color-error)",padding:"5px",fontWeight:600,margin:"5px",fontSize:"14px",alignItems:"center",color:"var(--ab-color-text-on-defaultbackground)",background:"var(--ab-color-defaultbackground)"},n=e=>{const t=[["display","none"],["opacity","0"],["position","absolute"],["position","fixed"],["position","relative"],["visibility","hidden"]];for(const[r,o]of t)if(e.style[r]===o)return!1;return!0};export const LicenseWatermark=i=>{const l=e.useRef(null);return e.useEffect(()=>{const e=setInterval(()=>{l.current?.isConnected||alert("It is not allowed to remove the Adaptable watermark."),n(l.current)||alert("It is not allowed to modify the Adaptable watermark."),l?.current?.style&&(l.current.style.border=o.border,l.current.style.padding=o.padding,l.current.style.fontWeight=`${o.fontWeight}`,l.current.style.margin=o.margin,l.current.style.fontSize=o.fontSize,l.current.style.color=o.color,l.current.style.background=o.background,l.current.style.display="flex",l.current.style.position="static",l.current.style.opacity="1",l.current.style.visibility="visible")},5e3);return()=>clearTimeout(e)},[]),e.createElement(r,{style:o,ref:l},e.createElement(t,{style:{marginRight:10}}),e.createElement("div",null,i.children))};
@@ -26,5 +26,5 @@ export const NamedQueryExpressionWizardSection = (props) => {
26
26
  const initialData = useMemo(() => api.internalApi.getQueryPreviewData(), []);
27
27
  return (React.createElement(ExpressionEditor, { allowSaveNamedQuery: false, showQueryBuilder: true, type: 'boolean', module: moduleInfo.ModuleName, value: data.BooleanExpression, onChange: (BooleanExpression) => {
28
28
  props.onChange({ ...data, BooleanExpression });
29
- }, initialData: initialData, columns: api.columnApi.getQueryableColumns(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api }));
29
+ }, initialData: initialData, columns: api.columnApi.internalApi.getQueryableColumnsForUIEditor(), fields: api.expressionApi.internalApi.getAvailableFields(), namedQueries: api.namedQueryApi.getNamedQueries(), api: api }));
30
30
  };
@@ -12,11 +12,12 @@ export const QuickSearchInput = (props) => {
12
12
  const QuickSearchText = useSelector((state) => state.QuickSearch.QuickSearchText);
13
13
  const dispatch = useDispatch();
14
14
  const onRunQuickSearch = React.useCallback((newQuickSearchText) => dispatch(QuickSearchRedux.QuickSearchRun(newQuickSearchText)), []);
15
+ const isServerSideRowModel = adaptable.api.gridApi.getAgGridRowModelType() === 'serverSide';
15
16
  const [searchText, search] = useQuickSearchDebounced({
16
17
  QuickSearchText,
17
18
  onRunQuickSearch,
18
19
  });
19
- return (React.createElement(AdaptableFormControlTextClear, { "aria-label": 'Quick Search', type: "text", autoFocus: props.autoFocus, placeholder: adaptable.api.optionsApi.getQuickSearchOptions().quickSearchPlaceholder, className: join('ab-DashboardToolbar__QuickSearch__text', props.className), value: searchText, OnTextChange: search, style: { height: '100%' }, inputStyle: { width: props.width ?? '10rem' }, actionTools: React.createElement(Box, { display: "flex", flexDirection: "row", alignItems: "center", flex: 'none' },
20
+ return (React.createElement(AdaptableFormControlTextClear, { "aria-label": 'Quick Search', type: "text", autoFocus: props.autoFocus, placeholder: adaptable.api.optionsApi.getQuickSearchOptions().quickSearchPlaceholder, className: join('ab-DashboardToolbar__QuickSearch__text', props.className), value: searchText, OnTextChange: search, style: { height: '100%' }, inputStyle: { width: props.width ?? '10rem' }, actionTools: isServerSideRowModel ? null : (React.createElement(Box, { display: "flex", flexDirection: "row", alignItems: "center", flex: 'none' },
20
21
  React.createElement(SimpleButton, { "aria-label": 'Previous Match', icon: "arrow-up", px: 0, py: 0, mr: 1, disabled: !searchText, variant: "text", onClick: () => adaptable.api.quickSearchApi.gotoPreviousMatch() }),
21
- React.createElement(SimpleButton, { "aria-label": 'Next Match', icon: "arrow-down", px: 0, py: 0, mr: 1, disabled: !searchText, variant: "text", onClick: () => adaptable.api.quickSearchApi.gotoNextMatch() })) }));
22
+ React.createElement(SimpleButton, { "aria-label": 'Next Match', icon: "arrow-down", px: 0, py: 0, mr: 1, disabled: !searchText, variant: "text", onClick: () => adaptable.api.quickSearchApi.gotoNextMatch() }))) }));
22
23
  };
@@ -6,7 +6,7 @@ interface QuickSearchPopupProps extends ModuleViewPopupProps<any> {
6
6
  QuickSearchText: string;
7
7
  QuickSearchStyle: AdaptableStyle;
8
8
  onRunQuickSearch: (quickSearchText: string) => QuickSearchRedux.QuickSearchRunAction;
9
- onSetStyle: (style: AdaptableStyle) => QuickSearchRedux.QuickSearchSetStyleAction;
9
+ onSetMatchingCellStyle: (style: AdaptableStyle) => QuickSearchRedux.QuickSearchSetMatchingCellStyleAction;
10
10
  }
11
11
  export declare const QuickSearchPopup: import("react-redux").ConnectedComponent<(props: QuickSearchPopupProps) => React.JSX.Element, {
12
12
  [x: string]: any;
@@ -11,6 +11,7 @@ import { CheckBox } from '../../components/CheckBox';
11
11
  import StringExtensions from '../../Utilities/Extensions/StringExtensions';
12
12
  import { useQuickSearchDebounced } from './useQuickSearchDebounced';
13
13
  import { QuickSearchInput } from './QuickSearchInput';
14
+ import HelpBlock from '../../components/HelpBlock';
14
15
  const QuickSearchPopupComponent = (props) => {
15
16
  const [searchText, search] = useQuickSearchDebounced(props);
16
17
  const [state, setState] = useState({
@@ -19,7 +20,7 @@ const QuickSearchPopupComponent = (props) => {
19
20
  });
20
21
  const onUpdateStyle = (style) => {
21
22
  setState({ ...state, EditedStyle: style });
22
- props.onSetStyle(style);
23
+ props.onSetMatchingCellStyle(style);
23
24
  };
24
25
  const onQuickSearchBehaviourChange = (checked) => {
25
26
  setState({ ...state, RunQueryAfterQuickSearch: checked });
@@ -33,21 +34,23 @@ const QuickSearchPopupComponent = (props) => {
33
34
  React.createElement(Panel, { header: props.api.internalApi.getCorrectEnglishVariant('Behaviour'), style: { height: 'auto' }, variant: "default", borderRadius: "none", marginTop: 3, marginLeft: 2, marginRight: 2 },
34
35
  ' ',
35
36
  React.createElement(Flex, { flexDirection: "column" },
37
+ React.createElement(HelpBlock, { fontSize: 2, marginTop: 2, marginBottom: 2 }, "Filters the Grid to only show rows with matching cells; use with care as can cause performance issues"),
38
+ ' ',
36
39
  React.createElement(FormLayout, { columns: [1, 2] },
37
40
  React.createElement(FormRow, null,
38
41
  React.createElement(CheckBox, { "data-name": "filter-quick-search-results", value: "existing", marginLeft: 1, marginRight: 3, checked: state.RunQueryAfterQuickSearch, disabled: StringExtensions.IsNotNullOrEmpty(searchText), onChange: onQuickSearchBehaviourChange }, "Filter using Quick Search Results"))))),
39
- React.createElement(StyleComponent, { style: { height: '100%' }, api: props.api, Style: props.QuickSearchStyle, UpdateStyle: onUpdateStyle })));
42
+ React.createElement(StyleComponent, { style: { height: '100%' }, headerText: 'Cell Matching Style', api: props.api, Style: props.QuickSearchStyle, UpdateStyle: onUpdateStyle })));
40
43
  };
41
44
  function mapStateToProps(state, ownProps) {
42
45
  return {
43
46
  QuickSearchText: state.QuickSearch.QuickSearchText,
44
- QuickSearchStyle: state.QuickSearch.Style,
47
+ QuickSearchStyle: state.QuickSearch.CellMatchStyle,
45
48
  };
46
49
  }
47
50
  function mapDispatchToProps(dispatch) {
48
51
  return {
49
52
  onRunQuickSearch: (quickSearchText) => dispatch(QuickSearchRedux.QuickSearchRun(quickSearchText)),
50
- onSetStyle: (style) => dispatch(QuickSearchRedux.QuickSearchSetStyle(style)),
53
+ onSetMatchingCellStyle: (style) => dispatch(QuickSearchRedux.QuickSearchSetCellMatchingStyle(style)),
51
54
  };
52
55
  }
53
56
  export const QuickSearchPopup = connect(mapStateToProps, mapDispatchToProps)(QuickSearchPopupComponent);
@@ -90,7 +90,7 @@ import { weightedAverage } from '../Utilities/weightedAverage';
90
90
  import { ROW_SUMMARY_ROW_ID } from '../AdaptableState/Common/RowSummary';
91
91
  import { FlashingCellService } from '../Utilities/Services/FlashingCellService';
92
92
  import { AgGridExportAdapter } from './AgGridExportAdapter';
93
- import { checkForDuplicateColumns, isPivotLayout, layoutModelToLayoutState, layoutStateToLayoutModel, normalizeLayout, } from '../Api/Implementation/LayoutHelpers';
93
+ import { checkForDuplicateColumns, getLayoutRowGroupValuesExceptionGroupKeys, isPivotLayout, layoutModelToLayoutState, layoutStateToLayoutModel, normalizeLayout, } from '../Api/Implementation/LayoutHelpers';
94
94
  import { LayoutManager } from '../layout-manager/src';
95
95
  import { isPivotLayoutModel } from '../layout-manager/src/isPivotLayoutModel';
96
96
  import { ACTION_COLUMN_TYPE, CALCULATED_COLUMN_TYPE, FDC3_COLUMN_TYPE, FREE_TEXT_COLUMN_TYPE, PIVOT_AGGREGATION_TOTAL_COLUMN_TYPE, PIVOT_ANY_TOTAL_COLUMN_TYPE, PIVOT_COLUMN_TOTAL_COLUMN_TYPE, PIVOT_GRAND_TOTAL_COLUMN_TYPE, } from '../AdaptableState/Common/AdaptableColumn';
@@ -449,7 +449,7 @@ export class AdaptableAgGrid {
449
449
  this.updateColumnModelAndRefreshGrid();
450
450
  }
451
451
  const layoutModelForApply = layoutStateToLayoutModel(currentLayout);
452
- this.layoutManager.applyRowGroupValues(layoutModelForApply.RowGroupValues);
452
+ this.layoutManager.applyRowGroupValues(layoutModelForApply.RowGroupValues, layoutModelForApply.RowGroupedColumns);
453
453
  this.layoutManager.applyColumnGroupCollapseExpandState(layoutModelForApply);
454
454
  this.autoSizeLayoutIfNeeded();
455
455
  this.ModuleService.createModuleUIItems();
@@ -1322,12 +1322,12 @@ You need to define at least one Layout!`);
1322
1322
  this.autoSizeLayoutIfNeeded();
1323
1323
  }));
1324
1324
  /**
1325
- * Use Case: A format column that has ColumnGroupState needs to be re-evaluated
1325
+ * Use Case: A format column that has ColumnGroupScope needs to be re-evaluated
1326
1326
  * whenever a column group is expanded or collapsed
1327
1327
  */
1328
1328
  this.agGridAdapter.getAgGridApi().addEventListener('columnGroupOpened', (this.listenerColumnGroupOpened = () => {
1329
1329
  if (this.api.formatColumnApi.getActiveFormatColumns().some((fc) => {
1330
- return fc.ColumnGroupState != null;
1330
+ return fc.ColumnGroupScope != null;
1331
1331
  })) {
1332
1332
  this.updateColumnModelAndRefreshGrid();
1333
1333
  }
@@ -2014,7 +2014,7 @@ You need to define at least one Layout!`);
2014
2014
  layout = this.api.layoutApi.getCurrentLayout();
2015
2015
  }
2016
2016
  const layoutModel = layoutStateToLayoutModel(layout);
2017
- this.layoutManager.applyRowGroupValues(layoutModel.RowGroupValues);
2017
+ this.layoutManager.applyRowGroupValues(layoutModel.RowGroupValues, layoutModel.RowGroupedColumns);
2018
2018
  }
2019
2019
  isGroupRowNode(rowNode) {
2020
2020
  if (!rowNode) {
@@ -3107,12 +3107,23 @@ You need to define at least one Layout!`);
3107
3107
  checkForDuplicateColumns(layout);
3108
3108
  const isLayoutSwitch = this._prevLayout && layout.Name != this._prevLayout.Name;
3109
3109
  let shouldUpdateExpandState = isLayoutSwitch;
3110
- if (!isLayoutSwitch &&
3111
- this._prevLayout &&
3112
- layout.RowGroupValues?.RowGroupDefaultBehavior &&
3113
- this._prevLayout?.RowGroupValues?.RowGroupDefaultBehavior !=
3114
- layout.RowGroupValues?.RowGroupDefaultBehavior) {
3115
- shouldUpdateExpandState = true;
3110
+ if (!isLayoutSwitch && this._prevLayout) {
3111
+ if (layout.RowGroupValues?.RowGroupDefaultBehavior &&
3112
+ this._prevLayout?.RowGroupValues?.RowGroupDefaultBehavior !=
3113
+ layout.RowGroupValues?.RowGroupDefaultBehavior) {
3114
+ shouldUpdateExpandState = true;
3115
+ }
3116
+ else {
3117
+ const prevLayoutExceptionGroupKeys = getLayoutRowGroupValuesExceptionGroupKeys(this._prevLayout)
3118
+ .flat()
3119
+ .join(',');
3120
+ const currentLayoutExceptionGroupKeys = getLayoutRowGroupValuesExceptionGroupKeys(layout)
3121
+ .flat()
3122
+ .join(',');
3123
+ if (prevLayoutExceptionGroupKeys !== currentLayoutExceptionGroupKeys) {
3124
+ shouldUpdateExpandState = true;
3125
+ }
3126
+ }
3116
3127
  }
3117
3128
  this._prevLayout = layout;
3118
3129
  const perfSetLayout = this.logger.beginPerf(`setLayout(${layout.Name})`);
@@ -425,6 +425,7 @@ export class AgGridAdapter {
425
425
  const isFdc3MainActionColumn = this.adaptableApi.fdc3Api.internalApi.isFdc3MainActionColumn(colId);
426
426
  let friendlyName;
427
427
  const isGeneratedRowGroupColumn = columnApi.isAutoRowGroupColumn(ColumnId);
428
+ const isGeneratedSelectionColumn = columnApi.isSelectionColumn(ColumnId);
428
429
  const isGeneratedPivotResultColumn = columnApi.isPivotResultColumn(ColumnId) && !agGridColumn.isPrimary();
429
430
  const colExists = columnApi.doesColumnExist(ColumnId) ||
430
431
  isGeneratedRowGroupColumn ||
@@ -464,7 +465,7 @@ export class AgGridAdapter {
464
465
  colDef.lockVisible === true &&
465
466
  colDef.suppressColumnsToolPanel === true &&
466
467
  colDef.suppressFiltersToolPanel === true;
467
- const isGenerated = isGeneratedRowGroupColumn || isGeneratedPivotResultColumn;
468
+ const isGenerated = isGeneratedRowGroupColumn || isGeneratedPivotResultColumn || isGeneratedSelectionColumn;
468
469
  const abColumn = {
469
470
  Uuid: createUuid(),
470
471
  isTreeColumn,
@@ -491,6 +492,7 @@ export class AgGridAdapter {
491
492
  hideable: this.isColumnHideable(colDef),
492
493
  isGrouped: isGenerated ? false : this.isColumnRowGrouped(colDef),
493
494
  isGeneratedRowGroupColumn,
495
+ isGeneratedSelectionColumn,
494
496
  isGeneratedPivotResultColumn,
495
497
  isFixed: this.isColumnFixed(colDef),
496
498
  pinned: this.getColumnPinnedPosition(colDef),
@@ -676,6 +678,9 @@ export class AgGridAdapter {
676
678
  this.adaptableApi.columnApi.isAutoRowGroupColumn(colDef.colId)) {
677
679
  return false;
678
680
  }
681
+ if (this.adaptableApi.columnApi.isSelectionColumn(colDef.colId)) {
682
+ return false;
683
+ }
679
684
  if (colDef.lockVisible != null && colDef.lockVisible == true) {
680
685
  return false;
681
686
  }
@@ -36,6 +36,7 @@ export declare class AgGridColumnAdapter {
36
36
  private setupColumnValueSetter;
37
37
  private setupColumnComparator;
38
38
  private setupColumnGetFindText;
39
+ private getCellSearchText;
39
40
  private isCellSearchable;
40
41
  private isQuickSearchActive;
41
42
  private getEditableCellClass;
@@ -1,3 +1,4 @@
1
+ import kebabCase from 'lodash/kebabCase';
1
2
  import merge from 'lodash/merge';
2
3
  import { FilterWrapperFactory } from './FilterWrapper';
3
4
  import { FloatingFilterWrapperFactory } from './FloatingFilterWrapper';
@@ -87,12 +88,16 @@ export class AgGridColumnAdapter {
87
88
  }
88
89
  shouldSkipColumn(colId) {
89
90
  /**
90
- * This skips columns like `ag-Grid-SelectionColumn` and possibly other columns
91
- * that ag grid will implement in the future
91
+ * This skips special columns that ag grid will likely implement in the future
92
92
  *
93
- * BUT DOES NOT SKIP GROUP COLUMNS!!!
93
+ * BUT DOES NOT SKIP GROUP COLUMNS or SELECTION COLUMNS!!!
94
+ *
95
+ * It's probably here for historical reasons - previously it used to skip the selection column
96
+ * but now it's not skipping it anymore
94
97
  */
95
- return colId.startsWith('ag-Grid-') && !this.adaptableApi.columnApi.isAutoRowGroupColumn(colId);
98
+ return (colId.startsWith('ag-Grid-') &&
99
+ !this.adaptableApi.columnApi.isAutoRowGroupColumn(colId) &&
100
+ !this.adaptableApi.columnApi.isSelectionColumn(colId));
96
101
  }
97
102
  setupColumns() {
98
103
  const pivotMode = this.agGridApi.isPivotMode();
@@ -152,10 +157,8 @@ export class AgGridColumnAdapter {
152
157
  setupColumnCellClass({ col, colId, abColumn }) {
153
158
  this.setColDefProperty(col, 'cellClass', (userCellClass) => {
154
159
  const formatColumns = this.adaptableApi.formatColumnApi.internalApi.getFormatColumnWithStyleClassNameForColumn(abColumn);
155
- const quickSearchStyleClassName = this.adaptableApi.quickSearchApi.getQuickSearchStyle().ClassName;
156
160
  const quickSearchTextMatchStyle = this.getQuickSearchTextMatchStyle();
157
161
  const quickSearchCurrentTextMatchStyle = this.getQuickSearchCurrentTextMatchStyle();
158
- const hasQuickSearchStyleClassName = StringExtensions.IsNotNullOrEmpty(quickSearchStyleClassName);
159
162
  const cellClass = (params) => {
160
163
  const gridCell = this.adaptableApi.gridApi.getGridCellFromRowNode(params.node, abColumn.columnId);
161
164
  if (!gridCell.column) {
@@ -182,7 +185,7 @@ export class AgGridColumnAdapter {
182
185
  !hasStyledColumn && formatColumns.length
183
186
  ? this.getFormatColumnCellClass(formatColumns, abColumn, params)
184
187
  : null,
185
- isQuickSearchActive && hasQuickSearchStyleClassName ? quickSearchStyleClassName : null,
188
+ // isQuickSearchActive && hasQuickSearchStyleClassName ? quickSearchStyleClassName : null,
186
189
  isQuickSearchActive && (quickSearchTextMatchStyle || quickSearchCurrentTextMatchStyle)
187
190
  ? 'ab-QuickSearchFind'
188
191
  : null,
@@ -210,15 +213,17 @@ export class AgGridColumnAdapter {
210
213
  const quickSearchCurrentTextMatchStyle = this.getQuickSearchCurrentTextMatchStyle();
211
214
  const textMatchStyle = quickSearchTextMatchStyle
212
215
  ? Object.entries(quickSearchTextMatchStyle).reduce((acc, [key, value]) => {
216
+ // needed as AG-Grid vanilla turns all CSS props
217
+ // to kebab, while AG Grid React does not
213
218
  // @ts-ignore
214
- acc[`--ab-dynamic-${key}`] = value;
219
+ acc[`--ab-dynamic-${kebabCase(key)}`] = value;
215
220
  return acc;
216
221
  }, {})
217
222
  : undefined;
218
223
  const currentTextMatchStyle = quickSearchCurrentTextMatchStyle
219
224
  ? Object.entries(quickSearchCurrentTextMatchStyle).reduce((acc, [key, value]) => {
220
225
  // @ts-ignore
221
- acc[`--ab-dynamic-${key}`] = value;
226
+ acc[`--ab-dynamic-${kebabCase(key)}`] = value;
222
227
  return acc;
223
228
  }, {})
224
229
  : undefined;
@@ -685,18 +690,25 @@ export class AgGridColumnAdapter {
685
690
  }
686
691
  const getCellSearchText = this.adaptableOptions.quickSearchOptions.getCellSearchText;
687
692
  if (getCellSearchText) {
688
- const quickSearchValue = this.adaptableApi.quickSearchApi.getQuickSearchValue();
689
- const quickSearchContext = {
690
- ...this.adaptableApi.internalApi.buildBaseContext(),
691
- gridCell,
692
- quickSearchValue,
693
- };
694
- return getCellSearchText(quickSearchContext);
693
+ return this.getCellSearchText(gridCell);
695
694
  }
696
695
  return userGetFindText?.(params) ?? gridCell.displayValue;
697
696
  };
698
697
  });
699
698
  }
699
+ getCellSearchText(gridCell) {
700
+ const getCellSearchText = this.adaptableOptions.quickSearchOptions.getCellSearchText;
701
+ if (getCellSearchText) {
702
+ const quickSearchValue = this.adaptableApi.quickSearchApi.getQuickSearchValue();
703
+ const quickSearchContext = {
704
+ ...this.adaptableApi.internalApi.buildBaseContext(),
705
+ gridCell,
706
+ quickSearchValue,
707
+ };
708
+ return getCellSearchText(quickSearchContext);
709
+ }
710
+ return gridCell.displayValue;
711
+ }
700
712
  isCellSearchable(gridCell) {
701
713
  const isCellSearchableFn = this.adaptableOptions.quickSearchOptions.isCellSearchable;
702
714
  if (!gridCell.column) {
@@ -732,6 +744,16 @@ export class AgGridColumnAdapter {
732
744
  if (!column) {
733
745
  return false;
734
746
  }
747
+ const isServerSideRowModel = this.adaptableApi.gridApi.getAgGridRowModelType() === 'serverSide';
748
+ if (isServerSideRowModel) {
749
+ const isCaseSensitive = this.adaptableOptions.quickSearchOptions.isQuickSearchCaseSensitive;
750
+ const cellDisplayValue = String(this.getCellSearchText(gridCell));
751
+ const displayValue = isCaseSensitive
752
+ ? cellDisplayValue
753
+ : cellDisplayValue.toLocaleLowerCase();
754
+ const searchText = isCaseSensitive ? quickSearchValue : quickSearchValue.toLocaleLowerCase();
755
+ return displayValue.indexOf(searchText) !== -1;
756
+ }
735
757
  return (this.agGridApi.findGetNumMatches({
736
758
  column,
737
759
  node: gridCell.rowNode,
@@ -828,7 +850,7 @@ export class AgGridColumnAdapter {
828
850
  return classNames;
829
851
  }
830
852
  getQuickSearchCellStyle() {
831
- const quickSearchStyle = this.adaptableApi.quickSearchApi.getQuickSearchStyle();
853
+ const quickSearchStyle = this.adaptableApi.quickSearchApi.getQuickSearchCellMatchStyle();
832
854
  if (!quickSearchStyle || StringExtensions.IsNotNullOrEmpty(quickSearchStyle.ClassName)) {
833
855
  return undefined;
834
856
  }