Search code examples
htmlcssangularcss-tables

How to correctly style sticky table header?


I have a little problem with style sticky header in my data table. I wrote simple Angular component and specific directive:

sticky.directive.ts

@Directive({
    selector: '[sticky]'
})
export class StickyDirective {

    constructor(private _element: ElementRef, private _window: WindowRef) {
        console.log('debug')
    }

    @HostListener('window:scroll', ['$event'])
    handleScrollEvent(e) {
        if (this._window.nativeWindow.pageYOffset > 100) {
            this._element.nativeElement.classList.add('stick');
        } else {
            this._element.nativeElement.classList.remove('stick');
        }
    }
}

The purpose of the directive is to add a class stick if user scroll below header. As a result, table header should be visible for user, even if he scroll long table. stick class look like that:

.stick {
    position: fixed;
    top: 55px;
} 

and part of my some.component.html (and use directive on thead element) look like:

<table class=" table table-bordered ">
 <thead sticky>
   <tr>
    <th width="40%">Name
    </th>
    <th width="10%">Priority
    </th>
    <th width="25%">Date created
    </th>
    <th width="25%">Date modified
    </th>   </tr>   </thead>   <tbody>   <tr *ngFor="let r of entitiesFiltered">
    <td>
      <div class="table-cell-flex">
        <div class="cell-content">
          {{r.name}}
        </div>
      </div>
    </td>
    <td>
      <div class="table-cell-flex">
        <div class="cell-content">
          {{r.priority}}
        </div>
      </div>
    </td>
...

My code meet basic functionality. It means that header stays in the same place during scroll page, but header width and columns width change. It's look like:enter image description here


Question:

Anyone can tell me how can I should style my table, that fixed header does not change form/shape table? Is it possible?


Solution

  • you get width any columns with javaScript then setting to header with px in position fixed or absolute, or with html and code:

    <div class="table-wrapper content">
      <!-- overall wrapper -->
      <table>
        <!-- header -->
        <thead>
          <tr>
            <th>Header 1</th>
            <th>Header 2</th>
            <th>Header 3</th>
          </tr>
        </thead>
      </table>
    </div>
    <div class="table-body-wrapper" style="position: relative; overflow: visible;">
      <!-- the element with the custom scrollbar -->
      <table>
        <!-- body -->
        <tbody>
          <!-- auto-generated data (see js function below) -->
          <tr>
            <td>Row 1, Column 1</td>
            <td>Row 1, Column 2</td>
            <td>Row 1, Column 3</td>
          </tr>
          <tr>
            <td>Row 2, Column 1</td>
            <td>Row 2, Column 2</td>
            <td>Row 2, Column 3</td>
          </tr>
          <tr>
            <td>Row 3, Column 1</td>
            <td>Row 3, Column 2</td>
            <td>Row 3, Column 3</td>
          </tr>
          <tr>
            <td>Row 4, Column 1</td>
            <td>Row 4, Column 2</td>
            <td>Row 4, Column 3</td>
          </tr>
          <tr>
            <td>Row 5, Column 1</td>
            <td>Row 5, Column 2</td>
            <td>Row 5, Column 3</td>
          </tr>
        </tbody>
      </table>
    </div>