Data changes width of <td>

This is probably very obvious to many, so maybe someone can explain it to me.

With lots of help from members of this forum, I have constructed a table for transactional data lines that changes with every line. There is a code on each data line that I use for styling and scripting (col.2-5)

I have a created a table with 7 columns, and a script that removes columns and spans table data across mulitple columns when necessary.

But different pages of data contain different transactions, and the addition of detail lines with more cells/columns is affecting finished transaction lines in strange ways.

Same Section, same table, different data: Note the spacing between the Date column and the Description.

These examples are page 1 and 2 of the account statement, and obviously it looks pretty bad when the spacing of like transactions fluctuates from page to page.

My unfinished script is here. Much thansk to @Erik for getting me started

const code = this.record.Code

if( code === "HDRH") {
	let tds = `<td colspan=7><div class="HDRH">${this.record.column3}</div></td>`
	this.html(tds)	
}

if( code === "SAS") {
	let tds = `<td colspan=7><div class="SAS">${this.record.column3}</div></td>`
	this.html(tds)	
}

if( code === "PLC") {
	let tds = `<td colspan=7><div class="PLC">${this.record.column3}</div></td>`
	this.html(tds)	
}

if( code === "MSG") {
	let tds = `<td colspan=7><div class="MSG">${this.record.column3}</div></td>`
	this.html(tds)	
}


if( code === "CHKH") {
	let tds = `<td colspan=7><div class="CHKH">${this.record.column3}</div></td>`
	this.html(tds)	
}

/*-------------------------------------------------------------------------------------*/
var codes = ["SUMH", "SUMT", "SUM"];
let isSum = codes.indexOf(code) >= 0;

if (isSum) {
	let tds = `
		<td class="${this.record.Code}" >${this.record.Date}</td>
		<td class="${this.record.Code}" colspan=4>${this.record.column3}</td>
		<td class="${this.record.Code}" style="text-align:right;">${this.record.column4}</td>
		<td class="${this.record.Code}" style="text-align:right;">${this.record.column5}</td>
		`
	this.html(tds)	
}

/*-------------------------------------------------------------------------------------*/
var codes = ["TRNH", "TRNX", "TRN"];
let isTrn = codes.indexOf(code) >= 0;

if (isTrn) {
	let tds = `
		<td class="${this.record.Code}">${this.record.Date}</td>
		<td class="${this.record.Code}" colspan=4>${this.record.column3}</td>
		<td class="${this.record.Code}" style="text-align:right;">${this.record.column4}</td>
		<td class="${this.record.Code}" style="text-align:right;">${this.record.column5}</td>
		`
	this.html(tds)		
}


/*-------------------------------------------------------------------------------------
var codes = ["CHK"];
let isChk = codes.indexOf(code) >= 0;

if (isChk) { 
	let tds = `
	    
		<td class="${this.record.Code}" style="width: 28%;">${this.record.column3}</td>
		<td class="${this.record.Code}" style="width: 5%; text-align:right;">${this.record.column4}</td>
		<td class="${this.record.Code}" style="width: 28%;">${this.record.column5}</td>
		<td class="${this.record.Code}" style="width: 5%; text-align:right;">${this.record.column6}</td>
		<td class="${this.record.Code}" colspan=2 style="width: 28%;">${this.record.column7}</td>
		<td class="${this.record.Code}" style="width: 5%; text-align:right;">${this.record.column8}</td> 
		
		`
	this.html(tds)	
}

*/

And the table. It is absolute positioned becasue I cannot have overflow to the next page. Pages are already delimited and there can be no deviation.

<table id="table-lines" data-column-resize="" data-hide-when-empty="" data-detail="" anchor="page_media_0"
style="width: 6.625in; position: absolute; top: 276px; left: 95.0333px; height: 0.1666in; border-color: transparent; border-bottom: 0px none transparent;"
data-expander="2019" offset-x="96" offset-y="420">
    <tbody data-ol-hascaret="">
        <tr class="line-item" data-repeat="group.values">
            <td class="{{{Code}}}" style="width: 10.78%;">{{{Date}}}</td> 
            <td class="{{{Code}}}" style="width: 14.87%;">{{{column3}}}</td> 
            <td class="{{{Code}}}" style="width: 14.87%; ">{{{column4}}}</td> 
            <td class="{{{Code}}}" style="width: 14.87%; ">{{{column5}}}</td> 
            <td class="{{{Code}}}" style="width: 14.87%; ">{{{column6}}}</td> 
            <td class="{{{Code}}}" style="width: 14.87%; ">{{{column7}}}</td> 
            <td class="{{{Code}}}" style="width: 14.88%; ">{{{column8}}}</td> 
        </tr>
    </tbody>
</table>

I assume this discrepency is becasue the table to trying to fit more columns on page 2, because there are some detail lines with more cells than page 1. The Check Summary section will use 6 columns (it is commented out in my script because it causes even more wild fluctuations in spacing).

There are a dozen more transaction types I have not scripted yet, but I wanted some insight before I continue. What can I do to preserve the spacing of the transaction lines from page to page, regardless of how many possible cells could be present on the page?

Please excuse me if this is too much for a foum post. I am hoping there is a simple solution that I just don’t know about yet.

Hello @rdaneel72, is this code applied to a Standard script? And what is the selector?

Looking at the code you may want to add the CSS property width to the <td>-elements within the if-statements with isSum and isTrn too.

P.S. All those “code is equal to…” if-statements at the start can also be replaced by the following:

const code = this.record.Code;
let codes = ["HDRH", "SAS", "PLC", "MSG", "CHKH"];

if (codes.indexOf(code) >= 0) {
	let tds = `<td colspan=7><div class="${code}">${this.record.column3}</div></td>`;
	
	this.html(tds);
}

I’d set classes and set absolute widths through CSS. You can use the colspan attribute in your selectors as shown below:

.column3 {
	width: 25mm;
	background: red;
}
.column3[colspan="7"] {
	width: 100mm;
	background: green;
}

@Marten Yes, this is a standard script. The selector is tr.line-item.

I did try adding width to the IF statements for (isSum) and (isTrn), and while I can alter the wdith of the first column on Page 1, the same transaction type on Page 2 is unaffected. It looks the same.

Do I need to add width to every < td >? Do I need to script the rermaiing transaction lines before the table can resolve the widths of all these different cells? I don’t understand why a line that is NOT (isSum) would affect the spacing of (isSum) at all.

I am sure this is a fundamental way HTML tables are constructed that I am just not getting.

Thank you for the condensed code. I did change let codes = [“HDRH”, “SAS”, “PLC”, “MSG”, “CHKH”]; to var, since there are other values for the variable codes later on. (I am learning)

@Erik So this code in the CSS sets a different width for column3 depending on if it has the colspan=7 attribute?

Thank you for the responses and a few options to try.This last stretch has been difficult but I feel like I will get there.

Correct, this is an selector for an element with classname .columm3 + the attribute colspan with value 7.

.column3 {
	width: 25mm;
	background: red;
}
.column3[colspan="7"] {
	width: 100mm;
	background: green;
}

See Attribute selectors on MDN

Ususally in tables, the width of each cell is defined in the very first <tr>, which is usually in a <head>.

<table style="width :100%" data-column-resize="" data-hide-when-empty="" data-expander="2019" id="table1">
	<thead>
		<tr>
			<th style="width: 10.35%;">Column1</th>
			<th style="width: 14.61%;">Column2</th>
			<th style="width: 13.15%;">Column3</th>
			<th style="width: 11.47%;">Column4</th>
			<th style="width: 16.81%;">Column5</th>
			<th style="width: 13.31%;">Column6</th>
			<th style="width: 19.93%;">Column7</th>
		</tr>
	</thead>
	<tbody>
		<tr data-repeat="detail">
			<td>{{{Column1}}}</td>
			<td>{{{Column2}}}</td>
			<td>{{{Column3}}}</td>
			<td>{{{Column4}}}</td>
			<td>{{{Column5}}}</td>
			<td>{{{Column6}}}</td>
			<td>{{{Column7}}}</td>
		</tr>
	</tbody>
</table>

In your case, you don’t have a <thead>, so the first row that will appear is the one in need of width for each cell.

If you don’t know which row that could be, then you could define a <thead> and set its cell height (line-height) to 0, so it doesn’t show but still defines the width.

If you do know which row will always be the first, then you’ll have to define twice, once when it is use as the first (with the cell width) and once when it is being reused (no cell width).

Also, when table are used, percentage widths are often treated as hints, not absolute rules, especially with the default table layout algorithm.

The default behavior of a table is table-layout: auto:

table {
    table-layout: auto;
}

The browser examines the content of all cells and chooses column widths that best fit the content, even if that means deviating from your percentages.

But then you can use:

table {
    width: 100%;
    table-layout: fixed;
}

With table-layout: fixed:

  • Column widths are determined from the table width and declared column widths.
  • Content does not influence the column width calculation as much.
  • Overflowing content will wrap, clip, or overflow according to your CSS.

Of course, you can always “bypass” this by creating a table inside a cell, colspaned (is that a word?) to its max. Then what you do inside that cell will remain as part of that new enclosure.
It will respect the maximum size of that enclosure.

<table style="width :100%" data-column-resize="" data-hide-when-empty="" data-expander="2019" id="table1">
	<tbody>
		<tr data-repeat="detail">
			<td colspan="7">
                <table style="width :100%" data-column-resize="" data-hide-when-empty="" id="innercelltable">
	               <tbody>
		             <tr>
			             <td>...</td>
                         <td>...</td>
                         <td>...</td>
                         ...
		             </tr>
	               </tbody>
                </table>
           </td>
       </tr>
       <tr>
           <td>...</td>
           <td>...</td>
           <td>...</td>
           <td>...</td>
           <td>...</td>
           <td>...</td>
           <td>...</td>
	   </tr>
	</tbody>
</table>

Be aware that a table inside a dynamic table can be tricky to play with. You need to see it a any other element inside cell and not as another dynamic table.

An example would be a case when for a particuliar row of the parent table you need the cells displayed to have their own widths that don’t respect the parent cell width even when using colspan.

@jchamel Wow, that is a lot and most of it went over my head.

On each page the first row of every table will be the HDRH row, but that is just 1 column spanned across the entire width of the table. The maximum number of columns for any giver row will be 6 (the Check Summary table), but these rows do not include the Date column. It is kind of a mess.

But adding table-layout: fixed; to my CSS has standardize the column widths between pages.

Taking a little from each suggestion, I have cobbled together something that is working, but I don’t understand how.

I have used “colspan” to widen columns as necessary, but you can see that the value of colspan, in many cases, far exceeds the maximum nuimber of columns in the table.

I guess I don’t really understand how colspan works. Does it just muliply the value times the width of one column? Single column lines like the Account Header are colspan=12, but the maximum number of columns is only 7, and no more than 6 at one time.

I have no doubt this approach will only casue me headaches down the line.

That is the thing with HTML. It is an interpreted language which means every HTML interpreter will do with it what it wants. Most of them will agree on what it should produce but some can act differently.

Often, when you put something that make no sense, it won’t error out, it will just ignored it, like your colspan=“7” when there are a lot more column with their own colspan, but that is a recipe for problem.

You have to understand that when you change one thing, many other can be affected by it and produce different results even if they seem unrelated…that is the beauty of HTML :wink: LOL

I would review your script, make sure that the total number of cells never goes over 7, even with colspan. That is for a start.

Using table-layout: fixed, forced the solution to keep cell width fixed. But nothing says that in the future it will remain the same if your don’t clean-up your script and the end result.

You are still most likely using an older version of Connect which still rely on the previous engine (Gecko). Once you switch to the latest one, Chromium, chances are that your HTML might act differently, especially if you have unclean code in it.

Like I told you in some other thread, there are many free HTML, CSS and Javascript online classes that you should look at. From someone who had to learn it that way, you really do need to grasp what you are doing if you want to avoid headaches and boderline depression when trying to make something work and it just doesn’t want to.

Also, with AI everywhere, just ask on about what you are trying to do and follow its lead…it saves me time like you wouldn’t believe.

Point taken.

I need to figure this out. Gonna blow a bunch of it away and start over.

EDIT**********

How bad of an idea is it to add a bunch of empty < td > s to my table so I have more columns to span across?

<table id="table-lines" data-column-resize="" data-detail="" data-hide-when-empty="" anchor="page_media_0"
style="width: 6.625in; position: absolute; top: 76px; left: 89.0333px; height: 0.1in; border-color: transparent; border-bottom: 0px none transparent;"
data-expander="2019" offset-x="90" offset-y="220">
    <tbody data-ol-hascaret="">
        <tr class="line-item" data-repeat="group.values">
            <td class="{{{Code}}}" style="width: 0.375in;">{{{Date}}}</td> 
            <td class="{{{Code}}}" style="width: 1.04in">{{{column3}}}</td> 
            <td class="{{{Code}}}" style="width: 1.04in;">{{{column4}}}</td> 
            <td class="{{{Code}}}" style="width: 1.04in;">{{{column5}}}</td> 
            <td class="{{{Code}}}" style="width: 1.04in;">{{{column6}}}</td> 
            <td class="{{{Code}}}" style="width: 1.04in;">{{{column7}}}</td> 
            <td class="{{{Code}}}" style="width: 1.04in;">{{{column8}}}</td> 
            <td></td>
            <td></td>
            <td></td>
        </tr>
    </tbody>
</table>

Why would you need to span accross more column than you actually need?
When you use colspan, you tell the browser that a specific column will span accross X number of cell.

Adding more column would simply patch your earlier problem of not having the right logic in your script. Review your script, find out where there is a column calculation wrong and fix it there. Adding more column could eventually cause more issues that you’ll hve to either fix or worst, patch!.

The issue is that some cells in the same column need to be different widths for different transaction lines. This was an option suggested by Google Gemini.

Look at the section "Summary of Fees and Service Charges above. The Description spans three columns, but then the headings “Total for this Period” and “Total Year-To-Date” broke onto a second line. There were not enough remaining columns for them to span and be wide enough for the content they contained..

I have had no success adjusting widths in my script. If the content of a cell is too wide, Connect breaks that content onto a second line, which does not replicate the PlanetPress job. This seems to be working.

Then make sure that there is no remaining cell at the end of your lines that haven’t been used or colspaned into. If not you’ll end-up with distorsion due to those cell margin, padding and width.

Yes, I am making sure the total columns spanned is always 12 (the total)

Thanks to you and everyone on this forum for the help, suggestions, explanations and straight-up JavaScript code. I know I sound like an idiot, but I really have been coding PPTalk for 15 years, and Xerox VIPP before that. But HTML and JS have been a real struggle.

It is my responsibility to convert over 100 PlanetPress jobs to Connect, and also teach my 3 empoyees to do the same. The task is daunting, and I question my ability to do it every day. This very active and welcoming forum has been a huge resource for me and I would not be able to do it without you all.