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

Image is displayed in browser, but doesn't come through with download (Safari) #348

Open
Yehuda-Edelstein opened this issue Dec 16, 2022 · 33 comments
Labels

Comments

@Yehuda-Edelstein
Copy link

Yehuda-Edelstein commented Dec 16, 2022

Expected Behavior

I'm trying to download html including an img tag using safari, but the source doesn't show up, just an empty div.

Current Behavior

I have a preview box:

function Preview() {
          const mobileRef = useRef(null);
          const download = () => {
            setIsLoading(true);
            toPng(mobileRef.current, {})
              .then((dataUrl) => {
                const link = document.createElement("a");
                link.download = "youtube.png";
                link.href = dataUrl;
                link.click();
                setIsLoading(false);
              })
              .catch((err) => {
                console.log(err);
              });
          };
        
        return (
                <div>
                  <div ref={mobileRef}>
                    <img src={img} alt="" />
                  </div>
                  <button onClick={download}>DOWNLOAD</button>
                </div>
        )
}

When I download the image I get all the html besides the picture; instead just an empty div. where the image should be. All other parts of the html convert and download as a PNG, so I'm confused as to why the only issue is converting the img, especially when the img is being displayed in the browser. I'm wondering if this is a react issue, or just an issue with downloading images of an img.

Possible Solution

I'm not sure what's causing this, maybe it's an issue with my set up or css, but it doesn't really make sense to me. Someone mentioned in the comments that it may be an issue with CORS; I checked the network tab on safari when I hit download and there are a few things that come up:

Screenshot 2022-12-26 at 12 40 03 AM

The bottom is the png file (my static file) that is displayed in the browser but not when I download the html. Here it is displayed as a png, headers read 200, status okay.

Next up is an svg of the entire downloaded html. Inside the network tab, the svg file shows everything even the static png that doesn't show up in the downloaded html-to-image. Headers also read 200.

Next is an xhr, looks the same as the first png. Also 200.

The top 3 are all 304 not modified.

I'm pretty new to coding so all of this doesn't really make a lot of sense to me.

Steps To Reproduce

Best way to reproduce this is to just use the code example I gave and replace the src with any photo you have locally or online. I tried downloading with local photos and with google photos/gifs online and both ways come back with an empty div. I think it's important to state again that the images are displaying in the safari browser, they just don't get converted from html to PNG.

Your Environment

Since this is only happening to me in safari, I can't help but think it's not an issue with my code. Of course it could be -- I am setting my img with a react setState and having the src={require('')} but again, since the img displays in the browser, I can't help but think it's just a bug. Would love to help more, just not really sure what's causing the issue.

  • html-to-image: 1.11.2
  • OS: macOS Monteray 12.6
  • Browser: chrome (108.0.5359.98) but also safari.
@vivcat
Copy link
Contributor

vivcat bot commented Dec 16, 2022

👋 @Yehuda-Edelstein

Thanks for opening your first issue here! If you're reporting a 🐞 bug, please make sure you include steps to reproduce it.
To help make it easier for us to investigate your issue, please follow the contributing guidelines.

We get a lot of issues on this repo, so please be patient and we will get back to you as soon as we can.

@pabloiea1995
Copy link

Hello Yehuda!
We faced the same issue, and it turned out to be a cors error with our image server. checkout the network Tab to see if that's the case. If it is, we solved it through the server configuration.

Hope it helps!

@Yehuda-Edelstein
Copy link
Author

how do i test that out tho, if the error only happens through safari, or other mobile os? Is there a way to just add a fix assuming the issue is with cors?

@Yehuda-Edelstein
Copy link
Author

WebSocket network error: The operation couldn’t be completed. (OSStatus error -9847.) I get this error in network/messages when I run the code over browserstack to recreate apple os

@Yehuda-Edelstein
Copy link
Author

Hello Yehuda! We faced the same issue, and it turned out to be a cors error with our image server. checkout the network Tab to see if that's the case. If it is, we solved it through the server configuration.

Hope it helps!

Also what do you mean through server configuration exactly.

@pabloiea1995
Copy link

I am not sure what that error means exactly as I tested it in Chrome browser and it shows a CORS error. Maybe you should checkout if that error is related to CORS.
When I talk about server configuration I mean proxy headers.
We realized it was our server problem because internet images (for example from google images) loaded correctly. You could do the same test to discard this problem

@labaran1
Copy link

Facing the same issue here. I'm getting a cors error. @pabloiea1995 I currently don't get your fix.

@Yehuda-Edelstein
Copy link
Author

Yehuda-Edelstein commented Dec 19, 2022 via email

@labaran1
Copy link

Desktop. Using Ubuntu 22.04.1 LTS chrome.
Mobile Safari
@pabloiea1995

@Yehuda-Edelstein
Copy link
Author

how did you see what type of errors it was on mobile safari? Like I can't figure out how to inspect or see errors with mobile safari

@labaran1
Copy link

Okay, my bad. I mean the issue is also on safari mobile. but, if you have a mac, you can use the web inspector. Go to settings on your phone, then safari, then toggle Web Inspector.

how did you see what type of errors it was on mobile safari? Like I can't figure out how to inspect or see errors with mobile safari

@Yehuda-Edelstein
Copy link
Author

So I think the issue is with safari, not just on mobile. Just use safari on my mac and it downloads all the html besides the image, however the image is previewed in the browser. I checked and there are no errors. The network tab shows a 200, what's even weirder is that when I look at the data when I download the html as png, in the preview tab it shows the image I upload, but doesn't come through when I download the html.

@labaran1
Copy link

So I think the issue is with safari, not just on mobile. Just use safari on my mac and it downloads all the html besides the image, however the image is previewed in the browser. I checked and there are no errors. The network tab shows a 200, what's even weirder is that when I look at the data when I download the html as png, in the preview tab it shows the image I upload, but doesn't come through when I download the html.

before the cors error, I experienced this same issue with chrome.

@Yehuda-Edelstein
Copy link
Author

Yehuda-Edelstein commented Dec 19, 2022 via email

@labaran1
Copy link

I've not fixed it yet. It's a ticket I'm working on.

Have you seen the same error using safari? Also what was ur fix?

On Mon, Dec 19, 2022 at 12:41 PM labaran1 @.> wrote: So I think the issue is with safari, not just on mobile. Just use safari on my mac and it downloads all the html besides the image, however the image is previewed in the browser. I checked and there are no errors. The network tab shows a 200, what's even weirder is that when I look at the data when I download the html as png, in the preview tab it shows the image I upload, but doesn't come through when I download the html. before the cors error, I experienced this same issue with chrome. — Reply to this email directly, view it on GitHub <#348 (comment)>, or unsubscribe https://github.com/notifications/unsubscribe-auth/AWAMRK2OTO24IJPAJEKPL6TWOCM5BANCNFSM6AAAAAATAKQYQM . You are receiving this because you were mentioned.Message ID: @.>

@Yehuda-Edelstein Yehuda-Edelstein changed the title Image is displayed in the browser, but doesn't come through with download Image is displayed in browser, but doesn't come through with download (Safari) Dec 26, 2022
@Yehuda-Edelstein
Copy link
Author

After going over the issue more, it's definitely limited to safari.

@dhruvilxcode
Copy link

I am facing a similar issue, I tested the library with Chrome on iOS, and The behaviour is the same as safari on iOS.
The issue is only on iPhone. as I tested with Android, and Desktop, I got good results.

If anyone has a fix for it, I would greatly appreciate it. 👍🏻

@Yehuda-Edelstein
Copy link
Author

Yehuda-Edelstein commented Jan 1, 2023 via email

@s-kris
Copy link

s-kris commented Jan 1, 2023

Same issue.
The image is lost after downloading.

Bug appears in safari on iPhone and desktop.

@dhruvilxcode
Copy link

Used html2canvas for now, and rendered the dynamic content on the page until the image is created, once the image is created, removed the dynamic content from a page. Through this process, I was able to get good results on iPhone (Safari and Chrome) and Android. Although you have to sacrifice on performance. Now, a 1080x1920 Pixel hi-res image takes anywhere between 2-7 seconds.

@minusmo
Copy link

minusmo commented Jan 21, 2023

@dhruvilxcode hey! Can you please tell me how you overcame this issue with ios safari?
I also have same issue and tried other solutions but nothing worked.

@dhruvilxcode
Copy link

@minusmo I replaced this library with the html2canvas. what I did is rendered the content on the page by inserting the dynamically generated content then I called the method to convert data to base64 image. once image is generated I removed the content from page that I added previously programmatically.

The implementation really depends on the usecase. and I found that if content is available on the page (not dynamic content) then these libraries works well.

@qq15725
Copy link

qq15725 commented Feb 2, 2023

The problem seems to be a bug of Safari requiring multiple delayed calls to drawImage 😓

#361 (comment)

@Yehuda-Edelstein
Copy link
Author

The problem seems to be a bug of Safari requiring multiple delayed calls to drawImage 😓

#361 (comment)

How can I implement that instead of this package? Yours is typscript, can't figure out how to replace this function with that.

@Yehuda-Edelstein
Copy link
Author

Hello Yehuda! We faced the same issue, and it turned out to be a cors error with our image server. checkout the network Tab to see if that's the case. If it is, we solved it through the server configuration.

Hope it helps!

your issue was also exclusively on Safari?

@wenlittleoil
Copy link

I have the same issue with iphone mobile, the android mobile and pc browser web are all normal.

@juliabelle1
Copy link

juliabelle1 commented Jun 1, 2023

Hi! I also had the same issue with safari when I used html-to-image https://www.npmjs.com/package/html-to-image. I solved it with another library html2canvas https://www.npmjs.com/package/html2canvas. I have converted the html to image in this library and rendered them in @react-pdf/renderer.

Here is my code:
const [image, setImage]=useState(null)

function to convert image

const handleCreateImage = async () => {
    const element = document.getElementById('element-id'),
      canvas = await html2canvas(element),
      data = canvas.toDataURL("image/jpg", 1);
    setImage(data);
  };

this data i convert to image
<div id='element-id'>some data</div>

And here I render my image in pdf.

<PDFViewer style={viewerStyle}>
        <Document>
          <Page size="A4" style={pageStyle}>
            <View style={styles.section}>
              <Image src={`${image}`} />
            </View>
          </Page>
        </Document>
      </PDFViewer>

Hope it will help.

@mattscotty
Copy link

mattscotty commented Mar 5, 2024

The problem seems to be a bug of Safari requiring multiple delayed calls to drawImage 😓
#361 (comment)

How can I implement that instead of this package? Yours is typscript, can't figure out how to replace this function with that.

Did you figure this out?
I'm in the same boat.

Ironically I'm trying to migrate from html-to-canvas because of issues with nested images inside SVGs.
html-to-image solves my issues and seems more accurate, but isn't working on safari :(

@s-kris
Copy link

s-kris commented Mar 6, 2024

I switched to this lib: https://github.com/qq15725/modern-screenshot
Works great.

@mattscotty
Copy link

I switched to this lib: https://github.com/qq15725/modern-screenshot Works great.

Thanks @s-kris you've saved the day with that, much appreciated.
This is the third or fourth type of plugin I've tried and this one seems to be the best so far.
Just one issue I can see with pseudo element font icons not working, but it's a minor issue;
qq15725/modern-screenshot#68

@s-kris
Copy link

s-kris commented Mar 9, 2024

Oh! I didn't know the font issue.

But glad it helped you.

@MohamedAlosaili
Copy link

Hello Yehuda! We faced the same issue, and it turned out to be a cors error with our image server. checkout the network Tab to see if that's the case. If it is, we solved it through the server configuration.

Hope it helps!

Thanks your solution worked with me. Another way might help is to download the image before add it to the dom that being converted into an image.

@hungdev
Copy link

hungdev commented Aug 28, 2024

I switched to this lib: https://github.com/qq15725/modern-screenshot Works great.

greate, thank for sharing solution

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