Skip to content
Version:

Master Page ​

Component nesting ​

  • Vertical Layout
    • Filter Panel
      • Inputs
      • Additional filter action buttons
    • Toolbar (connected to Filter Panel and Grid)
      • Additional grid batch actions
    • Grid

Implementation ​

tsx
function MasterPage() {
  const [items, setItems] = useState(allItems);
  const usernameFilter = useRef('');
  const prenameFilter = useRef('');
  const familyNameFilter = useRef('');
  const gridRef = useRef(null);
  const gridAddonRef = useRef(null);

  useEffect(() => {
    const addon = gridAddonRef.current;
    if (!addon) return;

    addon.rowProvider = item => {
      if (!item) return {};
      return { disabled: item.username.startsWith('s'), hasDetails: item.gender === DummyGender.Female };
    };

    addon.primaryActionColumnProvider = item => {
      if (!item) return {};
      return {
        tooltipText: `Aktionen für ${item.username}`,
        children: [
          { text: 'Bearbeiten' },
          { text: 'Löschen', disabled: true, tooltipText: 'Du kannst dieses Element nicht löschen' },
          { text: 'Children', children: [
            { text: 'Test', tooltipText: 'My tooltip' },
            { text: 'Male', hidden: item.gender !== DummyGender.Male }
          ]}
        ]
      };
    };
  }, []);

  const arrayFilter = (ref: React.MutableRefObject<string>, property: string) => (item: any) => {
    const val = ref.current;
    if (!val || val.length < 1) return true;
    const itemVal = item[property];
    if (!itemVal || itemVal.length < 1) return false;
    return itemVal.toLowerCase().includes(val.toLowerCase());
  };

  const handleSearch = () => {
    setItems(allItems
      .filter(arrayFilter(usernameFilter, 'username'))
      .filter(arrayFilter(prenameFilter, 'prename'))
      .filter(arrayFilter(familyNameFilter, 'familyName'))
    );
  };

  const handleReset = () => {
    usernameFilter.current = '';
    prenameFilter.current = '';
    familyNameFilter.current = '';
    setItems([...allItems]);
  };

  const handleDelete = () => {
    const grid = gridRef.current as any;
    if (grid?.selectedItems) {
      grid.selectedItems.forEach((item: any) => allItems.splice(allItems.indexOf(item), 1));
      setItems([...allItems]);
    }
  };

  return (
    <MateVerticalLayout theme="padding spacing" style={{ alignItems: 'stretch' }}>
      <MateFilterPanel onSearchClick={handleSearch} onResetClick={handleReset}>
        <MateTextField label="Username" onValueChanged={e => { usernameFilter.current = e.detail.value; }} />
        <MateTextField label="Vorname" onValueChanged={e => { prenameFilter.current = e.detail.value; }} />
        <MateTextField label="Nachname" onValueChanged={e => { familyNameFilter.current = e.detail.value; }} />
      </MateFilterPanel>
      <hr />
      <MateToolbar titleText="Users">
        <MateButton onClick={handleDelete}>Löschen</MateButton>
      </MateToolbar>
      <Grid ref={gridRef} items={items} theme="column-borders" style={{ flexGrow: '1' }}>
        <MateGridAddon ref={gridAddonRef} />
        <GridSelectionColumn />
        <GridSortColumn header="Username" path="username" resizable />
        <GridSortColumn
          header="Geburtstag"
          resizable
          renderer={({ item }: any) =>
            item.birthdate.toLocaleString('de-DE', { year: 'numeric', month: '2-digit', day: '2-digit' })
          }
        />
        <GridSortColumn
          header="Geschlecht"
          resizable
          renderer={({ item }: any) =>
            item.gender === DummyGender.Female ? 'Weiblich' : item.gender === DummyGender.Male ? 'Männlich' : 'Divers'
          }
        />
        <GridSortColumn header="Vorname" path="prename" resizable />
        <GridSortColumn header="Nachname" path="familyName" />
      </Grid>
    </MateVerticalLayout>
  );
}

For lazy loading examples see Grid component examples.