사용자가 jQuery를 사용하여 볼 수 없을 때 맨 위에 고정 된 테이블 헤더


145

사용자가 볼 수 없을 때만 헤더를 페이지 상단에 유지할 HTML 테이블을 디자인하려고합니다. 예를 들어, 표가 페이지에서 500 픽셀 아래에있을 수 있습니다. 사용자가 헤더를 화면 밖으로 스크롤하면 (브라우저가 더 이상 창보기에서 더 이상 감지하지 않는 경우) 상단에 유지됩니다. ? 누구든지 이것에 대한 자바 스크립트 솔루션을 제공 할 수 있습니까?

<table>
  <thead>
    <tr>
      <th>Col1</th>
      <th>Col2</th>
      <th>Col3</th>
    </tr>
  </thead>
  <tbody>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
  </tbody>
</table>

위의 예 <thead>에서 페이지가 보이지 않으면 페이지와 함께 스크롤 하고 싶습니다 .

중요 : 스크롤 막대가 있는 솔루션을 찾고 있지 않습니다<tbody> (오버플로 : 자동).




나는 또 다른 질문에 이것에 대답했다. stackoverflow.com/a/56764334/9388978
Ersel Aktas

답변:


131

scroll이벤트 핸들러를 탭 하고 고정 된 위치의 window다른 것을 사용 table하여 페이지 상단에 헤더를 표시하면 이와 같은 작업을 수행 할 수 있습니다.

HTML :

<table id="header-fixed"></table>

CSS :

#header-fixed {
    position: fixed;
    top: 0px; display:none;
    background-color:white;
}

자바 스크립트 :

var tableOffset = $("#table-1").offset().top;
var $header = $("#table-1 > thead").clone();
var $fixedHeader = $("#header-fixed").append($header);

$(window).bind("scroll", function() {
    var offset = $(this).scrollTop();

    if (offset >= tableOffset && $fixedHeader.is(":hidden")) {
        $fixedHeader.show();
    }
    else if (offset < tableOffset) {
        $fixedHeader.hide();
    }
});

사용자가 원래 테이블 헤드를 숨길 수있을 정도로 아래로 스크롤하면 테이블 헤드가 표시됩니다. 사용자가 페이지를 다시 충분히 위로 스크롤하면 다시 숨겨집니다.

실례 : http://jsfiddle.net/andrewwhitaker/fj8wM/


60
나는 이것을 생각하고 있었지만 내용에 따라 헤더 열의 너비가 변경되면 어떻게됩니까? 열 너비가 고정되어 있지 않으면 머리글 행이 내용 행과 일치하지 않을 수 있습니다. 그냥 생각이야
이즈미르 라미레즈

16
이 예는 열 헤더 이름이 열 데이터 값보다 짧은 경우 작동하지 않습니다. 정보 대신 infoooooooo와 같은 값을 갖도록 바이올린을 변경하십시오. 테이블을 복제 할 때 설정되는 일종의 하드 코딩 된 너비를 생각하고 있습니다.
whiterook6

6
여기에는 주요 제한 사항이 있지만 그 이외의 다른 컨테이너에서 테이블을 사용하려고 할 때 가장 적습니다 window. mkoryak.github.io/floatThead 에는보다 일반적으로 적용 가능한 솔루션이 있습니다.
Yuck

13
폭 번째 동적을 필요로하는이 힘 도움말 사람, 내가 일을 감아 무엇, 그것은 @AndrewWhitaker의 포크입니다 : jsfiddle.net/noahkoch/wLcjh/1
노아 코흐

1
솔루션을 사용하는 @NoahKoch 고정 헤더는 원래 셀에 패딩이있을 때 원래 헤드만큼 넓지 않을 수 있습니다. 중복 셀에 패딩을 추가하도록 솔루션을 개선했습니다. JSFiddle의 포크 : jsfiddle.net/1n23m69u/2
fandasson

46

글쎄, 나는 고정 된 크기의 열에 의존하거나 전체 테이블의 고정 된 높이를 가지지 않고 동일한 효과를 얻으려고 노력했다.

내가 생각해 낸 해결책은 해킹입니다. 그것은 전체 테이블을 복제 한 다음 헤더를 제외한 모든 것을 숨기고 고정 된 위치로 만듭니다.

HTML

<div id="table-container">
<table id="maintable">
    <thead>
        <tr>
            <th>Col1</th>
            <th>Col2</th>
            <th>Col3</th>
        </tr>
    </thead>
    <tbody>
        <tr>
            <td>info</td>
            <td>info</td>
            <td>info</td>
        </tr>
        <tr>
            <td>info</td>
            <td>info</td>
            <td>info</td>
        </tr>
        <tr>
            <td>info</td>
            <td>some really long line here instead</td>
            <td>info</td>
        </tr>
        <tr>
            <td>info</td>
            <td>info</td>
            <td>info</td>
        </tr>
                <tr>
            <td>info</td>
            <td>info</td>
            <td>info</td>
        </tr>
                <tr>
            <td>info</td>
            <td>info</td>
            <td>info</td>
        </tr>
        <tr>
            <td>info</td>
            <td>info</td>
            <td>info</td>
        </tr>
    </tbody>
</table>
<div id="bottom_anchor"></div>
</div>

CSS

body { height: 1000px; }
thead{
    background-color:white;
}

자바 스크립트

function moveScroll(){
    var scroll = $(window).scrollTop();
    var anchor_top = $("#maintable").offset().top;
    var anchor_bottom = $("#bottom_anchor").offset().top;
    if (scroll>anchor_top && scroll<anchor_bottom) {
    clone_table = $("#clone");
    if(clone_table.length == 0){
        clone_table = $("#maintable").clone();
        clone_table.attr('id', 'clone');
        clone_table.css({position:'fixed',
                 'pointer-events': 'none',
                 top:0});
        clone_table.width($("#maintable").width());
        $("#table-container").append(clone_table);
        $("#clone").css({visibility:'hidden'});
        $("#clone thead").css({'visibility':'visible','pointer-events':'auto'});
    }
    } else {
    $("#clone").remove();
    }
}
$(window).scroll(moveScroll); 

여기를 보아라: http://jsfiddle.net/QHQGF/7/

편집 : thead가 포인터 이벤트를받을 수 있도록 코드를 업데이트했습니다 (따라서 헤더의 버튼과 링크는 여전히 작동합니다). 이것은 luhfluh와 Joe M이보고 한 문제를 해결합니다.

새로운 jsfiddle 여기 : http://jsfiddle.net/cjKEx/


3
먼저 시도해 보았습니다. 문제는 헤더의 요소 크기가 테이블의 내용에 달려 있다는 것입니다. 내용이 많은 행이 있으면 머리글을 포함한 전체 열이 커집니다. thead 만 복제하면 해당 정보가 손실되고 원하는 효과를 얻지 못합니다. 허용 된 답변에 대한 Yzmir Ramirez의 의견을 참조하십시오. 이것이 고정 너비 열없이 작동하는 유일한 방법입니다. 그것은 깨끗하지 않습니다, 나는 그것이 핵이라고 말한 방식입니다.
엔트로피

1
아, 알았어요 이 방법은 유동적 열에서 작동하기 때문에 훌륭합니다. 약간 봤지만 그 기능을 가진 다른 것을 찾을 수 없었습니다. Anywhay, 내가 어떻게 든 할 수 있다면, 여기에 언급하겠습니다
M2_

1
@ luhfluh, 예, 문제는 복제 된 테이블의 pointer-events : none 때문입니다. 클릭이 클론을 통해 원본 테이블로 이동하는 데 사용됩니다. 머리글 (및 머리글 만)을 클릭 할 수 있도록 복제 된 테이블의 머리글로 되 돌리면 문제가 해결됩니다. 나는 이것을 반영하기 위해 게시물을 업데이트했다 :)
entropy

4
<thead> <th>에 테두리 추가 문제
Jam Ville

1
@JamVille 복제 된 테이블이 있기 때문 visibility: hidden입니다. 당신은 숨길 수 #clone tbody있고 그 후에 국경을 설정할 수 있습니다 ... 작업 바이올린 : jsfiddle.net/QHQGF/1707
Lajdák Marek

46

순수 CSS (IE11 지원 없음) :

table th {
    position: -webkit-sticky; // this is for all Safari (Desktop & iOS), not for Chrome
    position: sticky;
    top: 0;
    z-index: 5;
    background: #fff;
}

1
Chrome에서도 작동하지 않습니다. 검사 도구가 -webkit-sticky에 대한 잘못된 값으로 표시 됩니다 position.
carmenism

@carmenism -webkit-sticky은 Chrome이 아닌 Safari (데스크탑 및 iOS) 용입니다. position: sticky: 두 규칙을 설정해야합니다 버전 56에서 크롬에서 작동 -webkit-sticky단지와 sticky내 코드 예제에서와 같은 순서로 정확하게. Safari는 webkit-sticky다른 모든 브라우저에서로 덮어 씁니다 sticky.
Ihor Zenich

2
나는 이것을 작동시키지 못했습니다. 빠른 Google에서는 position: sticky테이블 요소와 작동하지 않는 것 같습니다 .
rjh

3
일에 신청하는 것은 나를 위해 일했다 : table thead tr th {...}
nurp

1
당신은에 적용해야 할 때문에 것 THEAD도 TR에하지 작업
helado

26

나는 이것을하는 플러그인을 작성했다. 나는 약 1 년 동안이 작업을 해 왔으며 모든 코너 케이스를 잘 처리한다고 생각합니다.

  • 오버플로가있는 컨테이너 내에서 스크롤
  • 창 내에서 스크롤
  • 창의 크기를 조정할 때 발생하는 일을 처리
  • 이벤트를 헤더에 바인딩 유지
  • 가장 중요하게는 테이블의 CSS변경하여 작동하게하지 않습니다.

다음은 몇 가지 데모 / 문서입니다.
http://mkoryak.github.io/floatThead/


큰 노력을 기울이지 만 IE 10에서는 작동하지 않으며 firefox23 / ubuntu의 창 크기를 조정하는 데 약간의 문제가 있습니다.
Janning

2
참고 : 최신 버전의 IE9 및 10 문제를 해결했습니다.
mkoryak

2
jQuery가 필요없는 버전을 만들 수 있습니까?
Curtis W

2
아마도 그는 jquery를 사용하지 않기 때문에 ... 아니요-나는 jquery를 사용하지 않는 버전을 만들지 않을 것입니다.
mkoryak

1
간단한 jQery tableorter 플러그인을 사용하고 FAQ에 따르면 플러그인은 #sortable td {..}와 같은 대부분의 CSS 규칙을 좋아하지 않습니다. 조금 조정하려고했지만 작동하지 못했습니다.
masche

25

열 너비 변경과 관련된 문제를 해결할 수있었습니다. 위의 Andrew 솔루션을 시작하여 (감사합니다!) 작은 루프를 추가하여 복제 된 td의 너비를 설정했습니다.

$("#header-fixed td").each(function(index){
    var index2 = index;
    $(this).width(function(index2){
        return $("#table-1 td").eq(index).width();
    });
});

이렇게하면 전체 테이블을 복제하고 본문을 숨길 필요없이 문제를 해결합니다. JavaScript와 jQuery를 처음 접했고 오버플로가 많아서 의견을 보내주십시오.


4
잘 작동했지만 다음 줄을 추가해야했습니다 $ ( "# header-fixed"). width ($ ( "# table-1"). width ()); 열이 올바르게 정렬됩니다.
Ilya Fedotov

17

이것은 고정 테이블 헤더를 갖는 것으로 내가 찾은 최고의 솔루션입니다.

업데이트 5/11 : Kerry Johnson이 지적한 가로 스크롤 버그 수정

코드 펜 : https://codepen.io/josephting/pen/demELL

;(function($) {
   $.fn.fixMe = function() {
      return this.each(function() {
         var $this = $(this),
            $t_fixed;
         function init() {
            $this.wrap('<div class="container" />');
            $t_fixed = $this.clone();
            $t_fixed.find("tbody").remove().end().addClass("fixed").insertBefore($this);
            resizeFixed();
         }
         function resizeFixed() {
           $t_fixed.width($this.outerWidth());
            $t_fixed.find("th").each(function(index) {
               $(this).css("width",$this.find("th").eq(index).outerWidth()+"px");
            });
         }
         function scrollFixed() {
            var offsetY = $(this).scrollTop(),
            offsetX = $(this).scrollLeft(),
            tableOffsetTop = $this.offset().top,
            tableOffsetBottom = tableOffsetTop + $this.height() - $this.find("thead").height(),
            tableOffsetLeft = $this.offset().left;
            if(offsetY < tableOffsetTop || offsetY > tableOffsetBottom)
               $t_fixed.hide();
            else if(offsetY >= tableOffsetTop && offsetY <= tableOffsetBottom && $t_fixed.is(":hidden"))
               $t_fixed.show();
            $t_fixed.css("left", tableOffsetLeft - offsetX + "px");
         }
         $(window).resize(resizeFixed);
         $(window).scroll(scrollFixed);
         init();
      });
   };
})(jQuery);

$(document).ready(function(){
   $("table").fixMe();
   $(".up").click(function() {
      $('html, body').animate({
      scrollTop: 0
   }, 2000);
 });
});
body{
  font:1.2em normal Arial,sans-serif;
  color:#34495E;
}

h1{
  text-align:center;
  text-transform:uppercase;
  letter-spacing:-2px;
  font-size:2.5em;
  margin:20px 0;
}

.container{
  width:90%;
  margin:auto;
}

table{
  border-collapse:collapse;
  width:100%;
}

.blue{
  border:2px solid #1ABC9C;
}

.blue thead{
  background:#1ABC9C;
}

.purple{
  border:2px solid #9B59B6;
}

.purple thead{
  background:#9B59B6;
}

thead{
  color:white;
}

th,td{
  text-align:center;
  padding:5px 0;
}

tbody tr:nth-child(even){
  background:#ECF0F1;
}

tbody tr:hover{
background:#BDC3C7;
  color:#FFFFFF;
}

.fixed{
  top:0;
  position:fixed;
  width:auto;
  display:none;
  border:none;
}

.scrollMore{
  margin-top:600px;
}

.up{
  cursor:pointer;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<h1>&darr; SCROLL &darr;</h1>
<table class="blue">
  <thead>
    <tr>
      <th>Colonne 1</th>
      <th>Colonne 2</th>
      <th>Colonne 3</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Non</td>
      <td>MaisMaisMaisMaisMaisMaisMaisMaisMaisMaisMaisMaisMaisMaisMaisMaisMaisMaisMaisMais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
       <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
  </tbody>
</table>

<h1 class="scrollMore">&darr; SCROLL MORE &darr;</h1>
<table class="purple">
  <thead>
    <tr>
      <th>Colonne 1</th>
      <th>Colonne 2</th>
      <th>Colonne 3</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
       <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
    <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
       <tr>
      <td>Non</td>
      <td>Mais</td>
      <td>Allo !</td>
    </tr>
  </tbody>
</table>
<h1 class="up scrollMore">&uarr; UP &uarr;</h1>


테두리와 패딩이있는 <th> 요소를 처리 할 수 ​​있도록이 스크립트를 수정했습니다 (그렇지 않으면 고정 헤더 <th> 너비를 너무 넓게 설정합니다). 단순히 변경 outerWidthwidthresizeFixed () 함수의 정의에.
alanng

스크롤 할 때 테이블에서 페이지로드 후 렌더링 된 객체가 고정 된 헤더 위에 떠 다니지 않도록 클래스의 z-index일부 양수에 CSS 속성을 추가해야 할 수도 있습니다 .fixed.
alanng

간단하고 유용합니다.
RitchieD 2016

상단 위치를 동적으로 처리하는 방법 기본 페이지 고정 헤더 내용 아래로 스크롤해야한다고 가정 해 봅시다. .fixed {top : 0;} .
VijayVishnu

2
@KerryJohnson 감사합니다. 가로 스크롤 및 동적 열 너비를 지원하도록 변경했습니다.
josephting

7

가장 좋은 해결책은이 jquery 플러그인을 사용하는 것입니다.

https://github.com/jmosbech/StickyTableHeaders

이 플러그인은 우리에게 훌륭하게 작동했으며 다른 많은 솔루션을 시도했습니다. 우리는 IE, Chrome 및 Firefox에서 테스트했습니다.


헤더에서 녹아웃 데이터 바운드 컨트롤의 기능을 유지하는 솔루션을 알고 있습니까?
Csaba Toth

나를 위해 작동하지 않았습니다 : 헤더가 테이블 외부에 있고 옵션 "scrollableArea"를 사용하더라도 브라우저 상단 (창)에 붙어 있습니다. 나는 이것이 추가적인 언급없이 전에 언급 된 것을 보았다. 어쩌면 그가 사용하는 CSS가 필요할 수도 있고 작동하지 않을 수도 있습니다.
Exel Gamboa

6

여기에 정말 좋은 해결책이 많이 있습니다. 그러나 이러한 상황에서 사용하는 가장 간단한 CSS 전용 솔루션 중 하나는 다음과 같습니다.

table {
  /* Not required only for visualizing */
  border-collapse: collapse;
  width: 100%;
}

table thead tr th {
  /* Important */
  background-color: red;
  position: sticky;
  z-index: 100;
  top: 0;
}

td {
  /* Not required only for visualizing */
  padding: 1em;
}
<table>
  <thead>
    <tr>
      <th>Col1</th>
      <th>Col2</th>
      <th>Col3</th>
    </tr>
  </thead>
  <tbody>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
  </tbody>
</table>

JavaScript가 필요하지 않기 때문에 상황을 크게 단순화합니다. 본질적으로 두 번째 CSS 규칙 에 중점을 두어야합니다. 여기에는 스크롤 공간에 관계없이 테이블 헤드가 맨 위에 유지되도록하는 조건이 포함됩니다.

각 규칙에 대해 자세히 설명합니다. position는 헤드 오브젝트, 행 및 셀이 모두 맨 위에 붙어 있어야 함을 브라우저에 표시하기위한 것입니다. 이 경우 반드시 top머리글이 페이지 또는 뷰포트 상단에 고정되도록 브라우저에 지정해야합니다. 또한 z-index헤드의 내용이 항상 맨 위에 유지되도록 추가 할 수 있습니다 .

배경색은 단지 요점을 설명하기위한 것입니다. 이 효과를 얻기 위해 추가 JavaScript를 사용할 필요가 없습니다. 2016 년 이후 대부분의 주요 브라우저에서 지원됩니다.


1
가장 간단하고 깨끗한 답변, 항상 하나의 문제를 해결하는 간단한 방법이 있습니다. angularjs와 함께 ng-repeat를 사용하고 있지만 매력처럼 작동합니다.
David Castro



3

이 접근법을 사용할 수 있습니다. 순수한 HTML 및 CSS는 JS가 필요하지 않습니다. :)

.table-fixed-header {
  display: flex;
  justify-content: space-between;
  margin-right: 18px
}

.table-fixed {
  display: flex;
  justify-content: space-between;
  height: 150px;
  overflow: scroll;
}

.column {
  flex-basis: 24%;
  border-radius: 5px;
  padding: 5px;
  text-align: center;
}
.column .title {
  border-bottom: 2px grey solid;
  border-top: 2px grey solid;
  text-align: center;
  display: block;
  font-weight: bold;
}

.cell {
  padding: 5px;
  border-right: 1px solid;
  border-left: 1px solid;
}

.cell:nth-of-type(even) {
  background-color: lightgrey;
}
<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width">
  <title>Fixed header Bin</title>
</head>
<body>
<div class="table-fixed-header">
    
    <div class="column">
      <span class="title">col 1</span>
    </div>
    <div class="column">
      <span class="title">col 2</span>
    </div>
    <div class="column">
      <span class="title">col 3</span>
    </div>
    <div class="column">
      <span class="title">col 4</span>
    </div>
    
  </div>
  
  <div class="table-fixed">
    
    <div class="column">
      <div class="cell">alpha</div>
      <div class="cell">beta</div>
      <div class="cell">ceta</div>
    </div>
    
    <div class="column">
      <div class="cell">alpha</div>
      <div class="cell">beta</div>
      <div class="cell">ceta</div>
      <div class="cell">alpha</div>
      <div class="cell">beta</div>
      <div class="cell">ceta</div>
      <div class="cell">alpha</div>
      <div class="cell">beta</div>
      <div class="cell">ceta</div>
    </div>
    
    <div class="column">
      <div class="cell">alpha</div>
      <div class="cell">beta</div>
      <div class="cell">ceta</div>
      <div class="cell">beta</div>
      <div class="cell">beta</div>
      <div class="cell">beta</div>
      
    </div>
    
    <div class="column">
      <div class="cell">alpha</div>
      <div class="cell">beta</div>
      <div class="cell">ceta</div>
    </div>
    
  </div>
</body>
</html>


3

JQuery 를 사용 하지 않고 CSS 만 사용하는 간단한 솔루션을 찾았습니다 .

고정 된 내용을 'th'태그 안에 넣고 CSS를 추가해야합니다

table th {
    position:sticky;
    top:0;
    z-index:1;
    border-top:0;
    background: #ededed;
}
   

위치, z- 색인 및 상단 속성으로 충분합니다. 그러나 나머지를 적용하여 더 잘 볼 수 있습니다.


2

나는 또한 엔트로피의 코드를 사용하여 테두리 형식이 표시되지 않는 것과 같은 문제를 겪었지만 몇 가지 작은 수정 사항이 있었으며 이제 테이블을 확장 할 수 있으며 추가 할 수있는 모든 CSS 스타일 규칙을 표시합니다.

CSS에 추가 :

#maintable{width: 100%}    

다음은 새로운 자바 스크립트입니다.

    function moveScroll(){
    var scroll = $(window).scrollTop();
    var anchor_top = $("#maintable").offset().top;
    var anchor_bottom = $("#bottom_anchor").offset().top;
    if (scroll > anchor_top && scroll < anchor_bottom) {
        clone_table = $("#clone");
        if(clone_table.length === 0) {          
            clone_table = $("#maintable").clone();
            clone_table.attr({id: "clone"})
            .css({
                position: "fixed",
                "pointer-events": "none",
                 top:0
            })
            .width($("#maintable").width());

            $("#table-container").append(clone_table);
            // dont hide the whole table or you lose border style & 
            // actively match the inline width to the #maintable width if the 
            // container holding the table (window, iframe, div) changes width          
            $("#clone").width($("#maintable").width());
            // only the clone thead remains visible
            $("#clone thead").css({
                visibility:"visible"
            });
            // clone tbody is hidden
            $("#clone tbody").css({
                visibility:"hidden"
            });
            // add support for a tfoot element
            // and hide its cloned version too
            var footEl = $("#clone tfoot");
            if(footEl.length){
                footEl.css({
                    visibility:"hidden"
                });
            }
        }
    } 
    else {
        $("#clone").remove();
    }
}
$(window).scroll(moveScroll);

이것은 테두리 형식이 헤더에 들어가는 한 엔트로피 솔루션보다 효과적입니다. 그러나 현재 Firefox (Chrome 제외)에서는 스크롤이 시작되면 표 아래에 셀 경계 아티팩트가 표시됩니다.
alanng

2

다음은 허용되는 답변을 기반으로하는 솔루션입니다. 열 너비, 일치하는 테이블 스타일 및 테이블이 컨테이너 div에서 스크롤되는 경우를 수정합니다.

용법

광고 <thead>내용 만 수정되므로 테이블에 태그 가 있는지 확인하십시오 .

$("#header-fixed").fixHeader();

JavaSript

//Custom JQuery Plugin
(function ($) {
    $.fn.fixHeader = function () {
        return this.each(function () {
            var $table = $(this);
            var $sp = $table.scrollParent();
            var tableOffset = $table.position().top;
            var $tableFixed = $("<table />")
                .prop('class', $table.prop('class'))
                .css({ position: "fixed", "table-layout": "fixed", display: "none", "margin-top": "0px" });
            $table.before($tableFixed);
            $tableFixed.append($table.find("thead").clone());

            $sp.bind("scroll", function () {
                var offset = $(this).scrollTop();

                if (offset > tableOffset && $tableFixed.is(":hidden")) {
                    $tableFixed.show();
                    var p = $table.position();
                    var offset = $sp.offset();

                    //Set the left and width to match the source table and the top to match the scroll parent
                    $tableFixed.css({ left: p.left + "px", top: (offset ? offset.top : 0) + "px", }).width($table.width());

                    //Set the width of each column to match the source table
                    $.each($table.find('th, td'), function (i, th) {
                        $($tableFixed.find('th, td')[i]).width($(th).width());
                    });

                }
                else if (offset <= tableOffset && !$tableFixed.is(":hidden")) {
                    $tableFixed.hide();
                }
            });
        });
    };
})(jQuery);

1
이것은 나를 위해 잘 작동했습니다. 가로로 스크롤 해야하는 테이블의 문제 만입니다. 나는 여기에 JSFiddle에 업데이 트를했습니다 jsfiddle.net/4mgneob1/1 내가 빼기 $sp.scrollLeft()올바른 위치에 고정 테이블을 아래로 스크롤 할 때 너무 왼쪽에서 스크롤 양을 얻을 수있다. 왼쪽 테이블을 조정하기 위해 고정 테이블이 보이는 경우 가로로 스크롤 할 때 검사를 추가했습니다. 내가 해결할 수 없었던 또 다른 문제는 테이블이 뷰포트 위로 올라가면 고정 테이블이 사용자가 다시 스크롤 할 때까지 숨겨야한다는 것입니다.
Henesnarfel

1
점점Uncaught TypeError: $table.scrollParent is not a function
karlingen

1

이렇게하면 데이터와 함께 가로로 스크롤 할 수있는 고정 된 헤더를 가질 수 있습니다.

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Shubh</title>



<script type="text/javascript">
    var lastSeen = [ 0, 0 ];
    function checkScroll(div1, div2) {
        if (!div1 || !div2)
            return;
        var control = null;
        if (div1.scrollLeft != lastSeen[0])
            control = div1;
        else if (div2.scrollLeft != lastSeen[1])
            control = div2;
        if (control == null)
            return;
        else
            div1.scrollLeft = div2.scrollLeft = control.scrollLeft;
        lastSeen[0] = div1.scrollLeft;
        lastSeen[1] = div2.scrollLeft;
    }

    window
            .setInterval(
                    "checkScroll(document.getElementById('innertablediv'), document.getElementById('headertable'))",
                    1);
</script>

<style type="text/css">
#full {
    width: 400px;
    height: 300px;
}

#innertablediv {
    height: 200px;
    overflow: auto;
}

#headertable {
    overflow: hidden;
}
</style>
</head>
<body>

    <div id="full">




        <div id="headertable">
            <table border="1" bgcolor="grey" width="150px" id="headertable">
                <tr>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>

                    <td>&nbsp;&nbsp;&nbsp;</td>
                </tr>

            </table>
        </div>




        <div id="innertablediv">

            <table border="1" id="innertableid">
                <tr>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                </tr>
                <tr>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                </tr>
                <tr>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                </tr>
                <tr>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                </tr>
                <tr>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                </tr>
                <tr>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                </tr>
                <tr>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                </tr>
                <tr>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                </tr>
                <tr>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                    <td>shubh, ansh</td>
                </tr>

            </table>
        </div>
    </div>
</body>
</html>

이렇게하면 데이터와 함께 가로로 스크롤 할 수있는 고정 된 헤더를 가질 수 있습니다.
user2669926

1
function fix_table_header_position(){
 var width_list = [];
 $("th").each(function(){
    width_list.push($(this).width());
 });
 $("tr:first").css("position", "absolute");
 $("tr:first").css("z-index", "1000");
 $("th, td").each(function(index){
    $(this).width(width_list[index]);
 });

 $("tr:first").after("<tr height=" + $("tr:first").height() + "></tr>");}

이것은 나의 해결책이다


1

파티에 약간 늦었지만 여기에 동일한 페이지의 여러 테이블에서 작동하고 "jank"를 사용하지 않는 (requestAnimationFrame 사용) 구현이 있습니다. 또한 열에 너비를 제공 할 필요가 없습니다. 가로 스크롤도 작동합니다.

헤더는에 정의되어 div있으므로 필요한 경우 버튼과 같은 마크 업을 자유롭게 추가 할 수 있습니다. 이것이 필요한 모든 HTML입니다.

<div class="tbl-resp">
  <table id="tbl1" class="tbl-resp__tbl">
     <thead>
      <tr>
        <th>col 1</th>
        <th>col 2</th>
        <th>col 3</th>
      </tr>
    </thead> 
  </table>
</div>

https://jsfiddle.net/lloydleo/bk5pt5gs/


1

이 솔루션에서는 고정 헤더가 동적으로 작성되고 컨텐츠와 스타일이 THEAD에서 복제됩니다.

예를 들어 두 줄만 있으면됩니다.

var $myfixedHeader = $("#Ttodo").FixedHeader(); //create fixed header $(window).scroll($myfixedHeader.moveScroll); //bind function to scroll event

내 jquery 플러그인 FixedHeader 및 getStyleObject 아래에 제공되어 .js 파일에 넣을 수 있습니다

// JAVASCRIPT



/*
 * getStyleObject Plugin for jQuery JavaScript Library
 * From: http://upshots.org/?p=112
 
Basic usage:
$.fn.copyCSS = function(source){
  var styles = $(source).getStyleObject();
  this.css(styles);
}
*/

(function($){
    $.fn.getStyleObject = function(){
        var dom = this.get(0);
        var style;
        var returns = {};
        if(window.getComputedStyle){
            var camelize = function(a,b){
                return b.toUpperCase();
            };
            style = window.getComputedStyle(dom, null);
            for(var i = 0, l = style.length; i < l; i++){
                var prop = style[i];
                var camel = prop.replace(/\-([a-z])/g, camelize);
                var val = style.getPropertyValue(prop);
                returns[camel] = val;
            };
            return returns;
        };
        if(style = dom.currentStyle){
            for(var prop in style){
                returns[prop] = style[prop];
            };
            return returns;
        };
        return this.css();
    }
})(jQuery);



   
//Floating Header of long table  PiotrC
(function ( $ ) {
    var tableTop,tableBottom,ClnH;
    $.fn.FixedHeader = function(){
        tableTop=this.offset().top,
        tableBottom=this.outerHeight()+tableTop;
        //Add Fixed header
        this.after('<table id="fixH"></table>');
        //Clone Header
        ClnH=$("#fixH").html(this.find("thead").clone());
        //set style
        ClnH.css({'position':'fixed', 'top':'0', 'zIndex':'60', 'display':'none',
        'border-collapse': this.css('border-collapse'),
		'border-spacing': this.css('border-spacing'),
        'margin-left': this.css('margin-left'),
        'width': this.css('width')            
        });
        //rewrite style cell of header
        $.each(this.find("thead>tr>th"), function(ind,val){
            $(ClnH.find('tr>th')[ind]).css($(val).getStyleObject());
        });
    return ClnH;}
    
    $.fn.moveScroll=function(){
        var offset = $(window).scrollTop();
        if (offset > tableTop && offset<tableBottom){
            if(ClnH.is(":hidden"))ClnH.show();
            $("#fixH").css('margin-left',"-"+$(window).scrollLeft()+"px");
        }
        else if (offset < tableTop || offset>tableBottom){
            if(!ClnH.is(':hidden'))ClnH.hide();
        }
    };
})( jQuery );





var $myfixedHeader = $("#repTb").FixedHeader();
$(window).scroll($myfixedHeader.moveScroll);
/* CSS - important only NOT transparent background */

#repTB{border-collapse: separate;border-spacing: 0;}

#repTb thead,#fixH thead{background: #e0e0e0 linear-gradient(#d8d8d8 0%, #e0e0e0 25%, #e0e0e0 75%, #d8d8d8 100%) repeat scroll 0 0;border:1px solid #CCCCCC;}

#repTb td{border:1px solid black}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>


<h3>example</h3> 
<table id="repTb">
<thead>
<tr><th>Col1</th><th>Column2</th><th>Description</th></tr>
</thead>
<tr><td>info</td><td>info</td><td>info</td></tr>
<tr><td>info</td><td>info</td><td>info</td></tr>
<tr><td>info</td><td>info</td><td>info</td></tr>
<tr><td>info</td><td>info</td><td>info</td></tr>
<tr><td>info</td><td>info</td><td>info</td></tr>
<tr><td>info</td><td>info</td><td>info</td></tr>
<tr><td>info</td><td>info</td><td>info</td></tr>
<tr><td>info</td><td>info</td><td>info</td></tr>
<tr><td>info</td><td>info</td><td>info</td></tr>
<tr><td>info</td><td>info</td><td>info</td></tr>
<tr><td>info</td><td>info</td><td>info</td></tr>
</table>


1

기본 테이블과 동일한 헤더로 추가 테이블을 작성하십시오. 하나의 행과 모든 헤더가있는 새 테이블에 thead를 넣으십시오. 절대 및 배경을 흰색으로 배치하십시오. 메인 테이블의 경우 div에 넣고 높이와 overflow-y 스크롤을 사용하십시오. 이런 식으로 우리의 새로운 테이블은 메인 테이블의 헤더를 극복하고 거기에 머물 것입니다. div로 모든 것을 둘러싸십시오. 아래는 대략적인 코드입니다.

      <div class="col-sm-8">

        <table id="header-fixed" class="table table-bordered table-hover" style="width: 351px;position: absolute;background: white;">
        <thead>
        <tr>
            <th>Col1</th>
            <th>Col2</th>
            <th>Col3</th>
        </tr>
    </thead>
      </table>


    <div style="height: 300px;overflow-y: scroll;">
          <table id="tableMain" class="table table-bordered table-hover" style="table-layout:fixed;overflow-wrap: break-word;cursor:pointer">
<thead>
    <tr>
      <th>Col1</th>
      <th>Col2</th>
      <th>Col3</th>
    </tr>
  </thead>
  <tbody>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
     <tr>
       <td>info</td>
       <td>info</td>
       <td>info</td>
     </tr>
  </tbody>

                                    </table>
              </div>
        </div>

1

div.wrapper {
    padding:20px;
}
table.scroll thead {
    width: 100%;
    background: #FC6822;
}
table.scroll thead tr:after {
    content: '';
    overflow-y: scroll;
    visibility: hidden;
}
table.scroll thead th {
    flex: 1 auto;
    display: block;
    color: #fff;
}
table.scroll tbody {
    display: block;
    width: 100%;
    overflow-y: auto;
    height: auto;
    max-height: 200px;
}
table.scroll thead tr,
table.scroll tbody tr {
    display: flex;
}
table.scroll tbody tr td {
    flex: 1 auto;
    word-wrap: break;
}
table.scroll thead tr th,
table.scroll tbody tr td {
    width: 25%;
    padding: 5px;
    text-align-left;
    border-bottom: 1px solid rgba(0,0,0,0.3);
}
<div class="wrapper">
    <table border="0" cellpadding="0" cellspacing="0" class="scroll">
        <thead>
            <tr>
                <th>Name</th>
                <th>Vorname</th>
                <th>Beruf</th>
                <th>Alter</th>
            </tr>
        </thead>
        <tbody>
            <tr>
                <td>Müller</td>
                <td>Marie</td>
                <td>Künstlerin</td>
                <td>26</td>
            </tr>
            <tr>
                <td>Meier</td>
                <td>Stefan</td>
                <td>Chemiker</td>
                <td>52</td>
            </tr>
            <tr>
                <td>Schmidt</td>
                <td>Sabrine</td>
                <td>Studentin</td>
                <td>38</td>
            </tr>
            <tr>
                <td>Mustermann</td>
                <td>Max</td>
                <td>Lehrer</td>
                <td>41</td>
            </tr>
            <tr>
                <td>Müller</td>
                <td>Marie</td>
                <td>Künstlerin</td>
                <td>26</td>
            </tr>
            <tr>
                <td>Meier</td>
                <td>Stefan</td>
                <td>Chemiker</td>
                <td>52</td>
            </tr>
            <tr>
                <td>Schmidt</td>
                <td>Sabrine</td>
                <td>Studentin</td>
                <td>38</td>
            </tr>
            <tr>
                <td>Mustermann</td>
                <td>Max</td>
                <td>Lehrer</td>
                <td>41</td>
            </tr>
            <tr>
                <td>Müller</td>
                <td>Marie</td>
                <td>Künstlerin</td>
                <td>26</td>
            </tr>
            <tr>
                <td>Meier</td>
                <td>Stefan</td>
                <td>Chemiker</td>
                <td>52</td>
            </tr>
            <tr>
                <td>Schmidt</td>
                <td>Sabrine</td>
                <td>Studentin</td>
                <td>38</td>
            </tr>
            <tr>
                <td>Mustermann</td>
                <td>Max</td>
                <td>Lehrer</td>
                <td>41</td>
            </tr>
        </tbody>
    </table>
</div>

데모 : CSS 고정 테이블 헤더 데모


1

이것으로 문제를 해결하십시오

tbody {
  display: table-caption;
  height: 200px;
  caption-side: bottom;
  overflow: auto;
}

0

스타일 속성 변환을 사용하면됩니다. 고정 높이와 오버플로가 자동으로 설정된 div에 테이블을 래핑하면됩니다.

.tableWrapper {
  overflow: auto;
  height: calc( 100% - 10rem );
}

그런 다음 onscroll 핸들러를 첨부 할 수 있습니다. 여기에 다음과 <div class="tableWrapper"></div>같이 포장 된 각 테이블을 찾는 메소드가 있습니다 .

  fixTables () {
    document.querySelectorAll('.tableWrapper').forEach((tableWrapper) => {
      tableWrapper.addEventListener('scroll', () => {
        var translate = 'translate(0,' + tableWrapper.scrollTop + 'px)'
        tableWrapper.querySelector('thead').style.transform = translate
      })
    })
  }

그리고 여기에 행동이의 예를하고있다 (나는 그것을 예뻐하는 데 사용 부트 스트랩이) : 바이올린

IE와 Edge도 지원하고자하는 사람들을위한 스 니펫은 다음과 같습니다.

  fixTables () {
    const tableWrappers = document.querySelectorAll('.tableWrapper')
    for (let i = 0, len = tableWrappers.length; i < len; i++) {
      tableWrappers[i].addEventListener('scroll', () => {
        const translate = 'translate(0,' + tableWrappers[i].scrollTop + 'px)'
        const headers = tableWrappers[i].querySelectorAll('thead th')
        for (let i = 0, len = headers.length; i < len; i++) {
          headers[i].style.transform = translate
        }
      })
    }
  }

IE와 Edge에서 스크롤이 약간 느리지 만 작동합니다.

다음 날이를 찾는 데 도움이 대답은 : 대답


0

나는 이러한 솔루션의 대부분을 시도했으며 결국 (IMO) 최고의 현대적 솔루션을 발견했습니다.

CSS 그리드


CSS 그리드를 사용하면 '그리드'를 정의 할 수 있으며, 최종적으로 고정 된 헤더 및 스크롤 가능한 컨텐츠가있는 테이블에 대한 멋진 자바 스크립트가없는 크로스 브라우저 솔루션을 만들 수 있습니다. 헤더 높이는 동적 일 수도 있습니다.

CSS : 그리드로 표시하고 수를 설정합니다 template-rows.

.grid {
    display: grid;
    grid-template-rows: 50px auto; // For fixed height header
    grid-template-rows: auto auto; // For dynamic height header
}

HTML : 그리드 컨테이너와 정의 된 수를 만듭니다 rows.

<div class="grid">
    <div></div>
    <div></div>
</div>

다음은 실제 예입니다.

CSS

body {
  margin: 0px;
  padding: 0px;
  text-align: center;
}

.table {
  width: 100%;
  height: 100%;
  display: grid;
  grid-template-rows: 50px auto;
}
.table-heading {
  background-color: #ddd;
}
.table-content {
  overflow-x: hidden;
  overflow-y: scroll;
}

HTML

<html>
    <head>
    </head>
    <body>
        <div class="table">
            <div class="table-heading">
                HEADING
            </div>
            <div class="table-content">
                CONTENT - CONTENT - CONTENT <br/>
                CONTENT - CONTENT - CONTENT <br/>
                CONTENT - CONTENT - CONTENT <br/>
                CONTENT - CONTENT - CONTENT <br/>
                CONTENT - CONTENT - CONTENT <br/>
                CONTENT - CONTENT - CONTENT <br/>
            </div>
        </div>
    </body>
</html>

0

transformation : translate 사용하여 시도했습니다 . Firefox 및 Chrome에서 잘 작동하지만 IE11에는 기능이 없습니다. 이중 스크롤 막대가 없습니다. 테이블 풋 및 캡션을 지원합니다. 순수한 자바 스크립트, jQuery 없음.

http://jsfiddle.net/wbLqzrfb/42/

thead.style.transform="translate(0,"+(dY-top-1)+"px)";

0

jquery없이 솔루션을 찾았습니다.

HTML

<table class="fixed_header">
  <thead>
    <tr>
      <th>Col 1</th>
      <th>Col 2</th>
      <th>Col 3</th>
      <th>Col 4</th>
      <th>Col 5</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>row 1-0</td>
      <td>row 1-1</td>
      <td>row 1-2</td>
      <td>row 1-3</td>
      <td>row 1-4</td>
    </tr>
    <tr>
      <td>row 2-0</td>
      <td>row 2-1</td>
      <td>row 2-2</td>
      <td>row 2-3</td>
      <td>row 2-4</td>
    </tr>
    <tr>
      <td>row 3-0</td>
      <td>row 3-1</td>
      <td>row 3-2</td>
      <td>row 3-3</td>
      <td>row 3-4</td>
    </tr>
    <tr>
      <td>row 4-0</td>
      <td>row 4-1</td>
      <td>row 4-2</td>
      <td>row 4-3</td>
      <td>row 4-4</td>
    </tr>
    <tr>
      <td>row 5-0</td>
      <td>row 5-1</td>
      <td>row 5-2</td>
      <td>row 5-3</td>
      <td>row 5-4</td>
    </tr>
    <tr>
      <td>row 6-0</td>
      <td>row 6-1</td>
      <td>row 6-2</td>
      <td>row 6-3</td>
      <td>row 6-4</td>
    </tr>
    <tr>
      <td>row 7-0</td>
      <td>row 7-1</td>
      <td>row 7-2</td>
      <td>row 7-3</td>
      <td>row 7-4</td>
    </tr>
  </tbody>
</table>

CSS

.fixed_header{
    width: 400px;
    table-layout: fixed;
    border-collapse: collapse;
}

.fixed_header tbody{
  display:block;
  width: 100%;
  overflow: auto;
  height: 100px;
}

.fixed_header thead tr {
   display: block;
}

.fixed_header thead {
  background: black;
  color:#fff;
}

.fixed_header th, .fixed_header td {
  padding: 5px;
  text-align: left;
  width: 200px;
}

https://jsfiddle.net/lexsoul/fqbsty3h에서 작동하는 것을 볼 수 있습니다.

출처 : https://medium.com/@vembarrajan/html-css-tricks-scroll-able-table-body-tbody-d23182ae0fbc

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.