You should be familiar with box-sizing
property which determines how the width and height are calculated, in chrome the default value for box-sizing
set on a button is border-box
border-box: The width and height properties includes content, padding and border
Let's now talk about your case:
Content:
<button type="button" class="dot"></button>
The button has no text which means the width of it's content is 0px
Padding:
Default padding
on the button applied by the user agent(chrome in this case) is
padding-top: 1px;
padding-right: 6px;
padding-bottom: 1px;
padding-left: 6px;
Border:
we only care about the width of the border
Default border
on the button applied by the user agent(chrome in this case) is
border-top-width: 2px;
border-right-width: 2px;
border-bottom-width: 2px;
border-left-width: 2px;
we'll talk about the width alone, because it's pretty much same thing for the height
Without applying any styles, let's sum it all up
left border 2px
+ left padding 6px
+ content 0px
+ right padding 6px
+ right border 2px
So the overall width of a button by default will be 16px.
Now when you say width:9px
you explicitly setting the width in which border+padding+content
should live in, but their width is wider so it expands.
Why doesnt it happen on 15x15 tho.. (becomes 16x15 as if it has padding to fill till 16px on
That's because 16px
is the exact amount of space border+padding+content
need to live, that's why you see no change.
Now if you set the width to be wider than 16px
what will change is the content's width because border get set width border property
and padding width padding
property.
Solution
So to fix this we need to reset those predefined styles padding
and border
console.log(document.querySelector('button').getBoundingClientRect().width)
button {
width: 9px;
padding: 0;
border:none;
}
<button></button>