/* User-Agent stylesheet conforming to the current HTML standard/specs.

   All of the following (if not mentionned otherwise) is taken from the snippets in:
   https://html.spec.whatwg.org/multipage/rendering.html
   (excluding the ones tagged as "apply in quirks mode")
   as of 20240101 (it will be hard to track future changes in this page...).

   Some of these snippets have been splitted and merged by element name, to
   reduce the number of selectors (ie. 5 snippets targetting a plain <th>,
   3 targetting <ol> or <ul>, merged into a single one for each).
   Some of these have also been reordered by ascending specificity, for clarity.

   When multiple selectors are associated to a same declaration, we may have
   reorder the selectors from the specs snippets to have the rare ones on the
   left and the most popular on the right, to get less noise in our "Show
   matched stylesheet rules" output (as we truncate on the matched element).

   Those from sections (and writings) tagged as "presentational hints" have
   added to their declarations: "-cr-hint: presentational-hint;" which helps
   distinguish them and to not have them applied when "Embedded styles" are
   disabled. We may have also tagged other sections matching attributes as
   "presentational hints" even if not mentionned in the specs, to make it
   easy to disable them (the distinction in the specs between presentation
   and non-presentational might be just about the CSS cascade and the effect
   of non-important "user" stylesheet being applied after "non-presentational"
   but before "presentational", which we don't really handle - our style
   tweaks are made part of the useragent stylsheet, so mixed with presentational
   and non-presentational).

   Some of them in the specs use (margin|padding)-(block|inline)-(start|end),
   that crengine does not support.
   They have been translated to (margin|padding)-(top|bottom|left|right), with a
   note when they are unbalanced and will so not work as expected in RTL documents
   (without any note when balanced and strictly equivalent, not caring about
   vertical writing mode that we don't support).

   Some ideas and additional bits taken from Firefox UA stylesheet ("UAS" hereafter)
   https://searchfox.org/mozilla-central/source/layout/style/res/html.css

   (Comments on declarations and unsupported properties have been moved outside
   the declaration, so to not add noise to "View matched rulesets" output.
*/

/* crengine+: styling of internal elements, page breaks and non-linear flows, as per EPUB specs. */
/* DocFragment is the container of each individual HTML file from an EPUB */
DocFragment {
    page-break-before: always;
}
/* Element added for each empty line when rendering plain txt files */
empty-line {
    height: 1em;
}
/* crengine: support for non-linear fragments (hideable) */
DocFragment[NonLinear] {
    -cr-hint: non-linear;
}
section[type=footnotes] {
    -cr-hint: non-linear;
}
aside[type=footnote] {
    -cr-hint: non-linear-combining;
}
/* EPUB3 epub:type="pagebreak" may sometimes have the page number
 * as content: hide it. (Usually, its content is empty and the
 * page number is in a title= attribute.) */
span[type=pagebreak] {
    display: none;
}


/* Here start the snippets picked from https://html.spec.whatwg.org/multipage/rendering.html */

/* Hidden elements */

/* crengine-: included in the following list in the specs, but we keep them not invisible:
      <rp> is not shown by our ruby rendering algorithm, and not making it display:none allows
           showing it when <ruby> is set display:inline to get all its content rendered inline.
      <noframes>, better show its content than nothing, as we don't support <frame>
*/
area, base, basefont, datalist, head, link, meta, noembed,
param, script, style, template, title {
  display: none;
}

/* crengine: not caring about differences of embed[hidden] and [hidden=until-found i] */
input[type=hidden i],
[hidden] {
  -cr-hint: presentational-hint;
  display: none;
}


/* The page */

/* crengine-: these elements are "display:block" by default (fb2def.h)
html, body {
  display: block;
}
*/

body[background] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-background-image-from-background-attribute;
}
body[bgcolor] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-background-color-from-bgcolor-attribute;
}
body[text] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-color-from-text-attribute;
}

/* Other presentational hints not supported:
body[link]
body[alink]
body[vlink]
We also don't care about body attributes like 'marginheight and 'topmargin'.
*/


/* Flow content */

/* crengine-: these elements are "display:block" by default (fb2def.h)
address, blockquote, center, dialog, div, figure, figcaption, footer, form,
header, hr, legend, listing, main, p, plaintext, pre, search, xmp {
  display: block;
}
*/

p {
  margin-top: 1em;
  margin-bottom: 1em;
}

/* These about align= for P are mixed in the specs with table related rules...
   We have moved them here, for clarity.
   No "align descandants" mentionned for these, as they are not expected to have block children. */
p[align=left i] {
  -cr-hint: presentational-hint;
  text-align: left;
}
p[align=right i] {
  -cr-hint: presentational-hint;
  text-align: right;
}
p[align=center i] {
  -cr-hint: presentational-hint;
  text-align: center;
}
p[align=justify i] {
  -cr-hint: presentational-hint;
  text-align: justify;
}

blockquote, figure {
  margin-top: 1em;
  margin-bottom: 1em;
  margin-left: 40px;
  margin-right: 40px;
}

address {
  font-style: italic;
}

listing, plaintext, xmp, pre {
  font-family: monospace;
  white-space: pre;
  margin-top: 1em;
  margin-bottom: 1em;
}

/* crengine: not caring about styling 'dialog' and [popover] */

pre[wrap] {
  -cr-hint: presentational-hint;
  white-space: pre-wrap;
}

/* These are implemented with private text-align keywords, as Firefox and Webkit,
   which means any text-align override kills this block alignment effect... */
center {
  -cr-hint: presentational-hint;
  text-align: -cr-html-align-center;
}
div[align=left i] {
  -cr-hint: presentational-hint;
  text-align: -cr-html-align-left;
}
div[align=right i] {
  -cr-hint: presentational-hint;
  text-align: -cr-html-align-right;
}
div[align=middle i], div[align=center i] {
  -cr-hint: presentational-hint;
  text-align: -cr-html-align-center;
}
/* No private text-align keyword in Firefox/Webkit for this one */
div[align=justify i] {
  -cr-hint: presentational-hint;
  text-align: justify;
}


/* Phrasing content */

cite, dfn, var, em, i {
  font-style: italic;
}

strong, b {
  font-weight: bolder;
}

samp, tt, kbd, code {
  font-family: monospace;
}

big {
  font-size: larger;
}

small {
  font-size: smaller;
}

sub {
  vertical-align: sub;
  line-height: normal;
  font-size: smaller;
}

sup {
  vertical-align: super;
  line-height: normal;
  font-size: smaller;
}

/* The HTML specs have not much about ruby, Firefox UAS has more. We use our own. */
/* crengine+: tuned for prettier Ruby support */
/* (text-align and text-indent will have no effect when ruby is reset to display: inline) */
ruby {
  display: ruby;
  text-align: center;
  text-align-last: initial;
  text-indent: 0;
}
rb, rubyBox[T=rb] {
  line-height: 1;
}
rt, rubyBox[T=rt] {
  line-height: 1.6;
  font-size: 42%;
  font-variant-east-asian: ruby;
  -cr-hint: text-selection-skip;
}
/* Note: Firefox has this, marked 'bopofomo', see if needed.
rt:lang(zh-TW) { font-size: 30%; }
*/

/* crengine-: not supported
:link { color: #0000EE; }
:visited { color: #551A8B; }
:link:active, :visited:active { color: #FF0000; }
:link, :visited { text-decoration: underline; cursor: pointer; }
:focus-visible { outline: auto; }
*/

/* But have :link style set on all <a href=''> */
a[href] {
  color: #00E;
  text-decoration: underline;
}

mark {
  background: yellow;
  color: black;
}

abbr[title], acronym[title] {
  text-decoration: underline;
}
  /* by specs: text-decoration: dotted underline; but multiple values not supported */

ins, u {
  text-decoration: underline;
}

del, s, strike {
  text-decoration: line-through;
}

q::before {
  content: open-quote;
}

q::after {
  content: close-quote;
}

/* crengine-: not supported, <br> handled internally
br { display-outside: newline; }
wbr { display-outside: break-opportunity; }
*/

/* crengine: added 'hyphens:none' to be sure no hyphenation is triggered */
nobr {
  white-space: nowrap;
  hyphens: none;
}

nobr wbr {
  white-space: normal;
}

br[clear=left i] {
  -cr-hint: presentational-hint;
  clear: left;
}
br[clear=right i] {
  -cr-hint: presentational-hint;
  clear: right;
}
br[clear=all i], br[clear=both i] {
  -cr-hint: presentational-hint;
  clear: both;
}

font[color] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-color-from-color-attribute;
}
font[face] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-font-family-from-face-attribute;
}
font[size] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-font-size-from-size-attribute;
}


/* Bidirectional text */
/* crengine-: dir=ltr/rtl handled internally (unicode-bidi not supported, but bdo handled) */


/* Sections and headings */

/* crengine-: these elements are "display:block" by default (fb2def.h)
article, aside, h1, h2, h3, h4, h5, h6, hgroup, nav, section {
  display: block;
}
*/

/* Note: the specs specify the styles of h1...h6, and mention rules with "x x x h1"
   with the same properties as the h1...h6. We rewrite all that as done
   in Firefox UAS by bringing them with the hN selectors. */
h1 {
  margin-top: 0.67em;
  margin-bottom: 0.67em;
  font-size: 2.00em;
  font-weight: bold;
  page-break-inside: avoid; /* crengine+ */
  page-break-after: avoid;  /* crengine+ */
}

:where(article, aside, nav, section) h1,
h2 {
  margin-top: 0.83em;
  margin-bottom: 0.83em;
  font-size: 1.50em;
  font-weight: bold;
  page-break-inside: avoid; /* crengine+ */
  page-break-after: avoid;  /* crengine+ */
}

:where(article, aside, nav, section) :where(article, aside, nav, section) h1,
h3 {
  margin-top: 1.00em;
  margin-bottom: 1.00em;
  font-size: 1.17em;
  font-weight: bold;
  page-break-inside: avoid; /* crengine+ */
  page-break-after: avoid;  /* crengine+ */
}

:where(article, aside, nav, section) :where(article, aside, nav, section) :where(article, aside, nav, section) h1,
h4 {
  margin-top: 1.33em;
  margin-bottom: 1.33em;
  font-size: 1.00em;
  font-weight: bold;
  page-break-inside: avoid; /* crengine+ */
  page-break-after: avoid;  /* crengine+ */
}

:where(article, aside, nav, section) :where(article, aside, nav, section) :where(article, aside, nav, section) :where(article, aside, nav, section) h1,
h5 {
  margin-top: 1.67em;
  margin-bottom: 1.67em;
  font-size: 0.83em;
  font-weight: bold;
  page-break-inside: avoid; /* crengine+ */
  page-break-after: avoid;  /* crengine+ */
}

:where(article, aside, nav, section) :where(article, aside, nav, section) :where(article, aside, nav, section) :where(article, aside, nav, section) :where(article, aside, nav, section) h1,
h6 {
  margin-top: 2.33em;
  margin-bottom: 2.33em;
  font-size: 0.67em;
  font-weight: bold;
  page-break-inside: avoid; /* crengine+ */
  page-break-after: avoid;  /* crengine+ */
}

/* crengine+: with plain HTML files, make a new page on top level H1 and section (but not with other formats
   like EPUB, publishers may not expect it; most EPUB renderers only break page on a new DocFragment). */
section, h1 {
  -cr-only-if: html-document;
    page-break-before: always;
}
section section, section h1 {
  -cr-only-if: html-document;
    page-break-before: auto;
}

/* These about align= for headings are mixed in the specs with table related rules...
   We have moved them here, for clarity.
   No "align descandants" mentionned for these, as they are not expected to have block children. */
h6[align=left i], h5[align=left i], h4[align=left i],
h3[align=left i], h2[align=left i], h1[align=left i] {
  -cr-hint: presentational-hint;
  text-align: left;
}
h6[align=right i], h5[align=right i], h4[align=right i],
h3[align=right i], h2[align=right i], h1[align=right i] {
  -cr-hint: presentational-hint;
  text-align: right;
}
h6[align=center i], h5[align=center i], h4[align=center i],
h3[align=center i], h2[align=center i], h1[align=center i] {
  -cr-hint: presentational-hint;
  text-align: center;
}
h6[align=justify i], h5[align=justify i], h4[align=justify i],
h3[align=justify i], h2[align=justify i], h1[align=justify i] {
  -cr-hint: presentational-hint;
  text-align: justify;
}


/* Lists */

/* crengine-: these elements are "display:block" by default (fb2def.h)
dir, dd, dl, dt, menu, ol, ul {
  display: block;
}
*/
/* crengine-: also "display:list-item" by default (fb2def.h)
   Additionally by specs, but not supported: text-align: match-parent
li {
  display: list-item;
}
*/

dl {
  margin-top: 1em;
  margin-bottom: 1em;
}
/* Unbalanced by specs, but not supported: margin-inline-start: 40px.
   (dl/dt/dd are rare, and we don't really care about the indentation,
   so let's keep this 40px.)
   Fix the unbalance if dir=rtl set on a parent */
dd {
  margin-left: 40px;
}
dd:dir(rtl) {
  margin-left: unset;
  margin-right: 40px;
}

/* By specs, the padding-left/right below should be: padding-inline-start: 40px.
   This fixed absolute 40px is to give room for the list item markers, rendered
   outside the <li> box, but it is not the best thing to use as it will vary
   with DPI and not with the font size.  Publishers ought to override that
   if they care about the list items rendering. If they don't, we'll use
   these -cr-special and compute dynamically some optimal padding from
   the widest marker width.
*/
dir, menu, ul {
  margin-top: 1em;
  margin-bottom: 1em;
  padding-left: -cr-special;
  padding-right: -cr-special;
  list-style-type: disc;
}

ol {
  margin-top: 1em;
  margin-bottom: 1em;
  padding-left: -cr-special;
  padding-right: -cr-special;
  list-style-type: decimal;
}

/* crengine-: not supported
ol, ul, menu { counter-reset: list-item; }
*/

/* This one and others below could be written as a single selector ending with ':is(dir,dl,menu,ol,ul)',
   but it would then be checked on all nodes.
   Having an element name at its tail end makes it only checked for nodes being that element.
   This is actually how Firefox has it in its UAS. */

/* Nested lists have no top/bottom margins */
:is(ol, ul, menu, dir, dl) dir,
:is(ol, ul, menu, dir, dl) menu,
:is(ol, ul, menu, dir, dl) dl,
:is(ol, ul, menu, dir, dl) ol,
:is(ol, ul, menu, dir, dl) ul {
  margin-top: 0;
  margin-bottom: 0;
}

/* 2-deep unordered lists use a circle */
:is(ol, ul, menu, dir) dir,
:is(ol, ul, menu, dir) menu,
:is(ol, ul, menu, dir) ul {
  list-style-type: circle;
}

/* 3-deep (or more) unordered lists use a square */
:is(ol, ul, menu, dir) :is(ol, ul, menu, dir) dir,
:is(ol, ul, menu, dir) :is(ol, ul, menu, dir) menu,
:is(ol, ul, menu, dir) :is(ol, ul, menu, dir) ul {
  list-style-type: square;
}

ol[type=1], li[type=1] {
  -cr-hint: presentational-hint;
  list-style-type: decimal;
}

ol[type=a], li[type=a] {
  -cr-hint: presentational-hint;
  list-style-type: lower-alpha;
}

ol[type=A], li[type=A] {
  -cr-hint: presentational-hint;
  list-style-type: upper-alpha;
}

ol[type=i], li[type=i] {
  -cr-hint: presentational-hint;
  list-style-type: lower-roman;
}

ol[type=I], li[type=I] {
  -cr-hint: presentational-hint;
  list-style-type: upper-roman;
}

ul[type=none i], li[type=none i] {
  -cr-hint: presentational-hint;
  list-style-type: none;
}

ul[type=disc i], li[type=disc i] {
  -cr-hint: presentational-hint;
  list-style-type: disc;
}

ul[type=circle i], li[type=circle i] {
  -cr-hint: presentational-hint;
  list-style-type: circle;
}

ul[type=square i], li[type=square i] {
  -cr-hint: presentational-hint;
  list-style-type: square;
}

/* These are handled internally (they are specified as to be handled as
   a presentational hint, but we don't: we don't want to hardcode that,
   and they feel rather semantic...
li[value]
ol[start]
ol[reversed]
*/


/* Tables */

/* crengine-: these elements have these "display:" values by default (fb2def.h)
   Those with [hidden] are re-set below.
table {
  display: table;
}
caption {
  display: table-caption;
}
colgroup, colgroup[hidden] {
  display: table-column-group;
}
col, col[hidden] {
  display: table-column;
}
thead, thead[hidden] {
  display: table-header-group;
}
tbody, tbody[hidden] {
  display: table-row-group;
}
tfoot, tfoot[hidden] {
  display: table-footer-group;
}
tr, tr[hidden] {
  display: table-row;
}
th, td {
  display: table-cell;
}
*/

table {
  box-sizing: border-box;
  border-spacing: 2px;
  border-collapse: separate;
  text-indent: initial;
}

caption {
  text-align: center;
}

thead, tbody, tfoot {
  border-color: inherit;
}

tr {
  vertical-align: inherit;
  border-color: inherit;
}

thead, tbody, tfoot, table > tr {
  vertical-align: middle;
}

/* User agents are expected to have a rule in their user agent style
   sheet that matches th elements that have a parent node whose
   computed value for the 'text-align' property is its initial
   value, whose declaration block consists of just a single declaration
   that sets the 'text-align' property to the value 'center'.
   (Firefox has it named: th { text-align: -moz-center-or-inherit; }.) */
th {
  vertical-align: inherit;
  padding: 1px;
  font-weight: bold;
  -cr-apply-func: css-text-align-center-if-parent-text-align-initial;
}

td {
  vertical-align: inherit;
  padding: 1px;
}

/* We need to re-set "display:" to the proper value if [hidden] (as they are set
   set display:none by our rule above), by specs, or for th/td because our table
   rendering algorithm expects them to to be table-cell */
colgroup[hidden] {
  display: table-column-group;
  visibility: collapse;
}
col[hidden] {
  display: table-column;
  visibility: collapse;
}
thead[hidden] {
  display: table-header-group;
  visibility: collapse;
}
tbody[hidden] {
  display: table-row-group;
  visibility: collapse;
}
tfoot[hidden] {
  display: table-footer-group;
  visibility: collapse;
}
tr[hidden] {
  display: table-row;
  visibility: collapse;
}
th[hidden], td[hidden] {
  display: table-cell;
  visibility: collapse;
}


/* Note: huge list of selectors in the specs simplified to use :where(...) and :is(...)
   (this all seems to be just to check frame= and rules= have valid named values).
   Note that Firefox does not have this and use currentColor, while Edge seems to have it. */
table[frame]:where([frame=void i], [frame=above i], [frame=below i], [frame=hsides i], [frame=lhs i], [frame=rhs i], [frame=vsides i], [frame=box i], [frame=border i]),
table[rules]:where([rules=none i], [rules=groups i], [rules=rows i], [rules=cols i], [rules=all i]),
table[rules]:where([rules=none i], [rules=groups i], [rules=rows i], [rules=cols i], [rules=all i]) > :where(thead, tbody, tfoot) > tr > th,
table[rules]:where([rules=none i], [rules=groups i], [rules=rows i], [rules=cols i], [rules=all i]) > :where(thead, tbody, tfoot) > tr > td,
table[rules]:where([rules=none i], [rules=groups i], [rules=rows i], [rules=cols i], [rules=all i]) > tr > th,
table[rules]:where([rules=none i], [rules=groups i], [rules=rows i], [rules=cols i], [rules=all i]) > tr > td {
  -cr-hint: presentational-hint;
  border-color: black;
}
/* The above rules, even if matching attributes, are not specified as being "presentational hints"
   in the specs. But the following ones are. We tag both kinds as presentational-hint though. */

table[align=left i] {
  -cr-hint: presentational-hint;
  float: left;
}

table[align=right i] {
  -cr-hint: presentational-hint;
  float: right;
}

table[align=center i] {
  -cr-hint: presentational-hint;
  margin-left: auto;
  margin-right: auto;
}
/* Note: Firefox UAS has other related rules starting with: table[align="center"] > caption */

thead[align=left i], tbody[align=left i], tfoot[align=left i],
tr[align=left i], th[align=left i], td[align=left i] {
  -cr-hint: presentational-hint;
  text-align: -cr-html-align-left;
}
thead[align=justify i], tbody[align=justify i], tfoot[align=justify i],
tr[align=justify i], th[align=justify i], td[align=justify i] {
  -cr-hint: presentational-hint;
  text-align: justify;
}
thead[align=right i], tbody[align=right i], tfoot[align=right i],
tr[align=right i], th[align=right i], td[align=right i] {
  -cr-hint: presentational-hint;
  text-align: -cr-html-align-right;
}
thead[align=center i], tbody[align=center i], tfoot[align=center i],
thead[align=middle i], tbody[align=middle i], tfoot[align=middle i],
tr[align=center i], th[align=center i], td[align=center i],
tr[align=middle i], th[align=middle i], td[align=middle i] {
  -cr-hint: presentational-hint;
  text-align: -cr-html-align-center;
}
/* This one is presented as-is in the specs, which do not mention any required "align descendants" behaviour */
thead[align=absmiddle i], tbody[align=absmiddle i], tfoot[align=absmiddle i],
tr[align=absmiddle i], th[align=absmiddle i], td[align=absmiddle i] {
  -cr-hint: presentational-hint;
  text-align: center;
}

caption[align=bottom i] {
  -cr-hint: presentational-hint;
  caption-side: bottom;
}

/* The specs have here selectors regarding p[align] and h1...h6[align] that we have moved above. */

thead[valign=top i], tbody[valign=top i], tfoot[valign=top i],
tr[valign=top i], th[valign=top i], td[valign=top i] {
  -cr-hint: presentational-hint;
  vertical-align: top;
}

thead[valign=middle i], tbody[valign=middle i], tfoot[valign=middle i],
tr[valign=middle i], th[valign=middle i], td[valign=middle i] {
  -cr-hint: presentational-hint;
  vertical-align: middle;
}

thead[valign=bottom i], tbody[valign=bottom i], tfoot[valign=bottom i],
tr[valign=bottom i], th[valign=bottom i], td[valign=bottom i] {
  -cr-hint: presentational-hint;
  vertical-align: bottom;
}

thead[valign=baseline i], tbody[valign=baseline i], tfoot[valign=baseline i],
tr[valign=baseline i], th[valign=baseline i], td[valign=baseline i] {
  -cr-hint: presentational-hint;
  vertical-align: baseline;
}

th[nowrap], td[nowrap] {
  -cr-hint: presentational-hint;
  white-space: nowrap;
}

/* Comment in Firefox UAS: "this first so 'border' and 'frame' rules can override it" */
/* Note: Firefox UAS avoids this 'border-collapse: collapse' when [rules=none] */
table[rules=none i], table[rules=groups i], table[rules=rows i],
table[rules=cols i], table[rules=all i] {
  -cr-hint: presentational-hint;
  border-style: hidden;
  border-collapse: collapse;
}

/* Comment in Firefox UAS: "border' before 'frame' so 'frame' overrides" */
/* If border is not equivalent to zero, this -cr-apply-func will additionally set 'border-style: outset' */
table[border] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-border-from-table-border-attribute;
}

table[frame=void i] {
  -cr-hint: presentational-hint;
  border-style: hidden;
}

table[frame=above i] {
  -cr-hint: presentational-hint;
  border-style: outset hidden hidden hidden;
}

table[frame=below i] {
  -cr-hint: presentational-hint;
  border-style: hidden hidden outset hidden;
}

table[frame=hsides i] {
  -cr-hint: presentational-hint;
  border-style: outset hidden outset hidden;
}

table[frame=lhs i] {
  -cr-hint: presentational-hint;
  border-style: hidden hidden hidden outset;
}

table[frame=rhs i] {
  -cr-hint: presentational-hint;
  border-style: hidden outset hidden hidden;
}

table[frame=vsides i] {
  -cr-hint: presentational-hint;
  border-style: hidden outset;
}

table[frame=box i], table[frame=border i] {
  -cr-hint: presentational-hint;
  border-style: outset;
}

/* Note: following list of selectors in the specs simplified to use :where(...) */
/* If table's border is not equivalent to zero, this -cr-apply-func will set 'border-width: 1px; border-style: inset' */
table[border] > :where(thead, tbody, tfoot) > tr > th,
table[border] > :where(thead, tbody, tfoot) > tr > td,
table[border] > tr > th,
table[border] > tr > td {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-border-from-table-border-attribute;
}

/* Note: following lists of selectors in the specs simplified to use :where(...) */
table[rules]:where([rules=none i], [rules=groups i], [rules=rows i]) > :where(thead, tbody, tfoot) > tr > th,
table[rules]:where([rules=none i], [rules=groups i], [rules=rows i]) > :where(thead, tbody, tfoot) > tr > td,
table[rules]:where([rules=none i], [rules=groups i], [rules=rows i]) > tr > th,
table[rules]:where([rules=none i], [rules=groups i], [rules=rows i]) > tr > td {
  -cr-hint: presentational-hint;
  border-width: 1px;
  border-style: none;
}

table[rules=cols i] > :where(thead, tbody, tfoot) > tr > th,
table[rules=cols i] > :where(thead, tbody, tfoot) > tr > td,
table[rules=cols i] > tr > th,
table[rules=cols i] > tr > td {
  -cr-hint: presentational-hint;
  border-width: 1px;
  border-style: none solid;
}

table[rules=all i] > :where(thead, tbody, tfoot) > tr > th,
table[rules=all i] > :where(thead, tbody, tfoot) > tr > td,
table[rules=all i] > tr > th,
table[rules=all i] > tr > td {
  -cr-hint: presentational-hint;
  border-width: 1px;
  border-style: solid;
}

table[rules=groups i] > colgroup {
  -cr-hint: presentational-hint;
  border-left-width: 1px;
  border-left-style: solid;
  border-right-width: 1px;
  border-right-style: solid;
}

table[rules=groups i] > thead,
table[rules=groups i] > tbody,
table[rules=groups i] > tfoot {
  -cr-hint: presentational-hint;
  border-top-width: 1px;
  border-top-style: solid;
  border-bottom-width: 1px;
  border-bottom-style: solid;
}

table[rules=rows i] > :where(thead, tbody, tfoot) > tr,
table[rules=rows i] > tr {
  -cr-hint: presentational-hint;
  border-top-width: 1px;
  border-top-style: solid;
  border-bottom-width: 1px;
  border-bottom-style: solid;
}

/* crengine-:
colgroup[span]: not supported
col[span]: not supported
td[colspan] td[rowspan] th[colspan] th[rowspan]: handled internally
*/

:is(table, thead, tbody, tfoot, tr) > form {
  display: none !important;
}

table[cellspacing] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-border-spacing-from-cellspacing-attribute;
}

/* Note: following list of selectors in the specs simplified to use :where(...) */
table[cellpadding] > :where(thead, tbody, tfoot) > tr > th,
table[cellpadding] > :where(thead, tbody, tfoot) > tr > td,
table[cellpadding] > tr > th,
table[cellpadding] > tr > td {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-padding-from-parent-table-cellpadding-attribute;
}

/* crengine support for height in table (and in general) is limited, but let's map these anyway */
table[height], thead[height], tbody[height], tfoot[height], tr[height] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-height-from-height-attribute;
}

th[height], td[height] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-height-from-height-attribute-ignoring-zero;
}

table[width], th[width], td[width] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-width-from-width-attribute-ignoring-zero;
}

col[width] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-width-from-width-attribute;
}

table[background], thead[background], tbody[background], tfoot[background], tr[background], th[background], td[background] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-background-image-from-background-attribute;
}

table[bgcolor], thead[bgcolor], tbody[bgcolor], tfoot[bgcolor], tr[bgcolor], th[bgcolor], td[bgcolor] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-background-color-from-bgcolor-attribute;
}

table[bordercolor] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-border-color-from-bordercolor-attribute;
}

/* Note: this is not specified, neither as CSS nor in writing, in the HTML specs.
   But Firefox has the following, and it feels it's the expected behaviour that inner
   cell borders get the color specified as table bordercolor=. Edge does this too. */
table[bordercolor] > tbody,
table[bordercolor] > thead,
table[bordercolor] > tfoot,
table[bordercolor] > col,
table[bordercolor] > colgroup,
table[bordercolor] > * > tr,
table[bordercolor] > tr,
table[bordercolor] > * > tr > th,
table[bordercolor] > tr > th,
table[bordercolor] > * > tr > td,
table[bordercolor] > tr > td {
  -cr-hint: presentational-hint;
  border-color: inherit;
}


/* Form controls */

input, select, button, textarea {
  letter-spacing: initial;
  word-spacing: initial;
  line-height: initial;
  text-transform: initial;
  text-indent: initial;
}
  /* text-shadow: initial; crengine-: not supported */
  /* appearance: auto; crengine-: not supported */

/* crengine-: not supported
input:not([type=image i]) {
  overflow: clip !important;
  overflow-clip-margin: 0 !important;
}
*/

input, select, textarea {
  text-align: initial;
}

input, button {
  display: inline-block;
}

input:is([type=reset i], [type=button i], [type=submit i]), button {
  text-align: center;
}

/* crengine-: not supported
input[type=hidden i], input[type=file i], input[type=image i] {
  appearance: none;
}
*/

input:is([type=radio i], [type=checkbox i], [type=reset i], [type=button i],
[type=submit i], [type=color i], [type=search i]), select, button {
  box-sizing: border-box;
}

textarea {
  white-space: pre-wrap;
}


/* The hr element */

hr {
  color: gray;
  border-style: inset;
  border-width: 1px;
  margin: 0.5em auto;
}
  /* overflow: hidden; crengine-: not supported */

hr[align=left i] {
  -cr-hint: presentational-hint;
  margin-left: 0;
  margin-right: auto;
}

hr[align=right i] {
  -cr-hint: presentational-hint;
  margin-left: auto;
  margin-right: 0;
}

hr[align=center i] {
  -cr-hint: presentational-hint;
  margin-left: auto;
  margin-right: auto;
}

hr[color], hr[noshade] {
  -cr-hint: presentational-hint;
  border-style: solid;
}

hr[size] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-various-from-hr-size-attribute;
}

hr[width] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-width-from-width-attribute;
}

hr[color] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-color-from-color-attribute;
}


/* The fieldset and legend elements */
/* crengine: basic styling as specified, but complicated handling described not supported. */

fieldset {
  display: block;
  margin-left: 2px;
  margin-right: 2px;
  border: groove 2px gray;
  padding: 0.35em 0.75em 0.625em;
}
  /* border: groove 2px ThreeDFace; crengine-: color 'ThreeDFace' not supported */
  /* min-inline-size: min-content; crengine-: not supported */

legend {
  padding-left: 2px;
  padding-right: 2px;
}

/* crengine-: not supported
legend[align=left i] {
  justify-self: left;
}
legend[align=center i] {
  justify-self: center;
}
legend[align=right i] {
  justify-self: right;
}
*/


/* Replaced elements */

iframe {
  border: 2px inset;
}

/* crengine-: not supported
video {
  object-fit: contain;
}
img:is([sizes="auto" i], [sizes^="auto," i]) {
  contain: size !important;
  contain-intrinsic-size: 300px 150px;
}
*/

/* Note: the HTML specs do not explicitely mention the following are to be presentational,
   but let's consider them presentational, as most similar others. */
iframe[frameborder='0'], iframe[frameborder=no i] {
  -cr-hint: presentational-hint;
  border: none;
}

embed[align=left i], iframe[align=left i], input[align=left i],
object[type=image i][align=left i], img[align=left i] {
  -cr-hint: presentational-hint;
  float: left;
}

embed[align=right i], iframe[align=right i], input[align=right i],
object[type=image i][align=right i], img[align=right i] {
  -cr-hint: presentational-hint;
  float: right;
}

embed[align=top i], iframe[align=top i], input[align=top i],
object[type=image i][align=top i], img[align=top i] {
  -cr-hint: presentational-hint;
  vertical-align: top;
}

embed[align=baseline i], iframe[align=baseline i], input[align=baseline i],
object[type=image i][align=baseline i], img[align=baseline i] {
  -cr-hint: presentational-hint;
  vertical-align: baseline;
}

embed[align=texttop i], iframe[align=texttop i], input[align=texttop i],
object[type=image i][align=texttop i], img[align=texttop i] {
  -cr-hint: presentational-hint;
  vertical-align: text-top;
}

/* align=middle/center should have a specific treatment: middle of image aligned
   to the baseline, a behaviour that none of the classic CSS vertical-align
   values provide; so we fallback to handling them as absmiddle */
embed[align=middle i], iframe[align=middle i], input[align=middle i],
object[type=image i][align=middle i], img[align=middle i],
embed[align=center i], iframe[align=center i], input[align=center i],
object[type=image i][align=center i], img[align=center i],
embed[align=absmiddle i], iframe[align=absmiddle i], input[align=absmiddle i],
object[type=image i][align=absmiddle i], img[align=absmiddle i],
embed[align=abscenter i], iframe[align=abscenter i], input[align=abscenter i],
object[type=image i][align=abscenter i], img[align=abscenter i] {
  -cr-hint: presentational-hint;
  vertical-align: middle;
}

embed[align=bottom i], iframe[align=bottom i], input[align=bottom i],
object[type=image i][align=bottom i], img[align=bottom i] {
  -cr-hint: presentational-hint;
  vertical-align: bottom;
}

embed[hspace], input[hspace], object[type=image i][hspace], img[hspace] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-margin-from-hspace-attribute;
}

embed[vspace], input[vspace], object[type=image i][vspace], img[vspace] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-margin-from-vspace-attribute;
}

input[type=image i][border], object[border], img[border] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-border-from-border-attribute;
}

embed[width], iframe[width], input[type=image i][width], video[width], object[width], img[width] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-width-from-width-attribute;
}

embed[height], iframe[height], input[type=image i][height], video[height], object[height], img[height] {
  -cr-hint: presentational-hint;
  -cr-apply-func: css-height-from-height-attribute;
}

/* Widgets: button, details, summary, input[type], marquee, meter, progress, select, textarea
   crengine: no specific handling, their content may or may not be displayed as block or inline */

marquee {
  display: inline-block;
  text-align: initial;
}
