Spacer

Negative area between the components and the interface.

Props

hspacing
Spacing
Horizontal spacing.
Defaults to none.
vspacing
Spacing
Vertical spacing
Defaults to none.
testId
string
Sets a data-testid attribute for automated testing.
Examples

Form stepper with controlled navigation

const [step, setStep] = useState(1);

  function setPage(page: number) {
    if (page < 1 || page > 4) return;
    setStep(page);
  }
<GoabFormStepper step={step} onChange={(event: GoabFormStepperOnChangeDetail) => setStep(event.step)}>
        <GoabFormStep text="Personal details" />
        <GoabFormStep text="Employment history" />
        <GoabFormStep text="References" />
        <GoabFormStep text="Review" />
      </GoabFormStepper>

      <GoabPages current={step} mb="3xl" mt="xl" mr="xl" ml="xl">
        <div>
          <GoabSkeleton type="article" />
        </div>
        <div>
          <GoabSkeleton type="header" size="2" />
          <GoabSkeleton type="text" />
          <GoabSkeleton type="header" size="2" />
          <GoabSkeleton type="text" />
        </div>
        <div>
          <GoabSkeleton type="text" />
          <GoabSpacer vSpacing="m" />
          <GoabSkeleton type="text" />
        </div>
        <div>
          <GoabSkeleton type="header" size="2" />
          <GoabSkeleton type="text" />
          <GoabSpacer vSpacing="m" />
          <GoabSkeleton type="text" />
        </div>
      </GoabPages>

      <div style={{ display: "flex", justifyContent: "space-between" }}>
        <GoabxButton type="secondary" onClick={() => setPage(step - 1)}>
          Previous
        </GoabxButton>
        <GoabxButton type="primary" onClick={() => setPage(step + 1)}>
          Next
        </GoabxButton>
      </div>
step = 1;

  updateStep(event: GoabFormStepperOnChangeDetail): void {
    this.step = event.step;
  }

  setPage(page: number): void {
    if (page < 1 || page > 4) return;
    this.step = page;
  }
<goab-form-stepper ml="s" mr="s" [step]="step" (onChange)="updateStep($event)">
  <goab-form-step text="Personal details"></goab-form-step>
  <goab-form-step text="Employment history"></goab-form-step>
  <goab-form-step text="References"></goab-form-step>
  <goab-form-step text="Review"></goab-form-step>
</goab-form-stepper>

<goab-pages [current]="step" mb="3xl" mt="xl" mr="xl" ml="xl">
  <div>
    <goab-skeleton type="article"></goab-skeleton>
  </div>
  <div>
    <goab-skeleton type="header" size="2"></goab-skeleton>
    <goab-skeleton type="text"></goab-skeleton>
    <goab-skeleton type="header" size="2"></goab-skeleton>
    <goab-skeleton type="text"></goab-skeleton>
  </div>
  <div>
    <goab-skeleton type="text"></goab-skeleton>
    <goab-spacer vSpacing="m"></goab-spacer>
    <goab-skeleton type="text"></goab-skeleton>
  </div>
  <div>
    <goab-skeleton type="header" size="2"></goab-skeleton>
    <goab-skeleton type="text"></goab-skeleton>
    <goab-spacer vSpacing="m"></goab-spacer>
    <goab-skeleton type="text"></goab-skeleton>
  </div>
</goab-pages>

<div style="display: flex; justify-content: space-between">
  <goabx-button (onClick)="setPage(step - 1)" type="secondary">Previous</goabx-button>
  <goabx-button (onClick)="setPage(step + 1)" type="primary">Next</goabx-button>
</div>
const formStepper = document.getElementById('form-stepper');
const formPages = document.getElementById('form-pages');
const prevBtn = document.getElementById('prev-btn');
const nextBtn = document.getElementById('next-btn');

let currentStep = 1;

function updateStep(step) {
  if (step < 1 || step > 4) return;
  currentStep = step;
  formStepper.setAttribute('step', currentStep);
  formPages.setAttribute('current', currentStep);
}

formStepper.addEventListener('_change', (e) => {
  updateStep(e.detail.step);
});

prevBtn.addEventListener('_click', () => {
  updateStep(currentStep - 1);
});

nextBtn.addEventListener('_click', () => {
  updateStep(currentStep + 1);
});
<goa-form-stepper id="form-stepper" ml="s" mr="s" step="1">
  <goa-form-step text="Personal details"></goa-form-step>
  <goa-form-step text="Employment history"></goa-form-step>
  <goa-form-step text="References"></goa-form-step>
  <goa-form-step text="Review"></goa-form-step>
</goa-form-stepper>

<goa-pages id="form-pages" current="1" mb="3xl" mt="xl" mr="xl" ml="xl">
  <div>
    <goa-skeleton type="article"></goa-skeleton>
  </div>
  <div>
    <goa-skeleton type="header" size="2"></goa-skeleton>
    <goa-skeleton type="text"></goa-skeleton>
    <goa-skeleton type="header" size="2"></goa-skeleton>
    <goa-skeleton type="text"></goa-skeleton>
  </div>
  <div>
    <goa-skeleton type="text"></goa-skeleton>
    <goa-spacer vspacing="m"></goa-spacer>
    <goa-skeleton type="text"></goa-skeleton>
  </div>
  <div>
    <goa-skeleton type="header" size="2"></goa-skeleton>
    <goa-skeleton type="text"></goa-skeleton>
    <goa-spacer vspacing="m"></goa-spacer>
    <goa-skeleton type="text"></goa-skeleton>
  </div>
</goa-pages>

<div style="display: flex; justify-content: space-between">
  <goa-button version="2" id="prev-btn" type="secondary">Previous</goa-button>
  <goa-button version="2" id="next-btn" type="primary">Next</goa-button>
</div>

Show number of results per page

interface User {
  id: string;
  firstName: string;
  lastName: string;
  age: number;
}

const [users, setUsers] = useState<User[]>([]);
  const [pageUsers, setPageUsers] = useState<User[]>([]);
  const [page, setPage] = useState<number>(1);
  const [perPage, setPerPage] = useState<number>(10);

  useEffect(() => {
    // Generate sample data
    const firstNames = ["Emma", "Liam", "Olivia", "Noah", "Ava", "James", "Sophia", "William", "Isabella", "Oliver", "Mia", "Benjamin", "Charlotte", "Elijah", "Amelia", "Lucas", "Harper", "Mason", "Evelyn", "Logan"];
    const lastNames = ["Smith", "Johnson", "Williams", "Brown", "Jones", "Garcia", "Miller", "Davis", "Rodriguez", "Martinez", "Wilson", "Anderson", "Taylor", "Thomas", "Moore", "Jackson", "Martin", "Lee", "Thompson", "White"];
    const _users: User[] = [];
    for (let i = 1; i <= 100; i++) {
      _users.push({
        id: `user-${i}`,
        firstName: firstNames[(i - 1) % firstNames.length],
        lastName: lastNames[(i - 1) % lastNames.length],
        age: 20 + (i % 40),
      });
    }
    setUsers(_users);
    setPageUsers(_users.slice(0, perPage));
  }, [perPage]);

  function changePage(newPage: number) {
    const offset = (newPage - 1) * perPage;
    const _users = users.slice(offset, offset + perPage);
    setPage(newPage);
    setPageUsers(_users);
  }

  function handlePerPageCountChangeEvent(event: GoabDropdownOnChangeDetail) {
    const perPageValue = parseInt(event.value || "10");
    setPage(1);
    setPerPage(perPageValue);
    const _users = users.slice(0, perPageValue);
    setPageUsers(_users);
  }
<GoabxTable width="100%" mb="xl">
        <thead>
          <tr>
            <th>First name</th>
            <th>Last name</th>
            <th>Age</th>
          </tr>
        </thead>
        <tbody>
          {pageUsers.map((u) => (
            <tr key={u.id}>
              <td>{u.firstName}</td>
              <td>{u.lastName}</td>
              <td>{u.age}</td>
            </tr>
          ))}
        </tbody>
      </GoabxTable>

      <GoabBlock alignment="center" width="100%">
        <GoabBlock mb="m" alignment="center">
          Show
          <GoabxDropdown
            onChange={handlePerPageCountChangeEvent}
            value={perPage.toString()}
            width="9ch"
          >
            <GoabxDropdownItem value="10" label="10" />
            <GoabxDropdownItem value="20" label="20" />
            <GoabxDropdownItem value="30" label="30" />
          </GoabxDropdown>
          <span style={{ width: "75px" }}>per page</span>
        </GoabBlock>
        <GoabSpacer hSpacing="fill" />
        <GoabxPagination
          itemCount={users.length}
          perPageCount={perPage}
          pageNumber={page}
          onChange={(event) => changePage(event.page)}
        />
      </GoabBlock>
users: User[] = [];
  pageUsers: User[] = [];
  page = 1;
  perPage = 10;
  total = 100;

  constructor() {
    this.pageUsers = this.prepareUsers().slice(0, this.perPage);
  }

  prepareUsers(): User[] {
    const firstNames = ["Emma", "Liam", "Olivia", "Noah", "Ava", "James", "Sophia", "William", "Isabella", "Oliver", "Mia", "Benjamin", "Charlotte", "Elijah", "Amelia", "Lucas", "Harper", "Mason", "Evelyn", "Logan"];
    const lastNames = ["Smith", "Johnson", "Williams", "Brown", "Jones", "Garcia", "Miller", "Davis", "Rodriguez", "Martinez", "Wilson", "Anderson", "Taylor", "Thomas", "Moore", "Jackson", "Martin", "Lee", "Thompson", "White"];
    for (let i = 1; i <= this.total; i++) {
      this.users.push({
        id: `user-${i}`,
        firstName: firstNames[(i - 1) % firstNames.length],
        lastName: lastNames[(i - 1) % lastNames.length],
        age: 20 + (i % 40),
      });
    }
    return this.users;
  }

  handlePageChange(event: GoabPaginationOnChangeDetail): void {
    this.page = event.page;
    const offset = (this.page - 1) * this.perPage;
    this.pageUsers = this.users.slice(offset, offset + this.perPage);
  }

  handlePerPageCountChangeEvent(event: GoabDropdownOnChangeDetail): void {
    this.page = 1;
    this.perPage = Number(event.value);
    this.pageUsers = this.users.slice(0, this.perPage);
  }
<goabx-table width="100%" mb="xl">
  <thead>
    <tr>
      <th>First name</th>
      <th>Last name</th>
      <th>Age</th>
    </tr>
  </thead>
  <tbody>
    @for (user of pageUsers; track $index) {
    <tr>
      <td>{{ user.firstName }}</td>
      <td>{{ user.lastName }}</td>
      <td>{{ user.age }}</td>
    </tr>
    }
  </tbody>
</goabx-table>

<goab-block alignment="center" width="100%">
  <goab-block mb="m" alignment="center">
    Show
    <goabx-dropdown
      (onChange)="handlePerPageCountChangeEvent($event)"
      value="10"
      width="9ch">
      <goabx-dropdown-item value="10" label="10"></goabx-dropdown-item>
      <goabx-dropdown-item value="20" label="20"></goabx-dropdown-item>
      <goabx-dropdown-item value="30" label="30"></goabx-dropdown-item>
    </goabx-dropdown>
    <span style="width: 75px">per page</span>
  </goab-block>

  <goab-spacer hSpacing="fill"></goab-spacer>

  <goabx-pagination
    [itemCount]="users.length"
    [perPageCount]="perPage"
    [pageNumber]="page"
    (onChange)="handlePageChange($event)">
  </goabx-pagination>
</goab-block>
const firstNames = ["Emma", "Liam", "Olivia", "Noah", "Ava", "James", "Sophia", "William", "Isabella", "Oliver", "Mia", "Benjamin", "Charlotte", "Elijah", "Amelia", "Lucas", "Harper", "Mason", "Evelyn", "Logan"];
const lastNames = ["Smith", "Johnson", "Williams", "Brown", "Jones", "Garcia", "Miller", "Davis", "Rodriguez", "Martinez", "Wilson", "Anderson", "Taylor", "Thomas", "Moore", "Jackson", "Martin", "Lee", "Thompson", "White"];
const users = [];
for (let i = 1; i <= 100; i++) {
  users.push({
    id: "user-" + i,
    firstName: firstNames[(i - 1) % firstNames.length],
    lastName: lastNames[(i - 1) % lastNames.length],
    age: 20 + (i % 40),
  });
}

let page = 1;
let perPage = 10;

const tableBody = document.getElementById("table-body");
const pagination = document.getElementById("pagination");
const dropdown = document.getElementById("per-page-dropdown");

function renderTable() {
  const offset = (page - 1) * perPage;
  const pageUsers = users.slice(offset, offset + perPage);

  tableBody.innerHTML = pageUsers
    .map(
      (u) => `
      <tr>
        <td>${u.firstName}</td>
        <td>${u.lastName}</td>
        <td>${u.age}</td>
      </tr>
    `
    )
    .join("");
}

pagination.addEventListener("_change", (e) => {
  page = e.detail.page;
  renderTable();
});

dropdown.addEventListener("_change", (e) => {
  perPage = parseInt(e.detail.value);
  page = 1;
  pagination.setAttribute("perpagecount", perPage);
  pagination.setAttribute("pagenumber", "1");
  renderTable();
});

renderTable();
<goa-table version="2" width="100%" mb="xl">
  <table width="100%">
    <thead>
      <tr>
        <th>First name</th>
        <th>Last name</th>
        <th>Age</th>
      </tr>
    </thead>
    <tbody id="table-body">
      <!-- Rows populated by JavaScript -->
    </tbody>
  </table>
</goa-table>

<goa-block alignment="center" width="100%">
  <goa-block mb="m" alignment="center">
    Show
    <goa-dropdown version="2" id="per-page-dropdown" value="10" width="9ch">
      <goa-dropdown-item value="10" label="10"></goa-dropdown-item>
      <goa-dropdown-item value="20" label="20"></goa-dropdown-item>
      <goa-dropdown-item value="30" label="30"></goa-dropdown-item>
    </goa-dropdown>
    <span style="width: 75px">per page</span>
  </goa-block>

  <goa-spacer hspacing="fill"></goa-spacer>

  <goa-pagination version="2"
    id="pagination"
    itemcount="100"
    perpagecount="10"
    pagenumber="1">
  </goa-pagination>
</goa-block>

No usage guidelines have been documented for this component yet.

All GoA Design System components are built to meet WCAG 2.2 AA standards. The following guidelines provide additional context for accessible implementation.

No accessibility-specific guidelines have been documented for this component yet.