ngFor Elements in Row - css

Hello currently I'm trying to display my items from ngFor in a row, but it's not working.
My Code:
<ng-container>
<div class="model" *ngFor="let model of modelService;" >
<div id="Ppicture" > {{model.modelPic}} </div>
<div id="Name" > {{model.modelName}} </div>
<div id="Age"> {{model.modelAge}} </div>
</div>
</ng-container>
CSS:
ng-container{
display: flex;
flex-direction: row;
}
.model{
padding-left: 10px;
padding-top: 10px;
border: solid 1px;
height: 150px;
width: 150px;
justify-content: center;
text-align: center;
}
I also tried to put display flex into the .model class, but flex is only putting the text in a row, not the boxes.
That's how it looks like
https://ibb.co/VLSKVcS

try to put width: 100% in ng-container.
ng-container{
width: 100%;
display: flex;
flex-direction: row;
}

Try this
<ng-container>
<div class="model_sec">
<div class="model" *ngFor="let model of modelService;" >
<div id="Ppicture" > {{model.modelPic}} </div>
<div id="Name" > {{model.modelName}} </div>
<div id="Age"> {{model.modelAge}} </div>
</div>
</div>
</ng-container>
ng-container {
display: block;
width: 100%;
}
.model {
padding-left: 10px;
padding-top: 10px;
border: solid 1px;
height: 150px;
width: 150px;
text-align: center;
}
.model_sec {
display: flex;
width: 100%
}

Related

How to make adaptive centered div?

What I have now:
display: flex;
align-items: center;
flex-direction: column;
How it looks with error:
What's the target:
I can do it with
margin-left: *X*px, but it is not the way I want to solve it.
May I do it with some flex properties ?
It is important to do it without bootstrap and grid.
This could be a possible solution: Center the box with flexbox and display the errors with position: absolute;. You need to take care of responsive optimization if you want to use it on a wider range of devices.
* {
box-sizing: border-box;
}
.container {
display: flex;
align-items: center;
justify-content: center;
}
.box {
border: 1px solid black;
padding: 10px;
width: 400px;
}
.field {
position: relative;
}
.input {
margin-bottom: 10px;
width: 100%;
}
.error {
position: absolute;
left: 105%;
top: 0;
width: 200px;
}
<div class="container">
<div class="box">
<div class="field">
<input class="input" type="text">
<div class="error">error 1</div>
</div>
<div class="field">
<input class="input" type="text">
<div class="error">error 2</div>
</div>
<button>Send</button>
</div>
</div>

Flexbox: Why isn't whole div shown when element below becomes hidden?

I need a flexible column where a couple of widgets are placed below each other and they are supposed to take up space dynamically. A widget has a title, and a scrollable content.
The last widget is supposed to be collapsible (by clicking on the widget title).
The problem is: When I collapse the widget, part of the title becomes hidden.
See here (click "Batch runs" to see the problem):
http://jsfiddle.net/stoefln/Ls0aqnvf/8/
$('.batchRunsTitle').on('click', function() {
$('.batchRuns').toggle()
})
* {
margin: 0;
padding: 0;
}
html,
body {
height: 100%;
width: 100%;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="column" style="height: calc(100% - 80px); background: #AAA; display: flex; flex-direction: column; ">
<div class="batchView" style="flex-grow: 1; display: flex; flex-direction: column; border: 1px solid #F00; overflow: hidden;">
<div class="header" style="">widget title 1</div>
<div class="tests" style="flex-basis: 70%; border: 1px solid #F0F; overflow: auto;">test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/></div>
<div>
widget title 2
</div>
<div class="ehs" style="flex-basis: 30%; border: 1px solid #00F; overflow: auto;">test2<br/>test2<br/>test2<br/>test2<br/>test2<br/>test2<br/>test2<br/>test2<br/>test2<br/></div>
</div>
<div class="batchRunsContainer" style="flex-grow: 1; display: flex; flex-direction: column; overflow: auto">
<div class="batchRunsTitle" style="cursor: pointer; background-color: #6c2; border: 10px solid #55F; ">
widget title 3
</div>
<!-- why is the "Batch runs" title only half visible when the next block gets hidden??? -->
<div class="batchRuns" style="overflow: auto; display: block;">
test3<br/>test3<br/>test3<br/>test3<br/>test3<br/>test3<br/>test3<br/>test3<br/>test3<br/>
</div>
</div>
</div>
<div class="log" style="height: 80px; background-color: #EEAEEE66; position: absolute; bottom: 0; right: 0; left: 0;">
Log
</div>
Also for reference here the 2 states as screenshots:
Open:
Collapsed:
Looks like it is being cut due to the overflow: auto on the batchRunsContainer. One way to fix this is to put the batchRunsTitle div outside the batchRunsContainer. Here is a working demo (check in full page):
const title = document.querySelector('.batchRunsTitle')
const content = document.querySelector('.batchRuns')
title.addEventListener('click', () => {
if (content.style.display !== 'none') {
content.style.display = 'none'
} else {
content.style.display = ''
}
})
* {
margin: 0;
padding: 0;
}
html,
body {
height: 100%;
width: 100%;
}
<div class="column" style="height: calc(100% - 80px); background: #AAA; display: flex; flex-direction: column; ">
<div class="batchView" style="flex-grow: 1; display: flex; flex-direction: column; border: 1px solid #F00; overflow: hidden;">
<div class="header" style="">widget title 1</div>
<div class="tests" style="flex-basis: 70%; border: 1px solid #F0F; overflow: auto;">test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/>test<br/></div>
<div>
widget title 2
</div>
<div class="ehs" style="flex-basis: 30%; border: 1px solid #00F; overflow: auto;">test2<br/>test2<br/>test2<br/>test2<br/>test2<br/>test2<br/>test2<br/>test2<br/>test2<br/></div>
</div>
<div class="batchRunsTitle" style="cursor: pointer; background-color: #6c2; border: 10px solid #55F; ">
widget title 3
</div>
<div class="batchRunsContainer" style="flex-grow: 1; display: flex; flex-direction: column; overflow: auto">
<div class="batchRuns" style="overflow: auto; display: block;">
test3<br/>test3<br/>test3<br/>test3<br/>test3<br/>test3<br/>test3<br/>test3<br/>test3<br/>
</div>
</div>
</div>
<div class="log" style="height: 80px; background-color: #EEAEEE66; position: absolute; bottom: 0; right: 0; left: 0;">
Log
</div>

Scale images inside divs with text

For a personal project with Angular, Angular Material and Flex-Layout I am trying to achieve a similar layout used by Bring! App:
Having images of different size (not all squared) I would like to center them proportionally and allow some text under them.
I have the following template and scss styles:
<div fxLayout="row" fxLayoutGap="5px" class="cards-container">
<div class="item-card">
<div class="image">
<img src="../../../../assets/icons/apple.png" alt="Mela" />
</div>
<span class="item-name">Mela</span>
<span class="description">12</span>
</div>
<div class="item-card">
<div class="image">
<img src="../../../../assets/icons/milk.png" alt="Latte" />
</div>
<span class="item-name">Latte</span>
<span class="description">1 description comes here, must be hidden if long text</span>
</div>
</div>
//---------------------------------------------------
.cards-container {
flex-wrap: wrap;
.item-card {
display: flex;
flex-direction: column;
justify-items: end;
color: white;
width: 7em;
height: 7em;
text-align: center;
background-color: darkslategray;
margin: 5px 0;
img {
width: 40%; // TODO: how to scale?
height: 40%;
}
.text-container {
display: flex;
flex-direction: column;
.item-name {
display: inline-block;
font-size: 1.1em;
}
.description {
width: 99%;
font-size: 0.8em;
text-align: center;
overflow: hidden;
white-space: nowrap;
text-overflow: ellipsis;
display: inline-block;
}
}
}
}
However the images do not scale down to keep the proportions with the others images, especially if narrow and long.
It all seems to look fine but it looks like your HTML code is missing the .text-container div and class.
<div class="item-card">
<div class="image">
<img src="../../../../assets/icons/apple.png" alt="Mela" />
</div>
<span class="item-name">Mela</span>
<span class="description">12</span>
</div>
should be
<div class="item-card">
<div class="image">
<img src="../../../../assets/icons/apple.png" alt="Mela" />
</div>
<div class="text-container">
<span class="item-name">Mela</span>
<span class="description">12</span>
</div>
</div>
Now for the text-overflow: ellipsis; this doesn't work on multi-lines unless you implement some JavaScript or something.
If there is any change to your code, I'd make the images a background-image instead. There could be other ways without this, but it's what I use to make sure the container is responsive with the image always responsive and centred.
For Example: https://codepen.io/StudioKonKon/pen/wRjOzr (Includes SCSS)
.image {
background-position: center center;
background-size: contain;
background-repeat: no-repeat;
font-size: 0;
}
.image-mela {
background-image: url("https://via.placeholder.com/150x175");
}
.image-latte {
background-image: url("https://via.placeholder.com/200x50");
}
.image-long {
background-image: url("https://via.placeholder.com/50x100");
}
.cards-container {
width: 100%;
margin: auto;
display: flex;
flex-wrap: wrap;
}
.cards-container .item-card {
display: flex;
flex-direction: column;
justify-items: end;
color: white;
width: 7em;
height: 7em;
text-align: center;
background-color: darkslategray;
margin: 5px;
padding: 0.5em;
box-sizing: border-box;
overflow: hidden;
}
.cards-container .item-card .image {
display: block;
margin: auto;
width: 40%;
height: 40%;
}
.cards-container .item-card .text-container {
display: flex;
flex-direction: column;
}
.cards-container .item-card .text-container .item-name {
display: inline-block;
font-size: 1.1em;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.cards-container .item-card .text-container .description {
font-size: 0.8em;
text-align: center;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
display: inline-block;
}
<div fxLayout="row" fxLayoutGap="5px" class="cards-container">
<div class="item-card">
<div class="image image-mela">Mela</div>
<div class="text-container">
<span class="item-name">Mela</span>
<span class="description">12</span>
</div>
</div>
<div class="item-card">
<div class="image image-latte">Latte</div>
<div class="text-container">
<span class="item-name">Latte</span>
<span class="description">1 description comes here, must be hidden if long text</span>
</div>
</div>
<div class="item-card">
<div class="image image-long">Long Image</div>
<div class="text-container">
<span class="item-name">Long Image Text</span>
<span class="description">must be hidden if long text</span>
</div>
</div>
</div>
Have you tried:
img {
width: 40%;
height: auto;
}
It should leave the image proportions consistent.
It is simple. I think it will solve the problem. :)
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<title>item</title>
<style type="text/css" media="screen">
.item-single{
width: 100px;
background-color: #e7e7e7;
height: 100px;
text-align: center;
}
.item-single span{
display: block;
border: 1px solid #000; /* just to show the alignment */
}
.item-single img{
width: 50%; /* you can scale it down using width */
border:1px solid #000; /* just to show the alignment */
display: block;
margin: auto;
}
</style>
</head>
<body>
<div class="item-single">
<img src="http://sugamparajuli.com.np/wp-content/uploads/2019/01/banana.png">
<span class="item-name">Mela</span>
<span class="description">12</span>
</div>
</body>
</html>
This is the result.
item-image

Bootstrap nested row margin top/bottom

I am trying to build an application that has a metro interface.
Rows are stacked like columns and the children are tiled.
in bootstrap rows have a margin-left of -15px and the same for the right. I have then added 15px padding to the .row. My columns then have a margin of 15px all around. So, I have to make my margin-top: -15px and the padding-top: 15px on my row (aswell as the bottom).
All this should give me exactly 30px between every column and row. The problem is when I nest, it all goes to pot.
My CSS looks like this:
.metro {
width: 10000px;
}
.metro .row-title {
position: absolute;
height: 100px;
top: -50px;
}
.metro > .row {
position: relative;
float: left;
height: 630px;
margin-top: -15px;
margin-right: -15px;
padding: 15px;
}
.metro > .row .row {
padding: 0;
}
.metro > .row > .col-md-1 {
width: 75px;
}
.metro > .row > .col-md-2 {
width: 150px;
}
.metro > .row > .col-md-3 {
width: 225px;
}
.metro > .row > .col-md-4 {
width: 300px;
}
.metro > .row > .col-md-5 {
width: 375px;
}
.metro > .row > .col-md-6 {
width: 450px;
}
.metro > .row > .col-md-7 {
width: 525px;
}
.metro > .row > .col-md-8 {
width: 600px;
}
.metro > .row > .col-md-9 {
width: 675px;
}
.metro > .row > .col-md-10 {
width: 750px;
}
.metro > .row > .col-md-11 {
width: 825px;
}
.metro > .row > .col-md-12 {
width: 900px;
}
.flex {
display: -webkit-box;
/* Safari */
display: flex;
/*> div {
-webkit-box-flex: 1;
flex-basis: auto;
flex-grow: 1;
flex-shrink: 1;
}*/
}
.flex.flex-wrap {
-ms-flex-wrap: wrap;
-webkit-flex-wrap: wrap;
flex-wrap: wrap;
}
.flex.flex-vertical {
-ms-flex-direction: column;
-webkit-flex-direction: column;
flex-direction: column;
}
.row div[class*="col-"] {
padding-top: 15px;
padding-bottom: 15px;
}
[class*="col-"] > div:not(.row):not(.alert),
[class*="col-"] > a,
[class*="col-"] > form {
display: block;
background-color: #3C60EF;
padding: 10px;
height: 100%;
}
[class*="col-"] > div:not(.row):not(.alert) .form-group:last-child,
[class*="col-"] > a .form-group:last-child,
[class*="col-"] > form .form-group:last-child {
margin-bottom: 0;
}
and the HTML that is messing up is this:
<div class="container metro">
<div class="row">
<div class="col-xs-12 row-title">
<h1>Login</h1>
</div>
<div class="col-md-12">
<div class="row flex flex-vertical">
<div class="col-md-12">
<div class="row">
<div class="col-xs-12 col-sm-6 col-md-6">
<div class="box-shadow">
<p>
Some welcome text
</p>
</div>
<div class="row">
<div class="col-md-12">
<div>
<p>Nesting</p>
</div>
<div class="row">
<div class="col-md-12">
<div>
<p>Nesting</p>
</div>
</div>
</div>
</div>
</div>
</div>
<div class="col-xs-12 col-sm-6 col-md-6">
<div class="box-shadow">
<p>Disclaimer</p>
</div>
</div>
</div>
</div>
<form class="col-md-12" name="loginForm" role="form">
<div class="box-shadow">
<div class="form-group">
<input class="form-control" type="text" id="userName" placeholder="Enter Username" required="" ng-model="controller.user.userName">
</div>
<div class="form-group">
<input class="form-control" type="password" id="password" placeholder="Enter Password" required="" ng-model="controller.user.password">
</div>
<div class="form-group">
<button class="btn btn-primary" type="submit" ng-disabled="loginForm.$invalid" ng-click="controller.loginUser()">Login</button>
</div>
</div>
<div class="row">
<div class="col-md-12">
<div>
<p>Another nested row</p>
</div>
</div>
</div>
</form>
</div>
</div>
</div>
</div>
I have created a codepen where you can see my issue:
http://codepen.io/r3plica/pen/ojNVeX
does anyone know how I can achieve this?
I managed to do this myself
Basically I just started with the default bootstrap and then played around until I got my desired results.
Here is the CSS that I changed:
.metro > .row {
background-color: red;
padding-left: 15px;
padding-right: 15px;
padding-bottom: 30px;
}
.metro > .row .row {
background-color: orange;
}
.metro > .row .row .row {
background-color: yellow;
}
.row div[class*="col-"] {
border: 1px dashed black;
}
.row [class*="col-"] > div:not(.row),
.row [class*="col-"] > form,
.row [class*="col-"] > a {
background-color: blue;
padding: 15px;
margin-top: 30px;
}
There was no need to add anything else, this solved all my issues.
If I got your question right, you want to create a metro-style UI. Here's a snippet which could be the base for this. As I mentioned in a comment above, do not use bootstrap rows as columns.
body, html {
height: 100%;
}
.metro {
width: 10000px;
height: 100%;
padding-left: 15px;
padding-right: 15px;
}
.metro .page {
width: 100vw;
height: 100%;
display: flex;
flex-direction: column;
float: left;
}
.content {
flex: 1;
}
.content-login {
background-color: #f0f0f0;
}
.content-page2 {
background-color: #e0e0e0;
}
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/js/bootstrap.min.js"></script>
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap.min.css" rel="stylesheet"/>
<div class="metro">
<div class="page">
<h1>Login</h1>
<div class="row content content-login">
Content
</div>
</div>
<div class="page">
<h1>Page 2</h1>
<div class="row content content-page2">
Content
</div>
</div>
</div>

get image and caption into one flex item?

AI want to put an image and its caption into one flex-item and have several such flex-items in one flex-container. I want the image to be above its caption. But what happens is that each caption is beside its image. How do I get them one above the other?
I tried putting the captions into another flex-container below the images. But when the screen size is less wide, the images stack, then the captions stack instead of being image, then its caption, image, then its caption.
<div class="flex-item-popup" id="popup">
<div class="close"><i class="fa fa-2x fa-times-circle"></i></div>
<h2></h2>
<div class='text'></div>
<div class="videos"></div>
<div class="flex-container images"></div>
<div class="flex-container captions"></div>
</div>
css:
#popup {
width: 90%;
height: auto;
padding: 20px;
border-radius: 10px;
background-color: black;
color: white;
}
#popup .close {
/*position: absolute;
right: 10px;
top: 10px;*/
float: right;
color: white;
opacity: 1;
}
#popup .close:hover {
opacity: .7 !important;
}
.images, .captions {
display: flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: flex-start;
align-content: flex-start;
align-items: flex-start;
}
.images {
margin-top: 20px;
}
.images .flex-item, .captions .flex-item {
display: flex;
flex-grow: 0;
flex-shrink: 0;
flex-basis: 300px;
}
Look into <figure> and <figcaption> HTML5 tags. I am pretty certain that is going to help you and it is what you are looking for.
Here is updated fiddle link.
And the SO code snippet here...
.flex-container {
display: flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: center;
align-content: flex-start;
align-items: center;
}
.flex-item {
/*width: 350px;
height: null;*/
flex-grow: 1;
flex-shrink: 0;
flex-basis: 200px;
justify-content: flex-start;
display: flex;
padding-left: 20px;
}
.flex-item img {
cursor: pointer;
}
<div class="flex-container images">
<div class="flex-item">
<figure>
<img src="http://newsinteractive.post-gazette.com/hbcu/morehouse/img/grads.jpg" />
<!--<div style="clear: both;"></div>-->
<figcaption>Our grads.</figcaption>
</figure>
</div>
<div class="flex-item">
<figure>
<img src="http://newsinteractive.post-gazette.com/hbcu/morehouse/img/building.jpg" />
<figcaption>A building</figcaption>
</figure>
</div>
<div class="flex-item">
<figure>
<img src="http://newsinteractive.post-gazette.com/hbcu/morehouse/img/campus.jpg" />
<figcaption>The campus.</figcaption>
</figure>
</div>
<div class="flex-item">
<figure>
<img src="http://newsinteractive.post-gazette.com/hbcu/morehouse/img/trio.jpg" />
<figcaption>Three people</figcaption>
</figure>
</div>
</div>
Hope this helps

Resources