racket / scribble

Other
201 stars 93 forks source link

Make @emph nestable, logical markup #220

Closed rrthomas closed 4 years ago

rrthomas commented 4 years ago

Use \emph in the LaTeX renderer and CSS in the HTML renderer to make nested emphasis toggle between italics and upright.

The CSS for this is not very nice (the nesting is written out); it would be nicer if the proposed "toggle()" function were available.

Also, it would seem sensible to use em elements in HTML, but I can't work out how to generate those at the point where styles are dealt with.

samth commented 4 years ago

This looks good to me.

rrthomas commented 4 years ago

@samth Thanks! Re my question above, is there a way I overlooked to generate em elements rather than invent a new emph style? (The CSS can be made to work just as easily for em elements.)

mflatt commented 4 years ago

@rrthomas If you want to generate <em>, the place to change would probably be style->tag in "html-render.rkt". Also, it would be nice to include an update to "markdown-render.rkt".

rrthomas commented 4 years ago

On Wed, 13 Nov 2019 at 15:25, Matthew Flatt notifications@github.com wrote:

@rrthomas https://github.com/rrthomas If you want to generate , the place to change would probably be style->tag in "html-render.rkt".

Thanks for the hint. I looked into this, but couldn't get it to work yet.

I can't find another case that works the same (where a style becomes a particular tag), but this does seem to be the right thing in this case.

So, I changed style-tag to:

(define (style->tag style) (case style [(emph) 'em] [else (for/or ([s (in-list (style-properties style))]) (and (alt-tag? s) (string->symbol (alt-tag-name s))))]))

I also found that I had to have 'emph mentioned in element-style->attribs, as otherwise I get an "unrecognized style symbol" error, reasonably enough. So I guessed that I need to add "elem" to the same arm of the case as 'newline, not generating any attributes.

So far so good, except that style->tag is never called on an element with style 'emph. I verified this by using define/debug on style->tag to trace its calls. But I can see that style->tag doesn't seem to be called for elem styles, only para styles (i.e. only for things that become HTML elements other than spans).

I presume that the part of define/private render-plain-content that goes:

            (,(cond
               [alt-tag alt-tag]
               [link? 'a]
               [newline? 'br]
               [else 'span])

should come into play (i.e. alt-tag should be defined as 'em at this point).

As for implementation in Markdown, I see that there for italic & bold the renderer takes care not to insert markdown if the text is already italic or bold; for emph, it seems to me, I simply need to implement it like italic but without that test, so that the italics alternate. Does that sound right?

-- https://rrt.sc3d.org

rrthomas commented 4 years ago

I have now implemented support in the markdown renderer, so this PR is ready to be merged.

I didn't manage to make the change I wanted to the HTML renderer to use <em> elements, but that could be changed later. In any case, perhaps it's better to use style annotations consistently?

Also, in Markdown I output the underscores (for italics) with a zero-width space before the opening underscore, and one after the closing underscore. This prevents pairs of underscores that would be interpreted as "strong" rather than "italics". An alternative would be to just output one underscore every time the "italics" state changes, but that would make the markdown look rather odd, and I couldn't see a simple way to write it.