I have an element that needs to scale to be 100% of the parent element. Because the element contains pixel based animations with images that can scale I can't use percentages. Is there anyway to do this using css transform scale?
The relative css transform values are relative to itself (border-box). E.g some absolute centering snippet:
width: 100px;
height: 200px;
left: 50%;
top: 50%;
transform: translate(-50%, -50%);
In Firefox you can try some hack with your parent element:
background-image: -moz-element(#yourElementToScale);
background-size: contain;
But generally its not possible without using percentages on width/height in pure CSS. If you wanna use javascript just scale by the factors:
var scaleX = parentElement.offsetWidth / element.offsetWidth;
var scaleY = parentElement.offsetHeight / element.offsetHeight;
Apply this scale-factors as transform could look like:
transform: scale(scaleX, scaleY);
Related
I have read that in order to place a background image inside a container block in CSS you can use the background-position property. And you can give labels to it like, top-right-bottom-left-center or css units, mostly percents. And the way it acts is kind of like this:
background-position: 25% 25%, will place the (25%,25%) point of the background image from the top-right edge centered to the (25%,25%) point of the CSS element that contains that background.
So if I would like to center the (50% 50%) point of the background image to the (0,0) point of the container, how can I achieve it?
I know I can do it with pseudo elements (:before, :after) but is there a math calculation that can help me use the background property to make this work? Unfortunately I haven't found a property like a registry point that could allow me to place the point I would like use as my center for the background (background-origin despite the close meaning it is used for something completely different as I discovered).
This question is in regards to any situation but as an example I'm sharing a quick and simple snippet to make it more graphical.
By the way, I'm trying to find the most responsive solution I could. It will be much better if we can assume that I don't know the exact dimensions of the background image so that if I later change that image for another of different size, it stays centered to the same place. This means I prefer % over px.
.foo {
margin: 0 auto;
width: 400px;
height: 300px;
background: url('https://source.unsplash.com/random/200x200') no-repeat, blue
}
<! -- Let's supose I would like to center the (50%, 50%) of that image placeholder at the (0,0) of the container div. -- >
<div class='foo'></div>
Thanks in advance
Since you know the size of the background image (200x200), you can use half the amount of those pixel values as negative values for the background position in order to have the image's center exactly at the upper left corner of its div element. In your case, that would be background-position: -100px -100px;:
.foo {
margin: 0 auto;
width: 400px;
height: 300px;
background: url('https://source.unsplash.com/random/200x200') no-repeat, blue;
background-position: -100px -100px;
}
<! -- Let's supose I would like to center the (50%, 50%) of that image placeholder at the (0,0) of the container div. -- >
<div class='foo'></div>
Second version: If you use a regular image instead of a background-image, you can use transform: translate(-50%, -50%); on it, and overflow: hidden on the parent. So that way using percentage values works.
However, in this case it becomes more complex to add content to the main div if you also need the background color for the rest of the container - You'd have to add an absolutely positioned element for that.
.foo {
margin: 0 auto;
width: 400px;
height: 300px;
background: #bbf;
overflow: hidden;
position: relative;
}
.foo>img {
transform: translate(-50%, -50%);
}
.foocontent {
position: absolute;
top: 0;
left: 0;
right: 0;
bottom: 0;
}
<div class='foo'>
<img src="https://source.unsplash.com/random/200x200" />
<div class="foocontent">
Here's some text and even some more text to demonstrate how text content could be placed above the image that serves as a background here.
</div>
</div>
The percentage unit cannot be used to offset the background image because it defines the entire image point relative to its container.
What you can do is define the size and position of the image, which uses pixel units.
Use background shorthand:
background: url(img) -100px -150px / 200px 300px;
body {
background: url(https://images.unsplash.com/photo-1519940640025-75fdf32010d7?ixlib=rb-1.2.1&auto=format&fit=crop&w=1234&q=80) -100px -150px / 200px 300px no-repeat pink;
}
In the following code why do we use the webkit and ms keywords?
#svgelem {
position: relative;
left: 50%;
-webkit-transform: translateX(-20%);
-ms-transform: translateX(-20%);
transform: translateX(-20%);
}
EDIT: The ms- and webkit- keywords are used so each of the different CSS processors versions (microsoft (ms) and webkit) know how to handle that line. This is because of experimental features, like transform, being added by each of the CSS processors at different times.
The typical use of a block of CSS like this is used to move an element to the centre of it's parent object on the horizontal axis.
The idea is to move the element to so the left edge is in the middle of the parent:
#svgelemn {
position: relative;
left: 50%;
}
Now that the element is just to the right of the middle (remember that it's the left edge that is in the middle), you need to move the element to the left by 50% of it's own width (not it's parents width). Because we're moving the element to the left, we also need to invert the percentage so it's negative (-50%). So now you add the transform section:
#svgelemn {
position: relative;
left: 50%;
-webkit-transform: translateX(-50%); /* Webkit specific transform */
-ms-transform: translateX(-50%); /* Microsoft specific transform */
transform: translateX(-50%); /* Generic transform (all evergreen browsers) */
}
The code that you have only makes a final adjustment of only 20%, so that's not quite the middle.
You can see an example here. You can see how the top element is in the middle, while the original code makes it slightly off centre.
I'm trying to position an element on screen based on the following formula:
element.style.top = element.pivot_y + window.scrollY;
I'm doing this using JavaScript, with window.requestAnimationFrame. The problem is that requestAnimationFrame is not available on certain browsers, so I have to fallback to a timer, which makes my element wiggle due to lack of synchronisation with rendering. This, can I position an element similarly, without invoking JavaScript?
As far as I understand you this should be easily possible with position: fixed; and top: pivot_y where pivot_y has to be a fixed number
You can use a position: fixed;.
CSS
.square {
background: red;
position: fixed;
height: 100px;
width: 100px;
top: 30%;
}
JsFiddle
Is there any way to use skew only in a parent element?
I need to create something like a 'diamond' as a mask and the child elements can't be affected. There is no way, in this case, to use png as a mask.
Thanks in advance!
It's really easy, you just need to unskew the thing for the children. Unskew means applying another skew transform, but of opposite angle this time.
.parent { transform: skewX(45deg); }
.parent > * { transform: skew(-45deg); }
In general, if you apply a number of transforms on a parent element and you want the child elements to go back to normal, then you have to apply the same transforms, only in reverse order (the order does matter in most cases!) and with a minus for angle/ length values used for skew, rotate or translate. In the case of scale, you need a scale factor of 1/scale_factor_for_parent. That is, for scale, you would do something like this:
.parent { transform: scale(4); }
.parent > * { transform: scale(.25); /* 1/4 = .25 */ }
A diamond shape with children is pretty easy.
DEMO
Result:
HTML:
<div class='wrapper'>
<div class='diamond'>
<div class='child'>Yogi Bear</div>
<div class='child'>Boo Boo</div>
</div>
</div>
CSS:
.wrapper {
overflow: hidden;
margin: 0 auto;
width: 10em; height: 10em;
}
.diamond {
box-sizing: border-box;
margin: 0 auto;
padding: 4em 1em 0;
width: 86.6%; height: 100%;
transform: translateY(-37.5%) rotate(30deg) skewY(30deg);
background: lightblue;
}
.child {
transform: skewY(-30deg) rotate(-30deg);
}
Any transform property affects the element which is applied to and all of his children.
So the only way to skew a single "parent" element is to have it with no children (i.e.: it can't be also a parent!).
Could ou try to elaborate a bit on what do you want to get as a result ?
skew(), like all transform properties always affects the child elements. You could try to use two HTML blocks at the same position, one with the skew() and the other with the contents.
Also, if you just want a diamond, a rectangular box with scale() and rotate() should be enough, but again with no children.
And if you want that diamond as a mask, I'm pretty sure it would be easier to render the parts NOT present in the diamond. Rendering the outside parts of the diamond should not be that hard, after all, they're only rectangle triangles.
the only way to achieve this is to take the child element out of the document flow using position:absolute; and putting an equal negative degree skew on the child.
The problem with this is that you will now have to resize your parent manually.
So, I am trying to set an image to be 100% of the height and width of the html element (really the browser window is what I'm going for). I have the CSS set as
html{
width: 100%;
height: 100%;
}
img{
width: 100%;
height: 100%;
z-index: 0%;
}
And the width behaves right, but the height does not change. I tried setting it to height: 2% and it stayed the same height. I don't want to use px to set the height because I want this to work on mobile devices, but HEIGHT, Y U NO WORK?
You also need to set height: 100% on body.
Going with your exact example, you could do:
html, body, img {
width: 100%;
height: 100%;
}
However, it looks like you're possibly trying to get a fullscreen background image (because you used z-index - by the way z-index does not use %, just a plain number).
In that case, you should instead use one of the methods from here:
http://css-tricks.com/perfect-full-page-background-image/
That is because the image element is not the direct child of the html element. You have to specify the height for the body element also, and any other element containing the image element.