Odoo - Move invoice total at the bottom - odoo

I created a custom invoice but how can I add make the payment terms and total row at the bottom on the page? (see image for desired scenario)
<div class="clearfix" style="line-height:0">
<p t-if="o.narration" name="comment">
<span t-field="o.narration"/>
</p>
<p t-if="o.invoice_payment_term_id" name="payment_term" style="font-size:12px;margin-left:-120px;text-transform:uppercase;line-height:0">
Payment <b><span t-field="o.invoice_payment_term_id"/></b> after statement of accounts
<!--<span t-field="o.invoice_payment_term_id.note"/>-->
</p>
<p t-if="o.amount_total" style="font-size:12px;margin-left:-120px;text-transform:uppercase;line-height:normal">
<span t-esc="o.compute_amount_in_word(o.amount_total)"/>
</p>
<div id="total" class="row" style="margin-top:-30px !important;">
<div t-attf-class="#{'col-6' if report_type != 'html' else 'col-sm-7 col-md-6'} ml-auto">
<table class="table table-sm table-borderless" style="page-break-inside: avoid; width:222px; margin-left:235px !important;border-bottom: 4px solid white">
<tr>
<td class="text-right"><strong>TOTAL</strong></td>
<td style="" class="text-right">
<span class="text-nowrap text-right" style="" t-field="o.amount_total"/>
</td>
</tr>
</table>
</div>
</div>
</div>
Right now it's showing payment terms, amount in words, and total just below where the table ends. I tried to make the position: relative, but then it shows only on the first page and will overlap if the invoice is more than one page. (see image)

Related

ASP.Net Core 5 Print Div Vertical Alignment Problem

I have tried various alignment settings, but nothing is making a difference. Please have a look at the far right column in the image below and notice that the price is shifted down compared with the columns to the left.
Note that this is the print preview
This is what the same table looks like on the web page when not printing.
You can see that in the web page, I have set the margin for the last column to mt-0.
Here is my code:
<div class="row">
<div class="col-4">
<button class="btn btn-primary" onclick="printDiv()">Print</button>
</div>
</div>
<div class="row" id="PrintDiv">
<div class="col-md-8 offset-2">
<div class="row d-flex">
<div class="col-8">
<p>
<h2>#ViewBag.FullName</h2>
<h4>Order History</h4>
</p>
</div>
<div class="col me-1">
<img src="#(Configuration.GetValue<string>("StorageContainerURL"))/store-logo.png" )
class="img-fluid " style="max-height:75px;width:auto" alt="Alternate Text" />
</div>
</div>
<table class="table">
<thead>
<tr>
<th>Date</th>
<th>Order ID</th>
<th>Items</th>
<th>Total</th>
</tr>
</thead>
<tbody>
#foreach (var order in Model)
{
<tr>
<td class="align-middle">#order.OrderDate.ToLocalTime().ToShortDateString()</td>
<td class="align-middle">#order.Id</td>
<td class="align-middle">
<ul style="list-style-type:none">
#foreach (var item in order.OrderItems)
{
<li>
<div class="alert alert-info" role="alert">
<span class="badge bg-success">#item.Amount</span> [#item.Price.ToString("c")] - #item.Product.Name
</div>
</li>
}
</ul>
</td>
<td class="mt-0">#order.OrderItems.Select(m => m.Product.Price * m.Amount).Sum().ToString("c")</td>
</tr>
}
</tbody>
</table>
</div>
</div>
#section Scripts{
<script type="text/javascript">
function printDiv() {
var divContents = document.getElementById("PrintDiv").innerHTML;
var a = window.open('', '', 'height=500, width=500');
a.document.write('<html>');
a.document.write('<body > <br>');
a.document.write(divContents);
a.document.write('</body></html>');
a.document.close();
a.print();
}
</script>
}
Does anyone have any suggestions to make Total column align properly with the other columns?
I figured out the problem shortly after I posted the question. I realized that the Printed Version of the page would not recognize the Bootstrap classes. So instead, I changed all columns to use inline styles for alignment.
<tbody>
#foreach (var order in Model)
{
<tr>
<td style="vertical-align:text-top">#order.OrderDate.ToLocalTime().ToShortDateString()</td>
<td style="vertical-align:text-top">#order.Id</td>
<td style="vertical-align:text-top">
<ul style="list-style-type:none">
#foreach (var item in order.OrderItems)
{
<li>
<div class="alert alert-info" role="alert">
<span class="badge bg-success">#item.Amount</span> [#item.Price.ToString("c")] - #item.Product.Name
</div>
</li>
}
</ul>
</td>
<td style="vertical-align:text-top">#order.OrderItems.Select(m => m.Product.Price * m.Amount).Sum().ToString("c")</td>
</tr>
}
</tbody>

Header alignment data table after added style ='100%'

I cant align the datatable suppose to show that header and bottom must be equal but on the image below it seems it does not equal to each other
how to fix this datatable
Here is the sample code below i created to display the datatable
<div class="row" id='content'>
<div class="col-md-4 pull-left">
<div class="customCenter" >
<img class="img-responsive rounded chooseTicket rounded mx-auto d-block" src="https://www.w3schools.com/bootstrap/paris.jpg" alt="Generic placeholder image" >
</div>
<h2 class='chooseHeader'>Commendation</h2>
</div>
<div class=" " id='dataList'>
<div class="">
<table class="hover dataTable data-table test table-responsive" id="example" style="width:100%">
<thead>
<tr>
<th>Ticket Number</th>
<th>Details</th>
<th>Created Date</th>
<th>Status</th>
</tr>
</thead>
</table>
</div>
</div>

Not able to check the check box, exception "element not visible"

In an table which can contain more rows, user is searchable using the email id. After searching, selecting the first check box. But selenium is throwing the element not visible exception.
//*[#id='share_user']/tbody/tr1/td1//label
//*[#id='share_user']/tbody/tr1/td1//input
//label[#for='checkbox_416']
last identifier is dynamic. Still getting the element not visible exception.
Table code is mentioned below
<table class="table table-striped table-hover dataTable" id="share_user"
aria-describedby="share_user_info">
<thead>
<tr role="row">
<th class="small-cell sorting" role="columnheader" tabindex="0"
aria-controls="share_user" rowspan="1" colspan="1" style="width: 137px;"
aria-label="Share Profile : activate to sort column ascending">Share Profile </th>
<th class="medium-cell sorting" role="columnheader" tabindex="0"
aria-controls="share_user" rowspan="1" colspan="1" style="width: 523px;"
aria-label="User Details: activate to sort column ascending">User Details</th>
<th class="medium-cell sorting_asc" role="columnheader" tabindex="0"
aria-controls="share_user" rowspan="1" colspan="1" style="width: 366px;"
aria-sort="ascending" aria-label="Access: activate to sort column descending">Access</th>
</tr>
</thead>
<tbody role="alert" aria-live="polite" aria-relevant="all">
<tr class="odd">
<td class="">
<div class="checkbox check-default">
<input name="checkUser" id="checkbox_416" value="416" class="shareCheck"
type="checkbox">
<label for="checkbox_416"></label>
</div>
</td>
<td class=" ">
<img src="" class="img-responsive display-inline share-image">
<div class="display-inline">
<p class="share-name">alexx</p>
<p class="muted">
<i class="fa fa-envelope" hidden="true"></i>
<span>alexxm360#gmail.com</span>
</p>
</div>
</td>
<td style="vertical-align: middle;" class=" sorting_1">
<div class="select2-container medium-cell" id="s2id_rolelink416"
style="float:left;">
<a href="javascript:void(0)" onclick="return false;" class="select2-choice"
tabindex="-1">
<span class="select2-chosen">PROFILE ADMIN</span>
<abbr class="select2-search-choice-close"></abbr>
<span class="select2-arrow">
<b></b>
</span>
</a>
<input class="select2-focusser select2-offscreen" id="s2id_autogen11"
type="text">
<div class="select2-drop select2-display-none select2-with-searchbox">
<div class="select2-search">
<input autocomplete="off" autocorrect="off"
autocapitalize="off" spellcheck="false" class="select2-input"
type="text">
</div>
<ul class="select2-results">
</ul>
</div>
</div>
<select name="profileUsers.roleId" id="rolelink416"
class="medium-cell select2-offscreen" style="float:left;" tabindex="-1">
<option value="6">PROFILE ADMIN</option>
<option value="7">PROFILE AGENT</option>
<option value="8">PROFILE VIEWER</option>
<option value="196">profile role</option>
</select>
</td>
</tr>
</tbody>
</table>
providing the screen shots as well.
Try to use explicit wait with Expected Conditions
WebDriverWait wait = new WebDriverWait(driver, 10);
WebElement checkbox = wait.until(ExpectedConditions.visibilityOfElementLocated(By.xpath("//*[#id='share_user']/tbody/tr[1]/td[1]//input")));
checkbox.click();
You can use the following expression, I have verified working fine.
driver.findElement(By.xpath("//*[#id='share_user']/tbody/tr[1]/td[1]/div")).click();
Try this
int ele_size=driver.findElements(By.xpath("locator")).size();
driver.findElements(By.xpath("locator")).get(ele_size-1).click();
We might encounter element not visible exception if element matching the locator existed in the DOM but is not currently visible. So we have to take the size of the element in first statement then in next statement we have to take the first element from the list and click on element.
Used this //*[#id='share_user']/tbody/tr[1]/td[1]/div worked

How to get the updated count of rows in a table after changing the page number

Actually in the table i'm working on there is pagination. I could get the count of rows present in the first page.
When i change the page number, table row count is not getting updated as per the second page.
How to force selenium to update the count after changing the page number. page refresh is not the solution as i need to navigate to second page again
public Boolean checkMessageIsFailed(String message, String channelNameToCheck, String channelTypeToCheck) {
UIPublish uiPublish = new UIPublish(driver);
Boolean isMessageSent = null;
SimplifyUtils.waitTillElementFound(uiPublish.currentPageNumber, 60);
//getting the page count
int pageCount = Integer.parseInt( uiPublish.totalPages.getText());
for (int j=1; j< pageCount;pageCount++)
{
//getting the rows present in the table
int messagesCount = uiPublish.listOfTextInMessages.size();
for (int i = 0; i < messagesCount; i++)
{
//getting the text from each row to match
//matching the text of the required message sent with the messages present in the sent messages
if (uiPublish.listOfTextInMessages.get(i).getText().equalsIgnoreCase(message))
{
String currentChannel = driver.findElements(By.xpath("//*[#id='inbox-wrapper']//tr["+ (i + 1)+ "]")).get(i).getAttribute("data-original-title");
}
}
//navigating to naxt page if the condition is not matched
uiPublish.navigateToNextPage.click();
}
return isMessageSent;
}
<div class="grid simple">
<div class="grid-body no-border email-body">
<br>
<div class="row-fluid">
<div id="email-list" class="table-responsive">
<form id="schMsgFORM" name="schMsgFORM" action="/viewSentSchMessage.action"
method="post">
<table class="table table-striped table-hover" id="emails">
<thead>
<tr>
<th>
</th>
<th>Social Channel
</th>
<th>Message
</th>
<th>Scheduled Time
</th>
<th>Actions
</th>
</tr>
</thead>
<tbody>
<tr id="outputWTFrUjUyYlE1d1piNG1XUmNuUFBnUT09">
<td class="small-cell v-align-middle" style="width: 2%">
<div class="checkbox check-success ">
<input name="msgcheckbox" id="chkboxWTFrUjUyYlE1d1piNG1XUmNuUFBnUT09"
value="WTFrUjUyYlE1d1piNG1XUmNuUFBnUT09" type="checkbox">
<label for="chkboxWTFrUjUyYlE1d1piNG1XUmNuUFBnUT09"></label>
</div>
</td>
<td style="width: 150px">
<div class="account-sent">
<div class="row">
<div class="display-inline">
<div class="profile-pic" data-toggle="tooltip" title=""
data-original-title="galloway360">
<img class="account-profile"
src="http://pbs.twimg.com/profile_images/378800000473105984/b0ad2b50b4fb81303d32720afea274ea_normal.png"
alt="">
<div class="social-icon-pub">
<span
class="social-icon-twitter img-responsive social-icon-box">
</span>
</div>
</div>
</div>
</div>
</div>
</td>
<td style="width: 50%">
<div class="muted message-wrap">
<br>
Source: Auto 2016/12/08 17:35:30 Message: How's your day?
</div>
<p class="sch-details">
Sent by: Nagarjuna reddy
<em>Scheduled from Profile :
NA
</em>
</p>
</td>
<td style="width: 15%">
<p class="muted m-t-5">
2016-12-08 05:35 PM
</p>
<p class="region">
(Asia/Calcutta)
</p>
</td>
<td style="width: 10%">
<a
href="/social/editUpdate?s360securetoken=SU0wxc4jrR8DE8Lf5hzKnRYasjg&schMsgId=WTFrUjUyYlE1d1piNG1XUmNuUFBnUT09&pageSource=publish"
data-toggle="tooltip" title="" type="button"
class="btn btn-success btn-small" data-original-title="Edit">
<i class="fa fa-pencil">
</i>
</a>
</td>
</tr>
</tbody>
</table>
</form>
</div>
</div>
</div>
</div>

Assistance with a dynamically generated field

I have another dynamic question for you. I have three input fields that I need to enter values for. These "dijit_form_DateTextBox_36" are created dynamically (the 36 is variable). There is a value earlier in the code that is unique and can be searched for. I know I need to use something like:
driver.findElement(By.xpath("//div[contains(., 'QA GM 04012014 1424 Item Name')]/parent::...somepath.sendKeys("...");
But I am still too new to this stuff to be able to figure it out. And if someone can assist me with what I need to put, as well as how they figured it out, I would greatly appreciate it. I'd really love to solve these on my own! Code is below. Bolded portion is the static text that can be searched. Bolded and italicized lines are the three controls that need to be modified. NOTE: The id="shipDate0_0" is also dynamic, it can be shipDate0_0, shipDate1_0, etc. So can't key on that.
<tr class="tableControlHeader twTableHeaderTR"></tr>
<tr class="tableControlDataRow evenRow twTableTR">
<td class="twTableTD details" align="center" rowspan="2"></td>
<td class="twTableTD details" align="center" rowspan="2">
<p>
<b>
QA GM 04012014 1424 Item Name
</b>
</p>
<br></br>
<p></p>
<p></p>
<p></p>
<p></p>
<p></p>
</td>
<td class="twTableTD" align="center" rowspan="2"></td>
<td class="twTableTD" align="center"></td>
<td class="twTableTD" align="center"></td>
<td id="shipDate0_0" class="twTableTD" align="center">
<div style="padding-right: 20px;">
<div id="dateWrap-projectedFirstShipDate_0_0" class="inputText_Full twControl twDateSelector" ;="" onblur="updateAvgPerWeek(0,0)" initialvalue="" value="" name="tw#local#quoteComparison#0#country#0#projectedFirstShipDate" style="white-space:nowrap;">
<div id="projectedFirstShipDate_0_0" lang="" dojoattachpoint="pickerDiv" widgetid="projectedFirstShipDate_0_0" name="tw#local#quoteComparison#0#country#0#projectedFirstShipDate">
<span dojoattachpoint="leftPicker">
<div id="widget_dijit_form_DateTextBox_36" class="dijit dijitReset dijitInlineTable dijitLeft dateSelectionSin…tBox dijitComboBox dijitDateTextBox dijitComboBoxOpenOnClick" role="combobox" widgetid="dijit_form_DateTextBox_36">
<div class="dijitReset dijitRight dijitButtonNode dijitArrowButton dijitDownArrowButton dijitArrowButtonContainer" role="presentation" dojoattachpoint="_buttonNode, _popupStateNode" popupactive="true"></div>
<div class="dijitReset dijitValidationContainer"></div>
<div class="dijitReset dijitInputField dijitInputContainer">
<input id="dijit_form_DateTextBox_36" class="dijitReset dijitInputInner" type="text" aria-haspopup="true" role="textbox" dojoattachpoint="textbox,focusNode" autocomplete="off" aria-valuenow="null" aria-invalid="false" tabindex="0" value="" style="" delocalized="null" aria-disabled="false"></input>
<input type="hidden" value=""></input>
</div>
</div>
</span>
<span dojoattachpoint="rightPicker"></span>
<span style="position: absolute;" dojoattachpoint="calImage"></span>
<input id="projectedFirstShipDate_0_0" type="text" isdatefield="true" name="tw#local#quoteComparison#0#country#0#projectedFirstShipDate" style="display:none" dojoattachpoint="hiddenInput" delocalized="null"></input>
</div>
</div>
</div>
</td>
<td id="InDate0_0" class="twTableTD" align="center" ;="" onclick="updateAvgPerWeek(0,0)">
<div style="padding-right: 20px;">
<div id="dateWrap-inDate_0_0" class="inputText_Full twControl twDateSelector" ;="" onblur="updateAvgPerWeek(0,0)" initialvalue="" value="" name="tw#local#quoteComparison#0#country#0#inDate" style="white-space:nowrap;">
<div id="inDate_0_0" lang="" dojoattachpoint="pickerDiv" widgetid="inDate_0_0" name="tw#local#quoteComparison#0#country#0#inDate">
<span dojoattachpoint="leftPicker">
<div id="widget_dijit_form_DateTextBox_35" class="dijit dijitReset dijitInlineTable dijitLeft dateSelectionSin…tBox dijitComboBox dijitDateTextBox dijitComboBoxOpenOnClick" role="combobox" widgetid="dijit_form_DateTextBox_35">
<div class="dijitReset dijitRight dijitButtonNode dijitArrowButton dijitDownArrowButton dijitArrowButtonContainer" role="presentation" dojoattachpoint="_buttonNode, _popupStateNode" popupactive="true"></div>
<div class="dijitReset dijitValidationContainer"></div>
<div class="dijitReset dijitInputField dijitInputContainer">
<input id="dijit_form_DateTextBox_35" class="dijitReset dijitInputInner" type="text" aria-haspopup="true" role="textbox" dojoattachpoint="textbox,focusNode" autocomplete="off" aria-valuenow="null" aria-invalid="false" tabindex="0" value="" style="" delocalized="null" aria-disabled="false"></input>
<input type="hidden" value=""></input>
</div>
</div>
</span>
<span dojoattachpoint="rightPicker"></span>
<span style="position: absolute;" dojoattachpoint="calImage"></span>
<input id="inDate_0_0" type="text" isdatefield="true" name="tw#local#quoteComparison#0#country#0#inDate" style="display:none" dojoattachpoint="hiddenInput" delocalized="null"></input>
</div>
</div>
</div>
</td>
<td id="OutDate0_0" class="twTableTD" align="center" onclick="updateAvgPerWeek(0,0)">
<div style="padding-right: 20px;">
<div id="dateWrap-outDate_0_0" class="inputText_Full twControl twDateSelector" ;="" onblur="updateAvgPerWeek(0,0)" initialvalue="" value="" name="tw#local#quoteComparison#0#country#0#outDate" style="white-space:nowrap;">
<div id="outDate_0_0" lang="" dojoattachpoint="pickerDiv" widgetid="outDate_0_0" name="tw#local#quoteComparison#0#country#0#outDate">
<span dojoattachpoint="leftPicker">
<div id="widget_dijit_form_DateTextBox_34" class="dijit dijitReset dijitInlineTable dijitLeft dateSelectionSin…tBox dijitComboBox dijitDateTextBox dijitComboBoxOpenOnClick" role="combobox" widgetid="dijit_form_DateTextBox_34">
<div class="dijitReset dijitRight dijitButtonNode dijitArrowButton dijitDownArrowButton dijitArrowButtonContainer" role="presentation" dojoattachpoint="_buttonNode, _popupStateNode" popupactive="true"></div>
<div class="dijitReset dijitValidationContainer"></div>
<div class="dijitReset dijitInputField dijitInputContainer">
<input id="dijit_form_DateTextBox_34" class="dijitReset dijitInputInner" type="text" aria-haspopup="true" role="textbox" dojoattachpoint="textbox,focusNode" autocomplete="off" aria-valuenow="null" aria-invalid="false" tabindex="0" value="" style="" delocalized="null" aria-disabled="false"></input>
<input type="hidden" value=""></input>
</div>
</div>
</span>
<span dojoattachpoint="rightPicker"></span>
<span style="position: absolute;" dojoattachpoint="calImage"></span>
<input id="outDate_0_0" type="text" isdatefield="true" name="tw#local#quoteComparison#0#country#0#outDate" style="display:none" dojoattachpoint="hiddenInput" delocalized="null"></input>
</div>
</div>
</div>
</td>
<td id="BuyQuantity0_0" class="twTableTD" align="center" onblur="updateAvgPerWeek(0,0)" name="BuyQuantity0"></td>
<td id="TotalCost0_0" class="twTableTD" align="center" name="TotalCost0"></td>
<td id="NumberOfWarehouses0_0" class="twTableTD" align="center" onblur="updateAvgPerWeek(0,0)" td=""></td>
<!--
# of Warehouses
-->
<td id="AveragePerWarehouse0_0" class="twTableTD" align="center" name="AvgPerWhouseWeek0"></td>
<!--
Cost per Warehouse
-->`enter code here`
<td id="ProjectedSellPrice0_0" class="twTableTD" align="center" td=""></td>
<!--
Projected Sell Price
-->
<td id="PercentOfTotal0_0" class="twTableTD" align="center"></td>
<td class="twTableTD" align="center" rowspan="2"></td>
</tr>
The best xpath I am able to come up with is this:
//td[normalize-space()='QA GM 04012014 1424 Item Name']/following-sibling::td[contains(#id, 'shipDate')]//input[contains(#class,'dijitInputInner')]
Let me explain:
This part finds the td element with the text you're looking for, the normalize-space() call is just like text(), but trims any whitespace before/after the text & I've found it to be invaluable since discovering it a short time ago. text() will return whitespace and is often difficult to match
//td[normalize-space()='QA GM 04012014 1424 Item Name']
This next part finds ALL td's after the previous element. From the code snippet provided this will find ALL 13 td's that follow
/following-sibling::td
Narrow down that set of 13 by finding only the td containing the ID you're interested in, this is better than using a hardcoded number like /following-sibling::td[2] to find the second td
/following-sibling::td[contains(#id, 'shipDate')]
Then find the input field that you're interested in, there are number of ways you could do this, choose whichever you prefer
//input[contains(#class,'dijitInputInner')]
//input[contains(#id,'dijit_form_DateTextBox')]
I hope that's clear enough & works well for you, please let me know if not