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

Can't style embedded videos properly due to inline width & height #8383

Closed
maddisondesigns opened this issue Aug 2, 2018 · 33 comments · Fixed by #10213
Closed

Can't style embedded videos properly due to inline width & height #8383

maddisondesigns opened this issue Aug 2, 2018 · 33 comments · Fixed by #10213
Assignees
Labels
[Feature] Blocks Overall functionality of blocks [Type] Enhancement A suggestion for improvement.

Comments

@maddisondesigns
Copy link

Describe the bug
There's numerous issues open that discuss the inability to style various blocks so I'm not going to repeat all that again here. The only thing I will say is that we need the ability to specify the content width, and Wide width, at the very minimum.

When you insert a YouTube or Vimeo embed Block, it adds inline width and height to the iframe:

screenshot_763

This causes the content to end up looking something like this (when you have Wide and Full videos):

gutenberg_videoembeds

Whilst its possible to override the width settings by doing something like .wp-block-embed.is-type-video iframe {width: 100%;}, this just makes it look even worse as we can't control the height and the vid just ends up looking squished.

There needs to be a better way to style these video embeds on the front-end.

To Reproduce
Steps to reproduce the behavior:

  1. Add YouTube or Vimeo Embed
  2. View inline iframe styles on front-end

Desktop (please complete the following information):

  • macOS 10.12.6
  • Firefox Quantum 61.0.1 (64-bit)
  • Gutenberg 3.4.0

Some related issues:
#5650
#6131

@designsimply designsimply added [Type] Enhancement A suggestion for improvement. [Feature] Blocks Overall functionality of blocks labels Aug 2, 2018
@notnownikki
Copy link
Member

This is an interesting one. In the editor we try to detect iframed content with a fixed width and height, and make it responsive while preserving the aspect ratio. On the front end though, the HTML put into the page is whatever oEmbed gives us, and so it'll have the fixed width and height. So that width and height is coming from YouTube or Vimeo's oEmbed API, not from Gutenberg.

How did we solve this in the classic editor? Was there javascript or different styles on the front end? Or did we strip out height and width?

@maddisondesigns
Copy link
Author

maddisondesigns commented Aug 31, 2018

@notnownikki Using the Classic Editor, Video Embeds still specify the width & height for the iframe. This is controlled by $content_width variable though, which we can adjust in the theme based on whether we're showing a page with a sidebar or a full width page (i.e. one without a sidebar).

screenshot_819

It works in the Classic Editor because it's only dealing with one width, which is basically the same width that Gutenberg uses when you haven't selected the Wide or Full buttons.

Since Gutenberg is now allowing extra widths (i.e. the wide and full widths), it either (A) needs to let us supply those widths in the same way that we can specify $content_width or (B) It needs to automatically fix these hard-coded widths based on how the vid (or any embed) is getting embeded.

Basically, Gutenberg has introduced this issue by introducing the Wide and Full widths, so likewise, it also needs to provide a solution for it as well.

@notnownikki
Copy link
Member

Thanks, that's filling in bits of the puzzle for me!

it either (A) needs to let us supply those widths in the same way that we can specify $content_width

I need to look more into the internals of how this works, but I'm pretty sure this is the way we need to go with things, because...

or (B) It needs to automatically fix these hard-coded widths based on how the vid (or any embed) is getting embeded.

... all the editor does when it saves an embed block is to put the URL on its own line, and oEmbed does the rest when the post is rendered, so by that point, Gutenberg isn't involved.

The bit about (A) that seems trickiest to me at the moment is that we wouldn't have a single content width for the post, so the problem becomes how we let oEmbed know that one bit of embedded content is $content_width, but another embed is $wide_width. I do think that (A) seems the way to go, and we should start discussions around this. Perhaps there would a post-oembed filter that fixes the widths...

@karmatosed, @jasmussen might have some input here?

@jasmussen
Copy link
Contributor

jasmussen commented Aug 31, 2018

Would it be a solution to provide two configurations for embedded video, perhaps as advanced settings in the sidebar?

  • Option 1: Responsive & full-width (default)
    This would be what we have now — the video embed is as wide as the main column, and uses aspect-ratio CSS to make the video responsive.
  • Option 2: Full-width
    This would basically be the same as what's in the classic editor — the full dimensions are output in the iframe like in the screenshot above, and perhaps we bundle the max-width CSS along with it. But it's not responsive beyond that, or it let's the theme itself handle that responsiveness.

Edit: Gutenberg might not have a $content_width variable, but given editor styles we can probably assume that the main content width (max-width: 100%) would be the same as the $content_width, no?

@notnownikki
Copy link
Member

@jasmussen

Option 1: Responsive & full-width (default)

This would get 100% of my vote! However my CSS-fu hasn't been able to come up with anything that makes the embed 100% width and keeps the aspect ratio. It's not as simple as setting the iframe width to 100% and height to auto is it? I really want to see how this works :)

@jasmussen
Copy link
Contributor

I could swear we had this working at one time, with CSS in place for it. Perhaps this regressed a bit? I can take a look next week.

The basic idea is that the video is 100% full wide. We then decide an assume an aspect ratio for the video, 16:9, and use that knowledge to use paddings to define the aspect ratio.

It's all in this pamphlet: http://www.mademyday.de/css-height-equals-width-with-pure-css.html

Sidenote, it would be nice to expand this further so the user can choose the aspect ratio from a sidebar dropdown, like 1:1 (square) 4:3, etc.

I can take a look at this next week if it regressed.

@notnownikki
Copy link
Member

Ah.

We can't assume an aspect ratio of 16:9 for video any more, because YouTube have started putting 4:3 videos in 4:3 aspect ratio. That's why the code in the embed block (which I think has regressed due to some style changes, but fundamentally works) gets the initial height and width and calculates an aspect ratio so that the iframe can resize correctly.

@jasmussen
Copy link
Contributor

Oh that's interesting. I'll take a look next week and see how we can handle that.

@notnownikki
Copy link
Member

Perhaps the embed block can get the aspect ratio (should be able to access to that information when it renders the preview) and set styles on the block so that the CSS can be told about the aspect ratio?

@jasmussen
Copy link
Contributor

That would be sort of amazing. We'd have to work out the math to figure out the percentage, though, but that should be simple enough:

  • To get a 1:1 aspect ratio, we have a 100% top padding
  • To get a 2:1 aspect ratio, we have a 50% top padding
  • To get a 1:2 aspect ratio, we have a 200% top padding
  • To get a 4:3 aspect ratio, we have a 75% top padding
  • To get a 16:9 aspect ratio, we have a 56.25% top padding

@notnownikki
Copy link
Member

Yep, the HTML that would be embedded in the front end is available to the editor, so if we get the height and width from the iframe in the preview, we can calculate that and set the styles as needed and preserve the aspect ratio on the front end, no matter what the width is.

@notnownikki notnownikki self-assigned this Aug 31, 2018
@maddisondesigns
Copy link
Author

I've just been playing around with some styles, using the browser dev tools, based on that 'mademyday' link and your solution might actually work.

I altered figure.wp-block-embed.is-type-video and iframe based on the styles for .box and .content respectively, as per that article. As you mentioned above, it would also rely on you being able to add a class so that padding-top can be set to the appropriate aspect ratio.

Because all my content is inside a containing div to give it a boxed layout, I have to use negative margins for the .alignwide elements. That means for this video embed, I also had to do figure.alignwide.wp-block-embed.is-type-video {width: calc(100% + 400px);} to calculate the proper width as a simple width of 100% doesn't allow for the negative margins.

You also have to specifically set figure.wp-block-embed.is-type-video iframe {width: 100%;height: 100%;} to override the inline width and height on the iframe. For this particular example, I also just assumed a 16:9 aspect ratio and used padding-top: 56.25%;.

In then end, this is what I was able to display, which was the original goal.

gutenberg_fixedvideoembeds

@notnownikki
Copy link
Member

That's great! I think that having the block apply the correct class for the content's aspect ratio will work nicely then, and we should be able to apply it to any embed that comes in an iframe with fixed height and width.

I'll update here when there's a PR up 😄

@notnownikki
Copy link
Member

In progress PR at #9500

That will apply the correct class names, we need to get the CSS written that applies the correct padding etc.

@notnownikki
Copy link
Member

#9500 has been merged, and on embeds that have a fixed size iframe, it sets CSS classes that allow it to resize and keep the correct aspect ratio. You'll see a new wrapper div with classes that look like wp-has-aspect-ratio wp-embed-aspect-16-9 and the embedded content will automatically be set to 100% width.

@shaunrfox
Copy link

shaunrfox commented Sep 13, 2018

Hi there. I'm working on a custom Wordpress theme and trying to use Gutenberg. The responsive video thing is one of the last things I'm running into. In my googling I found this thread :) Do you know when this will be released? (I just updated to 3.8.0 today and don't see it) (I like the way y'all are thinking about it, btw)

@jasmussen
Copy link
Contributor

Hi @shaunrfox, the pull request for this feature was merged for the 3.9 milestone. We hope to release 3.9 release candidate today (which you can manually install, follow https://make.wordpress.org/test/ for details), and push 3.9 out hopefully next week.

@shaunrfox
Copy link

Ok, awesome! Thanks for the reply @jasmussen

@maddisondesigns
Copy link
Author

Have just tried v3.9. YouTube vids get the wp-embed-aspect- class and now display nicely, which is great, but Vimeo vids still don't get that aspect ratio class and therefore look the same as before.

screenshot_860

@notnownikki
Copy link
Member

@maddisondesigns that's strange, we use a Vimeo video on the demo page and it gets the classes applied... Could you try embedding https://vimeo.com/22439234 and see what happens? Also, what's the address of the video you're embedding there? I'll see if there's anything unexpected in the embed response that stops us calculating the correct styles.

@maddisondesigns
Copy link
Author

@notnownikki I tried adding your Vimeo vid and it added the aspect ratio classes ok. I also tried adding in the same video in my screenshot above (https://vimeo.com/139290912), again, but it still didn't added the aspect ratio classes.

While your video did get the classes on the front-end, it also caused a number of issues in the editor though.

First up, I embedded the video twice, I wanted to see if it displayed properly in wide/full widths. The second one that I embedded though, displayed at a completely different width than the first embed. In the following pic, neither of those embeds have the wide/full buttons selected. They should appear identical, but they don't.

screenshot_862

Here's a better look at the second embed that I added. You can see a heap of empty space in the embed container.

screenshot_865

After embedding multiple vids, the whole editor goes completely weird. When you try to scroll down the page, it jumps back up again. If you do manange to scroll down, and then try to scroll up, you get huge gaps of white space between the blocks. Here's a vid...

https://cl.ly/1c6d5d307b77

This last issue I've raised before but it was marked as low priority, which it obviously shouldn't be because it's still happening - #8603

@notnownikki
Copy link
Member

@maddisondesigns thanks. I'm looking at this now. The video you're using isn't getting the aspect ratio recognised, so that's why it's not getting responsive classes applied to it, so I'll see what's happening there. Embedding the same video twice and the second time it doesn't get the classes applied at all - not sure why that's happening, but I'm on it.

@notnownikki
Copy link
Member

@maddisondesigns the scroll problem seems to be related to drag-n-drop and toolbars, I've pinged @nosolosw who knows more about that.

I'm on the way to a fix for the other issues.

@oandregal
Copy link
Member

Hi - regarding the scroll. Is #8603 that we're talking about, right? That has nothing to do with drag-n-drop. As @maddisondesigns suggested, the problem is reproducible when the embed is selected. My guess would that the code that makes the toolbar pinnable is somewhat related to that?

@notnownikki
Copy link
Member

Yes, #8603. Sorry, I misunderstood, not dnd.

@jasmussen
Copy link
Contributor

I may have fixed the scrolling issue in #8603 (comment).

@niklasp
Copy link
Contributor

niklasp commented Nov 23, 2018

Can you help me getting this work on the front-end? In the backend everything works for me and also in the front end the embeds are getting their respective classes attached like:

<figure class="wp-block-embed-youtube alignfull wp-block-embed is-type-video is-provider-youtube wp-embed-aspect-16-9 wp-has-aspect-ratio">
  <div class="wp-block-embed__wrapper">
    <iframe width="500" height="281" src="https://www.youtube.com/embed/4iO5INzXLNc?feature=oembed" frameborder="0" allow="accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture" allowfullscreen></iframe>
  </div>
</figure>

But where can I get the responsive styling of these classes from in my frontend?

@GlennMartin1
Copy link

If I understand properly, the reason it doesn't work in the front-end is because of themes that have not yet adapted.

The theme needs to opt into Gutenberg styles, and when they do, it will work correctly on the front-end.

@jasomdotnet
Copy link

jasomdotnet commented Sep 15, 2019

Here's basic front-end css:

figure.wp-block-embed.is-type-video {
    position: relative;
    width: 100%;
    height: 0;
    padding-bottom: 56.25%; /*16:9*/
}
figure.wp-block-embed.is-type-video iframe {
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
}

You are welcome.

@lbrand309
Copy link

Thank you so much for posting the CSS - fixed my issue marvelously!!

@nardbyte
Copy link

Here's basic front-end css:

figure.wp-block-embed.is-type-video {
    position: relative;
    width: 100%;
    height: 0;
    padding-bottom: 56.25%; /*16:9*/
}
figure.wp-block-embed.is-type-video iframe {
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
}

You are welcome.

This was definitely my solution, thank you very much boss!

@Mishkamshka
Copy link

Hey, I've just started using Gutenberg so I'm not sure if the code has changed. But when I was putting in @jasomdotnet code it showing up blank. But this works for me!

figure.wp-block-embed.is-type-video, .wp-block-embed__wrapper {
position: relative;
width: 100%;
height: 0;
padding-bottom: 56.25%; /16:9/
}
figure.wp-block-embed.is-type-video iframe {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
}

Thanks for this!

@anyway
Copy link

anyway commented Jun 24, 2021

figure.wp-block-embed.is-type-video, .wp-block-embed__wrapper {
position: relative;
width: 100%;
height: 0;
padding-bottom: 56.25%; /16:9/
}
figure.wp-block-embed.is-type-video iframe {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
}

@Mishkamshka thank you so much... this saved me my afernoon!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
[Feature] Blocks Overall functionality of blocks [Type] Enhancement A suggestion for improvement.
Projects
None yet
Development

Successfully merging a pull request may close this issue.