cloning a div is also cloning text values - javascript

I need the cloned element's value blank.
The code below works good, but it's cloning the values; cant figure out how to stop that.
var Move = {
copy : function(e, target) {
var eId = $(e);
var copyE = eId.cloneNode(true);
var cLength = copyE.childNodes.length -1;
copyE.id = e+'-copy';
for(var i = 0; cLength >= i; i++) {
if(copyE.childNodes[i].id) {
var cNode = copyE.childNodes[i];
var firstId = cNode.id;
cNode.value = '';
cNode.id = firstId+'-copy'; }
}
$('txtWoundCareLocation').value="";
$(target).appendChild(copyE);
},
element : function(e, target, type) {
var eId = $(e);
if(type == 'move') { $(target).appendChild(eId); }
else if(type == 'copy') {
this.copy(e, target);
}
}
}

eId.cloneNode(true) returns an jQuery object, not a HTMLNode. Thus copyE contains a jQuery object not an HTMLNode. You are using it like an HTMLNode however. This should introduce problems.
Also, setting value on a jQuery object (as in $('txtWoundCareLocation').value="") will not alter the HTMLNode value. Instead, you should call the jQuery.val method to unset the HTMLNode value: $('txtWoundCareLocation').val('');
I thought this was about jQuery. I'm not into prototype, sorry.

Put this at the end of copy:
$(cnode.id).value="";

Related

Add a paragraph or table etc. at Cursor

I have a function for adding the contents of a separate google document at the cursor point within the active document, but I haven't been able to get it to work. I keep getting the "Element does not contain the specified child element" exception, and then the contents gets pasted to the bottom of the document rather than at the cursor point!
function AddTable() {
//here you need to get document id from url (Example, 1oWyVMa-8fzQ4leCrn2kIk70GT5O9pqsXsT88ZjYE_z8)
var FileTemplateFileId = "1MFG06knf__tcwHWdybaBk124Ia_Mb0gBE0Gk8e0URAM"; //Browser.inputBox("ID der Serienbriefvorlage (aus Dokumentenlink kopieren):");
var doc = DocumentApp.openById(FileTemplateFileId);
var DocName = doc.getName();
//Create copy of the template document and open it
var docCopy = DocumentApp.getActiveDocument();
var totalParagraphs = doc.getBody().getParagraphs(); // get the total number of paragraphs elements
Logger.log(totalParagraphs);
var cursor = docCopy.getCursor();
var totalElements = doc.getNumChildren();
var elements = [];
for (var j = 0; j < totalElements; ++j) {
var body = docCopy.getBody();
var element = doc.getChild(j).copy();
var type = element.getType();
if (type == DocumentApp.ElementType.PARAGRAPH) {
body.appendParagraph(element);
} else if (type == DocumentApp.ElementType.TABLE) {
body.appendTable(element);
} else if (type == DocumentApp.ElementType.LIST_ITEM) {
body.appendListItem(element);
}
// ...add other conditions (headers, footers...
}
Logger.log(element.editAsText().getText());
elements.push(element); // store paragraphs in an array
Logger.log(element.editAsText().getText());
for (var el = 0; el < elements.length; el++) {
var paragraph = elements[el].copy();
var doc = DocumentApp.getActiveDocument();
var bodys = doc.getBody();
var cursor = doc.getCursor();
var element = cursor.getElement();
var container = element.getParent();
try {
var childIndex = body.getChildIndex(container);
bodys.insertParagraph(childIndex, paragraph);
} catch (e) {
DocumentApp.getUi().alert("There was a problem: " + e.message);
}
}
}
You want to copy the objects (paragraphs, tables and lists) from the document of 1MFG06knf__tcwHWdybaBk124Ia_Mb0gBE0Gk8e0URAM to the active Document.
You want to copy the objects to the cursor position on the active Document.
You want to achieve this using Google Apps Script.
If my understanding is correct, how about this answer? Please think of this as just one of several possible answers.
Modification points:
In your script, appendParagraph, appendTable and appendListItem are used at the 1st for loop. I think that the reason that the copied objects are put to the last of the document is due to this.
var body = docCopy.getBody(); can be put to the out of the for loop.
In your case, I think that when the 1st for loop is modified, 2nd for loop is not required.
When above points are reflected to your script, it becomes as follows.
Modified script:
function AddTable() {
var FileTemplateFileId = "1MFG06knf__tcwHWdybaBk124Ia_Mb0gBE0Gk8e0URAM";
var doc = DocumentApp.openById(FileTemplateFileId);
var docCopy = DocumentApp.getActiveDocument();
var body = docCopy.getBody();
var cursor = docCopy.getCursor();
var cursorPos = docCopy.getBody().getChildIndex(cursor.getElement());
var totalElements = doc.getNumChildren();
for (var j = 0; j < totalElements; ++j) {
var element = doc.getChild(j).copy();
var type = element.getType();
if (type == DocumentApp.ElementType.PARAGRAPH) {
body.insertParagraph(cursorPos + j, element);
} else if (type == DocumentApp.ElementType.TABLE) {
body.insertTable(cursorPos + j, element);
} else if (type == DocumentApp.ElementType.LIST_ITEM) {
body.insertListItem(cursorPos + j, element);
}
}
}
It seems that DocName is not used in your script.
References:
insertParagraph()
insertTable()
insertListItem()
If I misunderstood your question and this was not the result you want, I apologize. At that time, can you provide the sample source Document? By this, I would like to confirm it.

Javascript Substring replace with JQuerys contains selector

I'm trying to find a specific row in a column of an HTML table and replace an occurrence of a specific string with a given value.
I tried to use JQuery's .html but it just replaces everything in the row with the given value. A .text().replace() returned me false.
Here's my code:
function ReplaceCellContent(find, replace)
{
//$(".export tr td:nth-child(4):contains('" + find + "')").html(function (index, oldHtml) {
// return oldHtml.replace(find, replace);
//});
$(".export tr td:nth-child(4):contains('" + find + "')").text($(this).text().replace(find, replace));
//$(".export tr td:nth-child(4):contains('" + find + "')").html(replace);
}
$('.export tr td:nth-child(4)').each(function () {
var field = $(this).text();
var splitter = field.split(':');
if (splitter[2] === undefined) {
return true;
} else {
var splitter2 = splitter[2].split(',');
}
if (splitter2[0] === undefined) {
return true;
} else {
$.post(appPath + 'api/list/', {action: 'getPW', pw: splitter2[0]})
.done(function (result) {
ReplaceCellContent(splitter2[0], result);
});
}
});
I'm iterating through every row of the column 4 and extracting the right string. This is going through an AJAX post call to my function which returns the new string which I want to replace it with.
splitter2[0] // old value
result // new value
I hope someone could help me. I'm not that deep into JS/JQuery.
findSmith findJill findJohn
var classes = document.getElementsByClassName("classes");
var replaceCellContent = (find, replace) => {
for (var i = 0; i < classes.length; i++) {
if (classes[i].innerText.includes(find)) {
classes[i].innerText = classes[i].innerText.replace(find, replace);
}
}
}
this replaces all "fill" occurrences to "look".
I love to use vanilla JS, I'm not really a fan of JQuery but this surely should work on your code.
Do like this :
var tds = $("td");
for( var i = 0; i < tds.length ; i++){
if ( $(tds[i]).text().includes("abc") ){
var replacetext = $(tds[i]).text().replace("abc", "test");
$(tds[i]).text(replacetext);
}
}
Say give all your table rows a class name of "trClasses"
var rows = document.getElementsByClassName("trClasses");
for (var I = 0; I < rows.length; I++) {
rows.innerText.replace("yourText");
}
The innerText property would return the text in your HTML tag.
I'm a newbie too, but this should work. Happy Coding!

Javascript, var contains

I currently use this script:
wHandle.setNick = function (arg) {
userNickName = arg;
var fnicks = ["porno","ibne","amcık","amcik","piç","salak","orospu","pkk","sik","kürdistan","kurdistan","kÜrdistan","kürt","sikeyim","sıkeyim","götoş","yönetici","YÖNETICI","YONETICI","yonetici","admın","admin","yarah","yarrah","agario","sike","s1ke","anan"];
var nctr = arg.toLowerCase();
if(fnicks.indexOf(nctr) > -1) {
alert("Unknown Nickname!");
} else {
hideOverlays();
sendNickName();
wjQuery("#mini-map-wrapper").show();
userScore = 0
wjQuery(".btn-needs-nick").prop("disabled", false);
}
};
I wanted to make some kind of filter, so that it blocks these nicknames BUT it isn't covering all of my cases. For example it blocks porno but not pornoo
I want it to use if(contains).
You've essentially done your logic backwards. Instead of checking if the nickname is in your block list, you'd be better served checking if an element of your blocklist is in your nickname like so:
var nick = args.toLowerCase();
for (var i; i < fnicks.length; i++) {
if (nick.indexOf(fnicks[i]) != -1) {
//bad name!
}
}
well I would just loop through the array, and search if the argument you pass (nctr in that case) contains the current entry (fnicks[i]).
you can replace the console.log() by your usual alert()
var arg = "pornoo";
var fnicks = ["porno","ibne","amcık","amcik","piç","salak","orospu","pkk","sik","kürdistan","kurdistan","kÜrdistan","kürt","sikeyim","sıkeyim","götoş","yönetici","YÖNETICI","YONETICI","yonetici","admın","admin","yarah","yarrah","agario","sike","s1ke","anan"];
var nctr = arg.toLowerCase();
for(var i=0,c=fnicks.length;i<c;i++) {
if(nctr.indexOf(fnicks[i]) > -1) {
console.log('boom');
}
}

How do you dynamically assign a function to an element's onclick event?

As opposed to setting individual functions to each element's click event, I would like to iterate elements and assign based on id or whatever?
document.getElementById('measure').onclick = function() { clickMe(1); };
How would I approach this?
In the past I've done something along these lines:
var setClickOnElements = function(selector) {
$(selector).each(function() {
$(this).click(function(event) {
// behaviour on click
});
});
};
...where selector is a class selector, e.g. .my-class. Within the callback passed to each you can get at other properties of the selected elements, e.g. id etc. If you add that class to the elements you'd like to set a click function and call setClickOnElements('.my-class'); on load, you should be good to go!
EDIT: The above uses jQuery. If you're restricted to pure Javascript, you could use one of the methods described in John Resig's post on implementations of getElementByClass: http://ejohn.org/blog/getelementsbyclassname-speed-comparison/
Here's an example (using Dustin Diaz's method from http://www.dustindiaz.com/getelementsbyclass):
var getElementsByClass = function(searchClass,node,tag) {
var classElements = new Array();
if ( node == null )
node = document;
if ( tag == null )
tag = '*';
var els = node.getElementsByTagName(tag);
var elsLen = els.length;
var pattern = new RegExp("(^|\\s)"+searchClass+"(\\s|$)");
for (i = 0, j = 0; i < elsLen; i++) {
if ( pattern.test(els[i].className) ) {
classElements[j] = els[i];
j++;
}
}
return classElements;
}
var setClickOnElements = function(className) {
var elements = getElementsByClass(className);
for (var i = 0; i < elements.length; i++) {
var element = elements[i];
element.onclick = function(event) {
// click behaviour here
};
}
};

Find DOM-element that occurs the most

A container div.example can have different 1st-level child elements (section, div, ul, nav, ...). Quantity and type of those elements can vary.
I have to find the type (e.g. div) of the direct child that occurs the most.
What is a simple jQuery or JavaScript solution?
jQuery 1.7.1 is available, although it should work in IE < 9 (array.filter) as well.
Edit: Thank you #Jasper, #Vega and #Robin Maben :)
Iterate through the children using .children() and log the number of element.tagNames you find:
//create object to store data
var tags = {};
//iterate through the children
$.each($('#parent').children(), function () {
//get the type of tag we are looking-at
var name = this.tagName.toLowerCase();
//if we haven't logged this type of tag yet, initialize it in the `tags` object
if (typeof tags[name] == 'undefined') {
tags[name] = 0;
}
//and increment the count for this tag
tags[name]++;
});
Now the tags object holds the number of each type of tag that occurred as a child of the #parent element.
Here is a demo: http://jsfiddle.net/ZRjtp/ (watch your console for the object)
Then to find the tag that occurred the most you could do this:
var most_used = {
count : 0,
tag : ''
};
$.each(tags, function (key, val) {
if (val > most_used.count) {
most_used.count = val;
most_used.tag = key;
}
});
The most_used object now holds the tag used the most and how many times it was used.
Here is a demo: http://jsfiddle.net/ZRjtp/1/
Edit: I think a jQuery function like below should be more useful..
DEMO
$.fn.theMostChild = function() {
var childs = {};
$(this).children().each(function() {
if (childs.hasOwnProperty(this.nodeName)) {
childs[this.nodeName] += 1;
} else {
childs[this.nodeName] = 1;
}
});
var maxNode = '', maxNodeCount = 0;
for (nodeName in childs) {
if (childs[nodeName] > maxNodeCount) {
maxNode = nodeName;
maxNodeCount = childs[nodeName];
}
}
return $(maxNode);
}
And then you can,
$('div.example').theMostChild().css('color', 'red');
A function like below should give you the count of child elements, from which you can get the max count. See below,
DEMO
$(function () {
var childs = {};
$('div.example').children().each(function () {
if (childs.hasOwnProperty(this.nodeName)) {
childs[this.nodeName] += 1;
} else {
childs[this.nodeName] = 1;
}
});
for (i in childs) {
console.log(i + ': ' + childs[i]);
}
});
That is not possible without some information about the expected types of child nodes.
EDIT : It is possible as Jasper pointed out that we need not know the tag names before hand. The following works in case you're looking only within a specific set of selectors.
var selectorArray = ['div', 'span', 'p',........]
var matches = $(div).children(selectorArray.join());
var max = 0, result = [];
$.each(selectorArray, function(i, selector){
var l = matches.filter(selector).length;
if(l > max){
max = l;
result[max] = selector;
}
});
result[max] gives you the tag name and max gives you the occurrence count

Categories