I've got a jade email template. It includes a mixin file which includes the header mixin, which should be in all emails. It gets included properly, but due to the nesting level within it (3 levels deep), anything I put after the mixin, doesn't maintain nesting where it should.
views/mixins/email.jade
mixin header(siteLogo)
div(style='margin-bottom: 20px; border: 1px solid #ddd; padding: 20px; width: 50%; margin: 0 auto 20px;')
div(style='text-align: center; border-bottom: 1px solid #EEE; padding-bottom: 10px;')
img(src='#{siteLogo}', style='text-align: center;')
views/emails/forgot_password.jade:
include ../mixins/email
+header(siteLogo)
p
| Hi #{name},
p
| Welcome to the site!
Generates the email html like:
<div style="margin-bottom:20px;border:1px solid #ddd;padding:20px;width:50%;margin:0 auto 20px">
<div style="text-align:center;border-bottom:1px solid #eee;padding-bottom:10px">
<img src="path/to/image/logo" style="text-align:center">
</div>
</div>
<p>Hi BobCobb</p>
<p>Welcome to the site!</p>
But I want both of those paragraph tags to be inside of the main <div> like:
<div style="margin-bottom:20px;border:1px solid #ddd;padding:20px;width:50%;margin:0 auto 20px">
<div style="text-align:center;border-bottom:1px solid #eee;padding-bottom:10px">
<img src="path/to/image/logo" style="text-align:center">
</div>
<p>Hi BobCobb</p>
<p>Welcome to the site!</p>
</div>
To actually answer the original question, you need to specify within the mixin where the block should render.
views/mixins/email.jade
mixin header(siteLogo)
div(style='margin-bottom: 20px; border: 1px solid #ddd; padding: 20px; width: 50%; margin: 0 auto 20px;')
div(style='text-align: center; border-bottom: 1px solid #EEE; padding-bottom: 10px;')
img(src='#{siteLogo}', style='text-align: center;')
if block
block
Jade is useless for html email. I would strongly recommend against using any web intended framework.
Read up more on how html email differs from the web.
Here is what your code should look like if it is optimized for html email:
<table width="50%" border="0" cellpadding="0" cellspacing="0" style="border:1px solid #dddddd">
<tr>
<td align="center">
<img alt="" src="path/to/image/logo" width="100" height="75" style="margin: 0; border: 0; padding: 0; display: block;">
</td>
</tr>
<tr>
<td style="font-family: Helvetica, Arial, sans-serif; font-size: 14px; color: #000000; padding:20px; border-top:1px solid #dddddd;">
<p>Hi BobCobb</p>
<p>Welcome to the site!</p>
</td>
</tr>
</table>
Related
Unable to render borders properly in xhtml2pdf. It is applying to individual elements.
Here is invoice template for rendering:-
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>SRS Mess | Invoice</title>
<style>
#import url('https://fonts.googleapis.com/css2?family=Poppins:wght#300&display=swap');
#import url('https://fonts.googleapis.com/css2?family=Merriweather&display=swap');
body{
font-family: 'Poppins', sans-serif;
user-select: none;
}
/* Keeping paragraph together */
p{
margin: 0;
-pdf-keep-with-next: true;
}
*,
::after,
::before {
box-sizing: border-box;
}
#media (prefers-reduced-motion: no-preference) {
:root {
scroll-behavior: smooth;
}
}
.container{
--bs-gutter-x: 1.5rem;
width: 100%;
padding-right: 7.5rem;
padding-left: 7.5rem;
margin-right: auto;
margin-left: auto;
}
.text-center {
text-align: center !important;
}
.mt-3 {
margin-top: 1rem !important;
}
.mt-2 {
margin-top: 0.5rem !important;
}
.text-danger {
color: rgba(220, 53, 69, 1) !important;
}
</style>
</head>
<body>
<div class="container mt-2 mb-2" style="background: rgb(237, 237, 255); border-top: 2px solid black; border-bottom: 2px solid black; border-left: 2px solid black; border-right: 2px solid black; border-radius: 1rem;">
<div class="text-center mt-3">
<img src="{{ST_ROOT}}/logo.png" alt="" height="200" width="200">
<p class="mt-2" style="font-size: 1.5rem; color: orange;">SRS Mess</p>
<br>
<p style="font-family: 'Merriweather', serif; font-size: 2rem; text-decoration: underline;">INVOICE</p>
<p style="font-size: 1.5rem; font-weight:bold; color: green;">Monthly Mess subscription of Rs. {{amount}} /- </p>
</div>
<br>
<div class="details">
<p><strong>Name: </strong>{{name}}</p>
<p><strong>Email: </strong>{{email}}</p>
<p><strong>Mobile: </strong>{{mobile}}</p>
<p><strong>Hostel: </strong>{{hostel}} {{room}}</p>
<p><strong>Branch: </strong>{{branch}}</p>
<p><strong>Date: </strong>{{date}}</p>
<p><strong>Time: </strong>{{time}}</p>
</div>
<br>
<div class="subscriptions text-center" style="border: 2px solid green; background-color: #e9ffe9;">
<p class="text-danger" style="font-size: 1.5rem;">Mess Subscription</p>
<p><strong>Start date: </strong>{{start_date}}</p>
<p><strong>End date: </strong>{{end_date}}</p>
</div>
<br>
<div class="footer">
<p>Thank you for taking the monthly mess subscription! <br> We hope that you will enjoy our meal!</p>
<p>If you have any issues, please contact us here</p>
</div>
</div>
</body>
</html>
This is the render_to_pdf function:
def render_to_pdf(template_src, context_dict={}):
template = get_template(template_src)
html = template.render(context_dict)
result = BytesIO()
pdf = pisa.pisaDocument(BytesIO(html.encode("UTF-8")), result, link_callback=fetch_resources)
if not pdf.err:
return HttpResponse(result.getvalue(), content_type='application/pdf')
return None
Downloading the pdf by:
pdf = render_to_pdf('invoice.html', usr_data)
return HttpResponse(pdf, content_type="application/pdf")
When we render the pdf it looks like this:
Rendered PDF
But by HTML template it should be:
invoice.html
So I want to render the HTML template as it is. You can see that the borders are been applied to all the individual elements in the tag. It should not happen. So please let me know the solution for this.
Thanks in advance !!
I created a 3x3 table for my tic-tac-toe game using the table tag and i added a click event listener to the each of the row using forEach loop but unfortunately nothing is showing in my console
const boxes = document.querySelectorAll('.box');
const strategy = document.querySelector('#strategy');
const restartBtn = document.querySelector('#restart');
const arry = [];
const tick_x = 'X';
const tick_o = 'O';
const userAction = () => {
boxes.forEach((box) => {
box.addEventListener('click', function clk() {
console.log("clicked")
})
})
}
html {
height: 100%;
}
body {
margin: 0;
padding: 0;
background-color: teal;
overflow: hidden;
font-family: "Itim", cursive;
}
.game {
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
}
p {
color: white;
text-align: center;
margin: 40px auto;
width: 200px;
}
table {
margin-bottom: 50px;
border-radius: 10px;
border-top: 2px solid white;
border-left: 2px solid white;
border-bottom: 2px solid white;
border-right: 2px solid white;
}
button {
width: 100px;
}
h1 {
width: 100%;
height: 100%;
text-align: center;
}
.row1 td {
width: 100px;
height: 100px;
border-bottom: 1px solid white;
border-left: 1px solid white;
}
.row2 td {
width: 100px;
height: 100px;
border-bottom: 1px solid white;
border-left: 1px solid white;
}
.row3 td {
width: 100px;
height: 100px;
border-left: 1px solid white;
}
.r11 {
border-left: none;
}
<div class="intro">
<p class="name">TIC-TAC-TOE</p>
<h2 id="strategy"></h2>
<p class="player">Player X'S turn</p>
</div>
<table>
<tr class="row1">
<td class="r11">
<h1 class="box" id="0"> </h1>
</td>
<td class="r12">
<h1 class="box" id="1"> </h1>
</td>
<td class="r13">
<h1 class="box" id="2"> </h1>
</td>
</tr>
<tr class="row2">
<td class="r21">
<h1 class="box" id="3"> </h1>
</td>
<td class="r22">
<h1 class="box" id="4"> </h1>
</td>
<td class="r23">
<h1 class="box" id="5"> </h1>
</td>
</tr>
<tr class="row3">
<td class="r31">
<h1 class="box" id="6"> </h1>
</td>
<td class="r32">
<h1 class="box" id="7"> </h1>
</td>
<td class="r33">
<h1 class="box" id="8"> </h1>
</td>
</tr>
</table>
<button id="restart"><h3>Reset</h3></button>
</div>
I recommend that you use a single event handler for the whole table rather than creating one for each row. (This used to be known as a "delegated event handler.")
That would look like this:
let table = document.querySelector('table')
function onClickCell( event, cellId ) {
// this is invoked when a cell is clicked
console.log(`onClickCell`, cellId)
}
// this is the delegated event handler
table.addEventListener('click', event => {
// figure out which table cell it occurs within
let td = event.target.closest('.box')
// if click wasn't inside a cell (e.g. was in gutter), don't fire the cell-click handler
if(!td) return true
// click WAS inside a cell: fire cell-click handler with some helpful data
let cellId = td.getAttribute('id')
return onClickCell(event, cellId)
})
Some reasons for using a delegated event handler:
Better runtime performance
Admittedly, this is less of an issue with modern browsers than it was 10 years ago, and isn't a major problem given that your use-case is so small, but it's still a good practice.
One handler is easier to manage than three
You will want clicks on the table to do different things depending on the current game phase. During the "gameplay" phase, clicking on a cell should claim the cell for the active player. Before gameplay begins, maybe there is no visible grid of cells, or maybe you have an invented mechanic for choosing which player goes first. After the gameplay phase, you may want clicking on a cell to reveal on which turn that cell was claimed (so players can study the game they just finished). No matter what you've got in mind, having a single root-level click handler for the table will drastically simplify the job of re-wiring how clicks are handled.
Survivability
If you modify the document, either by overwriting some innerHTML, or by using the DOM API to modify nodes, you'll obliterate existing click handlers that are attached to the modified portion of the document. But a delegated handler is, by definition, attached to a distant ancestor of the relevant part of the DOM, meaning it will survive and stay active.
Define your own API
You have zero control over the arguments that the browser provides to a regular DOM event handler. But a delegated handler can pass any data you want to your specialty function, meaning you can define a custom API for the functions it calls. In my example, I make the delegated handler do the work of grabbing the cell's ID, and then it passes that value as an argument to the cell-click handler; that's work the cell-click handler no longer needs to do. The delegated handler could also collect other info about the current game state and provide that to the cell-click handler. A delegated handler can also selectively ignore some some clicks, or call additional functions, or even call the cell-click function multiple times -- essentially letting you invent new kinds of events. A more sophisticated version might even fire literal CustomEvents that are listened for at the document level.
You never call userAction, so you can either call it or wrap it in a closure and call it (as below)
const boxes = document.querySelectorAll('.box');
const strategy = document.querySelector('#strategy');
const restartBtn = document.querySelector('#restart');
const arry = [];
const tick_x = 'X';
const tick_o = 'O';
(() => {
boxes.forEach((box) => {
box.addEventListener('click', function clk () {
console.log("clicked")
})
})
})()
html{
height: 100%;
} body{
margin: 0;
padding: 0;
background-color: teal;
overflow: hidden;
font-family: "Itim", cursive;
}
.game{ display: flex; flex-direction: column; justify-content: center; align-items: center; } p{ color: white; text-align: center; margin: 40px auto; width: 200px; }
table{
margin-bottom: 50px;
border-radius: 10px;
border-top: 2px solid white;
border-left: 2px solid white;
border-bottom: 2px solid white;
border-right: 2px solid white;
}
button{
width: 100px;
} h1{ width: 100%; height: 100%; text-align: center;
}
.row1 td{
width: 100px;
height: 100px;
border-bottom: 1px solid white;
border-left: 1px solid white;
}
.row2 td{
width: 100px;
height: 100px;
border-bottom: 1px solid white;
border-left: 1px solid white;
}
.row3 td{
width: 100px;
height: 100px;
border-left: 1px solid white;
}
.r11 {
border-left: none;
}
<!DOCTYPE html>
<head></head>
<body>
<div class="intro">
<p class="name">TIC-TAC-TOE</p>
<h2 id="strategy"></h2>
<p class="player">Player X'S turn</p>
</div>
<table>
<tr class="row1">
<td class="r11"><h1 class = "box" id ="0"> </h1></td>
<td class="r12"><h1 class = "box" id ="1"> </h1></td>
<td class="r13"><h1 class = "box" id ="2"> </h1></td>
</tr>
<tr class="row2">
<td class="r21"><h1 class="box" id ="3"> </h1></td>
<td class="r22"><h1 class="box" id ="4"> </h1></td>
<td class="r23"><h1 class="box" id ="5"> </h1></td>
</tr>
<tr class="row3">
<td class="r31"><h1 class="box" id ="6"> </h1></td>
<td class="r32"><h1 class="box" id ="7"> </h1></td>
<td class="r33"><h1 class="box" id ="8"> </h1></td>
</tr>
</table>
<button id="restart"><h3>Reset</h3></button>
</div>
</body>
You create the userAction function, but never call it.
Add at the end:
userAction()
Alright so basically i've been searching for a way that when someone clicks a text , a scroll down menu drops down with basically more information ( Sort of like a read more ).
I little experience in Java or Jquery and im not even sure where the problem is wether it's in my functions.php or my script itself . I've done alot of research and tried alot of things but none seem to be able to help me out so i figured id make my own post .
Keep in my , i took most of the codes in templates given by other member and tried to modify the code so it works with my site, I am trying to accomplish something similar to this site : http://www.randomsnippets.com/2011/04/10/how-to-hide-show-or-toggle-your-div-with-jquery/ the second example where there are 3 boxes and only one shows up when you click on it, However mine will simply be text instead of boxes)
My Javascript file looks like this(as stated in comment idk what thechosenone is , my guess is when you select a box it is now known as the chosen one ) :
jQuery(document).ready(function (){
$('.newboxes').each(function(index) {
if ($(this).attr("id") == thechosenone) {
$(this).show(200);
}
else {
$(this).hide(600);
}
});
}(jQuery)
So i went ahead and modified my function.php and added these line of code :
add_action('wp_enqueue_scripts', 'showonlyone' );
function showonlyone() {
wp_enqueue_script('showonlyone', get_template_directory_uri() . "/js/showonlyone.js");
}
As for calling the java script into my wordpress page I have no idea how to do this . The template gave me something like this :
<table>
<tr>
<td>
<div style="border: 1px solid blue; background-color: #99CCFF; padding: 5px; width: 150px;">
<a id="myHeader1" href="javascript:showonlyone('newboxes1');" >show this one only</a>
</div>
<div class="newboxes" id="newboxes1" style="border: 1px solid black; background-color: #CCCCCC; display: block;padding: 5px; width: 150px;">Div #1</div>
</td>
<td>
<div style="border: 1px solid blue; background-color: #99CCFF; padding: 5px; width: 150px;">
<a id="myHeader2" href="javascript:showonlyone('newboxes2');" >show this one only</a>
</div>
<div class="newboxes" id="newboxes2" style="border: 1px solid black; background-color: #CCCCCC; display: none;padding: 5px; width: 150px;">Div #2</div>
</td>
<td>
<div style="border: 1px solid blue; background-color: #99CCFF; padding: 5px; width: 150px;">
<a id="myHeader3" href="javascript:showonlyone('newboxes3');" >show this one only</a>
</div>
<div class="newboxes" id="newboxes3" style="border: 1px solid black; background-color: #CCCCCC; display: none;padding: 5px; width: 150px;">Div #3</div>
</td>
</tr>
</table>
Can someone please tell me how im supposed to be calling this function and add it to a block of text ? I just want that when someone clicks on it , this box or whatever, drops down and displays additional information and when you click on another line of text this window will scroll back up and the other one will drop down .
Took me a minute but here you go:
http://jsfiddle.net/V4DTZ/
Now, for whats going on in the code:
<table>
<tr>
<td>
<div style="border: 1px solid blue; background-color: #99CCFF; padding: 5px; width: 150px;">
<a class="newboxes" href="#" id="newboxes1">show this one only</a>
</div>
<div class ="div_newboxes" id="div_newboxes1" style="border: 1px solid black; background-color: #CCCCCC; display: block;padding: 5px; width: 150px;">Div #1</div>
</td>
<td>
<div style="border: 1px solid blue; background-color: #99CCFF; padding: 5px; width: 150px;">
<a class="newboxes" href="#" id="newboxes2" >show this one only</a>
</div>
<div class ="div_newboxes" id="div_newboxes2" style="border: 1px solid black; background-color: #CCCCCC; display: none;padding: 5px; width: 150px;">Div #2</div>
</td>
<td>
<div style="border: 1px solid blue; background-color: #99CCFF; padding: 5px; width: 150px;">
<a class="newboxes" href="#" id="newboxes3" >show this one only</a>
</div>
<div class ="div_newboxes" id="div_newboxes3" style="border: 1px solid black; background-color: #CCCCCC; display: none;padding: 5px; width: 150px;">Div #3</div>
</td>
</tr>
You'll see that I changed the id of the links to their corresponding div, and I added a div_ prefix on the ids of the div.
This way we have an easy way to select the div that matches with the link
I gave all of the links the same class, so that we can set up one onclick event for all of the links.
All of the div that contain your content also has the same class, so we can toggle them all at once.
Here is the jquery:
jQuery(document).ready(function (){
$('.newboxes').on('click', function(){
var div_id = "#div_" + $(this).prop('id');
$('.div_newboxes').each(function(i, value){
if($(value).prop('id')=== $(div_id).prop('id')){
$(div_id).show(200);
}
else{
$(value).hide(600);
}
});
})
}(jQuery))
Note that because we used an onclick event for all elements with class = "newboxes"
we are now able to use this to refer to the specific calling element. There is now no need to have theChosenOne variable.
When document is ready, attach event handlers to all of the elements needed
The event handler that is called every time a click happens on these elements
Event Handler
var ShowHideBlocks = function(){
$('.newboxes').each(function(index) {
if ($(this).attr("id") == thechosenone) {
$(this).show(200);
}
else {
$(this).hide(600);
}
});
}
Attached to all interested elements
jQuery(document).ready(function (){
$('.newboxes').each(function(index) {
$(this).bind('click',function(){
thechosenone = $(this).attr(id); //thechosenone is a global variable
ShowHideBlocks(); // Invoke the showHide method as part of anonymous handler
});
}
});
}(jQuery)
I am currently using jquery slideonlyone function. I am having problems implementing an expanding/collapsing image(Plus.png)(Minus.png) change when clicked on. this is my jquery code.
<script type="text/javascript">
function slideonlyone(thechosenone) {
$('div[name|="newboxes2"]').each(function(index) {
if ($(this).attr("id") == thechosenone) {
$(this).find("img").attr({src:"Minus.png"}).slideDown(200);
}
else {
$(this).find("img").attr({src:"Plus.png"}).slideUp(600);
}
});
}</script>
<table><tr>
<td>
<div style="border: 1px solid blue; background-color: #99CCFF; padding: 5px;">
<a id="myHeader1" href="javascript:slideonlyone('newboxes1');" ><img src="images/faq_cuts/Plus_Circle.png";/>slide this one only</a>
</div>
<div name="newboxes2" id="newboxes1" style="border: 1px solid black; background-color: #CCCCCC; display: block;padding: 5px;">Div #1</div>
</td>
<td>
<div style="border: 1px solid blue; background-color: #99CCFF; padding: 5px;">
<a id="myHeader2" href="javascript:slideonlyone('newboxes2');" ><img src="images/faq_cuts/Plus_Circle.png";/>slide this one only</a>
</div>
You don't actually have any images in your html.
Also, you are using attr incorrectly. If you want to set the src of an image it would be .attr("src","Minus.png").
I am newbie to my project. Here we use Javascript,CSS and HTML to display web page. I am not at all familiar with all these. In IE8, letters in a word are displaying vertically but the same code works in IE7.
It should appear as "Channel Preference" and not as
c
h
a
n
n
e
l
p
r
e
f
r
e
n
c
e
CSS parameters are as follows ::
.SubjectAreaChoiceAnchor, .SubjectAreaChoiceAnchor:link, .SubjectAreaChoiceAnchor:visited
{
font: normal 11px Tahoma;
color: #000000;
padding: 2px 2px 2px 29px;
display: block;
cursor: default;
white-space: nowrap;
text-decoration: none;
}
.SubjectAreaChoiceAnchor:hover
{
color: black;
background-color: #D1DDE7;
padding: 1px 2px 1px 29px;
border-top: solid 1px white;
border-bottom: solid 1px white;
margin: 0px 0px 0px 0px;
}
HTML Looks like this::
< div class="dialogBody" style="max-height: 400px; overflow-y: auto;">
< div style="display: block;" id="idExtTagSelector">
< table cellspacing="0" cellpadding="0">
< a onclick="WebExpressionSelector.onChoose('idExtTagSelector','channelPref','','true','Channel Preference'); return false;" href="javascript:void(null)" displayname="Channel Preference" usequotes="true" defaultvalue="" name="channelPref" eid="idExtTagSelector" class="SubjectAreaChoiceAnchor" id="idWebExprchannelPref">Channel Preference
< /a>
< /table>< /div>< /div>
Please help.Thanks in advance.
Prathima
As mentioned your HTML table isn't formatted correctly. The correct way for you to have a table should be as follows:
<table>
<tr>
<td>content</td>
</tr>
</table>
In your case, if you must use a table to get all the values next to each other the table should be as follows:
<table>
<tr>
<td>A</td>
<td>B</td>
<td>C</td>
</tr>
</table>
You should also only really use tables for tabular data. Anything else should be styles via the CSS.
First and foremost you have to type your html correctly, expecially closing tags, and the table structure needs at least a <tr> and <td> inside. Then you can see if the problem persist and we can try to find a solution.
<div class="dialogBody" style="max-height: 400px; overflow-y: auto;">
<div style="display: block;" id="idExtTagSelector">
<table cellspacing="0" cellpadding="0">
<tr>
<td>
<a onclick="WebExpressionSelector.onChoose('idExtTagSelector','channelPref','','true','Channel Preference'); return false;" href="javascript:void(null)" displayname="Channel Preference" usequotes="true" defaultvalue="" name="channelPref" eid="idExtTagSelector" class="SubjectAreaChoiceAnchor" id="idWebExprchannelPref">Channel Preference
</a>
</td>
</tr>
</table>
</div>
</div>