3

I am attempting to automate alternating row colors in a longtable environment. My rows alternate between gray and white, and the alternating persists across pagebreaks. My issue is that I would like the first non-head row after a pagebreak to reset the alternating colors and always be gray again.

Here is a (very M)WE. xelatex is necessary for other things I am doing in case it breaks any solutions.

% !TeX program = xelatex
\documentclass{article}
\usepackage{longtable}
\usepackage[table]{xcolor}
\begin{document}
{\rowcolors{5}{white}{gray!25}
 \begin{longtable}{ccc}
  Talks.&&\\\endfirsthead
  Talks, continued.&&\\\endhead
  \multicolumn{3}{r}{Continued on next page.}\\\endfoot
  \endlastfoot

Talk A&Place A&Date A\ Talk B&Place B&Date B\ Talk C&Place C&Date C\ \newpage %Only a contrivance to see a pagebreak; in practice the pagebreak will be automatically determined. Talk D&Place D&Date D\ Talk E&Place E&Date E\ Talk F&Place F&Date F\ \end{longtable}} \end{document}

I'd like rows D and F to be gray, and row E to be white; currently the opposite is true. I'd like to have this done automatically, so that as I add new rows and the pagebreak occurs in different locations, it automatically assigns the top non-head row to be gray and alternates from there.

Eric
  • 83
  • Thanks @user202729. It looks like the asker there gave up but I'm still hoping that some solution can be constructed. If pagebreaks occur after assigning background colors, it seems like perhaps we could automate things in such a way where after two typesets, we get the desired result (like with pagenumbering in a table of contents). Some pseudocode: at the start of a table, assign it the current page number n. Check for the smallest, if any, row which lives on page n+1. If so, create a new rowcolors command starting at that row. Repeat the check for rows on subsequent pages. Can this be done? – Eric Dec 12 '21 at 22:50
  • Probably can, but someone have to implement it. (not me at the moment.) – user202729 Dec 13 '21 at 03:34
  • you can use labels to detect if you are at the begin of a page and then reset the color, see e.g. https://tex.stackexchange.com/a/384925/2388 – Ulrike Fischer Dec 14 '21 at 22:13
  • Thank you @UlrikeFischer. As of right now it's still unclear to me how to cut the wheat from the chaff in that link and implement exactly what I want to do, but maybe I will make progress, or it can jump start anyone else to provide a solution. – Eric Dec 15 '21 at 20:04
  • Maybe have a look at the package tabularray. I tried to make this work using the package, but wasn't succesfull. I have created an issue for this on GitHub. – marv Dec 17 '21 at 08:30

1 Answers1

4

I will give an alternative solution with longtblr environment of the new LaTeX3 package tabularray:

\documentclass{article}
\usepackage[a6paper,margin=10mm]{geometry}
\usepackage{xcolor}
\usepackage{tabularray}
\DefTblrTemplate{firsthead}{default}{%
  \centering\InsertTblrText{caption}.\par
}
\DefTblrTemplate{middlehead,lasthead}{default}{%
  \centering\InsertTblrText{caption}, continued.\par
}
\colorlet{realoddcolor}{gray!25}
\colorlet{realevencolor}{white}
\ExplSyntaxOn
\prg_generate_conditional_variant:Nnn \str_if_eq:nn { en } { TF }
\cs_gset_eq:NN \SavedNewPage \newpage
\cs_gset_eq:NN \SavedColor \color
\NewDocumentCommand \MyNewPage { }
  {
    \SavedNewPage
    \cs_set_eq:NN \color \MyColor
  }
\NewDocumentCommand \MySavedColor { o m }
  {
    \IfNoValueTF {#1} { \SavedColor{#2} } { \SavedColor[#1]{#2} }
  }
\NewDocumentCommand \MyColor { o m } 
  {
     \str_if_eq:enTF {#2} {oddcolor}
       {
         \xglobal \colorlet { oddcolor } { realoddcolor }
         \xglobal \colorlet { evencolor } { realevencolor }
         \MySavedColor [#1] { #2 }
         \cs_gset_eq:NN \color \SavedColor
       }
       {
         \str_if_eq:enTF {#2} {evencolor}
           {
             \xglobal \colorlet { evencolor } { realoddcolor }
             \xglobal \colorlet { oddcolor } { realevencolor }
             \MySavedColor [#1] { #2 }
             \cs_gset_eq:NN \color \SavedColor
           }
           {
             \MySavedColor [#1] { #2 }
           }     
       } 
  }  
\NewDocumentCommand \ResetRowColor {}
  {
    \cs_set_eq:NN \newpage \MyNewPage
    \cs_set_eq:NN \color \MyColor
  }
\ExplSyntaxOff

\begin{document}

\begingroup \ResetRowColor \begin{longtblr}[ caption = {Talks}, entry = none, label = none, ]{ colspec = {ccc}, row{odd} = {oddcolor}, row{even} = {evencolor}, } Talk A&Place A&Date A\ Talk B&Place B&Date B\ Talk C&Place C&Date C\ Talk D&Place D&Date D\ Talk E&Place E&Date E\ Talk F&Place F&Date F\ Talk A&Place A&Date A\ Talk B&Place B&Date B\ Talk C&Place C&Date C\ Talk D&Place D&Date D\ Talk E&Place E&Date E\ Talk F&Place F&Date F\ Talk A&Place A&Date A\ Talk B&Place B&Date B\ Talk C&Place C&Date C\ Talk D&Place D&Date D\ Talk E&Place E&Date E\ Talk F&Place F&Date F\ Talk A&Place A&Date A\ Talk B&Place B&Date B\ Talk C&Place C&Date C\ Talk D&Place D&Date D\ Talk E&Place E&Date E\ Talk F&Place F&Date F\ Talk A&Place A&Date A\ Talk B&Place B&Date B\ Talk C&Place C&Date C\ Talk D&Place D&Date D\ Talk E&Place E&Date E\ Talk F&Place F&Date F\ \end{longtblr} \endgroup

\end{document}

enter image description here

L.J.R.
  • 10,932
  • Thanks @L.J.R. Right now I am having some issues implementing this code. I get the error "File 'tabularray.sty' not found." Also this implementation changes some of the properties my MWE had. It no longer has the foot before pagebreaks, and the head now contains "Title n: --" instead of "Talks." and "Talks, continued." The coloring look great if I could get TeXworks to discover the tabularray package, but otherwise there are some stylistic changes I'd prefer to have kept. My MWE is pared down to the absolute essentials I wanted to keep. – Eric Dec 17 '21 at 15:39
  • @Eric tabularray is a recent package, you should update your TeX distribution to use it. – CarLaTeX Dec 17 '21 at 16:42
  • @Eric There is a bug there to be fixed if you use \pagebreak. But if you have many rows in the tables to make it automatically break to pages, the table foots are correct. Please have a look at my updated answer. – L.J.R. Dec 18 '21 at 03:50
  • @L.J.R. thanks a bunch; this is very good. :) I now have 2 concerns taking your answer and changing it from a MWE into my actual table. These concerns weren't mentioned in my original post but your answer changes enough that I can't turn the MWE into exactly what I was originally doing anymore. Concern #1: I can't use multirow to vertically center my date cells anymore. #2: there's extra vertical space between rows, and the table and the heads/foots. Can these be fixed? See here: https://locallyringed.space/EXAMPLE.pdf for a further explanation and a MaximalWE. :) – Eric Dec 18 '21 at 21:06
  • Hi, I managed to fix the spacing between rows by adding the command "rowsep = 0pt" to the longtblr environment. Still working on making the head and foot spaced correctly vertically, and still working on a multirow replacement. Reading through the tabularray documentation. :) – Eric Dec 18 '21 at 23:57
  • And "headsep = 3.33pt, footsep = 0.67pt" appears to produce the correct head and foot spacing. All that remains is vertical centering a cell. :) – Eric Dec 19 '21 at 00:14
  • Found it! It's "cells = m" to vertically center the cells. I think as of now that fixes every issue I had, and thus this answer works great for me. Thank you again @L.J.R., and enjoy the bounty! :) – Eric Dec 19 '21 at 00:41