W3C home > Mailing lists > Public > www-style@w3.org > February 2016

Re: [gcpm] coalescing sequences of numbers for cross-references, back-of-the-book index etc

From: Florian Rivoal <florian@rivoal.net>
Date: Wed, 10 Feb 2016 12:02:12 +0900
Cc: "Tab Atkins Jr." <jackalmage@gmail.com>, www-style list <www-style@w3.org>
Message-Id: <0611A361-E9B9-466A-9F2A-DB40AF56814B@rivoal.net>
To: "Liam R. E. Quin" <liam@w3.org>

> On Dec 17, 2015, at 14:20, Liam R. E. Quin <liam@w3.org> wrote:
> 
> On Wed, 2015-12-16 at 15:01 -0800, Tab Atkins Jr. wrote:
>>  
>> Right, but you haven't proposed a mechanism for *finding* the page
>> numbers yet.
> 
> We already have such a mechanism in CSS, in gcpm:
>   content: target-counter(attr(href, url), page)
> 
> I omitted that since I don't need to propose it. A full solution would
> be using something like
> 
> a::::before  {
>   content: target-counter(attr(href, url), page)
> }

By the way, I don't think the spec says anything about how deal with the potentially unbounded number of layout passes that may be needed to implement target-counter.

Inserting the counter takes some space, triggering a relayout which may change the number of pages, which changes the value, and therefore potentially the size of the counter, which can trigger a relayout....

In most cases, this should stabilize pretty quickly, but not necessarily, and I believe you can even get infinite loops in corner cases. Here's an example of such a loop:

On my computer at least, using the Times Roman font face, "109" takes a tiny little bit more room than "110". Say I have an index at the beginning of a book with a target counter referencing an element which is at the very end of page 109. When I inject the "109" counter in the index, it is just barely large enough to push the content it wants to reference onto page 110. So I update the counter to say 110 instead of 109, and now it is barely small enough that the target fits in page 109. So I update the counter which makes it bigger, and the target gets moved back to page 110, and we can keep going at this for a while.

Yes, this is an edge case. But the possibility of infinite loops, even on edge cases, is bad.

As far as I can tell, the coalescing that you propose does not fundamentally change this, but probably makes it quantitatively worse, since coalescing can cause greater variation of size in the index.

Saying that we stop after at most n passes would create incorrect results, and banning target-counter from referring to subsequent content would be too limiting.

One possibility could be to change the syntax of target-counter to require it to declare the size it wants, so that changing the value does not change the layout. Something like this

  a::before  {
    content: target-counter(3ch, attr(href, url), page);
  }

would get you 3ch worth of space. If your actual counter is smaller, you get a bit of blank space. If it is larger, you get (ink) overflow. Using the coalescing functions would not affect this consumed space (and therefore leave you with more space consuming blank space as you coalesce more numbers).

This doesn't seem very elegant to me, but at least it avoids feedback loops.

Anyone has an idea for a less heavy handed approach that still gets us out of infinite looping, and hopefully out of many passes as well?

 - Florian
Received on Wednesday, 10 February 2016 03:02:38 UTC

This archive was generated by hypermail 2.3.1 : Monday, 2 May 2016 14:39:36 UTC