const fields = [
  { fieldName: 'KorName', dataType: 'text' },
  { fieldName: 'Gender', dataType: 'text' },
  { fieldName: 'Age', dataType: 'number' },
  { fieldName: 'Phone', dataType: 'text' },
  { fieldName: 'ProductId', dataType: 'text' },
  { fieldName: 'KorCountry', dataType: 'text' },
  { fieldName: 'OrderDate', dataType: 'datetime', datetimeFormat: 'yyyy-MM-dd', amText: 'AM', pmText: 'PM' },
  { fieldName: 'CardNumber', dataType: 'text' },
  { fieldName: 'Monetary', dataType: 'text' },
  { fieldName: 'StartDate', dataType: 'datetime', datetimeFormat: 'yyyy-MM-dd', amText: 'AM', pmText: 'PM' },
  { fieldName: 'EndDate', dataType: 'datetime', datetimeFormat: 'yyyy-MM-dd', amText: 'AM', pmText: 'PM' },
  { fieldName: 'ToMonth', dataType: 'number' },
  { fieldName: 'Month', dataType: 'number' },
  { fieldName: 'Year', dataType: 'number' },
  { fieldName: 'InterestRate', dataType: 'number' },
  { fieldName: 'SaveCost', dataType: 'number' },
  { fieldName: 'SaveMaturity', dataType: 'number' },
  { fieldName: 'CurrentSave', dataType: 'number' }
];

const columns = [
  { name: 'KorCountry', fieldName: 'KorCountry', width: '100', header: { text: 'Investment Country' } },
  { name: 'Monetary', fieldName: 'Monetary', width: '70', header: { text: 'Currency' } },
  { name: 'KorName', fieldName: 'KorName', width: '70', header: { text: 'Name' } },
  { name: 'Gender', fieldName: 'Gender', width: '70', header: { text: 'Gender' } },
  { name: 'Age', fieldName: 'Age', width: '70', header: { text: 'Age' }, styleName: 'right-column' },
  { name: 'StartDate', fieldName: 'StartDate', width: '100', header: { text: 'First Payment Date' } },
  { name: 'EndDate', fieldName: 'EndDate', width: '100', header: { text: 'End Date' } },
  { name: 'ToMonth', fieldName: 'ToMonth', width: '70', header: { text: 'Payment Count' }, styleName: 'right-column' },
  { name: 'Month', fieldName: 'Month', width: '70', header: { text: 'Remaining Count' }, styleName: 'right-column' },
  { name: 'InterestRate', fieldName: 'InterestRate', width: '70', numberFormat: '0.00', header: { text: 'Interest Rate' }, groupFooter: { text: 'Subtotal: ' }, footer: { text: 'Total: ' }, styleName: 'right-column' },
  { name: 'SaveCost', fieldName: 'SaveCost', width: '80', numberFormat: '#,##0', header: { text: 'Payment Amount' }, groupFooter: { numberFormat: '#,##0', expression: 'sum' }, footer: { numberFormat: '#,##0', expression: 'sum' }, styleName: 'right-column' },
  { name: 'SaveMaturity', fieldName: 'SaveMaturity', width: '80', numberFormat: '#,##0', header: { text: 'Maturity Amount' }, groupFooter: { numberFormat: '#,##0', expression: 'sum' }, footer: { numberFormat: '#,##0', expression: 'sum' }, styleName: 'right-column' },
  { name: 'CurrentSave', fieldName: 'CurrentSave', width: '80', numberFormat: '#,##0', header: { text: 'Current Balance' }, groupFooter: { numberFormat: '#,##0', expression: 'sum' }, footer: { numberFormat: '#,##0', expression: 'sum' }, styleName: 'right-column' }
];

let userCount = 1;
let personalizedList = {};

const { gridView, dataProvider } = RealGrid.createGrid('realgrid', {
  columns,
  header: {
    height: 40
  },
  display: {
    rowHeight: 36,
    emptyMessage: 'No data to display.'
  },
  edit: {
    insertable: true,
    appendable: true
  },
  footer: {
    height: 40
  },
  stateBar: {
    width: 16
  },
  groupPanel: {
    visible: true
  },
  onContextMenuPopup: function (grid, x, y, elementName) {
    if (elementName.cellType === 'header') {
      grid.setCurrent({ column: grid.mouseToIndex(x, y).column });
    }
    setContextMenu(gridView);
  },
  onContextMenuItemClicked: function (grid, item, clickData) {
    onContextMenuClick(grid, item, clickData);
  },
  onInitialized: (grid) => {
    fetch('/data/en/simple_data2700.json')
      .then((response) => response.json())
      .then((data) => {
        grid.getDataSource().setRows(data);
        personalizedList['default'] = {
          layout: null,
          rowGroup: [],
          sort: [],
          colFixed: 0,
          rowFixed: 0,
          rowHeight: 36
        };
      });
  }
}, {
  fields
});

window.gridView = gridView;
window.dataProvider = dataProvider;

function setContextMenu(grid) {
  const columns = grid.getColumnNames();
  const row = grid.getCurrent().itemIndex + 1;
  const visibleContextMenu = [];

  for (let i in columns) {
    const menuItem = {};
    const column = grid.layoutByName(columns[i]);
    if (column.column) {
      menuItem.label = column.lastColumn.header.text;
      menuItem.tag = column.lastColumn.name;
      menuItem.type = 'check';
      menuItem.checked = column.visible;
      visibleContextMenu.push(menuItem);
    }
  }

  visibleContextMenu.push(
    { label: '-' },
    { label: 'Show All Columns', tag: 'columnShow' },
    { label: '-' },
    { label: 'Turn on current column filter', tag: 'autoFilter' },
    { label: 'Turn off current column filter', tag: 'autoFilterFalse' }
  );

  const column = grid.columnByName(grid.getCurrent().column);
  const contextMenu = [
    {
      label: 'Fix',
      children: [
        { label: '1 Row', tag: '1rowFixed' },
        { label: '2 Rows', tag: '2rowFixed' },
        { label: 'Up to Current Row (' + row + ')', tag: 'rowFixed' },
        { label: '-' },
        { label: 'First Column', tag: '1colFixed' },
        { label: 'Second Column', tag: '2colFixed' },
        { label: 'Up to Current Column (' + column.header.text + ')', tag: 'colFixed' },
        { label: '-' },
        {
          label: 'Unfix',
          tag: 'cancelFixed',
          enabled: grid.fixedOptions.rightCount + grid.fixedOptions.colCount + grid.fixedOptions.rowCount !== 0
        }
      ]
    },
    { label: 'Column', tag: 'columnMenu', children: visibleContextMenu },
    {
      label: 'Row Height',
      children: [
        { label: 'Normal (28px)', tag: 'rowNormalHeight' },
        { label: 'Narrow (20px)', tag: 'rowSmallHeight' },
        { label: 'Wide (36px)', tag: 'rowLargeHeight' }
      ]
    }
  ];
  grid.setContextMenu(contextMenu);
}

function onContextMenuClick(grid, data, index) {
  const cell = grid.getCurrent();
  const col = grid.columnByName(cell.column);

  if (data.parent.label === 'Column' && data.tag !== 'columnShow' && data.tag !== 'autoFilter' && data.tag !== 'autoFilterFalse') {
    grid.layoutByName(data.tag).visible = data.checked;
  }

  switch (data.tag) {
    case '1rowFixed':
      grid.setFixedOptions({ rowCount: 1 });
      break;
    case '2rowFixed':
      grid.setFixedOptions({ rowCount: 2 });
      break;
    case 'rowFixed':
      grid.setFixedOptions({ rowCount: cell.itemIndex + 1 });
      break;
    case '1colFixed':
      grid.setFixedOptions({ colCount: 1 });
      break;
    case '2colFixed':
      grid.setFixedOptions({ colCount: 2 });
      break;
    case 'colFixed':
      grid.setFixedOptions({ colCount: col.displayIndex + 1 });
      break;
    case 'cancelFixed':
      grid.setFixedOptions({ colCount: 0, rowCount: 0 });
      break;
    case 'rowNormalHeight':
      grid.displayOptions.rowHeight = 28;
      break;
    case 'rowSmallHeight':
      grid.displayOptions.rowHeight = 20;
      break;
    case 'rowLargeHeight':
      grid.displayOptions.rowHeight = 36;
      break;
    case 'autoFilter':
      col.autoFilter = true;
      grid.refresh();
      break;
    case 'autoFilterFalse':
      col.autoFilter = false;
      grid.refresh();
      break;
    case 'columnHide':
      col.visible = false;
      break;
    case 'columnShow':
      {
        const layout = grid.getColumnNames();
        for (let i in layout) {
          gridView.layoutByName(layout[i]).visible = true;
        }
      }
      break;
  }
}

window.addPersonalizedList = function () {
  const select = document.getElementById('personalizedList');

  const option = document.createElement('option');
  option.value = 'user' + userCount;
  option.text = 'User' + userCount;

  select.appendChild(option);
  userCount++;

  const filterColumns = [];
  for (let i = 0; i < gridView.getColumns().length; i++) {
    if (gridView.columnByName(gridView.getColumns()[i].name).autoFilter) {
      filterColumns.push(gridView.getColumns()[i].name);
    }
  }

  const activeColumnFilters = [];
  for (let j = 0; j < filterColumns.length; j++) {
    const filterList = gridView.getActiveColumnFilters(filterColumns[j]);
    activeColumnFilters.push(filterList);
  }

  const selectedValue = option.value;
  personalizedList[selectedValue] = {
    layout: gridView.saveColumnLayout(),
    rowGroup: gridView.getGroupFieldNames(),
    sort: gridView.getSortedFields(),
    colFixed: gridView.fixedOptions.colCount,
    rowFixed: gridView.fixedOptions.rowCount,
    rowHeight: gridView.displayOptions.rowHeight,
    filterColumns: filterColumns,
    activeColumnFilters: activeColumnFilters
  };

  select.value = option.value;
};

window.removePersonalizedList = function () {
  const select = document.getElementById('personalizedList');
  if (select.value !== 'default') {
    select.remove(select.selectedIndex);
    defaultLayout();
  }
};

function defaultLayout() {
  gridView.setColumnLayout(null);
  gridView.fixedOptions.colCount = 0;
  gridView.fixedOptions.rowCount = 0;
  gridView.groupBy([]);
  gridView.displayOptions.rowHeight = 36;

  for (let i = 0; i < gridView.getColumns().length; i++) {
    gridView.columnByName(gridView.getColumns()[i].name).autoFilter = false;
  }

  gridView.orderBy([], []);
}

window.selectChange = function () {
  const layout = personalizedList[document.getElementById('personalizedList').value];

  gridView.setColumnLayout(layout.layout);
  gridView.fixedOptions.colCount = layout.colFixed;
  gridView.fixedOptions.rowCount = layout.rowFixed;
  gridView.groupBy(layout.rowGroup);
  gridView.displayOptions.rowHeight = layout.rowHeight;

  for (let i = 0; i < gridView.getColumns().length; i++) {
    gridView.columnByName(gridView.getColumns()[i].name).autoFilter = false;
  }
  if (layout.filterColumns) {
    for (let i = 0; i < layout.filterColumns.length; i++) {
      gridView.columnByName(layout.filterColumns[i]).autoFilter = true;
    }
  }

  const sortFields = [];
  const sortDirs = [];
  if (layout.sort) {
    for (let j = 0; j < layout.sort.length; j++) {
      sortFields.push(layout.sort[j].orgFieldName);
      sortDirs.push(layout.sort[j].direction);
    }
    gridView.orderBy(sortFields, sortDirs);
  } else {
    gridView.orderBy([], []);
  }
};

window.setColumnLayout = function () {
  const layout = [
    {
      name: 'Group1',
      direction: 'horizontal',
      items: ['KorCountry', 'Monetary'],
      header: { text: 'Country' }
    },
    {
      name: 'Group2',
      direction: 'horizontal',
      items: ['KorName', 'Gender', 'Age'],
      header: { text: 'User' }
    },
    {
      name: 'Group3',
      direction: 'horizontal',
      items: ['StartDate', 'EndDate'],
      header: { text: 'Date' }
    }
  ];

  gridView.setColumnLayout(layout);
};

window.setDefaultLayout = function () {
  gridView.setColumnLayout(null);
};