Ag-Grid: 如何保存和重新加载列顺序

Ag-Grid: How to save and reload column order

使用 Ag-Grid,用户可以拖动列以按照自己喜欢的方式对其进行排序。我需要允许用户保存他们的列顺序(到 SQL 后端),以便它成为他们的默认列顺序。我试图像这样获取列名:

var cols = schedGridOptions.columnApi.getAllColumns();
for (col in cols) {
    var colDef = col.getColDef();
    console.log(colDef.headerName);
}

这是我找到的用于设置 header 名称的示例,因此我尝试对其进行调整以获取 header 名称。但是我得到这个错误:

JavaScript runtime error: Object doesn't support property or method 'getColDef'

也许我没有做对?我对使用 Ag-Grid 相当陌生。寻找建议。

您正在查找 setColumnState() 和 getColumnState()。请参阅 https://www.ag-grid.com/javascript-grid-column-api/

上的文档

在您的网格选项中,为 gridReady 和 columnMoved 设置事件处理程序。 https://www.ag-grid.com/javascript-grid-events/

类似于:

gridOptions = {
   rowData: myRowDataSource,
   columnDefs: myColumns,
   onGridReady: onGridReady,
   onColumnMoved: onColumnMoved,
}

在列移动事件中,保存列状态。这是保存到本地存储的示例。更改它以保存到您的数据库。

onColumnMoved(params) {
  var columnState = JSON.stringify(params.columnApi.getColumnState());
  localStorage.setItem('myColumnState', columnState);
}

在网格就绪事件中,获取并恢复网格状态。同样,将其更改为从您的数据库中提取。

onGridReady(params) {
    var columnState = JSON.parse(localStorage.getItem('myColumnState'));
    if (columnState) {
      params.columnApi.setColumnState(columnState);
    }
}

onColumnMoved will fire every time the column is moving but the drag didn't stopped.

使用 onColumnMoved 根本不高效。

如果您关心性能,您应该使用 onDragStopped

gridOptions.onDragStopped = function (params) {
  const colIds = params.columnApi.getAllDisplayedColumns().map(col => col.colId)
  console.log(colIds) // all visible colIds with the visible order
}

我的回答是对@roli 回答的小改进。只有在操作后更改了列顺序,才会触发该事件。如果用户拖动并决定停止并将列放在与以前相同的索引处,则不会触发该事件。

下面的代码是react中的实现。这个想法很简单:在拖动开始时将列顺序存储为 colId 列表,并在拖动停止时将其与最终列顺序进行比较。只有当两个订单之间存在差异时才会触发该事件。

function useDragColumnChange(cb: (e: DragStoppedEvent) => void) {
  const columnOrderRef = React.useRef<string[]>([])
  const onDragStarted = (e: DragStartedEvent) => {
    columnOrderRef.current = e.columnApi.getColumnState().map(c => c.colId);
  }
  const onDragStopped = (e: DragStoppedEvent) => {
    const newColumnOrder = e.columnApi.getColumnState().map(c => c.colId);
    const sameOrder = columnOrderRef.current.every(
      (c, i) => c === newColumnOrder[i]
    );

    if (!sameOrder) {
      cb(e);
    }
  }

  return { onDragStarted, onDragStopped };
}

用法

// in render()

const { onDragStarted, onDragStopped } = useDragColumnChange(e => console.log('Saving new column order!'))

return (
  <AgGridReact
    ...
    onDragStarted={onDragStarted}
    onDragStopped={onDragStopped}
  />
);

现场演示

 gridOptions: GridOptions ={
  onDragStopped:(
    event: DragStoppedEvent  
  ) =>  this.test(event)  
  }
  
  test(params){
let columnDragState = params.columnApi.getColumnState();
console.log(columnDragState, "columnDragState")
const colIds = params.columnApi.getAllDisplayedColumns().map(e=>{
  return e.colDef
});
console.log(colIds)

  let arr3 = colIds.map((item, i) => Object.assign({}, item, columnDragState[i]));
  console.log(arr3)
}
<ag-grid-angular
    style="width: 1500px; height: 750px; padding-top: 10px;"
    class="ag-theme-alpine"
    [columnDefs]="columnDefs"
    (gridReady)="onGridReady($event)"
    [rowDragManaged]="true"
    
    [gridOptions]="gridOptions"
    [rowData]="rowData"
>
</ag-grid-angular>