Table horizontal scroll without modifying outer wrappers - html

I have a table, and I'd like to add horizontal scroll on it.
However I cannot change the outer wrapper (.app) and the body values.
I've tried a couple of things like overflow-x: scroll; and white-space: nowrap; with no luck mostly I've ended with a scroll bar without scrolling...
I've made a codesandbox to experiment with... still no clue how should solve it with this "restrictions": https://codesandbox.io/s/keen-boyd-8cgw0w?file=/src/styles.css
body {
overflow: hidden;
}
.outer-wrap {
background-color: red;
width: 100vh;
height: 50vh;
}
/* Can't modifiy body, or the .outer-wrap */
.wrap {
background-color: green;
padding: 1rem;
/* can't modifiy this width! */
width: 100%;
overflow-x: scroll;
}
table {
overflow-x: scroll;
}
th,
tr,
td {
/* it just to make the table wide */
padding-left: 10rem;
}
And my html looks like this:
<div class="outer-wrap">
<div class="wrap">
<table>
<tbody>
<tr>
<th>1</th>
<th>2</th>
<th>3</th>
<th>4</th>
<th>5</th>
<th>6</th>
</tr>
<tr>
<td>A</td>
<td>B</td>
<td>C</td>
<td>D</td>
<td>E</td>
<td>F</td>
</tr>
</tbody>
</table>
</div>
</div>

here is the front end of trust ready to answer, first of all do not use vh to define the width because you do not want that when you make the resize of the screen vertically containers are resized horizontally, almost always for heights are used fixed or automatic sizes, regarding your problem instead you should set overflow-x: auto to the red container and put as width for the green container width:fit-content.
I hope I was helpful

Related

Force HTML table to exceed div width: CSS

This question is asking the opposite of what usually is desired: a fixed-width table that exceeds the width of its parent div(s).
In fact, the following implementation works as expected in Chrome/Chromium based browsers:
#myTable {
border-collapse: collapse;
/* Collapse borders */
border: 1px solid #ddd;
/* Add a grey border */
font-size: 18px;
/* Increase font-size */
width: 1040px;
/* Full-width */
table-layout: fixed;
}
/* This is intended to be in a media query for screens less than 768 px */
#myTable {
width: 745px;
/* Full-width + 225px */
}
td:nth-child(1),
th:nth-child(1) {
width: 51.9px;
}
td:nth-child(2),
th:nth-child(2) {
width: 158.783px;
}
td:nth-child(3),
th:nth-child(3) {
width: 225px;
}
td:nth-child(4),
th:nth-child(4) {
width: 78.2667px;
}
td:nth-child(5),
th:nth-child(5) {
width: 116.15px;
}
td:nth-child(6),
th:nth-child(6) {
width: 100.833px;
}
<div style="background-color: #f0f0f0; padding: 5px; width: 540px;">
<table id="myTable" cellspacing="0" cellpadding="2" border="1">
<thead>
<tr>
<th style="text-align:right;">col1</th>
<th>col2</th>
<th>col3</th>
<th>col4</th>
<th>col5</th>
<th>col6</th>
</tr>
</thead>
<tbody>
<tr>
<td align="right">col1</td>
<td>col2</td>
<td>col3</td>
<td>col4</td>
<td>col5</td>
<td>col6</td>
</tr>
<tr>
<td align="right">col1</td>
<td>col2</td>
<td>col3</td>
<td>col4</td>
<td>col5</td>
<td>col6</td>
</tr>
<tr>
<td align="right">col1</td>
<td>col2</td>
<td>col3</td>
<td>col4</td>
<td>col5</td>
<td>col6</td>
</tr>
<tr>
</tbody>
</table>
</div>
However, when checking in Firefox and Microsoft Edge, the specified table/column widths are not honored, instead conforming to the parent div.
Most suggested solutions I've found appear to recommend applying table-layout: fixed; rule to the table, however, it's already applied in this example to no effect.
Anyone have any ideas?
Typically I use a class/ID wrapper and based on the max-width of the wrapper assign the table's width:100% which will then create the scrollbar effect with the overflow:scroll hidden property which is what I think you're looking for? If you want vertical scroll.
I never use the table-layout fixed attribute which would seem to be the problem., but then again I don't use it.
Just assign the table CSS at width:100% and use the #media with the table's wrapper based on screen size. This will work great for the column's adaptations too. You will just have to adjust accordingly.
By assigning the parent div's width inline you are creating somewhat of a roadblock for your responsive css capabilities as you cannot override inline styles. I'd change that approach.
#myTable {
border-collapse: collapse;
/* Collapse borders */
border: 1px solid #ddd;
/* Add a grey border */
font-size: 18px;
/* Increase font-size */
width: 100%;
overflow: scroll hidden;
}
.tbl_wrapper{max-width: 540px;}
#media screen and (max-width: 768px){
<!--Do some edits based on screen size //-->
.tbl_wrapper{max-width: 540px;}
}
#media screen and (max-width: 1040px){
<!--Do some edits based on screen size //-->
.tbl_wrapper{max-width: 640px;}
}
<div class="tbl_wrapper" style="background-color: #f0f0f0; padding: 5px;">
<table id="myTable" cellspacing="0" cellpadding="2" border="1">
</table>
</div>

Display table with 'display: block;' at the center of a page

I have a very large table that doesn't fit a page and I added horizontal scrollbar like this:
.table-x-scroll {
display: block;
overflow-x: auto;
white-space: nowrap;
}
And <table class="table-x-scroll">...</table>
But I also want my table to be in the center of a page. I used to use align="center" but now, when I added display: block it doesn't work. Table is always at the left. How can I do these two things at the same time?
Would be better to use a wrapper for the table and add overflow to that wrapper not the table it self. This way you can control the behavior better.
And also use margin:0 auto on table to center it horizontally. No need for display:block
See below or better in jsFIddle
table {
border: 2px solid red;
width: 300px;
margin: 0 auto;
}
td {
border: 1px solid red;
}
.wrapper {
width: 100%;
overflow-x: auto;
}
<div class="wrapper">
<table>
<tr>
<td>a</td>
<td>a</td>
</tr>
<tr>
<td>a</td>
<td>a</td>
</tr>
<tr>
<td>a</td>
<td>a</td>
</tr>
</table>
</div>
Try to add margin-left:auto; margin-right:auto; in your style and specify the width
.table-x-scroll {
display: block;
overflow-x: auto;
white-space: nowrap;
margin-left:auto;
margin-right:auto;
width:50%;
}
<table class="table-x-scroll" border="1">
<tbody>
<row>
<td>AA</td>
<td>BB</td>
</row>
</tbody>
</table>
Try adding Margin : 0 auto
.table-x-scroll {
display: block;
overflow-x: auto;
white-space: nowrap;
margin : 0 auto
}
I can see that others have answered the aligning problem. But i couldn't see the "Doesn't fit to page" error so here is a solution for that:
In the css you specified overflow-x: auto;
If you change that to overflow-x scroll; it will make it scale to whatever size you choose to specify. and make it scrollable. The scrollbar within is possible to edit/remove, but it will still scroll ^^
I personally recommend the vw,vh values
example:
.bunnydiv {font-size: 1vw, 1vh;} This will make it scale to 1% of the width and of the height of the monitor. This can be specified with either vh, vw, vh and vw. Not both paramaters are needed, and it will scale accordingly :-)
I found some code I made myself some time ago, use this as a reference :-)
.div_scroll
{overflow-y: scroll;
display: block;
top:0px;
right: 0px;
position: absolute;
transform: translate(-23.6vw, 15vh);
border: 3px solid #dddddd;
max-height: 75vh;
width: 76vw;
margin: 0px;
background-color: white;}
It's copy-pasted, and setup this way for readability. Don't format you code like this unless it works better for you :-)

HTML, CSS: Make table vertically scrollable

I have a table that is dynamically created after an AJAX request (using vue.js). The number of columns and width of each column is calculated.
My problem is, that there should be a vertical scrollbar when theres not enough space in the table, but even when setting style="width: 600px; overflow-x: scroll" no scrollbar shows up and the header elements gets shrinked together to the width of the wrapper div and the table rows get clipped.
Heres my relevant code (using bootstrap and vue.js 2):
<div class="panel-body" id="datatable">
<table class="table data-table" id="datatable-content">
<thead class="datatable-head" id="datatable-head">
<tr>
<th v-for="value in tableHeader" v-text="value"></th>
</tr>
</thead>
<tbody class="datatable-body" id="datatable-body">
<tr v-for="row in tableRows">
<td v-for="key in tableHeader" v-html="highlightFilterString(row[key])"></td>
</tr>
</tbody>
</table>
</div>
and the css:
.data-table {
overflow-x: scroll;
display: block;
width: 100%;
}
.datatable-body {
display:block;
height: calc(100vh - 118px);/
overflow-y: scroll;
overflow-x: hidden;
}
.datatable-head {
display:block;
overflow-x: scroll;
}
.datatable-head, .datatable-body tr {
min-width: 100px;
text-align: center;
}
.datatable-body td {
min-width: 100px;
text-align: center;
}
.datatable-head th {
min-width: 100px;
text-align: center;
}
What is the problem here?
I commented out the overflow-x element and it seems to be working fine now. Made fiddle with static html content
https://jsfiddle.net/v7qpot2b/
.datatable-body {
display:block;
height: calc(100vh - 118px);/
overflow-y: scroll;
/* overflow-x: hidden; */
}

Responsive table column with CSS

There's a table with three columns, the first and the last are fixed and the middle one should be fluid.
The problem - inside of the middle column there's text with nowrap and it prevents it from being fluid.
How that could be done?
How it looks on wide page (correct behaviour):
How it should look on narrow page:
How it actually looks on narrow page (incorrect behaviour, see scrollbar):
The code https://jsfiddle.net/8c9msa71/
td {
border: 1px solid black;
}
.fluid {
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
<table>
<tr>
<td>first</td>
<td class="fluid">very-very-very-very-very-very-long-second-text</td>
<td>third</td>
</tr>
</table>
you can do it by adding a div
td { border: 1px solid black; }
.fluid { position: relative; width: 70%;}
.fluid div {
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
position: absolute;
left: 5px;
right: 5px;
top: 0;
}
<table width="100%">
<tr>
<td>first</td>
<td class="fluid">
<div>very-very-very-very-very-very-long-second-text</div>
</td>
<td>third</td>
</tr>
</table>
I noticed the solution to add a div.
If you don't want to or need to add a div, you could use max-width.
Explanation:
Your first problem is that none of your elements has a width attribute set. To start with I would set a max-width of your "very-very-long-second-text". For example you can add max-width: 60vw; to your .fluid. If you're not familiar with the vw syntax, read more here: https://www.w3.org/TR/css3-values/#vw
By only adding this, you'll be almost there. You'll still have one problem left: On very small devices / resolutions, you notice that your third table-data, <td></td> will disappear out of visible area.
Instead of collapsing ALL the content, I recommend using display: inline-block; on your table data <td></td>. What this does is that it will display your table data inline as long as they have enough space to be inline. In addition a small part of the information will be visible, instead of the result of NO information visible at all. When the available area becomes smaller (i.e. resizing the window), they will start jumping down one by one.
Full CSS:
td {
border: 1px solid black;
display: inline-block;
}
.fluid {
max-width: 60vw;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}

Different 100% height of table in Chrome/IE and FireFox

The problem is, that all of elements (main container, table container and table itself) must have 100% height. Table itself has slightly smaller size in Chrome and IE, than in Firefox, which causes a small gap between .table-container and table borders.
Do somebody know how to fix this? I've spent almost all day for this, and can't simply find a solution. Would be grateful for any help.
Here is a link for fiddle with my current problem: fiddle link
<div class="container">
<div class="buttons">
<div></div>
<div></div>
<div></div>
<div></div>
</div>
<div class="table-container">
<table>
<thead>
<tr>
<td>1</td>
<td>2</td>
<td>3</td>
<td>4</td>
</tr>
</thead>
<tbody>
<tr>
<td>a</td>
<td>b</td>
<td>c</td>
<td>d</td>
</tr>
<tr>
<td>aa</td>
<td>bb</td>
<td>cc</td>
<td>dd</td>
</tr>
<tr>
<td>aaa</td>
<td>bbb</td>
<td>ccc</td>
<td>ddd</td>
</tr>
</tbody>
</table>
</div>
</div>
and CSS:
html, body, .container, .table-container, table
{
height: 100%;
}
.container
{
display: block;
width: 500px;
margin: 0 auto;
text-align: center;
}
.table-container
{
width: 100%;
border: 1px solid red;
padding-top: 30px;
margin-top: -30px;
}
.buttons
{
height: 30px;
}
.buttons div
{
box-sizing: border-box;
-moz-box-sizing: border-box;
width: 25%;
float: left;
height: 30px;
border: 1px solid black;
}
table
{
border: 1px solid black;
width: 100%;
border-spacing: 0;
}
thead td, tbody td
{
width: 25%;
height: 25%;
}
Update: added padding and negative margin for .table-container
Update2: added border-spacing and border-collapse to an example. Still not working properly.
Update3: Now it works here, which means, that i couldn't fully reproduce my bug to show it to you :( But in general, the problem is, that the height of 5x5 table in Chrome is less from FF on 22px, which is 22px gap between table container and a table itself. Each cell has around 4px + to table height in Firefox.
It appears to be the border spacing on the table.
Apply this CSS to the table element:
border-spacing: 0;
Be aware that
width: 100%;
does not work the exactly the same way as
height: 100%;
does.
While width: 100% grabs 100% of the parent's width even if there has not been an explicit setting of that width, height: 100% works only on elements whose parents have a fixed height.
Simply speaking, %-width applies dynamically, while %-height applies to static parents container's heights.
I came here because I was having the same problems with different 100% height of table for Chrome and Firefox. The fix is to add a border the table. You can just add border-bottom as well and it won't actually show up in Chrome, but will fix the height issue.
table
{
**border-bottom: 1px solid black;**
width: 100%;
border-spacing: 0;
}