AG Grid 数据在组件之间持续存在导致重复节点错误
AG Grid data is persisting between components causing duplicate node errors
编辑:我试图在可重用组件中手动使用网格 api destroy 函数,而父组件实际上调用了 ag 网格(在模板中)。 ag-grid 保留旧数据仍然存在问题。
我正在为我们的应用程序使用一个可重复使用的组件(它有 50 个奇怪的表,所以我们已经封装了工具以便 update/change 更容易)。我已经编码了一些过滤器持久性和行持久性(所以如果你点击一个项目,导航到细节,然后回来,它会带你回到那个项目并选择它。对我们非常大的网格很有用)
问题是,当我从一个没有设置 getRowNodeId 回调的组件转到我设置回调的组件时,它吓坏了,说有重复的节点 ID(b/c 它仍然引用来自旧网格。属性 在那个数据集中不存在,所以一切都是空的)。
我试过手动销毁 aggrid onDestroy 的实例,但这似乎没有任何作用。我已经尝试在 init 上将行数据设置为空数组,但这似乎已经破坏了 init 逻辑(我有一些用于第一次数据绘制的逻辑)并且通常 ag 网格的初始加载逻辑似乎决定它立即完成.如果我这样做,持久性逻辑将不再有效。我也试过将回调设置延迟到第一次数据绘制之后,但它似乎没有使用回调。
关于如何在 ag 网格解析新网格数据时防止 getRowNodeId 溢出的任何想法? (或者正确清除之前的 ag grid 实例。它似乎在某处保留了对它的引用。)
网格是如何设置的
<grid-tools pagination = "true" IdField = "RouteId" agGrid = "true" persistFilters = "true" [gridEnum]="gridEnum" [agDataGrid]="transMatrixAgGrid" standardTools = "true" [filterOptions]="filterOptions"></grid-tools>
</div>
</div>
<div class="row add-top add-bottom">
<div class="col-xs-12" style="width:100%;height:500px;">
<mat-progress-bar mode="indeterminate" *ngIf="loading"></mat-progress-bar>
<ag-grid-angular #transMatrixAgGrid class="ag-theme-material agGrid"
[rowData]="routes"
[gridOptions] = "gridOptions"
(rowClicked) = "rowClick($event)"
(selectionChanged)="updateSelectedItems($event)"
[frameworkComponents] = "frameworkComponents"
[columnDefs]="agColumns">
</ag-grid-angular>
</div>
在组件中,保存对模板变量的引用。
@ViewChild("transMatrixAgGrid") transMatrixAgGrid;
重复使用的组件。我们正在从 devextreme 过渡,因此有一些适用于 ag 网格场景的条件逻辑。我不想尝试删除其中的一些代码,以防有人试图将此代码粘贴到 IDE 中。这是当前的工作状态。
import { Component, OnInit, Input, OnDestroy } from "@angular/core";
import { MatBottomSheet, MatBottomSheetRef } from "@angular/material";
import { ToolsOptionsMenu } from "./ToolsOptionsMenu/ToolsOptionsMenu.component";
import { DxDataGridComponent } from "devextreme-angular";
import * as _ from "lodash";
import FilterOption from "@classes/FilterOptions.class";
import { utc } from 'moment';
import { FormControl } from '@angular/forms';
// Careful about modifications. Large grids can become slow if this isn't efficient
export function compareDates(filterLocalDateAtMidnight, cellValue) {
var dateAsString = cellValue;
if (dateAsString == null) return 0;
// In the example application, dates are stored as dd/mm/yyyy
// We create a Date object for comparison against the filter date
var dateParts = dateAsString.split("T")[0].split("-");
var day = Number(dateParts[2]);
var month = Number(dateParts[1]) - 1;
var year = Number(dateParts[0]);
var cellDate = new Date(year, month, day);
// Now that both parameters are Date objects, we can compare
if (cellDate < filterLocalDateAtMidnight) {
return -1;
} else if (cellDate > filterLocalDateAtMidnight) {
return 1;
} else {
return 0;
}
}
//Ag-grid date formatter.
export function dateFormatter(dateIn) {
return dateIn.value ? utc(dateIn.value).format("MM/DD/YYYY") : "";
}
//Default grid options
export var gridOptions = {
rowSelection: "multiple",
pagination: true,
rowMultiSelectWithClick: true,
animateRows: true,
floatingFilter: true,
rowBuffer: 20
}
//Default checkbox column options
export var checkboxColumnOptions = {
field: 'RowSelect',
width: 50,
headerName: ' ',
headerCheckboxSelection: true,
headerCheckboxSelectionFilteredOnly: true,
checkboxSelection: true,
suppressMenu: true,
sortable: false,
}
@Component({
selector: "grid-tools",
templateUrl: "./grid-tools.component.html",
styleUrls: ["./grid-tools.component.scss"]
})
export class GridToolsComponent implements OnInit, OnDestroy {
maxSelection = 30000;
_filterOptions: Array<FilterOption> = []
currentlySelected = [];
currentPage = 1;
pageControl: FormControl;
storageKey = "";
selectionStorageKey = "";
ALL_FILTER = "ALL";
currentFilter = this.ALL_FILTER;
//!!!Using filterOptions.push will not trigger this!!!!
@Input() set filterOptions(value: Array<FilterOption>) {
// value.splice(0, 0, new FilterOption());
value.push(new FilterOption());
this._filterOptions = value;
};
get filterOptions() {
return this._filterOptions;
};
@Input() dataGrid: DxDataGridComponent;
@Input() agDataGrid;
@Input() agGrid: boolean = false;
@Input() standardTools: boolean = false;
@Input() persistGridViewChild?;
@Input() hideToolsButton = true; //This is until we make the change completely
@Input() hideExport = false;
@Input() hideColumnCustomization = false;
@Input() hideClearFilters = false;
@Input() hideResetGrid = false;
@Input() persistFilters = false;
@Input() pagination = false;
@Input() gridEnum = null;
@Input() IdField = null; //Required for navigating to the last selected row
constructor(private bottomSheet: MatBottomSheet) {
this.filterOptions = [];
}
ngOnDestroy() {
// console.log("Destroying component");
// if (this.agDataGrid) {
// this.agDataGrid.api.destroy();
// }
}
ngOnInit() {
this.pageControl = new FormControl(this.currentPage);
this.storageKey = "agGrid-" + this.gridEnum;
this.selectionStorageKey = "agGrid-" + this.gridEnum + "-selection";
if (this.dataGrid) {
this.dataGrid.onContentReady.subscribe(result => {
this.quickFilterSearch();
});
this.dataGrid.filterValueChange.subscribe(filterValue => {
this.quickFilterSearch();
});
this.dataGrid.selectedRowKeysChange.subscribe(
(selections) => {
this.currentlySelected = selections;
}
)
}
if (this.agDataGrid) {
if (this.IdField) {
this.agDataGrid.getRowNodeId = (data) => {
return data ? data[this.IdField] : data["Id"];
};
}
this.agDataGrid.gridReady.subscribe(
() => {
}
)
if (this.pagination) {
this.pageControl.valueChanges
.subscribe(newValue => {
if (newValue == undefined) {
newValue = 1;
}
this.agDataGrid.api.paginationGoToPage(newValue - 1);
});
this.agDataGrid.paginationChanged.subscribe(($event) => {
this.onPaginationChanged($event);
})
}
this.agDataGrid.selectionChanged.subscribe(
(event) => {
this.currentlySelected = this.agDataGrid.api.getSelectedRows();
}
);
this.agDataGrid.rowClicked.subscribe(
(event) => {
if (this.persistFilters) {
this.storeSelectedItem(event.node);
}
}
)
this.agDataGrid.rowSelected.subscribe(
(event) => {
if (this.persistFilters) {
if (event.node.isSelected()) {
this.storeSelectedItem(event.node);
}
else {
if (this.agDataGrid.api.getSelectedRows().length == 0) {
localStorage.setItem(this.selectionStorageKey, null);
}
}
}
}
)
this.agDataGrid.filterChanged.subscribe(
(event) => {
let currentFilter = this.agDataGrid.api.getFilterModel();
if (Object.keys(currentFilter).length == 0) {
this.currentFilter = 'ALL';
}
if (this.persistFilters) {
this.setPersistedFilterState(currentFilter);
}
this.quickFilterSearch();
}
)
this.agDataGrid.firstDataRendered.subscribe(
(event) => {
if (this.persistFilters) {
this.restoreFilters();
this.restoreSelection();
}
}
)
}
}
storeSelectedItem(node) {
let selectedItem = {
Id: node.id,
data: node.data
}
localStorage.setItem(this.selectionStorageKey, JSON.stringify(selectedItem));
}
onPaginationChanged($event) {
this.currentPage = this.agDataGrid.api.paginationGetCurrentPage()
this.pageControl.patchValue(this.currentPage + 1);
this.pageControl.updateValueAndValidity({ emitEvent: false, onlySelf: true });
}
restoreSelection() {
try {
let selection: any = localStorage.getItem(this.selectionStorageKey);
if (selection) {
selection = JSON.parse(selection);
let node = this.agDataGrid.api.getRowNode(selection.Id);
node.setSelected(true);
this.agDataGrid.api.ensureNodeVisible(node, "middle");
}
}
catch (error) {
console.log("Something wrong with getting " + this.selectionStorageKey + " local storage");
}
}
restoreFilters() {
let filterModel = localStorage.getItem(this.storageKey);
if (filterModel) {
filterModel = JSON.parse(filterModel);
//TODO: Manually compare to incoming filter options and see if something matches.
this.currentFilter = '';
}
this.agDataGrid.api.setFilterModel(filterModel);
}
setPersistedFilterState = (filterValue: any): void => {
const stringifiedState: string = JSON.stringify(filterValue);
localStorage.setItem(this.storageKey, stringifiedState);
};
resetColumns() {
if (this.persistGridViewChild) {
this.persistGridViewChild.resetColumnDefaults();
}
if (this.agDataGrid) {
this.agDataGrid.columnApi.resetColumnState();
}
}
customGrid() {
this.dataGrid.instance.showColumnChooser();
}
export() {
if (this.currentlySelected.length < this.maxSelection) {
let selectionOnly = this.currentlySelected.length == 0 ? false : true;
if (this.agDataGrid) {
this.agDataGrid.api.exportDataAsCsv({
onlySelected: selectionOnly
});
}
if (this.dataGrid) {
this.dataGrid.instance.exportToExcel(selectionOnly);
}
}
}
clearAgSelections() {
this.agDataGrid.api.clearSelections();
}
clearSelections() {
if (this.agDataGrid) {
this.agDataGrid.api.deselectAll();
}
else {
this.dataGrid.selectedRowKeys = [];
}
}
quickFilterSearch() {
let state: any = {};
if (this.agDataGrid) {
state = _.cloneDeep(this.agDataGrid.api.getFilterModel());
}
else {
state = _.cloneDeep(this.dataGrid.instance.state());
}
if (this.agDataGrid) {
//TODO
}
else {
this.currentFilter = ""; //If a custom filter is created by the user, we don't want any of the chips to be highlighted.
if (state.filterValue == null) {
this.currentFilter = this.ALL_FILTER;
} else {
_.map(this._filterOptions, (option: any) => {
let isEqual = _.isEqual(option.filter, state.filterValue);
if (isEqual) {
this.currentFilter = option.label;
}
});
}
}
}
isFilterActive(incomingFilter) {
return this.currentFilter == incomingFilter;
}
showToolsOptions() {
this.bottomSheet.open(ToolsOptionsMenu, {
data: {
grid: this.dataGrid,
persistGrid: this.persistGridViewChild
}
});
}
public filterGrid(filterOptions = new FilterOption()) {
if (this.dataGrid) {
this.currentFilter = filterOptions.label;
const state: any = _.cloneDeep(this.dataGrid.instance.state());
state.filterValue = filterOptions.filter; // New filterValue to be applied to grid.
this.dataGrid.instance.state(state);
//The state mechanism seems to not work if persistance is not active on the grid.
//This grid is stupid.
if (!this.persistGridViewChild) {
this.dataGrid.instance.clearFilter();
}
}
if (this.agDataGrid) {
this.currentFilter = filterOptions.label;
this.agDataGrid.api.setFilterModel(filterOptions.filter);
if (this.persistFilters) {
this.setPersistedFilterState(filterOptions.filter);
}
}
}
}
编辑:我已经停止使用自定义回调,但它仍在使用。 firstDataRendered 函数实际上是用旧数据触发的。不理想:(
我不确定这是否是 ag-grid 的错误,但最终我尝试重新使用组件中的 gridOptions。
网格工具组件
//Default grid options
export var gridOptions = {
rowSelection: "multiple",
pagination: true,
rowMultiSelectWithClick: true,
animateRows: true,
floatingFilter: true,
rowBuffer: 20
}
使用网格工具的组件
import { gridOptions } from '@app/grid-tools/grid-tools.component';
正在赋值
this.gridOptions = gridOptions;
模板
<ag-grid-angular #transMatrixAgGrid class="ag-theme-material agGrid"
[rowData]="routes"
[gridOptions] = "gridOptions"
[columnDefs]="agColumns">
</ag-grid-angular>
不知何故,这导致 ag-grid 保留了以前网格实例的数据。我通过简单地使用
解决了这个问题
this.gridOptions = Object.assign({}, gridOptions)
我假设 ag-grid 正在修改参考并且其中包含有关数据的信息。
编辑:我试图在可重用组件中手动使用网格 api destroy 函数,而父组件实际上调用了 ag 网格(在模板中)。 ag-grid 保留旧数据仍然存在问题。
我正在为我们的应用程序使用一个可重复使用的组件(它有 50 个奇怪的表,所以我们已经封装了工具以便 update/change 更容易)。我已经编码了一些过滤器持久性和行持久性(所以如果你点击一个项目,导航到细节,然后回来,它会带你回到那个项目并选择它。对我们非常大的网格很有用)
问题是,当我从一个没有设置 getRowNodeId 回调的组件转到我设置回调的组件时,它吓坏了,说有重复的节点 ID(b/c 它仍然引用来自旧网格。属性 在那个数据集中不存在,所以一切都是空的)。
我试过手动销毁 aggrid onDestroy 的实例,但这似乎没有任何作用。我已经尝试在 init 上将行数据设置为空数组,但这似乎已经破坏了 init 逻辑(我有一些用于第一次数据绘制的逻辑)并且通常 ag 网格的初始加载逻辑似乎决定它立即完成.如果我这样做,持久性逻辑将不再有效。我也试过将回调设置延迟到第一次数据绘制之后,但它似乎没有使用回调。
关于如何在 ag 网格解析新网格数据时防止 getRowNodeId 溢出的任何想法? (或者正确清除之前的 ag grid 实例。它似乎在某处保留了对它的引用。)
网格是如何设置的
<grid-tools pagination = "true" IdField = "RouteId" agGrid = "true" persistFilters = "true" [gridEnum]="gridEnum" [agDataGrid]="transMatrixAgGrid" standardTools = "true" [filterOptions]="filterOptions"></grid-tools>
</div>
</div>
<div class="row add-top add-bottom">
<div class="col-xs-12" style="width:100%;height:500px;">
<mat-progress-bar mode="indeterminate" *ngIf="loading"></mat-progress-bar>
<ag-grid-angular #transMatrixAgGrid class="ag-theme-material agGrid"
[rowData]="routes"
[gridOptions] = "gridOptions"
(rowClicked) = "rowClick($event)"
(selectionChanged)="updateSelectedItems($event)"
[frameworkComponents] = "frameworkComponents"
[columnDefs]="agColumns">
</ag-grid-angular>
</div>
在组件中,保存对模板变量的引用。
@ViewChild("transMatrixAgGrid") transMatrixAgGrid;
重复使用的组件。我们正在从 devextreme 过渡,因此有一些适用于 ag 网格场景的条件逻辑。我不想尝试删除其中的一些代码,以防有人试图将此代码粘贴到 IDE 中。这是当前的工作状态。
import { Component, OnInit, Input, OnDestroy } from "@angular/core";
import { MatBottomSheet, MatBottomSheetRef } from "@angular/material";
import { ToolsOptionsMenu } from "./ToolsOptionsMenu/ToolsOptionsMenu.component";
import { DxDataGridComponent } from "devextreme-angular";
import * as _ from "lodash";
import FilterOption from "@classes/FilterOptions.class";
import { utc } from 'moment';
import { FormControl } from '@angular/forms';
// Careful about modifications. Large grids can become slow if this isn't efficient
export function compareDates(filterLocalDateAtMidnight, cellValue) {
var dateAsString = cellValue;
if (dateAsString == null) return 0;
// In the example application, dates are stored as dd/mm/yyyy
// We create a Date object for comparison against the filter date
var dateParts = dateAsString.split("T")[0].split("-");
var day = Number(dateParts[2]);
var month = Number(dateParts[1]) - 1;
var year = Number(dateParts[0]);
var cellDate = new Date(year, month, day);
// Now that both parameters are Date objects, we can compare
if (cellDate < filterLocalDateAtMidnight) {
return -1;
} else if (cellDate > filterLocalDateAtMidnight) {
return 1;
} else {
return 0;
}
}
//Ag-grid date formatter.
export function dateFormatter(dateIn) {
return dateIn.value ? utc(dateIn.value).format("MM/DD/YYYY") : "";
}
//Default grid options
export var gridOptions = {
rowSelection: "multiple",
pagination: true,
rowMultiSelectWithClick: true,
animateRows: true,
floatingFilter: true,
rowBuffer: 20
}
//Default checkbox column options
export var checkboxColumnOptions = {
field: 'RowSelect',
width: 50,
headerName: ' ',
headerCheckboxSelection: true,
headerCheckboxSelectionFilteredOnly: true,
checkboxSelection: true,
suppressMenu: true,
sortable: false,
}
@Component({
selector: "grid-tools",
templateUrl: "./grid-tools.component.html",
styleUrls: ["./grid-tools.component.scss"]
})
export class GridToolsComponent implements OnInit, OnDestroy {
maxSelection = 30000;
_filterOptions: Array<FilterOption> = []
currentlySelected = [];
currentPage = 1;
pageControl: FormControl;
storageKey = "";
selectionStorageKey = "";
ALL_FILTER = "ALL";
currentFilter = this.ALL_FILTER;
//!!!Using filterOptions.push will not trigger this!!!!
@Input() set filterOptions(value: Array<FilterOption>) {
// value.splice(0, 0, new FilterOption());
value.push(new FilterOption());
this._filterOptions = value;
};
get filterOptions() {
return this._filterOptions;
};
@Input() dataGrid: DxDataGridComponent;
@Input() agDataGrid;
@Input() agGrid: boolean = false;
@Input() standardTools: boolean = false;
@Input() persistGridViewChild?;
@Input() hideToolsButton = true; //This is until we make the change completely
@Input() hideExport = false;
@Input() hideColumnCustomization = false;
@Input() hideClearFilters = false;
@Input() hideResetGrid = false;
@Input() persistFilters = false;
@Input() pagination = false;
@Input() gridEnum = null;
@Input() IdField = null; //Required for navigating to the last selected row
constructor(private bottomSheet: MatBottomSheet) {
this.filterOptions = [];
}
ngOnDestroy() {
// console.log("Destroying component");
// if (this.agDataGrid) {
// this.agDataGrid.api.destroy();
// }
}
ngOnInit() {
this.pageControl = new FormControl(this.currentPage);
this.storageKey = "agGrid-" + this.gridEnum;
this.selectionStorageKey = "agGrid-" + this.gridEnum + "-selection";
if (this.dataGrid) {
this.dataGrid.onContentReady.subscribe(result => {
this.quickFilterSearch();
});
this.dataGrid.filterValueChange.subscribe(filterValue => {
this.quickFilterSearch();
});
this.dataGrid.selectedRowKeysChange.subscribe(
(selections) => {
this.currentlySelected = selections;
}
)
}
if (this.agDataGrid) {
if (this.IdField) {
this.agDataGrid.getRowNodeId = (data) => {
return data ? data[this.IdField] : data["Id"];
};
}
this.agDataGrid.gridReady.subscribe(
() => {
}
)
if (this.pagination) {
this.pageControl.valueChanges
.subscribe(newValue => {
if (newValue == undefined) {
newValue = 1;
}
this.agDataGrid.api.paginationGoToPage(newValue - 1);
});
this.agDataGrid.paginationChanged.subscribe(($event) => {
this.onPaginationChanged($event);
})
}
this.agDataGrid.selectionChanged.subscribe(
(event) => {
this.currentlySelected = this.agDataGrid.api.getSelectedRows();
}
);
this.agDataGrid.rowClicked.subscribe(
(event) => {
if (this.persistFilters) {
this.storeSelectedItem(event.node);
}
}
)
this.agDataGrid.rowSelected.subscribe(
(event) => {
if (this.persistFilters) {
if (event.node.isSelected()) {
this.storeSelectedItem(event.node);
}
else {
if (this.agDataGrid.api.getSelectedRows().length == 0) {
localStorage.setItem(this.selectionStorageKey, null);
}
}
}
}
)
this.agDataGrid.filterChanged.subscribe(
(event) => {
let currentFilter = this.agDataGrid.api.getFilterModel();
if (Object.keys(currentFilter).length == 0) {
this.currentFilter = 'ALL';
}
if (this.persistFilters) {
this.setPersistedFilterState(currentFilter);
}
this.quickFilterSearch();
}
)
this.agDataGrid.firstDataRendered.subscribe(
(event) => {
if (this.persistFilters) {
this.restoreFilters();
this.restoreSelection();
}
}
)
}
}
storeSelectedItem(node) {
let selectedItem = {
Id: node.id,
data: node.data
}
localStorage.setItem(this.selectionStorageKey, JSON.stringify(selectedItem));
}
onPaginationChanged($event) {
this.currentPage = this.agDataGrid.api.paginationGetCurrentPage()
this.pageControl.patchValue(this.currentPage + 1);
this.pageControl.updateValueAndValidity({ emitEvent: false, onlySelf: true });
}
restoreSelection() {
try {
let selection: any = localStorage.getItem(this.selectionStorageKey);
if (selection) {
selection = JSON.parse(selection);
let node = this.agDataGrid.api.getRowNode(selection.Id);
node.setSelected(true);
this.agDataGrid.api.ensureNodeVisible(node, "middle");
}
}
catch (error) {
console.log("Something wrong with getting " + this.selectionStorageKey + " local storage");
}
}
restoreFilters() {
let filterModel = localStorage.getItem(this.storageKey);
if (filterModel) {
filterModel = JSON.parse(filterModel);
//TODO: Manually compare to incoming filter options and see if something matches.
this.currentFilter = '';
}
this.agDataGrid.api.setFilterModel(filterModel);
}
setPersistedFilterState = (filterValue: any): void => {
const stringifiedState: string = JSON.stringify(filterValue);
localStorage.setItem(this.storageKey, stringifiedState);
};
resetColumns() {
if (this.persistGridViewChild) {
this.persistGridViewChild.resetColumnDefaults();
}
if (this.agDataGrid) {
this.agDataGrid.columnApi.resetColumnState();
}
}
customGrid() {
this.dataGrid.instance.showColumnChooser();
}
export() {
if (this.currentlySelected.length < this.maxSelection) {
let selectionOnly = this.currentlySelected.length == 0 ? false : true;
if (this.agDataGrid) {
this.agDataGrid.api.exportDataAsCsv({
onlySelected: selectionOnly
});
}
if (this.dataGrid) {
this.dataGrid.instance.exportToExcel(selectionOnly);
}
}
}
clearAgSelections() {
this.agDataGrid.api.clearSelections();
}
clearSelections() {
if (this.agDataGrid) {
this.agDataGrid.api.deselectAll();
}
else {
this.dataGrid.selectedRowKeys = [];
}
}
quickFilterSearch() {
let state: any = {};
if (this.agDataGrid) {
state = _.cloneDeep(this.agDataGrid.api.getFilterModel());
}
else {
state = _.cloneDeep(this.dataGrid.instance.state());
}
if (this.agDataGrid) {
//TODO
}
else {
this.currentFilter = ""; //If a custom filter is created by the user, we don't want any of the chips to be highlighted.
if (state.filterValue == null) {
this.currentFilter = this.ALL_FILTER;
} else {
_.map(this._filterOptions, (option: any) => {
let isEqual = _.isEqual(option.filter, state.filterValue);
if (isEqual) {
this.currentFilter = option.label;
}
});
}
}
}
isFilterActive(incomingFilter) {
return this.currentFilter == incomingFilter;
}
showToolsOptions() {
this.bottomSheet.open(ToolsOptionsMenu, {
data: {
grid: this.dataGrid,
persistGrid: this.persistGridViewChild
}
});
}
public filterGrid(filterOptions = new FilterOption()) {
if (this.dataGrid) {
this.currentFilter = filterOptions.label;
const state: any = _.cloneDeep(this.dataGrid.instance.state());
state.filterValue = filterOptions.filter; // New filterValue to be applied to grid.
this.dataGrid.instance.state(state);
//The state mechanism seems to not work if persistance is not active on the grid.
//This grid is stupid.
if (!this.persistGridViewChild) {
this.dataGrid.instance.clearFilter();
}
}
if (this.agDataGrid) {
this.currentFilter = filterOptions.label;
this.agDataGrid.api.setFilterModel(filterOptions.filter);
if (this.persistFilters) {
this.setPersistedFilterState(filterOptions.filter);
}
}
}
}
编辑:我已经停止使用自定义回调,但它仍在使用。 firstDataRendered 函数实际上是用旧数据触发的。不理想:(
我不确定这是否是 ag-grid 的错误,但最终我尝试重新使用组件中的 gridOptions。
网格工具组件
//Default grid options
export var gridOptions = {
rowSelection: "multiple",
pagination: true,
rowMultiSelectWithClick: true,
animateRows: true,
floatingFilter: true,
rowBuffer: 20
}
使用网格工具的组件
import { gridOptions } from '@app/grid-tools/grid-tools.component';
正在赋值
this.gridOptions = gridOptions;
模板
<ag-grid-angular #transMatrixAgGrid class="ag-theme-material agGrid"
[rowData]="routes"
[gridOptions] = "gridOptions"
[columnDefs]="agColumns">
</ag-grid-angular>
不知何故,这导致 ag-grid 保留了以前网格实例的数据。我通过简单地使用
解决了这个问题this.gridOptions = Object.assign({}, gridOptions)
我假设 ag-grid 正在修改参考并且其中包含有关数据的信息。