# Table

Are you familiar with the pain of marking up HTML tables? I don't think I'll ever forget it. Fortunately, you'll never have to mark up another table again.

The `Table` component provides a dynamic table with sorting, search, and actions. Header rows are created dynamically from column names unless specified.

### Preview

<div align="left"><figure><img src="https://3357577683-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2F-LlnrBGdA8s50Vnplq1j%2Fuploads%2F26mdLzFFKwcgefDIthOO%2Ftable.png?alt=media&#x26;token=1d86edcb-7d1d-4c85-aafd-8e4c76a109b5" alt="Gravity table component" width="563"><figcaption></figcaption></figure></div>

## Code

```javascript
import { Table } from 'components/lib';

function MyComponent({ ...props }){

  const data = [
    { id: 1, email: 'user1@example.com', date_created: '2023-01-01' },
    { id: 2, email: 'user2@example.com', date_created: '2023-01-02' },
  ];

  return (
    <div>
      <Table
        data={ data }
        searchable
        selectable
        show=['email', 'date_created']
      />
    </div>
  );
}
```

### Props

<table data-full-width="true"><thead><tr><th>Prop</th><th>Description</th><th>Required</th><th>Value</th></tr></thead><tbody><tr><td>actions</td><td>array of action objects</td><td>optional</td><td><a href="#table-actions">object</a> (see below)</td></tr><tr><td>badge</td><td>add a badge to every row column</td><td>optional</td><td><a href="#table-badges">object</a> (see below)</td></tr><tr><td>data</td><td>array of table rows</td><td>required</td><td><a href="#table-data-object">object</a> (see below)</td></tr><tr><td>footer</td><td>footer row</td><td>optional</td><td>object ({ span: integer, value: string })</td></tr><tr><td>header</td><td>array of header column names</td><td>optional</td><td><a href="header">array</a> (see below)</td></tr><tr><td>hide</td><td>columns names to hide</td><td>optional</td><td>array of strings</td></tr><tr><td>loading</td><td>toggle loading spinner</td><td>optional</td><td>boolean</td></tr><tr><td>searchable</td><td>enable searching the table data</td><td>optional</td><td>boolean</td></tr><tr><td>selectable</td><td>enable selecting table rows</td><td>optional</td><td>boolean</td></tr><tr><td>show</td><td>columns names to show</td><td>optional</td><td>array of strings</td></tr><tr><td>translation</td><td>reference to <a href="../localization">locale</a> object for header translations</td><td>optional</td><td>string</td></tr></tbody></table>

### Table Header Object

Pass a header array to the table if you'd like to customise the column headings. If no header is specified, Gravity will use the object key names from the first row and format them.

```javascript
const header = ['Name', 'Email']
```

### Table Data Object

The table body contains an array of objects - each array item generates a new row, and each key/value pair will be mapped to a column.

```javascript
const data = [
  { id: 1, email: 'user1@example.com', date_created: '2023-01-01' },
  { id: 2, email: 'user2@example.com', date_created: '2023-01-02' },
];
```

### Table Links

You can add a link to a table cell by passing an object with { `label`, `url` } keys.

```javascript
const data = [
  { id: 1, email: { label: 'user@example.com', url: '/users/1' }
];
```

### Table Actions

The `actions` prop enables you to create a dropdown menu with action buttons for each table row. \
\
Global actions are also available by passing the `global` key with the optional `globalOnly` key to make this action available only in the global actions at the top of the table. Global actions can be performed on multiple rows when the `selectable` prop is passed to the table.

Global actions also accept a `color` key to set the button color.

Executing an action button will return the data of the row it belongs to so you can access IDs and values.

```javascript
<Table
  data={ data }
  actions={{ 
  
    { icon: 'edit', label: 'Edit', action: editUser }, 
    { icon: 'trash', label: 'Delete, action: deleteUser }, 
    { icon: 'mail', label: 'Contact', action: contactUser },
    { icon: 'circle-plus', 'New', action: createUser, global: true, globalOnly: true, color: 'green' }
  
  }}
/>
```

### Conditional Actions

You can conditionally render an action based on a cells value:

```javascript
{ icon: 'edit', label: 'Edit', action: editUser, condition: { status: 'verified' }
```

### Action Callbacks

Every action will return two callback helper functions: `editRowCallback` and `deleteRowCallback` to help with updating the table state once a row has been edited or deleted.

```javascript
// edit row callback
const editUser = useCallback(({ row, editRowCallback }) => {

  viewContext.dialog.open({
    form: {
      inputs: {
        id: {
          type: 'hidden',
          value: row.id
        },
        email: {
          type: 'email', 
          value: row.email,
          required: true    
        },
        buttonText: 'Edit User',
        url: '/api/user',
        method: 'PATCH'
      }
    }, (form) => {

      const newState = editRowCallback(form);
      setUsers(newState);

  });
}, [viewContext])

// delete row callback
const deleteUser = useCallback(({ row, deleteRowCallback }) => {

  viewContext.dialog.open({
    form: {
      inputs: false,
      buttonText: 'Delete User',
      url: `/api/user/${row.id}`,
      method: 'DELETE',
      destructive: true
    },
  }, () => {

    const newState = deleteRowCallback(row);
    setUsers(newState);

  });
}, [viewContext]);
```

## Table Badges

You can render a colored badge in your table rows using the `badge` pro&#x70;**.** If you need to use conditional colors, pass an array of conditions and the table cell will test them. If you need multiple badges, you can pass an array of these objects.

```javascript
badge={{ col: 'status', color: 'blue', condition: [

  { value: 'registered', color: 'green' },
  { value: 'invited', color: 'blue' }

]}}
```

### Notes

* The `Table` component uses the `Loader`, `Search`, `Icon`, and `cn` functions from `'components/lib'`.
* The `actions` prop specifies the actions that can be performed on the table rows.
* The `badge` prop allows for adding badges to specific columns based on conditions.
* The `data` prop provides the table rows.
* The `footer` prop specifies the footer row with a span and value.
* The `header` prop specifies the header column names.
* The `hide` prop allows for hiding specific columns.
* The `loading` prop toggles the loading spinner.
* The `searchable` prop enables the search field.
* The `selectable` prop allows users to select table rows and perform global actions.
* The `show` prop specifies the columns to show, defaulting to all.
* The `translation` prop refers to a locale object for header translations.
* For more details, refer to the [Shadcn Table documentation](https://ui.shadcn.com/docs/components/table).
