Table: Minimize column width (multiple colspans) - html

I have this:
and want this (second column using less space):
Is there a way without introducing absolute values or fixed columns? I don't mind any other hacks like wrappers or invisible columns as long as the content sizes dynamically.
HTML
table {
border-collapse: collapse;
height: 100%;
background-color: blue;
white-space: nowrap;
}
.wrapper {
width: 40%;
font-family: avenir;
height: 100vh;
}
td > div {
color: white;
background-color: darkblue;
padding: 5px;
display: inline-block;
}
td {
padding: 0px;
border: 1px dotted white;
}
.w1px {
width: 1px;
}
.h-100 {
height: 100%;
}
<div class="wrapper">
<table>
<tr>
<td class="w1px"><div>Item1</div></td>
<td><div>Item2</div></td>
<td><div>Item3</div></td>
</tr>
<tr>
<td colspan="3"><div>Item Spanning All Three Above</div></td>
</tr>
<tr>
<td colspan="2"><div>Item Spanning Two</div></td>
</tr>
<tr class="h-100">
</tr>
</table>
</div>

Related

How to restrict the height of an image in a table cell to the same as the adjacent cell, without JavaScript?

How can I make the image in the red box be no taller than the table to its right?
It is a high-resolution image that is downscaled using max-width: 100% on the image.
I've tried display: flex on #featured and display: block on #featured img but I must be missing something.
The desired behaviour is to set the image's height the same as #condition and center the image horizontally if it doesn't fill the width.
I want the image to print out on to physical paper by default (without the user changing printer settings), so using a background-image is out of the question.
The platform I am targeting has no support for JavaScript - I can only use HTML & CSS. I know it is sacrilege, but this particular platform has good support for table layouts and poor support for typical modern <div> layouts - so I'd prefer to keep it as a nested table layout.
table {
border-collapse: collapse;
border-spacing: 0;
border-style: none;
width: 100%;
}
#featured {
padding: 2% 1% 2% 2%;
text-align: center;
width: 47%;
}
#featured img {
border: 0.5em solid red;
max-width: 100%;
}
#condition {
padding: 2% 2% 2% 1%;
vertical-align: top;
width: 47%;
}
#condition table {
border: 1px solid #000;
}
#condition td {
border: 1px solid #000;
padding: 0.5em;
}
#product {
text-align: center;
}
<table>
<tr>
<td id="featured">
<a target="_blank" href="https://i.imgur.com/sNc50nG_d.webp?maxwidth=1520&fidelity=grand">
<img src="https://i.imgur.com/sNc50nG_d.webp?maxwidth=1520&fidelity=grand" alt="">
</a>
</td>
<td id="condition">
<table>
<tr>
<th>Category</th>
<th>Condition</th>
</tr>
<tr>
<td>Overall</td>
<td>Excellent</td>
</tr>
<tr>
<td>Box</td>
<td>Excellent</td>
</tr>
<tr>
<td>Game</td>
<td>Excellent</td>
</tr>
</table>
</td>
</tr>
<tr>
<td id="product" colspan="2">{Product ID}</td>
</tr>
</table>
JSFiddle
Put the image in an absolutely-positioned div and set its height to 100%.
Note that I'm using classes instead of IDs. CSS should be reusable when possible, and IDs must be unique in a document.
table {
border-collapse: collapse;
border-spacing: 0;
border-style: none;
width: 100%;
}
.featured {
width: 47%;
position: relative;
}
.featured-img {
position: absolute;
top: 0;
bottom: 0;
left: 0;
right: 0;
text-align: center;
}
.featured-img img {
height: calc(100% - 1em);
border: 0.5em solid red;
}
#condition {
vertical-align: top;
width: 47%;
}
#condition table {
border: 1px solid #000;
}
#condition td {
border: 1px solid #000;
padding: 0.5em;
}
#product {
text-align: center;
}
<table>
<tr>
<td class="featured">
<div class="featured-img">
<a target="_blank" href="https://i.imgur.com/sNc50nG_d.webp?maxwidth=1520&fidelity=grand">
<img src="https://i.imgur.com/sNc50nG_d.webp?maxwidth=1520&fidelity=grand">
</a>
</div>
</td>
<td id="condition">
<table>
<tr>
<th>Category</th>
<th>Condition</th>
</tr>
<tr>
<td>Overall</td>
<td>Excellent</td>
</tr>
<tr>
<td>Box</td>
<td>Excellent</td>
</tr>
<tr>
<td>Game</td>
<td>Excellent</td>
</tr>
</table>
</td>
</tr>
<tr>
<td id="product" colspan="2">{Product ID}</td>
</tr>
</table>
Seeming as you won't dispense with the outer <table>, I thusly present the nuclear option...
table#outer,
table#outer>tbody {
display: contents;
}
table#outer>tbody>tr:first-child {
display: flex;
align-items: stretch;
}
table#outer>tbody>tr>td#featured {
display: contents;
}
table#outer>tbody>tr>td#featured>a {
display: block;
flex-basis: 50%;
flex-grow: 0;
flex-shrink: 5;
position: relative;
}
table#outer>tbody>tr>td#featured>a>img {
/*
border: 0.5em solid red;
display: inline-block;
flex-basis: 50%;
flex-grow: 0;
flex-shrink: 5;
*/
position: absolute;
top: 0;
left: 0;
/* right: 0;
bottom: 0;*/
object-fit: contain;
width: 100%;
height: 100%;
object-fit: contain;
}
table#outer>tbody>tr>td#condition {
display: block;
flex-basis: 50%;
flex-grow: 1;
flex-shrink: 1;
}
td#condition>table {
border: 1px solid #000;
border-collapse: collapse;
border-spacing: 0;
border-style: none;
width: 100%;
}
#condition>table td {
border: 1px solid #000;
padding: 0.5em;
}
table#outer>tbody>tr:nth-child(2) {
display: flex;
justify-content: center;
}
table#outer>tbody>tr:nth-child(2)>td#product {
text-align: center;
}
<table id="outer">
<tr>
<td id="featured">
<a target="_blank" href="https://i.imgur.com/sNc50nG_d.webp?maxwidth=1520&fidelity=grand">
<img src="https://i.imgur.com/sNc50nG_d.webp?maxwidth=1520&fidelity=grand" alt="">
</a>
</td>
<td id="condition">
<table>
<tr>
<th>Category</th>
<th>Condition</th>
</tr>
<tr>
<td>Overall</td>
<td>Excellent</td>
</tr>
<tr>
<td>Box</td>
<td>Excellent</td>
</tr>
<tr>
<td>Game</td>
<td>Excellent</td>
</tr>
</table>
</td>
</tr>
<tr>
<td id="product" colspan="2">{Product ID}</td>
</tr>
</table>

Make Arbitrary Table Column Width Equal to Space Available

The scenario is I want a table column to consume all of the available with -- nothing more and nothing less. This is similar to using table td:last-child{width:100%} except the column many not be the last.
My sample code below demonstrates what I have so far.
The first table shows the result when the data fits comfortably.
The second table shows what happens when the column whose width I want to vary has too much data. What it does is it pushes the last column over. What I want it to do is to have a width still equal to the available space after accounting for the other columns and for the excess text to be treated as overflow, which means it should be hidden.
Please note that in the real-life scenario the table can be resized, so any solution that relies on setting the columns width to a value or percentage will probably not suffice.
Thanks in advance for any assistance.
<style>
.container {
position: relative;
width: 500px;
height: 200px;
display: inline-block;
font: 16px arial;
border: 1px solid steelblue;
background-color: lightgoldenrodyellow;
}
.variCell {
text-align: left;
width: 100%;
overflow: hidden;
white-space: nowrap;
}
.orderCell {
display: inline-block;
width: 65px;
text-align: right;
}
table {
position: absolute;
display: block;
margin-right: 10px;
border: none;
overflow: hidden;
width: 100%;
height: 100%;
cursor: pointer;
}
thead {
position: relative;
display: table-header-group;
height: 25px;
max-height: 25px;
background-color: #93aed2;
text-align: center;
font-size: 14px;
line-height: 25px;
white-space: nowrap;
}
tbody {
position: relative;
border: none;
overflow: hidden;
max-width: 100%;
max-height: 100%;
cursor: pointer;
}
</style>
<div class="container">
<table>
<thead>
<tr>
<td class="orderCell">
Col 1
</td>
<td class="variCell">
Col 2
</td>
<td class="orderCell">
Col 3
</td>
</tr>
</thead>
<tbody>
<tr>
<td class="orderCell">
1
</td>
<td class="variCell">
Please use available space only.
</td>
<td class="orderCell">
100
</td>
</tr>
</tbody>
</table>
</div>
<div class="container">
<table>
<thead>
<tr>
<td class="orderCell">
Col 1
</td>
<td class="variCell">
Col 2
</td>
<td class="orderCell">
Col 3
</td>
</tr>
</thead>
<tbody>
<tr>
<td class="orderCell">
1
</td>
<td class="variCell">
Please use available space only. Do not push the next column out of the table.
</td>
<td class="orderCell">
100
</td>
</tr>
</tbody>
</table>
</div>
I would suggest using table-layout:fixed for the table and white-space: break-word; for fixed columns and stop table from expanding.
.container {
position: relative;
width: 500px;
height: 200px;
font: 16px arial;
border: 1px solid steelblue;
background-color: lightgoldenrodyellow;
}
.variCell {
position: relative;
text-align: left;
width: 100%;
overflow: hidden;
white-space: nowrap;
}
.variCell span {
position: absolute;
top: 0;
left: 0;
right: 0;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.orderCell {
display: inline-block;
width: 65px;
text-align: right;
}
table {
position: absolute;
display: block;
margin-right: 10px;
border: none;
overflow: hidden;
width: 100%;
height: 100%;
cursor: pointer;
}
thead {
position: relative;
display: table-header-group;
height: 25px;
max-height: 25px;
background-color: #93aed2;
text-align: center;
font-size: 14px;
line-height: 25px;
white-space: nowrap;
}
tbody {
position: relative;
border: none;
overflow: hidden;
max-width: 100%;
max-height: 100%;
cursor: pointer;
}
<div class="container">
<table>
<thead>
<tr>
<td class="orderCell">
Col 1
</td>
<td class="variCell">
Col 2
</td>
<td class="orderCell">
Col 3
</td>
</tr>
</thead>
<tbody>
<tr>
<td class="orderCell">
1
</td>
<td class="variCell">
<span>Please use available space only. Do not push the next column out of the table.</span>
</td>
<td class="orderCell">
100
</td>
</tr>
</tbody>
</table>
</div>

multiple tables with the same TD width

To format these 2 tables I have a css sheet. The top table is a filter/sort selection. The second is a scrollable data table.
div#scrollTableContainer {
width: auto;
margin: 20px; /* just for presentation purposes */
border: 1px solid black;
}
#tHeadContainer {
background: #CC3600;
color: black;
font-weight: bold;
}
#tBodyContainer {
height: 750px;
overflow-y: scroll;
}
td:first-child {
min-width: 5%; /* EDIT */
max-width: 5%;
border-left:0;
}
td:first-child + td {
min-width: 4%;
max-width: 4%;
}
td:first-child + td + td {
min-width: 4%;
max-width: 4%;
}
<div id="scrollTableContainer">
<div id="tHeadContainer">
<table border="1" align="center" width="100%" cellpadding="0" cellspacing="0">
<tr>
<th bgcolor="<%=bgc0%>">USED</th>
<th bgcolor="<%=bgc0%>">STATUS</th>
</tr>
</table>
</div>
<div id="tBodyContainer">
<table border="1" align="center" id="tBody" class="TableData">
<td> stuff </td>
<td> More stuff </td>
</table>
</div>
</div>
Neither of the 2 tables are aligning column wise so that the Title/Header columns do not match the tables columns below. It also shows almost the same in chrome/IE, but firefox is a complete shamble.
Im at a loss to get this right guys, any help will be appreciated.
div#scrollTableContainer {
width: auto;
margin: 20px;
/* just for presentation purposes */
}
#tHeadContainer {
background: #CC3600;
color: black;
font-weight: bold;
}
#tBodyContainer {
height: 750px;
}
th:first-child, td:first-child {
min-width: 15%;
max-width: 15%;
width: 15%;
}
td:first-child+td {
min-width: 4%;
max-width: 4%;
}
td:first-child+td+td {
min-width: 4%;
max-width: 4%;
}
<div id="scrollTableContainer">
<div id="tHeadContainer">
<table border="1" align="center" width="100%" cellpadding="0" cellspacing="0">
<tr>
<th bgcolor="<%=bgc0%>">USED</th>
<th bgcolor="<%=bgc0%>">STATUS</th>
</tr>
</table>
</div>
<div id="tBodyContainer">
<table border="1" align="center" width="100%" cellpadding="0" cellspacing="0">
<td> stuff </td>
<td> More stuff </td>
</table>
</div>
</div>
You want to align the columns of both table vertically right?
If that is so, I have a solution for you
I have changed your css and u missed tr in second table.
https://jsfiddle.net/9ccwkoav/
div#scrollTableContainer {
width: auto;
margin: 20px; /* just for presentation purposes */
border: 1px solid black;
}
#tHeadContainer {
background: #CC3600;
color: black;
font-weight: bold;
}
#tHeadContainer th{
width:50%;
}
#tBodyContainer {
height: 750px;
overflow-y: auto;
}
.TableData{
width:100%;
}
.TableData td{
width:50%;
}
This should do the trick. Notice that there will be a little margin because of the scroll bar of the second table, but you can easily change it by adding a tab in the first array with the width of the scrollbar. Hope it will help
#scrollTableContainer {
width : 96%;
margin : auto;
border : 1px solid #ccc;
}
#tHeadContainer {
background-color : green;
width : 100%;
}
#tBodyContainer {
width : 100%;
height : 750px;
overflow-y : scroll;
}
#tHeadContainer table, #tBodyContainer table {
border-collapse : collapse;
width : 100%;
}
td, th {
border : 1px solid black;
}
tr {
width : 100%;
}
th:first-child, td:first-child {
min-width : 15%;
max-width : 15%;
width : 15%; /* Tweak this value to change the first column width */
}
<div id="scrollTableContainer">
<div id="tHeadContainer">
<table>
<tr>
<th>USED</th>
<th>STATUS</th>
</tr>
</table>
</div>
<div id="tBodyContainer">
<table>
<tr>
<td>Stuff</td>
<td>Some other stuff</td>
</tr>
</table>
</div>
</div>

How to correct an accidental "table overflow"?

I am currently coding an accessibility page, but I am visually impaired. I've been advised that the table on this page:
http://www.accessibilityagent.com/legal/
is overlapping the adjacent content. Below is the CSS code being used. Could someone please help adjust this code to not overlap the page in the link above:
<div>
<style type="text/css">
body {
color: purple;
background-color: #d8da3d
}
table.center {
margin-left:auto;
margin-right:auto;
}
body {
text-align:center;
}
table {
width: 50%;
}
table, th, td {
border: 20px solid black;
margin: auto;
padding: 5px;
}
td.wrappable,
table.data_table td.wrappable {
white-space: normal;
}
</style>
Try setting this CSS for the table:
table-layout: fixed;
width: 100%;
word-wrap: break-word;
you need to fit the table, so set table-layout:fixed , now you need to have it fit as large as possible so change width to 100% in table, then you need to fit the links in the cell, so break the words, using word-wrap:break-word in .center a
body {
background-color: #d8da3d;
color: purple;
}
table.center {
margin-left: auto;
margin-right: auto;
table-layout: fixed;
width: 100%;
}
table,
th,
td {
border: 20px solid black;
padding: 5px;
}
.center a {
display: block;
word-wrap: break-word;
}
<table class="center">
<thead>
<tr>
<th scope="col">Year</th>
<th scope="col">Plaintiff</th>
<th scope="col">Defendant</th>
<th scope="col">Link to More Info</th>
</tr>
</thead>
<tbody>
<tr>
<td scope="row">2015</td>
<td>US DOJ</td>
<td>YAKIMA COUNTY</td>
<td>http://www.ada.gov/yakima…
</td>
</tr>
</tbody>
</table>

CSS - setting table column height percentage changes row height

I have the following HTML and CSS:
table {
border-collapse: collapse;
}
table.patients,
table.patients > tr {
width: 100%;
}
table.patients td,
table.patients th {
border: 1px solid black;
}
table.patients_patient_table tr,
table.patients_patient_table td {
border: 1px solid red;
}
.patients_appointment {
text-align: left;
width: 25%;
}
.patients_patient {
text-align: left;
width: 25%;
padding: 0px;
}
.patients_patientID {
text-align: left;
width: 15%;
}
.patients_sex {
text-align: left;
width: 10%;
}
.patients_physician {
text-align: left;
width: 25%;
}
.patients_row {
height: 4em;
}
.patients_patient_table {
width: 100%;
height: 100%;
}
body {
font-family: verdana, sans-serif;
margin: 0;
padding: 0;
}
<table class="patients">
<tr class="patients_row">
<td class="patients_appointment">12/20/2014 7:00am</td>
<td class="patients_patient">
<table class="patients_patient_table">
<tr>
<td>Smith, John</td>
<td>55 Y</td>
</tr>
<tr>
<td colspan=2>test</td>
</tr>
</table>
</td>
<td class="patients_patientID">5678</td>
<td class="patients_sex">M</td>
<td class="patients_physician">Dr. John Smith</td>
</tr>
</table>
The results is the following table:
If I change the CSS for .patients_patient to this:
.patients_patient {
text-align: left;
width: 25%;
height: 100%;
padding: 0px;
}
table {
border-collapse: collapse;
}
table.patients,
table.patients > tr {
width: 100%;
}
table.patients td,
table.patients th {
border: 1px solid black;
}
table.patients_patient_table tr,
table.patients_patient_table td {
border: 1px solid red;
}
.patients_appointment {
text-align: left;
width: 25%;
}
.patients_patient {
text-align: left;
width: 25%;
height: 100%;
padding: 0px;
}
.patients_patientID {
text-align: left;
width: 15%;
}
.patients_sex {
text-align: left;
width: 10%;
}
.patients_physician {
text-align: left;
width: 25%;
}
.patients_row {
height: 4em;
}
.patients_patient_table {
width: 100%;
height: 100%;
}
body {
font-family: verdana, sans-serif;
margin: 0;
padding: 0;
}
<table class="patients">
<tr class="patients_row">
<td class="patients_appointment">12/20/2014 7:00am</td>
<td class="patients_patient">
<table class="patients_patient_table">
<tr>
<td>Smith, John</td>
<td>55 Y</td>
</tr>
<tr>
<td colspan=2>test</td>
</tr>
</table>
</td>
<td class="patients_patientID">5678</td>
<td class="patients_sex">M</td>
<td class="patients_physician">Dr. John Smith</td>
</tr>
</table>
Then the height of the outer table row changes:
Why does this happen? What I really want is the result to look like this:
Edit: I am testing this on Chrome.
Your first code uses
td.patients_patient {
height: auto; /* default value */
}
td.patients_patient > table.patients_patient_table {
height: 100%;
}
According to Table height algorithms,
The height of a table is given by the 'height' property for the
'table' or 'inline-table' element.
However, there is a problem, because the height is a percentage:
The percentage is calculated with respect to the height of the
generated box's containing block. If the height of the containing
block is not specified explicitly (i.e., it depends on content
height), and this element is not absolutely positioned, the value
computes to 'auto'.
A way to solve that issue is specifying an explicit height for td.patients_patient, as you did in your second code:
td.patients_patient {
height: 100%;
}
td.patients_patient > table.patients_patient_table {
height: 100%;
}
However, now there is another problem:
CSS 2.1 does not define how the height of table cells and table rows
is calculated when their height is specified using percentage values.
So you can't use a percentage. But don't worry:
The height of a 'table-row' element's box is calculated once the user
agent has all the cells in the row available: it is the maximum of the
row's computed 'height', the computed 'height' of each cell
in the row, and the minimum height (MIN) required by the cells.
Therefore, you can use any value not greater than the row's computed height, the computed height of other cells, and the minimum height required by the cells. Using greater values would also work, but the height of the row would be increased.
For example, you can use
.patients_patient {
height: 0;
}
table {
border-collapse: collapse;
}
table.patients,
table.patients > tr {
width: 100%;
}
table.patients td,
table.patients th {
border: 1px solid black;
}
table.patients_patient_table tr,
table.patients_patient_table td {
border: 1px solid red;
}
.patients_appointment {
text-align: left;
width: 25%;
}
.patients_patient {
text-align: left;
width: 25%;
height: 0;
padding: 0px;
}
.patients_patientID {
text-align: left;
width: 15%;
}
.patients_sex {
text-align: left;
width: 10%;
}
.patients_physician {
text-align: left;
width: 25%;
}
.patients_row {
height: 4em;
}
.patients_patient_table {
width: 100%;
height: 100%;
}
body {
font-family: verdana, sans-serif;
margin: 0;
padding: 0;
}
<table class="patients">
<tr class="patients_row">
<td class="patients_appointment">12/20/2014 7:00am</td>
<td class="patients_patient">
<table class="patients_patient_table">
<tr>
<td>Smith, John</td>
<td>55 Y</td>
</tr>
<tr>
<td colspan=2>test</td>
</tr>
</table>
</td>
<td class="patients_patientID">5678</td>
<td class="patients_sex">M</td>
<td class="patients_physician">Dr. John Smith</td>
</tr>
</table>