I want to write 2048 game using divs and css-grid. This is how I imagine the output:
I have the outer part, which fits to the browser window, and I just want to write 4x4 grid in the middle (horizontal and vertical) of the middle-left div (called game-container)
<div class = "game-container">
<div class = "game">
<div class = "game-cell"></div>
<!-- 16 game cells total -->
<div class = "game-cell"></div>
</div>
</div>
I made a 4x4 grid using:
div.game {
display: grid;
grid-template-columns: repeat(4, 1fr);
grid-template-rows: repeat(4, 1fr);
}
However, I have a problem with few things:
How to make each game-cell square (lets say 50px)
How to display a number in the middle of a game-cell
How to make divs touch each other
I can make each one of this, but not all at once.
Moreover, how to display game div in the middle (as in the picture) of the game-container div.
PS. I don't mind using some Bootstrap if it simplifies something.
Some info concerning outer container:
html, body, div.container{
height: 100%;
margin: 0;
padding: 0;
}
div.container {
display:grid;
grid-template-rows: 3fr 9fr 2fr;
grid-template-columns: 3fr 5fr;
grid-gap: 2px;
background-color: yellow;
}
use flexbox to acheive it outside grid.
div.game {
display: grid;
width: 50vw;
height: 50vh;
grid-template-columns: repeat(4, 1fr);
grid-template-rows: repeat(4, 1fr);
width: 120px;
height: 120px
}
.game-cell {
width: 30px;
height: 30px;
border: 1px solid ;
box-sizing: border-box;
}
.left-half{
width: 50vw;
height: 100vh;
border: 1px solid red;
display: flex;
align-items: center;
justify-content: center;
}
body{
padding: 0;
margin: 0;
}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width">
<title>JS Bin</title>
</head>
<body>
<div class = "game-container">
<div class="left-half">
<div class = "game">
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
<div class="game-cell"></div>
</div>
</div>
</div>
</body>
</html>
Add this to your .game-container css
display: flex;
align-items: center;
justify-content: center;
.game {
display: grid;
width: 120px;
height: 120px;
border:1px solid black;
}
.game-container{
height: 500px;
width: 500px;
display: flex;
align-items: center;
justify-content: center;
border: 1px solid black;
}
<div class = "game-container">
<div class = "game">
</div>
</div>
Here is the complete solution combined using answers and comments from comunity.
html, body, div.container{
height: 100%;
margin: 0;
padding: 0;
}
div.container {
display:grid;
grid-template-rows: 3fr 9fr 2fr;
grid-template-columns: 3fr 5fr;
grid-gap: 2px;
background-color: yellow;
}
div.container > div {
background-color: #99c2ff;
}
div.header {
grid-column: 1/3;
grid-row: 1/2;
}
div.game-container {
display: flex;
grid-column: 1/2;
grid-row: 2/3;
text-align: center;
}
div.menu {
grid-column: 2/3;
grid-row: 2/3;
}
div.footer {
grid-column: 1/3;
grid-row: 3/4;
}
div.game {
display: grid;
grid-template-columns: repeat(4, 80px);
grid-template-rows: repeat(4, 80px);
margin: auto;
}
div.grid-cell {
display: flex;
border: 1px solid rgba(0, 0, 0, 0.8);
font-size: 20px;
background-color: #e6f0ff;
}
div.value-cell {
margin: auto;
}
h1, h2, h3, h4 {
text-align: center;
}
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<link rel="stylesheet" type="text/css" href="styles.css">
<title>2048</title>
</head>
<body>
<div class="container">
<div class="header">
<h3>Title</h3>
</div>
<div class = "game-container">
<div class = "game">
<!-- <div class="grid-row"> -->
<div class="grid-cell"><div class="value-cell"></div></div>
<div class="grid-cell"><div class="value-cell"></div></div>
<div class="grid-cell"><div class="value-cell"></div></div>
<div class="grid-cell"><div class="value-cell"></div></div>
<!-- </div> -->
<!-- <div class="grid-row"> -->
<div class="grid-cell"><div class="value-cell"></div></div>
<div class="grid-cell"><div class="value-cell">2</div></div>
<div class="grid-cell"><div class="value-cell"></div></div>
<div class="grid-cell"><div class="value-cell"></div></div>
<!-- </div> -->
<!-- <div class="grid-row"> -->
<div class="grid-cell"><div class="value-cell"></div></div>
<div class="grid-cell"><div class="value-cell"></div></div>
<div class="grid-cell"><div class="value-cell">16</div></div>
<div class="grid-cell"><div class="value-cell"></div></div>
<!-- </div> -->
<!-- <div class="grid-row"> -->
<div class="grid-cell"><div class="value-cell"></div></div>
<div class="grid-cell"><div class="value-cell"></div></div>
<div class="grid-cell"><div class="value-cell">1024</div></div>
<div class="grid-cell"><div class="value-cell"></div></div>
<!-- </div> -->
</div>
</div>
<div class="menu">
<p>Some info</p>
</div>
<div class="footer">
<h4>Footer</h4>
</div>
</div>
</body>
</html>
Related
This question already has answers here:
In CSS Flexbox, why are there no "justify-items" and "justify-self" properties?
(6 answers)
Closed 2 years ago.
I need some help to align the div number 3 to always be on the bottom of the container. The right side container has more content but grid makes both the same size. Left container uses flex.
Since flex-direction is column, I tried to justify-self: flex-end for div number 3 but it's not working, but align-self: flex-end works, the other divs are centered while 3 is on the right.
How can I fix this?
body{
display: grid;
grid-template-columns: 1fr 1fr;
}
div.d {
width: 200px;
height: 200px;
background-color: red;
margin:20px;
font-size:50px;
text-align: center;
}
.flex{
border:1px solid black;
display: flex;
flex-direction: column;
align-items: center;
}
.second{
height:900px;
border:1px solid black;
}
.this{
justify-self: flex-end;
}
<!DOCTYPE html>
<html>
<head>
<link rel="stylesheet" type="text/css" href="style.css">
</head>
<body>
<div class="flex">
<div class="d">1</div>
<div class="d">2</div>
<div class="d this">3</div>
</div>
<div class="second">
<div class="d"></div>
<div class="d"></div>
<div class="d"></div>
<div class="d"></div>
</div>
</body>
</html>
Try playing with margins:
body{
display: grid;
grid-template-columns: 1fr 1fr;
}
div.d {
width: 200px;
height: 200px;
background-color: red;
margin:20px 20px 0;
font-size:50px;
text-align: center;
}
.flex{
border:1px solid black;
display: flex;
flex-direction: column;
align-items: center;
}
.second{
height:900px;
border:1px solid black;
}
div.this{
margin: auto 20px 20px;
}
<!DOCTYPE html>
<html>
<head>
<link rel="stylesheet" type="text/css" href="style.css">
</head>
<body>
<div class="flex">
<div class="d">1</div>
<div class="d">2</div>
<div class="d this">3</div>
</div>
<div class="second">
<div class="d"></div>
<div class="d"></div>
<div class="d"></div>
<div class="d"></div>
</div>
</body>
</html>
issue in the layout
I want the layout to be 100% of the page but apparently there is a small gap at the bottom
is there a way to make the layout 100% of the page unless i enter a rich content in one of the child grids then a scrollbar should appear.
there is a gap in the layout, even tho the parent grid is set to 100vh 100wh.
*{
margin: 0;
padding: 0;
list-style: none;
text-decoration: none;
box-sizing: border-box;
}
.grid {
width: 100vw;
height: 100vh;
display: grid;
grid-template-columns: 4.5% 95.5%;
grid-template-rows: 7% 89% 4%;
grid-template-areas:
"sidebar header"
"sidebar content"
"footer footer";
}
.header{
grid-area: header;
background-color: #EDEDED;
}
.sidebar{
grid-area: sidebar;
background-color: #EDEDED;
}
.content{
grid-area: content;
background-color: #f7f7f7;
display: grid;
width:100%;
height:100%;
}
.footer{
grid-area: footer;
background-color: green;
}
.img-circle {
width: 70%;
background: #fff;
margin-left: 15%;
z-index: 1000;
position: inherit;
margin-top: 20px;
border: 1px solid rgba(52,73,94,.44);
padding: 4px;
border-radius: 50%;
}
.sidebar{
padding-left: 0;
display: block;
margin-bottom: 0;
list-style: none;
}
.maintenance{
display:grid;
grid-template-rows: 15% 85%;
grid-template-areas:
"maintenance-nav"
"maintenance-info"
}
.maintenance-nav{
grid-area: maintenance-nav;
background-color: ##f7f7f7;
display: flex;
justify-content: center;
align-items: center;
border-bottom: 1px solid #25aaff;
}
.maintenance-info{
grid-area: maintenance-info;
background-color: blue;
}
.components{
display:grid;
grid-template-columns: 30% 70%;
grid-template-rows: 10% 90%;
grid-template-areas:
"components-name components-nav"
"components-name components-data";
width:100%;
height: 100%;
}
.components-name{
grid-area:components-name;
background-color: red;
}
.components-nav{
grid-area: components-nav;
background-color: blue;
display:flex;
justify-content: space-around;
align-items: center;
background-color: #f7f7f7;
}
.components-data{
grid-area: components-data;
background-color: yellow;
}
.maintenance-nav > div {
display: inline-block;
height: 60px;
background-color: white;
text-align: center;
margin: 30px;
border-radius: 10px;
width: 13%;
font-family: "Helvetica Neue",Roboto,Arial,"Droid Sans",sans-serif;
}
.components-nav-links li {
list-style: none;
display: inline-block;
padding: 0px 20px;
}
.components-nav-links li a{
transition: all 0.3s ease 0s;
}
.components-nav-links li a:hover {
color:#419C99;
}
<!DOCTYPE html>
<html>
<head>
<link rel="stylesheet" type="text/css" href="{{ url_for('static', filename='css/custom.css') }}">
<title></title>
</head>
<body>
<!--Layout grid -->
<div class="grid">
<!--header grid-->
<div class="header">Header</div>
<!--sidebar grid-->
<div class="sidebar">
<!--sidebar logo-->
<img src="{{ url_for('static', filename='images/fleet.png') }}" alt="..." class="img-circle profile_img"></div>
<!--nav list-->
<div>
</div>
<!--contenant grid-->
<div class="content">
<div class="maintenance">
<div class="maintenance-nav">
<div>Components</div>
<div>Worklist</div>
<div>Running Hours</div>
<div>Jobs Report</div>
<div>Cost Estimation</div>
<div>Logs</div>
</div>
<div class="maintenance-info">
<div class=components>
<div class="components-name"></div>
<div class="components-nav">
<nav>
<ul class="components-nav-links">
<li>Component Data</li>
<li>Jobs</li>
<li>Documents</li>
<li>Logs</li>
</ul>
</nav>
</div>
<div class="components-data">Components data</div>
</div>
</div>
</div>
</div>
</div>
<!--footer grid-->
<div class="footer">Footer</div>
</div>
</body>
</html>
Your .footer is outside the .grid element, because you have too many closing </div>'s.
Try this one:
<div class="grid">
<!--header grid-->
<div class="header">Header</div>
<!--sidebar grid-->
<div class="sidebar">
<!--sidebar logo-->
<img src="{{ url_for('static', filename='images/fleet.png') }}" alt="..." class="img-circle profile_img"></div>
<!--nav list-->
<div>
</div>
<!--contenant grid-->
<div class="content">
<div class="maintenance">
<div class="maintenance-nav">
<div>Components</div>
<div>Worklist</div>
<div>Running Hours</div>
<div>Jobs Report</div>
<div>Cost Estimation</div>
<div>Logs</div>
</div>
<div class="maintenance-info">
<div class=components>
<div class="components-name"></div>
<div class="components-nav">
<nav>
<ul class="components-nav-links">
<li>Component Data</li>
<li>Jobs</li>
<li>Documents</li>
<li>Logs</li>
</ul>
</nav>
</div>
<div class="components-data">Components data</div>
</div>
</div>
</div>
</div>
<!--footer grid-->
<div class="footer">Footer</div>
</div>
With this tool you can verify if your html structure is OK:
https://validator.w3.org/#validate_by_input
You have defined the display of the container .grid as grid and also have defined grid-template-areas within the container .grid. But, while writing markups in HTML file, you have put your .footer container outside the .grid parent container.
from the example I have three columns, when resized at a certain view-port it will wrap onto the next row, how can I target that individual div and make it fill the available width?
.boxes {
color: white;
display: grid;
grid-gap: 20px;
grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
}
.box {
background-color: blue;
padding: 10px;
}
<section class = "boxes">
<div class="box">
<p>Box 1</p>
</div>
<div class="box">
<p>Box 2</p>
</div>
<div class="box">
<p>Box 3</p>
</div>
</section>
Codepen:
CodePen
You need flexbox for this:
body {
color: white;
}
.boxes {
display: flex;
flex-wrap: wrap;
}
.box {
background-color: blue;
padding: 10px;
min-width: 250px;
box-sizing:border-box;
margin: 10px;
flex-grow: 1;
}
<section class="boxes">
<div class="box">
<p>Box 1</p>
</div>
<div class="box">
<p>Box 2</p>
</div>
<div class="box">
<p>Box 3</p>
</div>
</section>
Limit columns by max-width
you can stay with grid, but it look good only if you stay with 2 columns.
for more columns its more complicated and you can define what you want, to use grid or to use flex for convenient way.
html {
box-sizing: border-box;
}
body {
background-color: white;
color: white;
}
.boxes {
display: grid;
grid-gap: 20px;
grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
max-width: 700px;
margin: 0 auto;
text-align: center;
}
.box {
background-color: blue;
padding: 10px;
}
.box:last-child:nth-child(odd) {
grid-column: 1/3;
}
<!DOCTYPE html>
<html>
<head>
<title>Column Resize</title>
<link rel="stylesheet" type="text/css" href="style.css">
</head>
<body>
<section class="boxes">
<div class="box">
<p>Box 1</p>
</div>
<div class="box">
<p>Box 2</p>
</div>
<div class="box">
<p>Box 3</p>
</div>
</section>
</body>
</html>
I have grid section that has a grid-template-column for 3 columns. But this content is loaded dynamically so it has 2 columns sometimes. I am trying to center the columns when there is only 2 columns
I checked the documentation of the grid CSS and tried a lot of different CSS but nothing seems to work as I would like to.
.wrapper {
grid-template-columns: repeat(3,1fr);
display: grid;
align-items: stretch;
}
.items {
display: block;
}
Is this the behavior you were expecting?
More about flexbox: https://css-tricks.com/snippets/css/a-guide-to-flexbox/
.parent {
display: flex;
justify-content: center;
}
/* Addition styling */
.parent {
padding: 30px;
background: lightgrey;
opacity: 0.8;
}
.child {
padding: 30px;
text-align: center;
background: black;
margin: 10px;
color: white;
max-width: 300px;
}
<div class="parent">
<div class="child">Column</div>
<div class="child">Column</div>
</div>
<hr>
<div class="parent">
<div class="child">Column</div>
<div class="child">Column</div>
<div class="child">Column</div>
</div>
<hr>
<div class="parent">
<div class="child">Column</div>
<div class="child">Column</div>
<div class="child">Column</div>
<div class="child">Column</div>
</div>
.grid-container {
display: grid;
grid-template-columns: repeat(3,1fr);
grid-column-gap: 50px;
grid-row-gap: 50px;
justify-content: center;
align-content: center;
}
.grid-container div {
text-align: center;
}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width">
<title>JS Bin</title>
</head>
<body>
<div class="grid-container">
<div class="grid-item">1</div>
<div class="grid-item">2</div>
<div class="grid-item">3</div>
<div class="grid-item">4</div>
<div class="grid-item">5</div>
<div class="grid-item">6</div>
<div class="grid-item">7</div>
<div class="grid-item">8</div>
<div class="grid-item">9</div>
</div>
</body>
</html>
I am new to CSS grid, I have a nested grid layout page. I could not get a scroll bar for grid child div.fieldsContainer.
html,body,
.wrapper{
height: 100%;
width: 100%;
margin: 0;
padding: 0;
overflow: hidden;
}
.wrapper{
display: grid;
grid-template-rows: 50px 1fr 50px;
}
.header{
border: 1px solid #ddd;
background: lightyellow;
}
.footer{
background: lightpink;
}
.content{
display: grid;
grid-template-columns: 250px 1fr 300px;
grid-gap: 10px;
overflow: hidden;
}
.fieldTypes{
display: grid;
grid-template-rows: 40px 1fr;
}
.fieldTypes .search{
border: 1px solid red;
}
.fieldTypes .fieldsContainer{
display: grid;
grid-template-columns: repeat(3, minmax(70px,1fr));
grid-auto-rows: 50px;
grid-gap: 10px;
}
.card{
padding: 10px;
background: #ddd;
}
<div class="wrapper">
<div class="header">
Header
</div>
<div class="content">
<div class="fieldTypes">
<div class="search">search</div>
<div class="fieldsContainer">
<div class="card">1</div>
<div class="card">2</div>
<div class="card">3</div>
<div class="card">4</div>
<div class="card">5</div>
<div class="card">6</div>
<div class="card">7</div>
<div class="card">8</div>
<div class="card">9</div>
<div class="card">10</div>
<div class="card">11</div>
<div class="card">12</div>
<div class="card">10</div>
<div class="card">11</div>
<div class="card">12</div>
<div class="card">10</div>
<div class="card">11</div>
<div class="card">12</div>
</div>
</div>
<div class="inndercontent">
innder content
</div>
<div class="graphs">
graphs
</div>
</div>
<div class="footer">
Footer
</div>
</div>
One solution would be to set overflow-y:auto on the parent ( .fieldTypes ) and overflow-y:scroll on .fieldsContainer
There is no ' story ' behind this. Just that you have to set a default overflow for the parent to accept it, and then specify overflow-y:scroll( as you want vertical scroll ) on the child.
html,body,
.wrapper{
height: 100%;
width: 100%;
margin: 0;
padding: 0;
overflow: hidden;
}
.wrapper{
display: grid;
grid-template-rows: 50px 1fr 50px;
}
.header{
border: 1px solid #ddd;
background: lightyellow;
}
.footer{
background: lightpink;
}
.content{
display: grid;
grid-template-columns: 250px 1fr 300px;
grid-gap: 10px;
overflow: hidden;
}
.fieldTypes{
display: grid;
grid-template-rows: 40px 1fr;
overflow-y:auto;/*added*/
}
.fieldTypes .search{
border: 1px solid red;
}
.fieldTypes .fieldsContainer{
display: grid;
grid-template-columns: repeat(3, minmax(70px,1fr));
grid-auto-rows: 50px;
grid-gap: 10px;
overflow-y:scroll;/*added*/
}
.card{
padding: 10px;
background: #ddd;
}
<div class="wrapper">
<div class="header">
Header
</div>
<div class="content">
<div class="fieldTypes">
<div class="search">search</div>
<div class="fieldsContainer">
<div class="card">1</div>
<div class="card">2</div>
<div class="card">3</div>
<div class="card">4</div>
<div class="card">5</div>
<div class="card">6</div>
<div class="card">7</div>
<div class="card">8</div>
<div class="card">9</div>
<div class="card">10</div>
<div class="card">11</div>
<div class="card">12</div>
<div class="card">10</div>
<div class="card">11</div>
<div class="card">12</div>
<div class="card">10</div>
<div class="card">11</div>
<div class="card">12</div>
</div>
</div>
<div class="inndercontent">
innder content
</div>
<div class="graphs">
graphs
</div>
</div>
<div class="footer">
Footer
</div>
</div>
Here's a more reduced case (to cut through the irrelevant parts)
html, body, .A {
height: 100%; /* matters */
width: 100%;
margin: 0;
padding: 0;
}
.A {
max-height: 300px; /* matters */
display: grid; /* matters */
overflow: hidden; /* matters */
}
.B {
display: grid; /* matters */
overflow-y: auto; /* matters */
}
.D {
overflow-y: scroll; /* matters */
}
.C {
padding: 10px;
background-color: #07f;
}
.E {
padding: 10px;
background-color: #eee;
}
<div class="A">
<div class="B">
<div class="C">search</div>
<div class="D">
<div class="E">1</div>
<div class="E">2</div>
<div class="E">3</div>
<div class="E">4</div>
<div class="E">5</div>
<div class="E">6</div>
<div class="E">7</div>
<div class="E">8</div>
<div class="E">9</div>
<div class="E">10</div>
<div class="E">11</div>
<div class="E">12</div>
<div class="E">10</div>
<div class="E">11</div>
<div class="E">12</div>
<div class="E">10</div>
<div class="E">11</div>
<div class="E">12</div>
</div>
</div>
</div>
Set the parent's height to 100vh. Then overflow-y: scroll will work on the children.
See this example (based on the reduced case answer).
html, body, .A {
margin: 0;
padding: 0;
}
.A {
height: 100vh; /* matters */
display: grid; /* matters */
}
.B {
padding: 10px;
background-color: #07f;
}
.C {
overflow-y: scroll; /* matters */
}
.D {
padding: 10px;
background-color: #eee;
}
<div class="A">
<div class="B">search</div>
<div class="C">
<div class="D">1</div>
<div class="D">2</div>
<div class="D">3</div>
<div class="D">4</div>
<div class="D">5</div>
<div class="D">6</div>
<div class="D">7</div>
<div class="D">8</div>
<div class="D">9</div>
<div class="D">10</div>
<div class="D">11</div>
<div class="D">12</div>
<div class="D">10</div>
<div class="D">11</div>
<div class="D">12</div>
<div class="D">10</div>
<div class="D">11</div>
<div class="D">12</div>
</div>
</div>