If I have a <div>
with a relative width (such as width: 50%), is there a simple way to make it have the same width as it does height without resorting to JavaScript?

- 8,162
- 7
- 56
- 101

- 1,345
- 3
- 16
- 23
-
2do you mean dynamically, meaning if the width increased then the height would match it automatically? – zero Dec 13 '12 at 02:25
-
Thanks for pointing that out. Yes, I do; updated to reflect that. – Trey Keown Dec 13 '12 at 02:29
-
that sounds like you want to use logic in css, which to my knowledge is not possible at this time. remember, css's job is not to handle logic (at lease not of this caliber) but merely layouts and display. stuff like this (mathematic calculations) is exactly what javascript is meant to do. – zero Dec 13 '12 at 02:37
-
JavaScript is more a means of dynamic interaction, not a crutch to achieve a certain layout. This logic is really quite simple compared to current CSS capabilities. I'm surprised that there aren't methods to size an element using an aspect ratio. – Trey Keown Dec 13 '12 at 02:43
-
It's not a crutch when the current tools can't do what you need them to do. You being surprised doesn't change the fact that it can't be done in CSS alone at this time. – Rick Calder Dec 13 '12 at 03:01
-
@TreyKeown i guess a can relate. back in the day when i first started getting the hang of html/css/js i couldn't for the life of me understand why there wasn't a feature built into css or js to allow the rotation html elements, it seemed like an obvious feature (probably because i've done so in actionscript/flash). – zero Dec 13 '12 at 03:25
-
@TreyKeown take it form me, i've had to do a lot of black magic hacks to achieve stuff that seems almost elementary simply because it's a limitation the tools currently have. – zero Dec 13 '12 at 03:29
6 Answers
It is actually possible to achieve it with this neat trick i found at this blog
#square {
width: 100%;
height: 0;
padding-bottom: 100%;
}

- 20,030
- 7
- 43
- 238

- 1,951
- 2
- 16
- 18
-
This would work, and indeed it does answer my original question. However, my requirements have slightly changed, and I need to be able to size the element by having a certain percentage for the height, and then set the width accordingly to make the element square. This solution doesn't quite seem to work for that. Though, perhaps a kluge would be to use transform: rotate(90deg); for the element, and transform: rotate(270deg); for the content within. – Trey Keown Jan 08 '14 at 02:55
No, and Yes (Kinda)
Okay, so the short answer is "no," not possible. The long answer is, "yes," given certain constraints and concessions (i.e. extra html markup, and limitations on what can be done).
Given this CSS:
.square {
position: relative;
margin: 20px;
display: inline-block; /* could be float */
overflow: auto; /* UPDATE: if content may overflow square */
}
.sq-setter-w {
width: 100%;
height: auto;
visibility: hidden;
}
.sq-setter-h {
width: auto;
height: 100%;
visibility: hidden;
}
.sq-content {
position: absolute;
z-index: 1;
top: 0;
right: 0;
bottom: 0;
left: 0;
}
With this HTML:
<div class="square" style="width: 200px">
<img src="http://dummyimage.com/50x50/000/fff.gif&text=50x50" class="sq-setter-w"/>
<div class="sq-content">Here is content</div>
</div>
<div class="square" style="height: 100px">
<img src="http://dummyimage.com/50x50/000/fff.gif&text=50x50" class="sq-setter-h"/>
<div class="sq-content">Here is content</div>
</div>
<div class="extrawrapper">
<div class="square" style="width: 200px">
<img src="http://dummyimage.com/50x50/000/fff.gif&text=50x50" class="sq-setter-w"/>
<div class="sq-content">Here is content</div>
</div>
</div>
<div class="extrawrapper">
<div class="square" style="height: 100px">
<img src="http://dummyimage.com/50x50/000/fff.gif&text=50x50" class="sq-setter-h"/>
<div class="sq-content">Here is content</div>
</div>
</div>
You can get it to do what this fiddle shows.
The keys are:
- The image used needs to be a square image, as it is driving the proportional sizing (the
img
element is the only element that can do such proportional work, as it can base its size off the proportion of the image itself). - You have to know if you are going to set the
width
or theheight
so that you can set the image class correctly to size it. Optionally, set thewidth
orheight
on theimg
itself, then you don't need to worry about setting a class to the100%
value. My demo was assuming that you set the size on the wrapper div (my.square
class). - To get the
div
to collapse around theimg
which is driving the proportional sizing you need to setdisplay: inline-block
or afloat
on thediv
(as noted in the css above). - Because of #3, if you want that
div
to act more "block-like" you need to give them an extra wrapperdiv
like the third and fourth ones show.
Obviously, there is a lot of extra mark-up involved in this solution. So in many ways it is better to say "just use javascript," but I did want to prove that it could be done (at least in some cases) purely with HTML and CSS.
Update: To Show Flexible Sizing Possibility
See this fiddle for percentages driving the size, with this html example (width
set to 30%
):
<div class="square" style="width: 30%">
<img src="http://dummyimage.com/50x50/000/fff.gif&text=50x50" class="sq-setter-w"/>
<div class="sq-content">Here is content</div>
</div>

- 71,703
- 13
- 126
- 146
-
[This seems](http://stackoverflow.com/questions/6693956/how-can-i-create-a-perfectly-square-div-where-height-is-equal-to-viewport) to be working for me... – demaniak Oct 06 '13 at 18:14
-
Until the "update" part, I wasted my time trying to figure out how "not using fixed size" in the element to set it on the wrapping elements is of any use. It's like wishing not to grow and putting yourself in one of those boxes used to grow watermelon square. I'll take a look at the second fiddle, but so far you wasted my time. Your first example (did I say "useless" already?) with content does this http://jsfiddle.net/8x91z9a2/ Can you explain me what is the difference between all this extra code and setting width and height with one div and two lines of css? – sergio Jul 19 '15 at 17:53
-
@sergio: The challenge was to explicitly set the div to be _square_, using _only_ HTML/CSS, and only having _one_ value (either height or width) driving the size of the square, without necessarily even knowing ahead of time what that value might be (either dynamically generated or being a percentage). So form (square) is fixed with unknown values. That is the "use" of it. The content overflow in your example is a possible by-product of a designer not handling the content amount or the overflow, which [I would recommend `overflow:auto` on the square class](http://jsfiddle.net/8x91z9a2/2/). – ScottS Jul 20 '15 at 01:45
-
Making a container to stop working as a container (i.e. the content will overflow it) is the same that just setting a gradient single-color background with size set to "contain", or just using an image. There's no point on keeping the container as container if it's not gonna contain anything. – sergio Aug 01 '15 at 04:01
I needed to achieve something similar today and had the same idea with the image. I wanted to check other possibilities and google led me here.
...you don't really need an image src
. you can simply use a hash
if you want a square.
It saves a http request.
If you want to get different aspect ratio you should use a src
though. If you want to have a ratio of 16:9 the image should be 16px
wide and 9px
high (go as small as possible)
Comparing both techniques (see other answers in this thread)
img
vs. padding-bottom
Here's a fiddle to show how much more compatible the img
version is (can easily handle px
value too (an interval will resize the "square" each second)
If you use percentage values both techniques can achieve the same result but the padding version does not need the extra markup (<img src="#"/>
)
Conclusion:
Depending on the implementation each technique has it's pros and contras.
HTML
<div class="floater">
<div class="square square_noImg">
<div class="inner">Hey blue you look totally squared</div>
</div>
<div class="square square_img">
<img src="#"/>
<div class="inner">Hey red you seem off</div>
</div>
</div>
CSS
.floater {
font-size: 0;
}
.square {
position: relative;
display: inline-block;
width: 100px;
margin: 0 5px;
}
.square_noImg {
padding-bottom: 100px;
background: red;
}
.square_img {
background: blue;
}
img{
width: 100%;
height: auto;
border: 0;
visibility: hidden;
}
.inner {
position: absolute;
top: 10%;
right: 10%;
bottom: 10%;
left: 10%;
background: white;
font-size: 14px;
text-align: center;
overflow: hidden;
padding: 10px 5px;
}

- 1
- 1
A native JS approach in response to @Dave comment on @praveen-kumar answer:
var squareElement = function(el) {
el.style.height = el.offsetWidth + 'px';
}
and use it anywhere
squareElement(document.querySelector('your-selector'));

- 403
- 4
- 10
This cannot be done with CSS alone. Using jQuery you can achieve this by doing
var chld = $('.child').width();
$('.child').css({'height':chld+'px'});
Check working example at http://jsfiddle.net/4Jnfq/
A CSS only solution can be found here on the last "Resize with content" update.
Although it applies for circles, you can remove the border-radius: 50%
to make it work for squares.

- 4,169
- 3
- 39
- 67

- 164,888
- 24
- 203
- 252
-
5To note jQuery isn't the only answer... Javascript in general can do it. I'm not a fan on JS libraries personally. – Sir Dec 13 '12 at 02:57
-
1This can be done in CSS alone, as you check in [this answer](http://stackoverflow.com/a/9359039/607874) (see "Resize with content" update). It is an answer for responsive circles but the same applies for squares. – Jose Rui Santos May 13 '16 at 06:49
-
@JoseRuiSantos Been a long time buddy. Why digging up old ones? – Praveen Kumar Purushothaman May 13 '16 at 06:51
-
3@PraveenKumar I agree that's an old one, but nevertheless its always good to improve solutions for other fellows with the same problem. – Jose Rui Santos May 13 '16 at 06:56
-
@JoseRuiSantos Agreed... Go ahead and edit my answer... :) – Praveen Kumar Purushothaman May 13 '16 at 06:57
Not with relative units like %
, because they would be calculated relative to a container element. But it's possible to make an element square if you use units like px
or em
to set both dimensions.

- 71,580
- 16
- 111
- 150