Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

WIP: fix rmarkdown regarding new theme behaviour in pandoc #1489

Merged
merged 17 commits into from Dec 6, 2018

Conversation

cderv
Copy link
Collaborator

@cderv cderv commented Dec 4, 2018

This is a proposition to fix #1471. The issue resumes the problem introduced by recent changes in pandoc 2. The way pandoc > 2 insert css styling for highligting when converting to html conflicts with boostrap and theme.

This proposition tries to adapt rmarkdown default html template to insert css rules that deals with that.

This may be temporary if we try to report this impact to pandoc and find a clever solution that does not break this.

This is work in progress to get feedback and iterate. Also because I think the impact is rather broad among different format that rmarkdown convert to thanks to pandoc.


This change is Reviewable

@cderv
Copy link
Collaborator Author

cderv commented Dec 4, 2018

This simple insertion of to css rules fix the issue with html_document
image

but now, as pandoc 2 applies the highlighting rule to div, with notebook we have a the background color applied even when code is hidden.

image

and when opening the code
image

Not sure we want that... I'll see if I can add something to change that.

@yihui
Copy link
Member

yihui commented Dec 4, 2018

Perhaps we should check if the parent node is div.sourceCode before deciding where to insert the div containing the Show/Hide button:

If we are inside div.sourceCode, we need to insert this div to the parent node of div.sourceCode.

@cderv
Copy link
Collaborator Author

cderv commented Dec 4, 2018

Thanks for pointing this out.
It is exactly what I am trying to do ! That confirms the idea - thanks!
it took me some time to discover how rmarkdown inserted the collapsible code ! I do not know the 📦 inside / out ... yet 😉
I am currently modifying this js file. Will update the PR soon.

@cderv
Copy link
Collaborator Author

cderv commented Dec 4, 2018

Ok for notebook I guess
code-folding

Small customisation pandoc css introduce

div.sourceCode {
    margin-top: 1em;
    margin-right: 0px;
    margin-bottom: 1em;
    margin-left: 0px;
}

As we insert <div class='row'> just before, I found the margin a little big. So I modified to reduce, using em also and not px

div.row {
  /* to reduce the space introduce in pandoc div.sourceCode */
  margin-bottom: -0.8em;
}

🤔 not sure of that change...
I think I'll test several other format and option to see if something is wrong or if all is fixed.

@@ -45,7 +45,9 @@ window.initializeCodeFolding = function(show) {
buttonCol.append(showCodeButton);
buttonRow.append(buttonCol);

div.before(buttonRow);
var sourceCodeBlock = $('div.sourceCode');
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Will this also work with Pandoc 1.9.x? i.e. Does Pandoc 1.9 also generate div.sourceCode?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is part of the test I need to make. Yes pandoc 1.9.x have a div.sourceCode but the css applied to those part have changed.

So yes this line work and the button is added above without issue, but the margin trick does not work. Will change that.

Also the main fix

pre.sourceCode  {
  color: inherit;
  background-color: transparent;
}

does not work with pandoc 1.9 because in this pandoc version the background is applied to pre.sourceCode so it erase it... -
if we want something that work with old and new, I need to find another one... 😕

Copy link
Collaborator Author

@cderv cderv Dec 5, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ok - there is not div.sourceCode inserted if we use highlight = 'default', whatever the version of pandoc. This is because highlight default and textmate does not use pandoc but uses highlightjs and this does not insert the div. I did not know about that and I need to deal with that... More complicated that I thought 🤔

@cderv
Copy link
Collaborator Author

cderv commented Dec 4, 2018

@yihui here is a proposition to make the fix conditional to pandoc > 2. As the issue is due to change from pandoc 2, we can activate a variable for pandoc template based on the version. This way the changes are only applied if used with pandoc 2.
This also could be useful to add new features - at some point two template could exist.

This was for me the more obvious fix right now, rather than going with css mastery. (I did not find one that could work both with pandoc < 2 and pandoc > 2.

What do you think ?

@cderv
Copy link
Collaborator Author

cderv commented Dec 5, 2018

I just found that some highlight parameter for yaml header in Rmardown does not use pandoc. So the proposition does not deal with those, I need to continue working on a solution.

@cderv
Copy link
Collaborator Author

cderv commented Dec 5, 2018

this should now work. I will try to test thoroughly. You can give it a try also.

  • default and textmate (not pandoc theme) are working.
  • 1.9 and > 2 works also in both case.
  • new code is activated only when pandoc theme are added and when pandoc 2 is used

Copy link
Member

@yihui yihui left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sounds like there will be more work to do... :(

inst/rmd/h/default.html Show resolved Hide resolved
$if(ispandoc2)$
pre.sourceCode {
color: inherit;
background-color: transparent;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actually this will break themes that don't have a background color, such as pygments #654 (comment) Such themes should inherit the background color from Bootstrap's pre.

My head is starting to hurt...

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes it was not clear to me and I wanted to test it further. Thanks for the confirmation. This blog post shows the result of pandoc styling, and indeed pygment as a white background, but with bootstrap it is not the case. As we need to

  • override the pre style of bootstrap because pandoc apply the background color and color to the parent
  • inherits for the pre style of bootstrap to keep the pre css rule from bootstrap for theme that don't have background and color
    I think we should also do something conditional.

Of pandoc highlighting style, we have frome the src code

  • pygments with nothing ➡️ should inherit boostrap color and background-color
  • tango with no default color ➡️ should inherit boostrap color only
  • haddock is like pygments
  • monochrome is like pygments

I'll come up with something... 🤔 and yes 🤯

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I made a proposition by manually setting which style has background and color or not. Then with two more template variable, the correct rule is activated.

In the same idea, with pandoc2 we can do something more dynamic. I hesitate to introduce this in rmarkdown but it could be interesting. We can get highlight information with

  if (pandoc2.0()) {
    arg <- c("--print-highlight-style", pandoc_highlight)
    json_res <- system2(pandoc(), arg, stdout = TRUE)
    properties <- jsonlite::fromJSON(paste0(json_res, collapse = "\n"))
  }

we then get for pygments

> properties$`background-color`
NULL
> properties$`text-color`
NULL

and for tango

> properties$`text-color`
NULL
> properties$`background-color`
[1] "#f8f8f8"

We could introduce a function get_higligthing_styles in rmarkdown (that we could export) and use this here to test if is.null or not. This could even mean that we could fill in the value in
pre.sourceCode css rule, instead of inherits or transparent

I run this by you before pushing anything. I have a working code locally though - I can share then revert.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

in fact you can see it in another branch

R/html_document.R Outdated Show resolved Hide resolved
@yihui yihui added this to the v1.11 milestone Dec 5, 2018
Copy link
Member

@yihui yihui left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I thought for another hour on this, and I tend to use JavaScript to replace div.sourceCode{...} with pre.sourceCode{...} in CSS if div.sourceCode contains rules for color or background-color: https://developer.mozilla.org/en-US/docs/Web/API/CSSStyleSheet

e.g. change

div.sourceCode
  { color: #cccccc; background-color: #303030; }

to

pre.sourceCode
  { color: #cccccc; background-color: #303030; }

@cderv
Copy link
Collaborator Author

cderv commented Dec 5, 2018

Initially, I did not want to touch what pandoc is inserting.
I'll give it a go then.

Rather than modified, could'nt we add pre.sourceCode to the rule if existing with background or color ?

div.sourceCode, pre.sourceCode
  { color: #cccccc; background-color: #303030; }

kind of the same but maybe more compatible with pandoc ?

@yihui
Copy link
Member

yihui commented Dec 5, 2018

Yes you certainly can. I guess the risk is minimal if we only modify this single rule from div.sourceCode to pre.sourceCode, though. If we define rules for both div and pre, there is a subtle disadvantage:

pre.sourceCode only

image

both div.sourceCode and pre.sourceCode

image

Did you notice the differences in the four corners? That's because Bootstrap defined rounded corners for pre. If the div has a background color, the corners will be filled.

Implementation-wise, you probably have to loop through document.styleSheets to find this particular stylesheet.

@cderv
Copy link
Collaborator Author

cderv commented Dec 5, 2018

oh ! I did not notice before reading what the difference was. I read the doc you linked to and some others, I agree that this require iteration. I'll work on that ! thanks for pointing the direction.

@cderv
Copy link
Collaborator Author

cderv commented Dec 6, 2018

I reverted back everything and deal with this using javascript code now. So just one file changed 😄

Do you find this better and easier to maintain ?

I put the script at the end of the template but I wonder if it should be elsewhere... 🤔 Normally, if no pandoc highlighting is chosen, no need to insert this script. I hesitated to put it in this part, that i believe is activated only by using pandoc highlighting
https://github.com/rstudio/rmarkdown/blob/e91e4c27bb223b6b0380a185c6f2fe5fb2ee2404/inst/rmd/h/default.html#L50-65

Also, I think there is another small change. New pandoc 2.0 added the div.sourceCode part and applied also a css rule for margin (see in skylighting 25 and 26 that modified the style applied by pandoc)

div.sourceCode { margin: 1em 0; }

this create a difference in rendered rmarkdown. I think it is not really impacting but I let you decide if it should be dealt with.

Copy link
Member

@yihui yihui left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Many thanks! I'll take it from here. I don't care about the margin issue.

(function() {
var stylesheets = document.styleSheets;
for(var i=0; i<stylesheets.length; i++){
var rules = stylesheets[i].cssRules;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Need try/catch here since the cssRules property is not necessarily accessible: https://developer.mozilla.org/en-US/docs/Web/API/CSSStyleSheet#Notes

also add an identifier on Pandoc's CSS to save time on looking for the right <style> sheet to modify
@yihui yihui merged commit a0c0c68 into rstudio:master Dec 6, 2018
@cderv
Copy link
Collaborator Author

cderv commented Dec 6, 2018

Perfect ! So, my intuition was correct to move the hack. For rest, I am always learning - nice JS improvement.

Thanks @yihui for your review!

@cderv cderv deleted the fix-1471-pandoc-css branch December 6, 2018 06:57
@yihui
Copy link
Member

yihui commented Dec 6, 2018

You did 99% of the work, and I only did the rest 1% :)

yihui pushed a commit to RLesur/rmarkdown that referenced this pull request Apr 1, 2019
@github-actions github-actions bot locked as resolved and limited conversation to collaborators Nov 3, 2020
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Background color (using zenburn highlight) in R-chunks not showing correctly
2 participants