CSS: self-adjusting table with max width that clips to content width - css

I am struggling to make the adjustable parent div fit the content:
(I want the widening white space on the right to go away)
http://jsfiddle.net/TDq7T/42/
max-width: and width:fit-content or auto, don't work together
#parent {
display: block;
max-width:40%;
overflow:hidden;
background: rgba(255,255,255,1.0);
}
#child {
display: block;
width:50px;
height:50px;
background: rgba(0,0,0,1.0);
float:left;
margin: 10px;
}
I tried changing the display modes, clip: auto, width:auto adding another subparent but to no avail :(

since you used javascript to generate html elements I believe it won't be a problem to style them with javascript (jquery) as well:
http://jsfiddle.net/TDq7T/75/
function calculate_m_width() {
var d_width= $(document).width();
var m_width= Math.floor((d_width*.4)/70)*70;
$("#menu").css("width",m_width);
}
calculate_m_width();
window.onresize = function() {
calculate_m_width();
}
each time the browser is resized the width of the menu will be recalculated as number of elemnets x their width (50+2x10)

Use display: flex; on #menu (and erase float: center):
http://jsfiddle.net/d3rp294u/

I'm not sure that is what you want, but I will give a try.
var menu = document.createElement('div');
menu.id = 'menu';
document.body.appendChild(menu);
var d = document.createElement('div');
d.id = 'child';
document.body.appendChild(d);
var e = document.createElement('div');
e.id = 'child';
document.body.appendChild(e);
var f = document.createElement('div');
f.id = 'child';
document.body.appendChild(f);
var g = document.createElement('div');
g.id = 'child';
document.body.appendChild(g);
var h = document.createElement('div');
h.id = 'child';
document.body.appendChild(h);
menu.appendChild(d);
menu.appendChild(e);
menu.appendChild(f);
menu.appendChild(g);
menu.appendChild(h);
#menu {
padding: 0;
margin: 0;
max-width: 280px;
overflow: hidden;
background: #ccc;
display: flex;
float: center;
-webkit-flex-flow: row wrap;
-moz-justify-content: flex-start;
-webkit-justify-content: flex-start;
justify-content: flex-start;
}
#child {
background: rgba(0, 0, 0, 1.0);
width: 50px;
height: 50px;
margin: 10px;
align-self: flex-start;
display:
}

Related

How to add space between absolute elements

I'm working on a slider with gsap & nuxt but I can't find a way to add space between the absolute positioned slides. The absolute position is necessary for the animation to work properly. I tried inline-block to the slide and white-space: nowrap to the wrapper but the animation falls apart then.
Here's a minimal demo of the slider: https://codesandbox.io/s/withered-star-3y44ig?file=/pages/index.vue
Any help is much appreciated! Thanks in advance!
UPD 2:
Updating scripts to handle gap between slides with JS (here is part of updated scripts (and here is fork with updates of your code):
// ...
var percGap = 5; // gap between slides in percentages
var slideWidthWithGap = 100 + percGap;
var slideXPercent = (i) => i * slideWidthWithGap;
gsap.set(slides, {
xPercent: slideXPercent,
});
var wrap = gsap.utils.wrap(
-(slideWidthWithGap * 2),
(numSlides - 2) * slideWidthWithGap
);
var timer = gsap.delayedCall(slideDelay, autoPlay);
var animation = gsap.to(slides, {
xPercent: "+=" + numSlides * slideWidthWithGap,
duration: 1,
ease: "none",
paused: true,
repeat: -1,
modifiers: {
xPercent: wrap,
},
});
// ...
To add to slide rounded corners, add this to .slide
.slide {
/* ... */
border-radius: 1rem;
overflow: hidden; /* crop block outside border */
}
Like an option, you can use slide paddings to make it visually separated:
with using CSS variables:
.slide {
--slide-gap: 1rem;
position: absolute;
display: flex;
align-items: center;
justify-content: center;
height: 100%;
width: calc(100% / 1.5);
padding-left: calc(var(--slide-gap, 0) / 2);
padding-right: calc(var(--slide-gap, 0) / 2);
}
Without CSS variables:
.slide {
position: absolute;
display: flex;
align-items: center;
justify-content: center;
height: 100%;
width: calc(100% / 1.5);
padding-left: .5rem;
padding-right: .5rem;
}
Here is updated CodeSendbox.
UPD:
To add rounded corners to slides, update .slide-content selector:
.slide-content {
border-radius: 1rem;
/* another CSS props */
}

Why flex child jumps over to the next row when the width is one quarter of the container? [duplicate]

This question already has answers here:
Flex items not respecting margins and box-sizing: border-box
(2 answers)
Closed 2 years ago.
I am trying to create a 4x4 box. Why does the 4th div in a row jump to the next row, when it the width of the child div is 25%. Shouldn't it jump every 4 divs instead?
HTML
<div class="container"></div>
CSS
.container {
display: flex;
width: 600px;
height: 600px;
flex-wrap: wrap;
}
.item {
border: 1px solid black;
background-color: yellow;
}
JS
const container = document.querySelector(".container");
const calcWidth = 100/4;
for (let i = 0; i < 16; i++) {
const item = document.createElement("div");
item.classList.add("item");
item.style.width = `${calcWidth}%`;
item.style.height = `${calcWidth}%`;
container.appendChild(item);
}
https://codepen.io/pepegaa/pen/VwjZdEW
The border adds an extra 2px to the width, use this so elements don't change size when adding borders/padding:
* {
box-sizing: border-box;
}
const container = document.querySelector(".container");
const calcWidth = 100 / 4;
for (let i = 0; i < 16; i++) {
const item = document.createElement("div");
item.classList.add("item");
item.style.width = `${calcWidth}%`;
item.style.height = `${calcWidth}%`;
container.appendChild(item);
}
* {
box-sizing: border-box;
}
.container {
display: flex;
width: 600px;
height: 600px;
flex-wrap: wrap;
}
.item {
border: 1px solid black;
background-color: yellow;
}
<div class="container"></div>

Why is the image translated inside the div?

I have an image img inside a DIV modal, and a button + at the bottom right. This button calls the function imgfit() that toggles the image view as "fit and center inside the window" or "100%" (i.e., 1:1 pixel). It works, except for the fact that the scrollbars do not allow me to scroll the top/left of the image: the image is displaced negatively inside the div when seen at 1:1.
How do I tell the scrollbars that they "forgot" part of the image at the top/right? You can see the problem here (make your browser window relatively small to better see the problem).
The button calls the following function imgfit:
function imgfit()
{
if (fit) {
img.style.minWidth = "0px";
img.style.minHeight = "0px";
img.style.maxWidth = "100vw";
img.style.maxHeight = "100vh";
modal.style.overflow = "hidden"; // Prevent scroll of fullsize image
} else {
img.style.maxWidth = 'none';
img.style.maxHeight = 'none';
img.style.minWidth = img.naturalWidth+"px";
img.style.minHeight = img.naturalHeight+"px";
modal.style.overflow = "auto"; // Allow scroll of fullsize image
}
fit = ! fit;
}
This is the CSS of the image and the modal div (if I remove the align-items: center and the justify-content: center, problem is gone, but image is not centered):
.modal {
align-items: center;
justify-content: center;
position: fixed;
z-index: 100;
left: 0;
top: 0;
width: 100%;
height: 100%;
overflow: hidden;
background-color: #000;
-moz-user-select: none;
user-select: none;
touch-action: manipulation;
}
.img {
cursor: no-drop;
position: absolute;
margin: auto;
touch-action: manipulation;
}
I solved the problem thanks to the neat article here (I didn't know that sitepoint.com site). The culprit was the position: absolute thing. Changing to display: grid solved the issue:
.modal {
display: grid;
align-items: center;
position: fixed;
z-index: 100;
left: 0;
top: 0;
width: 100%;
height: 100%;
overflow: hidden;
background-color: #000;
-moz-user-select: none;
user-select: none;
touch-action: manipulation;
}
.img {
grid-column: 1;
grid-row: 1;
cursor: no-drop;
margin: auto;
touch-action: manipulation;
}

Tizen SDK CSS ID Not Being Rendered

I am using the Tizen 2.3.1 SDK for wearables and have run into an issue where no matter what I do to the style.css file, adding any new ids simply refuses to work.
* {
margin: 0;
padding: 0
}
html, body {
width: 100%;
height: 100%;
background-color: black;
}
#str_day {
position: absolute;
display: -webkit-flex;
width: 50%;
height: 50%;
background: yellow;
color: yellow;
z-index: 4;
opacity: 1;
}
h1 {
font-size: 1.4em;
margin: 10px 0 20px 10px;
color: #6587ac;
}
#box {
display: -webkit-flex;
-webkit-align-items: center;
width: 100%;
height: 100%
}
.canvas {
background: #000;
width: 320px;
height: 320px;
margin: auto;
}
This is my code. I am trying to add the str_day id however it doesn't show up when I run the package through the emulator. The rest of the css (the canvas element, mainly) works fine, but str_day just doesn't show up. I tried specifying the z-index and opacity in case some weird issue was occuring but that doesn't seem to be the problem.
This is my full code on github.
https://github.com/JoyfulOwl/RadialWatch/commit/86d096710c7187b6b3679e02416548e18a3e986e
Probably because of improper CSS layout str_day is rendered/painted outside the viewport of your watchface because of which its not visible.
I think better would be to use canvas fillText command to print the date on canvas.
Try below example.
var canvas = document.getElementById("myCanvas");
var context=canvas.getContext("2d");
context.font="30px Comic Sans MS";
context.fillStyle = "red";
context.textAlign = "center";
context.fillText(str_Day, mCenterX, mCenterY); // mCenterX & mCenterY are the position where text has to be shown.

Chrome doesn't use calculated width of flex items to size auto margins

I am trying to align a bunch of variable width divs in a horizontal flexbox using auto margins. I can't use justify-content: space-around, because of the Chrome-related issue I detailed in this question.
The divs that I am trying to align may contain other elements with variable-length text, so I used display: table to allow them to expand. I set a base width of 100 pixels on the divs, so that they don't get too thin if there isn't much text. However, Chrome seems to calculate the auto margins based on the base width of the divs, rather than the calculated width if they are expanded by inner text. There is too much space between them, causing them to overflow the container even when they could fit within it.
Here is a Codepen with an example of my problem.
var ITEM_WIDTHS = [350,250,110,370,110,150,400,150,170];
var ITEM_LABELS = [
"zzzzzz",
"zz",
"zzzz",
"zzzzzzzzzzzz",
"zzzz",
"zzzzzzzzzzzzzzzz",
"zzzzzzzz",
"zzzzzzzzzzzzzz",
"zz",
];
function createConsistentWidthItems(items) {
var i, div;
for (i = 0; i < ITEM_WIDTHS.length; i++) {
div = document.createElement("div");
div.setAttribute("class","item");
div.setAttribute("style","width: " + ITEM_WIDTHS[i] + "px; min-width: " + ITEM_WIDTHS[i] + "px;");
div.innerHTML = i + "";
items.push( { element: div } );
}
}
function createConsistentlyLabeledItems(items) {
var i, div;
for (i = 0; i < ITEM_WIDTHS.length; i++) {
div = document.createElement("div");
div.setAttribute("class","item");
div.innerHTML = i + ITEM_LABELS[i];
items.push( { element: div } );
}
}
function fillItemContainer(items, itemContainer) {
for (var itemIndex in items) {
itemContainer.appendChild(items[itemIndex].element);
}
}
function generateItemRows() {
var items = [];
createConsistentWidthItems(items);
var itemContainer = document.getElementById("itemContainer1");
fillItemContainer(items, itemContainer);
items =[];
createConsistentlyLabeledItems(items);
itemContainer = document.getElementById("itemContainer2");
fillItemContainer(items, itemContainer);
}
window.onload = generateItemRows;
.item-container {
padding: 0;
margin: 20px 0;
border: 4px solid black;
width: 1500px;
display: flex;
overflow: scroll;
}
.item {
background: tomato;
border: 2px solid black;
padding: 5px;
width: 100px;
min-width: 100px;
height: 100px;
margin: 10px auto;
line-height: 100px;
color: white;
font-weight: bold;
font-size: 2em;
text-align: center;
display: table;
}
<h1>Items given fixed widths</h1>
<h2>Since they overflow the container, there are no margins</h2>
<div id="itemContainer1" class="item-container"></div>
<h1>Items given minimum width, but allowed to grow variably to fit text</h1>
<h2>Even though they shouldn't overflow the container at all, the margins cause them to do so</h2>
<div id="itemContainer2" class="item-container"></div>
Is there some CSS-only trick that I could use to get around this?
Don't use tables nor explicit width. Only keep min-width.
width: auto; /* default value */
display: block; /* default value */
min-width: 100px;
var ITEM_WIDTHS = [350,250,110,370,110,150,400,150,170];
var ITEM_LABELS = [
"zzzzzz",
"zz",
"zzzz",
"zzzzzzzzzzzz",
"zzzz",
"zzzzzzzzzzzzzzzz",
"zzzzzzzz",
"zzzzzzzzzzzzzz",
"zz",
];
function createConsistentWidthItems(items) {
var i, div;
for (i = 0; i < ITEM_WIDTHS.length; i++) {
div = document.createElement("div");
div.setAttribute("class","item");
div.setAttribute("style","width: " + ITEM_WIDTHS[i] + "px; min-width: " + ITEM_WIDTHS[i] + "px;");
div.innerHTML = i + "";
items.push( { element: div } );
}
}
function createConsistentlyLabeledItems(items) {
var i, div;
for (i = 0; i < ITEM_WIDTHS.length; i++) {
div = document.createElement("div");
div.setAttribute("class","item");
div.innerHTML = i + ITEM_LABELS[i];
items.push( { element: div } );
}
}
function fillItemContainer(items, itemContainer) {
for (var itemIndex in items) {
itemContainer.appendChild(items[itemIndex].element);
}
}
function generateItemRows() {
var items = [];
createConsistentWidthItems(items);
var itemContainer = document.getElementById("itemContainer1");
fillItemContainer(items, itemContainer);
items =[];
createConsistentlyLabeledItems(items);
itemContainer = document.getElementById("itemContainer2");
fillItemContainer(items, itemContainer);
}
window.onload = generateItemRows;
.item-container {
padding: 0;
margin: 20px 0;
border: 4px solid black;
width: 1500px;
display: flex;
overflow: scroll;
}
.item {
background: tomato;
border: 2px solid black;
padding: 5px;
min-width: 100px;
height: 100px;
margin: 10px auto;
line-height: 100px;
color: white;
font-weight: bold;
font-size: 2em;
text-align: center;
}
<h1>Items given fixed widths</h1>
<h2>Since they overflow the container, there are no margins</h2>
<div id="itemContainer1" class="item-container"></div>
<h1>Items given minimum width, but allowed to grow variably to fit text</h1>
<h2>Even though they shouldn't overflow the container at all, the margins cause them to do so</h2>
<div id="itemContainer2" class="item-container"></div>
You don't need to apply display: table to the flex items to allow them to expand. You can use flex: auto instead.
Also, you can use justify-content: space-between on the flex container to align the flex items. If the items overflow they will, in accordance with the specification, resolve to flex-start.
Revised Codepen

Resources