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

Abnormal letter spacing in Chrome / Chromium #1272

Open
christopherkade opened this issue Nov 19, 2017 · 26 comments
Open

Abnormal letter spacing in Chrome / Chromium #1272

christopherkade opened this issue Nov 19, 2017 · 26 comments
Labels

Comments

@christopherkade
Copy link

When calling:

html2canvas(document.getElementsByClassName('console'), {
      onrendered: function(canvas) {
        var img = canvas.toDataURL()
        var iframe = '<iframe src="' + img + '" frameborder="0" style="border:0; top:0px; left:0px; bottom:0px; right:0px; width:100%; height:100%;" allowfullscreen></iframe>'
        var x = window.open();
        x.document.open();
        x.document.write(iframe);
        x.document.close();
      },
      letterRendering: true,
    });

Both with or without letterRendering, this is what Chrome outputs:

html2canvasbug

When the output in Firefox is:

screenshot-2017-11-19 http localhost

Any specific reason why it renders it like that?

@niklasvh
Copy link
Owner

niklasvh commented Nov 22, 2017

The letter spacing (word spacing in this case) looks correct actually, what doesn't appear to be correct is the font family. Which version of html2canvas are you using? Can you replicate the issue on jsfiddle?

Edit: with letterRendering it should render differently as you mentioned.

@christopherkade
Copy link
Author

christopherkade commented Nov 22, 2017

Thanks for your reply,

I'm using the version 0.5.0-beta4.

What do you mean the work spacing looks correct? Are you referring to the first picture I have shared? Would the font create such spacing between words?

Note that I'm using CodeMirror for the text editor that is rendered, specifically an Angular wrapper: ng2-codemirror.

I tried reproducing the issue to no avail here.

@LinkTree3
Copy link

I also found the same problem in firefox and chrome. If you have a letter-spacing css rule on the text it will render the text with large gaps between each word. This was not the case in version 0.4.1 it used to render text perfectly but it was missing pseudo elements(:before :after)

@christopherkade
Copy link
Author

Once you remove the letter-spacing rule everything goes back to normal for you? I'm not using it, neither in my component's css nor in my custom code-mirror's css file.

@LinkTree3
Copy link

Yes After removing the letter-spacing rule from the CSS the issue is gone. there are no large spaces between words. it's something in the rendering of the page at the part of the letter-spacing that is messing it up.

@LinkTree3
Copy link

LinkTree3 commented Nov 23, 2017

Update! I just built the library from the latest sources on master and it works perfectly. everything looks really good so far. Previously I tried with the v0.5.0-beta4 release.

Edit: Found 1 issue on firefox. background-images aren't being clipped to text when
-webkit-background-clip: text;
-webkit-text-fill-color: transparent;
are used.
works great in chrome though.

@christopherkade
Copy link
Author

I don't use any letter-spacing property in my CSS and the issue is still present. I am using v0.5.0-beta4 though.

@LinkTree3
Copy link

Try building from the latest master sources.

@christopherkade
Copy link
Author

Done, and yet this does not solve the problem, the display remains the same.

@niklasvh niklasvh added the Bug label Dec 12, 2017
@niklasvh
Copy link
Owner

Should be fixed with 77d258f

@christopherkade
Copy link
Author

Seems like the problem persists like such:

screenshot_2017-12-18_09-56-43

Here's how I rendered the element:

html2canvas(document.body).then(function(canvas) {      
      document.body.appendChild(canvas);
});    

I have downloaded the latest pre-release version as mentioned by you and replaced the old one.

@niklasvh niklasvh reopened this Dec 18, 2017
@niklasvh
Copy link
Owner

@christopherkade does it fix it if you set the option letterRendering: true?

@christopherkade
Copy link
Author

Sadly it does not, here's how I do it:

let element = document.getElementById('console');
const options = {
  letterRendering: true
};

html2canvas(element, options).then(function(canvas) {      
  document.body.appendChild(canvas);
      
  var url = canvas.toDataURL();
  var img = '<img src="' + url + '" style="border:0;"></img>'
  var x = window.open();
  x.document.open();
  x.document.write(img);
  x.document.close();
});

Same result if I try the example given in the repository.

@christopherkade
Copy link
Author

I have found a workaround for the matter (and it's not very clean):

// Package used to detect the browser used by the user
const browser = detect();
const element = document.getElementById('console');

// Set up my options
let options = {};
// For some reason foreignObjectRendering solves the spacing issue on Chrome but gives an error on Firefox, so I detect the browser and apply the adequate options.
if (browser && browser.name === 'chrome') {      
  options = {
    useCORS: true,
    foreignObjectRendering: true
  };  
}

// Open the canvas in a new window
html2canvas(element, options).then(function(canvas) {
  const url = canvas.toDataURL();
  const img = '<img src="' + url + '" style="border:0;"></img>'
  const x = window.open();
  x.document.open();
  x.document.write(img);
  x.document.close();
});

Note that the error I get on Firefox when using the second option is as follows:

Uncaught (in promise): [Exception... "Method not implemented" ...

@ordas
Copy link

ordas commented Apr 5, 2018

Same problem!!

@phillipegf
Copy link

Solved here by removing CSS attribute font-variant-numeric: proportional-nums from HTML body.

@c01nd01r
Copy link

c01nd01r commented Dec 19, 2018

Fixed similar problem with removing font-variant: tabular-nums; (in antd.css)
2018-12-19 19 20 38

@mohafouad
Copy link

same problem with Arabic language any suggestion please ?

@2xSamurai
Copy link

2xSamurai commented Dec 31, 2018

@mohafouad +1

Have you found any fix for this? Thank you.

@mohafouad
Copy link

@2xSamurai no :(

@maaoui
Copy link

maaoui commented Feb 13, 2019

I have fixed this also by going to the div I want to screenshot and then I set the " font-variant: normal; " this has worked for me hope it helps .

@Malarkey-Jhu
Copy link

fixed if I add font-variant: normal !important to outer div of whole content (in antd project)

@zxr3680166
Copy link

same problem, drived me crazy
image

font-variant: normal !important not working

@nora-white
Copy link

nora-white commented Aug 16, 2019

@Malarkey-Jhu's and @maaoui's answer solved my problem.

The problem I had: Font family wasn't working and spacing was very wonky. Sometimes I would have overlapping letters.

What I do: During export I call element.style.setProperty('font-variant', 'normal') on the element with the text, and this allows the font-family to show properly, and the spacing to not be all wonky. Then I remove that property after I've finished exporting.

@spideeee
Copy link

Based on the above solutions, this issue is fixed for me by changing -webkit-font-variant-ligatures and font-variant-ligatures to normal in codemirror css file. I am using CodeMirror version 5.42.2.

@chriszrc
Copy link

For me, this problem was caused by trying to take screenshots of text that was using a custom font (even if the fonts were loaded from the same domain). I had to change the font back to something built-in in the interim clone h2c creates, then everything worked perfectly (minus the custom fonts...):

html2canvas(element, {
      // removeContainer: false, //useful for testing changes to the interim iframe copy
      onclone: (document: Document) => {
        Array.from(
          document
            .querySelector(".analysis-container .ng-star-inserted")
            .children[0].querySelectorAll("*"),
        ).forEach((e) => {
          let existingStyle = e.getAttribute("style") || "";
          e.setAttribute("style", existingStyle + "; font-family: Helvetica, sans-serif !important");
        });
      },
    }).then(function (canvas) { //...etc

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests