Title: CSS Generated Content for Paged Media Module Level 3 Status: ED Prepare for TR: no Work Status: Exploring Shortname: css-gcpm Level: 3 Group: csswg ED: https://drafts.csswg.org/css-gcpm/ TR: https://www.w3.org/TR/css-gcpm-3/ Editor: Mike Bremford, BFO, mike@bfo.com, w3cid 118053 Editor: Rachel Andrew, Google, rachelandrew@google.com, w3cid 81117 Former Editor: Dave Cramer, Hachette Livre, dave.cramer@hbgusa.com, w3cid 65283 Former Editor: Håkon Wium Lie, Opera Software Link defaults: css-content-3 (property) counter-increment, css-content-3 (property) counter-reset, css21 (property) string, css2 (property) max-height Abstract: Books and other paged media often use special techniques to display information. Content may be moved to or generated for special areas of the page, such as running heads or footnotes. Generated content within pages, such as tab leaders or cross-references, helps readers navigate within and between pages. Ignored Terms:
spec:css-content-3; type:function; text:string() spec:css-content-3; type:property; text:bookmark-label spec:css-content-3; type:property; text:bookmark-level
Name: string-set Value: [ <> < > ]# | none Initial: none Applies to: all elements, but not pseudo-elements Inherited: no Percentages: N/A Computed value: specified value Animation type: discrete
User agents are expected to support this property on all media, including non-visual ones.
The 'string-set' property contains one or more pairs, each consisting of an custom identifier (the name of the named string) followed by a <<content-list> = [ <> | < > | < > | < > | < > ]+
content() = content([text | before | after | first-letter ])
How do we define the default value for this function?
white-space: normal had been set. This is the default value::before pseudo-element, determined as if white-space: normal had been set. ::after pseudo-element, determined as if white-space: normal had been set. ::first-letter pseudo-element <h1>Loomings</h1>CSS:
h1::before {
content: 'Chapter ' counter(chapter);
}
h1 {
string-set: header content(before) ':' content(text);
}
h1::after {
content: '.';
}
The value of the named string “header” will be “Chapter 1: Loomings”.
<section title="Loomings">CSS:
section {
string-set: header attr(title);
}
The value of the “header” string will be “Loomings”.
first is the default value.first, except that the empty string is used on the page where the value is assigned.
@page {
size: 15cm 10cm;
margin: 1.5cm;
@top-left {
content: "first: " string(heading, first);
}
@top-center {
content: "start: " string(heading, start);
}
@top-right {
content: "last: " string(heading, last);
}
}
h2 {
string-set: heading content();
}
The following figures show the first, start, and last assignments of the “heading” string on various pages.
@page {
@top {
content: element(header);
}
}
h1 {
position: running(header);
}
In this example, the h1 element is placed in the @top margin box, complete with formatting and any descendant elements. It does not display in the normal document flow.
position: running(custom-ident) removes the element (and associated ::before and ::after pseudo-elements) from the normal flow, and makes it available to place in a page margin box using ''element()''. The element inherits from its original position in the document, but does not display there.
Name: position New Values: <>
running() = running( <> )
<p class="rh"><i>Miranda v. Arizona</i> in Context</p> <h2><i>Miranda v. Arizona</i> in Context</h2>CSS:
@top-center {
content: element(heading);
}
p.rh {
position: running(heading);
}
p.rh::before {
content: counter(page) ' / ';
}
The ''element()'' value can only be used in page margin boxes. And it cannot be combined with other possible values for the content property.
This idea would be much more useful if we could also copy (rather than just move) elements. That would avoid the duplication of HTML in the example above.
Bert Bos has proposed an alternative syntax, which allows both moving and copying elements into running heads. In the example below, h2 elements appear in their normal place in the document, but are also copied into running heads.
h2 {
display: block;
running: chapter;
font-size: 18pt;
font-weight: bold;
}
h2:running {
display: inline;
font-size: 11pt;
font-weight: normal;
font-variant: small-caps;
letter-spacing: 1pt;
}
@page {
@top-center {
content: element(chapter);
}
}
Name: running Value: <> Initial: none Applies to: elements Inherited: no Percentages: N/A Computed value: specified value Animation type: discrete
User agents are expected to support this property on all media, including non-visual ones.
Name: content New Values: <>
element() = element( <> , [ first | start | last | first-except ]? )
float: footnote to that element. This triggers the following actions:
::footnote-call pseudo-element is inserted in its place, which serves as a reference to the footnote.::footnote-marker pseudo-element, identifying the footnote, is placed at the beginning of the footnote element. Together this is the footnote body.<p>Though the body was erect, the head was thrown back so that the closed eyes were pointed towards the needle of the tell-tale that swung from a beam in the ceiling.<span class="footnote">The cabin-compass is called the tell-tale, because without going to the compass at the helm, the Captain, while below, can inform himself of the course of the ship.</span></p>CSS:
@page {
@footnote {
float: bottom;
}
}
span.footnote {
float: footnote;
}
Why is float:bottom used with the footnote area? Floating footnotes to the footnote area, and then floating the footnote area itself, seems overly complex, given that implementations don’t allow the footnote area to float anywhere else. Note that some implementations do allow the footnote area to be absolutely positioned.
Name: float New Values: footnote
Name: footnote-display Value: block | inline | compact Initial: block Applies to: elements Inherited: no Percentages: N/A Computed value: specified value Animation type: discrete
@footnote rule. This rule defines a box that, if used, will contain all the footnote elements that appear on that page.
How would one describe this in the grammar of CSS3-Page?
How do footnotes work in multi-column text? Prince uses float: prince-column-footnote to create a footnote at the bottom of a column rather than the bottom of a page.
Implementations that support footnotes generally support page floats like float: bottom. Page floats should end up above the footnote area. How might this be specified?
::footnote-call {
content: counter(footnote, symbols('*', '†', '‡', '§'));
}
::footnote-marker {
content: counter(footnote, symbols('*', '†', '‡', '§')) '. ';
}
@page {
counter-reset: footnote;
@footnote { … }
}
footnote-call pseudo-element
::footnote-call pseudo-element is inserted in place of the footnote element when the latter is removed from the flow. By default, the content of this pseudo-element is the value of the footnote counter, styled as a superscripted number.
::footnote-call {
content: counter(footnote);
vertical-align: baseline;
font-size: 100%;
line-height: inherit;
font-variant-position: super;
}
footnote-marker pseudo-element
::footnote-marker pseudo-element represents the footnote element’s marker, the number or symbol that identifies each footnote. This pseudo-element behaves like a ::marker pseudo-element, as defined in [[CSS3LIST]]. It is placed at the beginning of the superior parent’s content, and is inline by default. The ::footnote-marker can be styled just as other ::marker elements can be. The default style should include list-style-position: inside.
::footnote-marker {
content: counter(footnote);
}
::footnote-marker::after {
content: '. ';
}
footnote policy
Name: footnote-policy Value: auto | line | block Initial: auto Applies to: elements Inherited: no Percentages: N/A Computed value: specified value Animation type: discrete
We need an algorithm for laying out footnotes
:nth() = :nth( <> [of < >]? )
'':nth()'' is not related to the page counter, which may reset and use various numbering schemes.
When the '':nth()'' selector is applied to a named page, and that named page is part of a page-group (see below), it selects the nth page in the page group.@page :nth(1)This selects the first page of the document.
@page :nth(2n)This selects all even document pages.
div {
page: A;
break-before: page;
}
child {
page: B;
break-before: page;
}
@page :nth(5 of A) /* will select 5th page of every <div> */ @page :nth(1 of B) /* will select first page of every <child> */ @page :nth(5) /* will select 5th page of document */
<div class="chapter"> <h1>Chapter One</h1> <p>some text</p> <table class="broadside"> ... </table> ... </div> <div class="chapter"> <h1>Chapter Two</h1> <p>some text</p> ... <table class="broadside"> ... </table> ... </div>And CSS:
div.chapter {
page: body;
break-before: page;
}
table.broadside {
page: broadside;
break-before: page;
}
In this case, each chapter will form a separate page group. @page:nth(3 of body) will select the third page of each chapter, even if that page happens to use the “broadside” named page. @page:nth(1) will select only the first page of the document, as will @page:first.
This section has been moved to CSS Paged Media Module Level 3.
This section has been moved to CSS Color Module Level 5.
This section has been moved to CSS Paged Media Module Level 3
This section has been moved to CSS Overflow Module Level 4.
This is discussed in WHATWG CSS Books.
This section has been moved to CSS Page Floats.
A brief mention of selecting columns is found in WHATWG CSS Books.
This appendix is informative, and is to help UA developers to implement a default stylesheet for HTML, but UA developers are free to ignore or modify as appropriate.
@page {
counter-reset: footnote;
@footnote {
counter-increment: footnote;
float: bottom;
column-span: all;
height: auto;
}
}
::footnote-marker {
content: counter(footnote);
list-style-position: inside;
}
::footnote-marker::after {
content: '. ';
}
::footnote-call {
content: counter(footnote);
vertical-align: super;
font-size: 65%;
}
@supports ( font-variant-position: super ) {
::footnote-call {
content: counter(footnote);
vertical-align: baseline;
font-size: 100%;
line-height: inherit;
font-variant-position: super;
}
}
h1 { bookmark-level: 1 }
h2 { bookmark-level: 2 }
h3 { bookmark-level: 3 }
h4 { bookmark-level: 4 }
h5 { bookmark-level: 5 }
h6 { bookmark-level: 6 }
Differences with the WHATWG CSS Books specification:
nth() page pseudo-class and the page-group concept is clarified, which may make the page-group property redundant.:first page pseudo-selector to select the first page of a page-group.range() page pseudo-class