Büyük bir HTML tablosu yazdırırken sayfa sonlarıyla nasıl başa çıkılır?


261

Birçok satır içeren bir HTML tablosu yazdırmayı gerektiren bir proje var.

Benim sorunum tablonun birden fazla sayfaya yazdırılma şeklidir. Bazen bir satırı ikiye böler, bu da okunamaz hale gelir, çünkü yarısı bir sayfanın kanayan kenarında ve geri kalanı bir sonraki sayfanın üstüne yazdırılır.

Aklıma gelen tek mantıklı çözüm, bir tablo yerine yığılmış DIV'leri kullanmak ve gerekirse sayfa sonlarını zorlamaktır ... ancak tüm değişikliği yapmadan önce daha önce burada sorabileceğimi düşündüm.


28
Bir tanjantta, tablo başlığını sonraki tüm sayfalara yazdırmak için tablonuza <thead>aşağıdaki css ile a eklemeye değer olabilir thead {display: table-header-group; }(loooooong veri tabloları için yararlıdır).
David, Monica

Yanıtlar:


277
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Test</title>
<style type="text/css">
    table { page-break-inside:auto }
    tr    { page-break-inside:avoid; page-break-after:auto }
    thead { display:table-header-group }
    tfoot { display:table-footer-group }
</style>
</head>
<body>
    <table>
        <thead>
            <tr><th>heading</th></tr>
        </thead>
        <tfoot>
            <tr><td>notes</td></tr>
        </tfoot>
        <tbody>
        <tr>
            <td>x</td>
        </tr>
        <tr>
            <td>x</td>
        </tr>
        <!-- 500 more rows -->
        <tr>
            <td>x</td>
        </tr>
    </tbody>
    </table>
</body>
</html>

18
Bu, WebKit tarayıcılarında da başarısız olur (örn. Safari ve Chrome)
Michael Haren

5
Bunu yapmanın standartlara uygun yolu olsa da, şu anda standardı uygulayan tek tarayıcı Opera'dır. Bunun css2'nin bir parçası olduğunu unutmayın ve bu nedenle uygulama eksikliğinin gelecek bir süre için bir sorun olması muhtemeldir, çünkü görünüşe göre kimse umursamıyor.
pkh

16
CSS 2.1 belirtimi, sayfa sonu stili niteliklerinin yalnızca blok düzeyindeki öğelere uygulandığını gösterir. Tablo satırları için varsayılan görüntüleme modu tablo satırıdır. Ne yazık ki, tablonun kendisi de dahil olmak üzere varsayılan olarak hiçbir tablo öğesi blok düzeyinde öğeler değildir.
lsuarez

2
@ SinanÜnür Bu bir gereklilik değil, bu yüzden ona güvenemezsiniz ve maalesef testlerimden sonra webkit'in "olabilir" olduğunu ve bunun ötesinde bir şey görmediğini görebiliyorum. Garip bir şekilde, IE'ler oldukça güzel büyük masa baskı desteği aldılar. Övgülerini herhangi bir noktada söyleyeceğimi hiç düşünmemiştim.
lsuarez

6
Chrome'da veya başka bir Webkit tarayıcısında (ör. Safari, Opera) iyi çalışmadığını onaylayabilirim - "iyi çalışır" ile "isteğe bağlı kabul edilen özellikleri hariç tuttuğunuz" anlamına gelmez. Çoğu insanın istediği, üstbilgi ve altbilgi ve yalnızca satırlar arasında sayfa sonlarına izin veren tabloların her ikisi de Webkit'te 2015/11/13 itibariyle uygulanmadığını düşünüyorum.
DoctorDestructo

47

Not: sayfa sonu karakterini kullanırken: her zaman etiket için tablonun son bitinden sonra bir sayfa sonu oluşturur ve sonunda her seferinde tamamen boş bir sayfa oluşturur! Bunu düzeltmek için sadece sayfa sonu olarak değiştirin: auto. Düzgün kırılır ve fazladan boş bir sayfa oluşturmaz.

<html>
<head>
<style>
@media print
{
  table { page-break-after:auto }
  tr    { page-break-inside:avoid; page-break-after:auto }
  td    { page-break-inside:avoid; page-break-after:auto }
  thead { display:table-header-group }
  tfoot { display:table-footer-group }
}
</style>
</head>

<body>
....
</body>
</html>

Chrome'da benim için çalışıyor ve hoş bir düz CSS çözümüdür.
Ryan

1
Aynı çözümü deniyorum, ancak tablo verilerini kırmıyor ve bir sonraki sayfada görüntülemek yerine fazladan veri yok. Tahmininiz var mı?
Boş İşaretçi

24

Sinan Ünür çözümünden genişleyen:

<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Test</title>
<style type="text/css">
    table { page-break-inside:auto }
    div   { page-break-inside:avoid; } /* This is the key */
    thead { display:table-header-group }
    tfoot { display:table-footer-group }
</style>
</head>
<body>
    <table>
        <thead>
            <tr><th>heading</th></tr>
        </thead>
        <tfoot>
            <tr><td>notes</td></tr>
        </tfoot>
        <tr>
            <td><div>Long<br />cell<br />should'nt<br />be<br />cut</div></td>
        </tr>
        <tr>
            <td><div>Long<br />cell<br />should'nt<br />be<br />cut</div></td>
        </tr>
        <!-- 500 more rows -->
        <tr>
            <td>x</td>
        </tr>
    </tbody>
    </table>
</body>
</html>

Gibi görünüyor page-break-inside:avoidbazı tarayıcılarda sadece hücre, masa, sıranın ne inline-block, blok elemanları dikkate alınır.

Eğer denerseniz etiketi ve orada kullanmak , bu tablo düzeniyle etrafında çalışır, ancak Messes.display:blockTRpage-break-inside:avoid


2
Div'leri jquery ile dinamik olarak eklemenin kolay bir yolu:$(document).ready(function(){$("table tbody th, table tbody td").wrapInner("<div></div>");});
Chris Bloom

1
Sinan Ürün, Vicenteherrera ve Chrisbloom'a teşekkürler7. Cevaplarınızın kombinasyonunu uyguladım ve şimdi işe yarıyor!
Nurhak Kaya

tr { display: block; }Tüm harici <div>öğeleri eklemek yerine , @media CSS ayarını Yalnızca Baskı için ayarlamayı deneyebilirsiniz . (Test etmedik ama bakmaya değer)
Stephen R

11

Buradaki yanıtların hiçbiri Chrome'da benim için çalışmadı. GitHub'daki AAverin bu amaç için bazı yararlı Javascript oluşturdu ve bu benim için çalıştı:

Sadece kodunuzu js ekleyin ve 'splitForPrint' sınıfını tablonuza ekleyin ve tabloyu düzgün bir şekilde birden çok sayfaya böler ve tablo başlığını her sayfaya ekler.


Bunun nasıl uygulanacağına dair bir örnek var mı? Benim tablo className olarak atamaya çalışıyorum splitForPrintama JS hiçbir yerde className kullanarak öğenin başvuru aldı splitForPrint. Sadece nerede olduğu var splitClassName = 'splitForPrint';ama bu kadar.
Compaq LE2202x

Down, bağlandığınız komut dosyası, kirazın önemli miktarda toplanması ve yeniden yapılandırılması olmadan OP'nin sorununu çözmediği için oy verdi ve birinin bunu nasıl yapabileceğine dair herhangi bir örnek vermediniz.
Chris Bloom

Benim için bir cazibe gibi çalıştı, diğer çözümlerin hiçbiri işe yaramadı. +1 Doğru araları almak için biraz css eklemek zorunda kaldım .page-break {page-break-after: always; }
fhugas

.Page-break {page-break-after: her zaman ekleyerek evet; } günümü kurtardı!
milodky

7

Bu CSS özelliklerini kullanın:

page-break-after

page-break-before 

Örneğin:

<html>
<head>
<style>
@media print
{
table {page-break-after:always}
}
</style>
</head>

<body>
....
</body>
</html>

üzerinden


Emin değilim, kontrol etmen gerekecek. Değilse, farklı dizilere bölün ve dizileri boş bir div ile
ayırın

Bunu tablo satırına veya hatta hücreye uygulamak zorunda kalacaksınız, ancak tabloya değil. Bunun dışında işe yaramalı.
Pekka

2
kromda çalışmaz. TR'ye uygulandığında 6/13/2012 yok
sayılıyor

5

Kısa bir süre önce bu sorunu iyi bir çözümle çözdüm.

CSS :

.avoidBreak { 
    border: 2px solid;
    page-break-inside:avoid;
}

JS :

function Print(){
    $(".tableToPrint td, .tableToPrint th").each(function(){ $(this).css("width",  $(this).width() + "px")  });
    $(".tableToPrint tr").wrap("<div class='avoidBreak'></div>");
    window.print();
}

Tıkır tıkır çalışıyor!


2

@ Vicenteherrera'nın yaklaşımını izledim, bazı tweaks (muhtemelen bootstrap 3'e özgü).

Temelde; Biz kıramazsak trs ya tdda blok seviyesinden elemanlar değil, çünkü bu. Bu yüzden divher birine gömdük ve page-break-*kurallarımızı div. İkincisi; stil artefaktlarını telafi etmek için bu div'lerin her birinin üstüne biraz dolgu ekliyoruz.

<style>
    @media print {
        /* avoid cutting tr's in half */
        th div, td div {
            margin-top:-8px;
            padding-top:8px;
            page-break-inside:avoid;
        }
    }
</style>
<script>
    $(document).ready(function(){
        // Wrap each tr and td's content within a div
        // (todo: add logic so we only do this when printing)
        $("table tbody th, table tbody td").wrapInner("<div></div>");
    })
</script>

Kenar boşluğu ve dolgu ayarlamaları, benim tahminime göre - bootstrap'tan gelen bir çeşit titremeyi dengelemek için gerekliydi. Bu sorunun diğer cevaplarından yeni bir çözüm sunduğumdan emin değilim, ama belki de bunun birisine yardımcı olacağını düşünüyorum.


1

Aynı sorunla karşılaştım ve her yerde bir çözüm aradım, sonunda her tarayıcıda benim için çalışan bir şey buldum.

html {
height: 0;
}

bu css kullanın veya css yerine bu javascript olabilir

$("html").height(0);

Umarım bu sizin için de işe yarar.


0

Birçok çözümü kontrol ettim ve kimse iyi çalışmadı.

Bu yüzden küçük bir numara denedim ve işe yarıyor:

stilde tfoot: position: fixed; bottom: 0px; son sayfanın altına yerleştirilir, ancak altbilgi çok yüksekse tablonun içeriği ile çakışır.

tfoot with only: örtüşmüyor display: table-footer-group; , ancak son sayfanın altında değil ...

İki adım atalım:

TFOOT.placer {
  display: table-footer-group;
  height: 130px;
}

TFOOT.contenter {
  display: table-footer-group;
  position: fixed;
  bottom: 0px;	
  height: 130px;
}
<TFOOT  class='placer'> 
  <TR>
    <TD>
      <!--  empty here
-->
    </TD>
  </TR>
</TFOOT>	
<TFOOT  class='contenter'> 
  <TR>
    <TD>
      your long text or high image here
    </TD>
  </TR>
</TFOOT>

Bir rezerv son olmayan sayfalara yerleştirilir, ikincisi ise altbilginizi alır.


-1

Yukarıda verilen tüm önerileri denedim ve bu sorun için basit ve çalışan çapraz tarayıcı çözümü buldum. Bu çözüm için stil veya sayfa sonu gerekmez. Çözüm için tablonun biçimi aşağıdaki gibi olmalıdır:

<table>
    <thead>  <!-- there should be <thead> tag-->
        <td>Heading</td> <!--//inside <thead> should be <td> it should not be <th>-->
    </thead>
    <tbody><!---<tbody>also must-->
        <tr>
            <td>data</td>
        </tr>
        <!--100 more rows-->
    </tbody>
</table>

Yukarıdaki format test edilmiş ve çapraz tarayıcılarda çalışmaktadır


-2

Peki beyler ... Buradaki Çözümlerin çoğu işe yaramadı. Benim için işler böyle yürüdü ..

HTML

<table>
  <thead>
   <tr>
     <th style="border:none;height:26px;"></th>
     <th style="border:none;height:26px;"></th>
     .
     .
   </tr>
   <tr>
     <th style="border:1px solid black">ABC</th>
     <th style="border:1px solid black">ABC</th>
     .
     .
   <tr>
  </thead>
<tbody>

    //YOUR CODE

</tbody>
</table>

İlk kafa kümesi, sayfa sonu sırasında 2. kafada (yani orijinal kafa) eksik bir üst kenarlık olmayacak şekilde kukla olarak kullanılır.


-3

Kabul edilen cevap tüm tarayıcılarda benim için çalışmadı, ancak aşağıdaki css benim için işe yaradı:

tr    
{ 
  display: table-row-group;
  page-break-inside:avoid; 
  page-break-after:auto;
}

Html yapısı:

<table>
  <thead>
    <tr></tr>
  </thead>
  <tbody>
    <tr></tr>
    <tr></tr>
    ...
  </tbody>
</table>

Benim durumumda, ile ilgili bazı ek sorunlar vardı thead tr, ancak bu, tablo satırlarının kırılmasını önleyen orijinal sorunu çözdü.

Başlık sorunları nedeniyle, sonuçta:

#theTable td *
{
  page-break-inside:avoid;
}

Bu, satırların kırılmasını engellemedi; sadece her hücrenin içeriği.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.