## Feature Examples

### Structure
- description: Each item shows a `value` in the first row and a `description` below it. An info icon set with `descriptionInfo` and a trend set with `percentage` are optional.
- example:
```jsx
<Card>
  <StatisticsWidget
    items={[
      {
        value: '$3,500',
        description: 'Revenue',
        descriptionInfo: 'Revenue from sales in the last 7 days',
        percentage: 11,
      },
    ]}
  />
</Card>;
```

### Values only
- description: Items can show a `value` alone. Use it when the meaning is clear from the surrounding context, for example a card title.
- example:
```jsx
<Card>
  <StatisticsWidget
    items={[
      { value: '$500' },
      { value: '$1,500' },
      { value: '$2,500' },
      { value: '$3,500' },
    ]}
  />
</Card>;
```

### Description
- description: Explain what each value measures with `description`. Keep it short. Items without a description show the value only.
- example:
```jsx
<Card>
  <StatisticsWidget
    items={[
      { value: '$500', description: 'Sales' },
      { value: '$1,500' },
      { value: '$2,500', description: 'Revenue' },
    ]}
  />
</Card>;
```

### Info icon
- description: Descriptions are short by design. Clarify the meaning of a statistic with `descriptionInfo`, which renders an info icon with the text in a tooltip. The icon appears only next to a description.
- example:
```jsx
<Card>
  <StatisticsWidget
    items={[
      {
        value: '$500',
        description: 'Revenue',
        descriptionInfo: 'Revenue from sales',
      },
      {
        value: '$1,500',
        descriptionInfo: 'Not shown because the item has no description',
      },
      {
        value: '2,500',
        description: 'Orders',
        descriptionInfo: 'Orders made this week',
      },
    ]}
  />
</Card>;
```

### Long text
- description: When there isn't enough space, part of the value or description is hidden with an ellipsis. Hover it to see the full text in a tooltip.
- example:
```jsx
<Box width="480px">
  <Card>
    <StatisticsWidget
      items={[
        { value: '$500,000,000', description: 'Revenue' },
        { value: '$1,500', description: 'Average sales on Tuesdays' },
        { value: '4,200,000', description: 'Number of active customers' },
      ]}
    />
  </Card>
</Box>;
```

### Short value
- description: Provide a shorter form of a long value with `valueInShort`. It replaces the ellipsis when there isn't enough space, and the full value is still shown on hover.
- example:
```jsx
<Box width="480px">
  <Card>
    <StatisticsWidget
      items={[
        {
          value: '$500,000,000',
          valueInShort: '$500M',
          description: 'Revenue',
        },
        {
          value: '$1,500,000',
          valueInShort: '$1.5M',
          description: 'Expenses',
        },
        {
          value: '4,200,000',
          valueInShort: '4.2M',
          description: 'Number of active customers',
          descriptionInfo: 'Customers with 10 or more orders',
        },
      ]}
    />
  </Card>
</Box>;
```

### Size
- description: Control the value size with `size` prop. It supports 2 sizes: - `tiny` (default) displays values as bold text and fits dense layouts. - `large` displays values as a heading and suits a prominent summary.
- example:
```jsx
<StorybookComponents.Stack flexDirection="column">
  <Card>
    <StatisticsWidget
      size="tiny"
      items={[
        { value: '$500', description: 'Sales' },
        { value: '1,500', description: 'Orders' },
        { value: '$2,500', description: 'Revenue' },
      ]}
    />
  </Card>
  <Card>
    <StatisticsWidget
      size="large"
      items={[
        { value: '$500', description: 'Sales' },
        { value: '1,500', description: 'Orders' },
        { value: '$2,500', description: 'Revenue' },
      ]}
    />
  </Card>
</StorybookComponents.Stack>;
```

### Loading state
- description: Show a loader in place of the values with `isLoading` prop while the data is being fetched. Descriptions stay visible, so the layout doesn't shift when the values arrive.
- example:
```jsx
<Card>
  <StatisticsWidget
    isLoading
    items={[
      { value: '$500', description: 'Sales' },
      { value: '1,500', description: 'Orders' },
      { value: '$2,500', description: 'Revenue' },
    ]}
  />
</Card>;
```

### Empty values
- description: An item with an empty `value` shows a dash instead. Use it when a figure isn't available yet.
- example:
```jsx
<Card>
  <StatisticsWidget
    items={[
      { value: '$1,200', description: 'Sales' },
      { value: '', description: 'Refunds' },
      { value: '', description: 'Revenue' },
    ]}
  />
</Card>;
```

### Alignment
- description: Align the content of each item with `alignItems` prop. It supports 3 options: - `center` (default) is for common cases. - `start` aligns the content to the leading edge, for example under a left-aligned card title. - `end` aligns the content to the trailing edge.
- example:
```jsx
<StorybookComponents.Stack flexDirection="column">
  <Card>
    <StatisticsWidget
      alignItems="center"
      items={[
        { value: '$1,700', description: 'Sales' },
        { value: '12,000', description: 'Views' },
        { value: '$9,300', description: 'Revenue' },
      ]}
    />
  </Card>
  <Card>
    <StatisticsWidget
      alignItems="start"
      items={[
        { value: '$1,700', description: 'Sales' },
        { value: '12,000', description: 'Views' },
        { value: '$9,300', description: 'Revenue' },
      ]}
    />
  </Card>
  <Card>
    <StatisticsWidget
      alignItems="end"
      items={[
        { value: '$1,700', description: 'Sales' },
        { value: '12,000', description: 'Views' },
        { value: '$9,300', description: 'Revenue' },
      ]}
    />
  </Card>
</StorybookComponents.Stack>;
```

### Trend
- description: Show the change since the last period with `percentage`. A positive number displays with an arrow up and a negative one with an arrow down. Zero displays as neutral without an arrow.
- example:
```jsx
<Card>
  <StatisticsWidget
    items={[
      { value: '500', description: 'Visits', percentage: 21 },
      { value: '1,500', description: 'Orders', percentage: 0 },
      { value: '$2,500', description: 'Revenue', percentage: -11 },
    ]}
  />
</Card>;
```

### Inverted trend
- description: By default a positive change is green and a negative one is red. Reverse the colors with `invertedPercentage` for metrics where growth is bad, such as refunds or bounce rate.
- example:
```jsx
<Card>
  <StatisticsWidget
    items={[
      { value: '500', description: 'Customers', percentage: 21 },
      {
        value: '42',
        description: 'Refunds',
        percentage: 21,
        invertedPercentage: true,
      },
      { value: '$2,500', description: 'Revenue', percentage: -11 },
      {
        value: '3.2%',
        description: 'Bounce rate',
        percentage: -11,
        invertedPercentage: true,
        descriptionInfo: 'Visits that left after viewing one page',
      },
    ]}
  />
</Card>;
```

### Clickable items
- description: Make a statistic clickable with an `onClick` handler on the item. Clickable items are focusable with the Tab key, and the handler also fires on Enter or Space.
- example:
```jsx
() => {
  const [selected, setSelected] = React.useState('Bookings');

  return (
    <Card>
      <StatisticsWidget
        items={[
          {
            value: '500',
            description: 'Bookings',
            percentage: 21,
            onClick: () => setSelected('Bookings'),
          },
          {
            value: '1,500',
            description: 'Visits',
            percentage: 8,
            onClick: () => setSelected('Visits'),
          },
          {
            value: '$3,500',
            description: 'Revenue',
            percentage: -11,
            descriptionInfo: 'Revenue from paid bookings',
            onClick: () => setSelected('Revenue'),
          },
        ]}
      />
      <Card.Divider />
      <Card.Content>
        <Text size="small">Showing details for {selected}</Text>
      </Card.Content>
    </Card>
  );
};
```

### Children
- description: Render additional content under an item with `children`. It appears below the description and trend, for example a comparison with the previous period.
- example:
```jsx
<Card>
  <StatisticsWidget
    items={[
      {
        value: '$3,500',
        description: 'Revenue',
        percentage: 12,
        children: (
          <Text size="tiny" secondary>
            vs. $3,125 last month
          </Text>
        ),
      },
      {
        value: '128',
        description: 'Orders',
        percentage: -4,
        children: (
          <Text size="tiny" secondary>
            vs. 133 last month
          </Text>
        ),
      },
    ]}
  />
</Card>;
```

## Common Use Case Examples

### Inside a card
- description: Place the widget in a card whose header names the metrics and the period they cover.
- example:
```jsx
<Card>
  <Card.Header title="Article performance" subtitle="Last 7 days" />
  <Card.Divider />
  <Card.Content>
    <StatisticsWidget
      items={[
        {
          value: '500',
          description: 'Views',
          percentage: 21,
          onClick: () => {},
        },
        {
          value: '350',
          description: 'Unique visitors',
          percentage: 21,
        },
        {
          value: '3.9',
          description: 'Pages per visit',
          percentage: -11,
        },
        {
          value: '$3,500',
          description: 'Revenue',
          percentage: -11,
          descriptionInfo: 'Revenue in the last 7 days',
          onClick: () => {},
        },
        {
          value: '0',
          description: 'Shares',
          percentage: 0,
          descriptionInfo: 'Shares in the last 7 days',
          onClick: () => {},
        },
      ]}
    />
  </Card.Content>
</Card>;
```

### Filters
- description: Combine the widget with filters in the card header, such as a period and a region, and pass the matching `items` for the current selection.
- example:
```jsx
() => {
  const [period, setPeriod] = React.useState('7d');
  const [region, setRegion] = React.useState('all');

  const periods = [
    { id: '7d', value: 'Last 7 days' },
    { id: '30d', value: 'Last 30 days' },
  ];
  const regions = [
    { id: 'all', value: 'All regions' },
    { id: 'us', value: 'United States' },
  ];

  const data = {
    '7d': {
      all: [
        { value: '1,200', description: 'Views', percentage: 21 },
        { value: '900', description: 'Unique visitors', percentage: 14 },
        { value: '4.1', description: 'Pages per visit', percentage: 2 },
        {
          value: '$5,200',
          description: 'Revenue',
          percentage: 7,
          descriptionInfo: 'Revenue in the last 7 days',
        },
      ],
      us: [
        { value: '500', description: 'Views', percentage: 19 },
        { value: '350', description: 'Unique visitors', percentage: 21 },
        { value: '3.9', description: 'Pages per visit', percentage: -11 },
        {
          value: '$3,500',
          description: 'Revenue',
          percentage: -11,
          descriptionInfo: 'Revenue in the last 7 days',
        },
      ],
    },
    '30d': {
      all: [
        { value: '5,300', description: 'Views', percentage: 29 },
        { value: '4,100', description: 'Unique visitors', percentage: 11 },
        { value: '3.2', description: 'Pages per visit', percentage: -1 },
        {
          value: '$21,400',
          description: 'Revenue',
          percentage: 11,
          descriptionInfo: 'Revenue in the last 30 days',
        },
      ],
      us: [
        { value: '2,700', description: 'Views', percentage: 12 },
        { value: '2,000', description: 'Unique visitors', percentage: 9 },
        { value: '3.4', description: 'Pages per visit', percentage: -3 },
        {
          value: '$12,700',
          description: 'Revenue',
          percentage: 4,
          descriptionInfo: 'Revenue in the last 30 days',
        },
      ],
    },
  };

  const renderFilter = (options, selectedId, onSelect) => (
    <DropdownBase
      selectedId={selectedId}
      options={options}
      onSelect={({ id }) => onSelect(id)}
    >
      {({ toggle, selectedOption }) => (
        <TextButton
          skin="dark"
          suffixIcon={<Icons.ChevronDown />}
          onClick={toggle}
        >
          {selectedOption.value}
        </TextButton>
      )}
    </DropdownBase>
  );

  return (
    <Card>
      <Card.Header
        title="Article performance"
        suffix={
          <Box gap="SP2">
            {renderFilter(periods, period, setPeriod)}
            {renderFilter(regions, region, setRegion)}
          </Box>
        }
      />
      <Card.Divider />
      <Card.Content>
        <StatisticsWidget items={data[period][region]} />
      </Card.Content>
    </Card>
  );
};
```
