Need to update the Date format on my Google Mail Script - date

I'm creating a Gmail script that includes 5 variables, one of which is a due date. I just want it to populate as MM/DD/YYYY, however, it is currently populating as Thu Sep 13 2018 00:00:00 GMT-0400 (EDT).
Is there a way I can do that? I've pasted my code below for your reference. Any assistance is much appreciated.
function getRowsData(sheet, range, columnHeadersRowIndex) {
columnHeadersRowIndex = columnHeadersRowIndex || range.getRowIndex() - 1;
var numColumns = range.getEndColumn() - range.getColumn() + 1;
var headersRange = sheet.getRange(columnHeadersRowIndex, range.getColumn(), 1, numColumns);
var headers = headersRange.getValues()[0];
return getObjects(range.getValues(), normalizeHeaders(headers));
}
function getObjects(data, keys) {
var objects = [];
for (var i = 0; i < data.length; ++i) {
var object = {};
var hasData = false;
for (var j = 0; j < data[i].length; ++j) {
var cellData = data[i][j];
if (isCellEmpty(cellData)) {
continue;
}
object[keys[j]] = cellData;
hasData = true;
}
if (hasData) {
objects.push(object);
}
}
return objects;
}
function normalizeHeaders(headers) {
var keys = [];
for (var i = 0; i < headers.length; ++i) {
var key = normalizeHeader(headers[i]);
if (key.length > 0) {
keys.push(key);
}
}
return keys;
}
function normalizeHeader(header) {
var key = "";
var upperCase = false;
for (var i = 0; i < header.length; ++i) {
var letter = header[i];
if (letter == " " && key.length > 0) {
upperCase = true;
continue;
}
if (!isAlnum(letter)) {
continue;
}
if (key.length == 0 && isDigit(letter)) {
continue;
}
if (upperCase) {
upperCase = false;
key += letter.toUpperCase();
} else {
key += letter.toLowerCase();
}
}
return key;
}
function isCellEmpty(cellData) {
return typeof(cellData) == "string" && cellData == "";
}
function isAlnum(char) {
return char >= 'A' && char <= 'Z' ||
char >= 'a' && char <= 'z' ||
isDigit(char);
}
function isDigit(char) {
return char >= '0' && char <= '9';

Related

A value of type 'Null' can't be assigned to a variable of type 'double'

Hello I have a connect four game who worked before null safety but I try to make the migration, but I have a problem with scores[i] = null; I can't write like that but without it I have a freeze when CPU is certain to loose
int _compute(Board board, int step, int deepness, List<double> scores) {
for (var i = 0; i < 7; ++i) {
final boardCopy = board.clone();
final target = boardCopy.getColumnTarget(i);
if (target == -1) {
scores[i] = null; // <<<---- HERE I CAN'T USE NULL
continue;
}
final coordinate = Coordinate(i, target);
boardCopy.setBox(coordinate, player);
if (boardCopy.checkWinner(coordinate, player)) {
scores[i] += deepness / (step + 1);
continue;
}
for (var j = 0; j < 7; ++j) {
final target = boardCopy.getColumnTarget(j);
if (target == -1) {
continue;
}
final coordinate = Coordinate(j, target);
boardCopy.setBox(coordinate, otherPlayer);
if (boardCopy.checkWinner(coordinate, otherPlayer)) {
scores[i] -= deepness / (step + 1);
continue;
}
if (step + 1 < deepness) {
_compute(board, step + 1, deepness, scores);
}
}
}
return _getBestScoreIndex(scores);
}
int _getBestScoreIndex(List<double> scores) {
int bestScoreIndex = scores.indexWhere((s) => s != null);
scores.asMap().forEach((index, score) {
if (score != null &&
(score > scores[bestScoreIndex] ||
(score == scores[bestScoreIndex] && _random.nextBool()))) {
bestScoreIndex = index;
}
});
return bestScoreIndex;
}
if I use List<double?>
int _compute(Board board, int step, int deepness, List<double?> scores) {
for (var i = 0; i < 7; ++i) {
final boardCopy = board.clone();
final target = boardCopy.getColumnTarget(i);
if (target == -1) {
scores[i] = null;
continue;
}
final coordinate = Coordinate(i, target);
boardCopy.setBox(coordinate, player);
if (boardCopy.checkWinner(coordinate, player)) {
scores[i] += deepness / (step + 1);//<<<---- HERE I CAN'T USE +=
continue;
}
for (var j = 0; j < 7; ++j) {
final target = boardCopy.getColumnTarget(j);
if (target == -1) {
continue;
}
final coordinate = Coordinate(j, target);
boardCopy.setBox(coordinate, otherPlayer);
if (boardCopy.checkWinner(coordinate, otherPlayer)) {
scores[i] -= deepness / (step + 1); //<<<---- HERE I CAN'T USE -=
continue;
}
if (step + 1 < deepness) {
_compute(board, step + 1, deepness, scores);
}
}
}
return _getBestScoreIndex(scores);
}
int _getBestScoreIndex(List<double?> scores) {
int bestScoreIndex = scores.indexWhere((s) => s != null);
scores.asMap().forEach((index, score) {
if (score != null && // <<<---- HERE I CAN'T USE score !=
(score > scores[bestScoreIndex] || // <<<---- HERE I CAN'T USE score >
(score == scores[bestScoreIndex] && _random.nextBool()))) {
bestScoreIndex = index;
}
});
return bestScoreIndex;
}
The issue with your code is that in the function definition you have defined the data type of score variable as List<double>. Due to which you get an error on assigning score[i] = null. To fix this use data type of score as List<double?>
i believe the param scores is a type-defined value and it has a double, which is a non null value. So you can't assign null to double as it has the type of value assigned.
You can make it double as an optional value, like a List<double?>. but with this, the values in the list will be optional and you need to force unwrap or do null check before using them.

In Flutter and if the number after decimal point is equal 0 convert the number to int

This is a function if the endValueFixed is equal for example 12.0 I want to print the number without zero so I want it to be 12.
void calculateIncrease() {
setState(() {
primerResult = (startingValue * percentage) / 100;
endValue = startingValue + primerResult;
endValueFixe`enter code here`d = roundDouble(endValue, 2);
});
}
This may be an overkill but it works exactly as you wish:
void main() {
// This is your double value
final end = 98.04;
String intPart = "";
String doublePart = "";
int j = 0;
for (int i = 0; i < end.toString().length; i++) {
if (end.toString()[i] != '.') {
intPart += end.toString()[i];
} else {
j = i + 1;
break;
}
}
for (int l = j; l < end.toString().length; l++) {
doublePart += end.toString()[l];
}
if (doublePart[0] == "0" && doublePart[1] != "0") {
print(end);
} else {
print(end.toString());
}
}
You may use this code as a function and send whatever value to end.
if (endValueFixed==12) {
print('${endValueFixed.toInt()}');
}
conditionally cast it to an int and print it then :)

E4X to JSON conversion fails for duplicate xml elements

Kindly see below code I am using to convert Mirth xml to JSON.
function E4XtoJSON(xml, ignored) {
var r, children = xml.*, attributes = xml.#*, length = children.length();
if(length == 0) {
r = xml.toString();
} else if(length == 1) {
var text = xml.text().toString();
if(text) {
r = text;
}
}
if(r == undefined) {
r = {};
for each (var child in children) {
var name = child.localName();
var json = E4XtoJSON(child, ignored);
var value = r[name];
if(value) {
if(value.length) {
value.push(json);
} else {
r[name] = [value, json]
}
} else {
r[name] = json;
}
}
}
if(attributes.length()) {
var a = {}, c = 0;
for each (var attribute in attributes) {
var name = attribute.localName();
if(ignored && ignored.indexOf(name) == -1) {
a["_" + name] = attribute.toString();
c ++;
}
}
if(c) {
if(r) a._ = r;
return a;
}
}
return r;
}
My concern is
<AdditionalMessageInformationCount AdditionalMessageInformationCount="02"><AdditionalMessageInformationQualifier>01</AdditionalMessageInformationQualifier><AdditionalMessageInformation>MEMBER MUST USE MAIL ORDER.</AdditionalMessageInformation><AdditionalMessageInformationQualifier>02</AdditionalMessageInformationQualifier><AdditionalMessageInformation>PLAN LIMITATIONS EXCEEDED</AdditionalMessageInformation></AdditionalMessageInformationCount>
Here AdditionalMessageInformation elemt is used two times so function fails to create JSON.
Kindly help if anyone have converted XML in json usingg javascript code not any API
We've had success with this version:
function E4XtoJSON(xml, ignored){
var r, children = xml.*,
attributes = xml.# * ,
length = children.length();
if (length == 0)
{
r = xml.toString();
}
else if (length == 1)
{
var text = xml.text().toString();
if (text)
{
r = text;
}
}
if (r == undefined)
{
r = {};
for each(var child in children)
{
var name = child.localName();
var json = E4XtoJSON(child, ignored);
var value = r[name];
if (value)
{
if (value instanceof Array)
{
value.push(json);
}
else
{
r[name] = [value, json]
}
}
else
{
r[name] = json;
}
}
}
if (attributes.length())
{
var a = {},
c = 0;
for each(var attribute in attributes)
{
var name = attribute.localName();
if (ignored && ignored.indexOf(name) == -1)
{
a["_" + name] = attribute.toString();
c++;
}
}
if (c)
{
if (r) a._ = r;
return a;
}
}
return r;
}
With the release of Mirth Connect version 3.3.0, you can use Mirth Connect to set your channel's interior data type to JSON. This will all be done for you.

Google Spreadsheet - How to avoid sending email duplicates?

I am having an issue with a script. I used the following script from Google Developers Website in order to do a simple merge mail. See https://developers.google.com/apps-script/articles/mail_merge
I modified a bit the script so to prevent email duplicates. However, even if the script seems to work as it marks 'EMAIL_SENT' in each row every time an email is sent. It does not pay attention if the mail as already been marked and still send the mail.
I believe there is an error at line 16 "var emailSent = rowData[6];"
I would really appreciate if someone could help me. Whoever you are thanks in advance.
Here is the modified script :
var EMAIL_SENT = "EMAIL_SENT";
function sendEmails() {
var ss = SpreadsheetApp.getActiveSpreadsheet();
var dataSheet = ss.getSheets()[0];
var dataRange = dataSheet.getRange(2, 1, dataSheet.getMaxRows() - 1, 7);
var templateSheet = ss.getSheets()[1];
var emailTemplate = templateSheet.getRange("A2").getValue();
var objects = getRowsData(dataSheet, dataRange);
for (var i = 0; i < objects.length; ++i) {
var Resume = DriveApp.getFilesByName('Resume.pdf') var Portfolio = DriveApp.getFilesByName('Portfolio.pdf') var rowData = objects[i];
var emailText = fillInTemplateFromObject(emailTemplate, rowData);
var emailSubject = "Architectural Internship";
var emailSent = rowData[6];
if (emailSent != EMAIL_SENT) {
MailApp.sendEmail(rowData.emailAddress, emailSubject, emailText, {
attachments: [Resume.next(), Portfolio.next()]
});
dataSheet.getRange(2 + i, 7).setValue(EMAIL_SENT);
SpreadsheetApp.flush();
}
}
}
function fillInTemplateFromObject(template, data) {
var email = template;
var templateVars = template.match(/\${\"[^\"]+\"}/g);
for (var i = 0; i < templateVars.length; ++i) {
var variableData = data[normalizeHeader(templateVars[i])];
email = email.replace(templateVars[i], variableData || "");
}
return email;
}
function getRowsData(sheet, range, columnHeadersRowIndex) {
columnHeadersRowIndex = columnHeadersRowIndex || range.getRowIndex() - 1;
var numColumns = range.getEndColumn() - range.getColumn() + 1;
var headersRange = sheet.getRange(columnHeadersRowIndex, range.getColumn(), 1, numColumns);
var headers = headersRange.getValues()[0];
return getObjects(range.getValues(), normalizeHeaders(headers));
}
function getObjects(data, keys) {
var objects = [];
for (var i = 0; i < data.length; ++i) {
var object = {};
var hasData = false;
for (var j = 0; j < data[i].length; ++j) {
var cellData = data[i][j];
if (isCellEmpty(cellData)) {
continue;
}
object[keys[j]] = cellData;
hasData = true;
}
if (hasData) {
objects.push(object);
}
}
return objects;
}
function normalizeHeaders(headers) {
var keys = [];
for (var i = 0; i < headers.length; ++i) {
var key = normalizeHeader(headers[i]);
if (key.length > 0) {
keys.push(key);
}
}
return keys;
}
function normalizeHeader(header) {
var key = "";
var upperCase = false;
for (var i = 0; i < header.length; ++i) {
var letter = header[i];
if (letter == " " && key.length > 0) {
upperCase = true;
continue;
}
if (!isAlnum(letter)) {
continue;
}
if (key.length == 0 && isDigit(letter)) {
continue;
}
if (upperCase) {
upperCase = false;
key += letter.toUpperCase();
} else {
key += letter.toLowerCase();
}
}
return key;
}
// Returns true if the cell where cellData was read from is empty. // Arguments: // - cellData: string function isCellEmpty(cellData) {
return typeof(cellData) == "string" && cellData == "";
}
// Returns true if the character char is alphabetical, false otherwise. function isAlnum(char) { return char >= 'A' && char <= 'Z' || char >= 'a' && char <= 'z' || isDigit(char); }
// Returns true if the character char is a digit, false otherwise. function isDigit(char) { return char >= '0' && char <= '9'; }
Your code is really hard to read and the functions that return 2 or more objects make it even harder...you are using variable names that are also a bit confusing.... but that is probably a personal pov :-)
Anyway, I think I've found the issue: when you write var rowData = objects[i];
This "object" is actually the result of the getRowData function but if you look at this function, you'll see that it returns 2 objects, the first one being itself the result of another function (getObjects) ...
You are checking the value is the 6th element of the array which is actually an object and compare it to a string. The equality will never be true.
I didn't go further in the analyse since I found it really confusing ( as I already said) but at least you have a first element to check .
I would suggest you rewrite this code in a more simple way and use more appropriate variable names to help you while debugging.
I would recommend logging both values before executing to make sure they are the same. I would also guess that the email_sent and EMAIL_SENT are different data types. Can also try forcing the value to string for comparison.
To clarify:
logger.Log(emailSent);
logger.Log(EMAIL_SENT);
if (emailSent.toString() != EMAIL_SENT.toString())
{...
Error is in this line of code -
var dataRange = sheet.getRange(startRow, 1, numRows, 2)
It's considering only 2 columns in the range. Changed 2 to 3 and it worked fine.

how to highlight user selected text within a piece of text which has already been highlighted?

I have a page where I am displaying some text in a div and I need to highlight this text in certain parts. I have done this by surrounding the text I need to highlight with a tag and appropriate css styling.
E.g.
<div>
My text will look like this with <span class="highlight">highlighted bits</span> in it.
</div>
This works fine. However, another requirement for this page is that the user must be able to select texts, click a button, and the selected text must be highlighted too.
The problem I have is when trying to identify the range of the selected text to grab (using window.getSelection.getRangeAt(0)), this gives me the range which resets after every <span> tag in the text, not from the beginning of the text.
For those who would like to know in the future this is how I did it:
jQuery.fn.highlight = function(startOffset,endOffset,type) {
function innerHighlight(node, startOffset,endOffset) {
var calledStartOffset = parseInt(startOffset);
var startOffsetNode=getChildNodeForOffset(node,parseInt(startOffset));
var endOffsetNode=getChildNodeForOffset(node,parseInt(endOffset));
startOffset = resizeOffsetForNode(startOffsetNode,parseInt(startOffset));
if (startOffsetNode == endOffsetNode){
endOffset = resizeOffsetForNode(endOffsetNode,parseInt(endOffset));
highlightSameNode(startOffsetNode, parseInt(startOffset),parseInt(endOffset),type,calledStartOffset);
} else {
highlightDifferentNode(startOffsetNode,endOffsetNode,parseInt(startOffset),parseInt(endOffset),type,calledStartOffset);
}
}
return this.each(function() {
innerHighlight(this, startOffset,endOffset);
});
};
function resizeOffsetForNode(offsetNode,offset){
if (offsetNode.id >= 0){
offset = parseInt(offset)-parseInt(offsetNode.id);
} else if (offsetNode.previousSibling != null && offsetNode.previousSibling.id > 0){
offset = parseInt(offset)-parseInt(offsetNode.previousSibling.id)-parseInt(offsetNode.previousSibling.textContent.length);
}
return offset;
}
function getChildNodeForOffset(testNode,offset) {
if (testNode.nodeType == 1 && testNode.childNodes && !/(script|style)/i.test(testNode.tagName)) {
var offsetNode=null;
var currentNode;
for (var i = 0; i < testNode.childNodes.length; ++i) {
currentNode=testNode.childNodes[i];
if (currentNode.id >= 0 && parseInt(currentNode.id) <= parseInt(offset) && ((parseInt(currentNode.id) + parseInt(currentNode.textContent.length)) >= parseInt(offset))){
offsetNode = currentNode;
break;
} else if (currentNode.id >= 0 && parseInt(currentNode.id) > parseInt(offset)){
offsetNode = currentNode.previousSibling;
break;
}
}
if (offsetNode==null){
offsetNode = testNode.childNodes[testNode.childNodes.length-1];
}
return offsetNode;
}
}
function highlightSameNode(node, startOffset,endOffset,type,calledStartOffset) {
var skip = 0;
if (node.nodeType == 3) {
if (startOffset >= 0) {
var spannode = document.createElement('span');
spannode.className = 'entity '+ type;
spannode.id=calledStartOffset;
var middlebit = node.splitText(startOffset);
var endbit = middlebit.splitText(endOffset-startOffset);
var middleclone = middlebit.cloneNode(true);
spannode.appendChild(middleclone);
middlebit.parentNode.replaceChild(spannode, middlebit);
}
} else if (node.nodeType == 1 && node.childNodes && !/(script|style)/i.test(node.tagName)) {
var childnode = node.childNodes[0];
highlightSameNode(childnode, startOffset,endOffset,type,calledStartOffset);
}
}
function highlightDifferentNode(startnode, endnode, startOffset,endOffset,type,calledStartOffset) {
var skip = 0;
if (startnode.nodeName == "#text") {
if (startOffset >= 0) {
var spannode = document.createElement('span');
spannode.className = 'entity '+ type;
spannode.id=calledStartOffset;
var endbit = node.splitText(startOffset);
var endclone = endbit.cloneNode(true);
spannode.appendChild(endclone);
endbit.parentNode.replaceChild(spannode, endbit);
}
} else if (startnode.nodeName == "SPAN") {
if (startOffset >= 0) {
var spannode = document.createElement('span');
spannode.className = 'entity '+ type;
spannode.id=calledStartOffset;
var endTextbit = startnode.childNodes[0].splitText(startOffset);
spannode.appendChild(endTextbit);
startnode.parentNode.insertBefore(spannode, startnode.nextSibling);
}
}
var currentTestNode=startnode.nextSibling;
while (currentTestNode!=endnode){
if (currentTestNode.nodeName == "#text") {
var spannode = document.createElement('span');
spannode.className = 'entity '+ type;
spannode.id=parseInt(currentTestNode.previousSibling.id)+parseInt(currentTestNode.previousSibling.textContent.length);
var currentNodeClone=currentTestNode.cloneNode(true);
spannode.appendChild(currentNodeClone);
endbit.parentNode.replaceChild(spannode, currentTestNode);
} else if (currentTestNode.nodeName == "SPAN") {
currentTestNode.className = 'entity overlap';
}
currentTestNode=currentTestNode.nextSibling;
}
var previousNodeEnd = parseInt(endnode.previousSibling.id)+parseInt(endnode.previousSibling.textContent.length);
var spannode = document.createElement('span');
spannode.className = 'entity '+ type;
spannode.id=previousNodeEnd;
if (endnode.nodeName == "#text") {
if (endOffset >= 0) {
//end offset here is the original end offset from the beginning of the text, not node
var unwantedbit = endnode.splitText(parseInt(endOffset)-parseInt(previousNodeEnd));
var endclone = endnode.cloneNode(true);
spannode.appendChild(endclone);
endnode.parentNode.replaceChild(spannode, endnode);
}
} else if (endnode.nodeName == "SPAN") {
if (endOffset >= 0) {
var wantTextbit = endnode.childNodes[0].splitText(parseInt(endOffset)-parseInt(previousNodeEnd));
spannode.appendChild(wantTextbit);
wantTextbit.parentNode.parentNode.insertBefore(spannode, endnode);
}
}
if (startnode.textContent.length < 1){
startnode.parentNode.removeChild(startnode);
}
if (endnode.textContent.length < 1){
endnode.parentNode.removeChild(endnode);
}
}
jQuery.fn.removeHighlight = function() {
return this.find("span.entity").each(function() {
this.parentNode.firstChild.nodeName;
with (this.parentNode) {
replaceChild(this.firstChild, this);
normalize();
}
}).end();
};
function contains(a, b){
return a.contains ? a != b && a.contains(b) : !!(a.compareDocumentPosition(b) & 16);
}