Get Child Element Value with Mootools - javascript

I'm trying to change a class by first discovering if it is the parent object to a particular image using Mootools (clients previous web developer seemed to have it in for me). I can't seem to find much good documentation on the subject.
<div class="textwidget">
<img src="share.jpg">
</div>
So far I've managed to locate all the divs with the class 'textwidget' using:
var obs = $$('.textwidget');
Now I need to cycle through them and discover which hosts a child node with the src listed above...
for(var i=0;i<obs.length;i++){
if(obs[i].childnode.src == 'share.jpg'){ // <-- non mootools syntax
obs[i].class = 'new class'; // <-- non mootools syntax.
}
}
i'd like to run a loop like this, but in mootools speak of course. Anyone familiar with the correct syntax?
Thanks
-J

I think what you want is something like:
for(var i=0;i<obs.length;i++){
if(obs[i].getChildren()[0].getProperty('src') == 'share.jpg'){ // <-- mootools syntax
obs[i].setProperty('class','new class'); // <-- mootools syntax.
}
}
You can find more details here:
http://mootools.net/docs/core/Element/Element

you could do something like this via a selector / parent combo:
document.getElements("div.textwidget img[src=share.jpg]").getParent("div.textwidget");
http://www.jsfiddle.net/MBc37/4/
or you can be more thorough / longwinded...
// css selector, divs array filtered by existance of a child img
results.mixedFilter = document.getElements("div.textwidget").filter(function(el) {
return el.getElement("img[src=share.jpg]");
});
// checking vs img src properties of all child imgs
results.longwinded = [];
document.getElements("div.textwidget").each(function(el) {
var imgs = el.getElements("img");
if (!imgs.length) return;
if (imgs.some(function(im) {
return im.get("src") == "share.jpg";
})) results.longwinded.push(el);
});

What you want to do here is filter the array of elements like this:
$$('.text-widget').filter(function(e) {
var child_img = e.getFirst('img');
return $defined(child_img) && child_img.get('src') == 'share.jpg'
});
If the function passed to 'filter' returns true the item gets included.
You could also use selectors as one of the other answers mentioned. Although there might be performance issues with using them in that way?

Is this what you are looking for:
$$('img[src=share.jpg]').getParent().set('class', 'newClass');

Related

Similar blocks of code found in 2 location in IF ELSE statement. Consider refactoring JS

if (notesValue) {
document.querySelector(`.card-${domain.id} .add-notes-button`).classList.add('notes-filled');
} else {
document.querySelector(`.card-${domain.id} .add-notes-button`).classList.remove('notes-filled');
}
The refactoring is simply done by using the second force param of the toggle Method:
Element.classList.toggle("className", forceBoolean)
MDN Docs DOMTokenList.toggle()
const EL_button = document.querySelector(`.card-${domain.id} .add-notes-button`);
EL_button.classList.toggle('notes-filled', notesValue);
document
.querySelector(`.card-${domain.id} .add-notes-button`)
.classList
.toggle('notes-filled', notesValue);
Using toggle is a good idea but for a more general case where a method like that doesn't exist you could choose which method on the object to target e.g.:
document.querySelector(`.card-${domain.id} .add-notes-button`)
.classList[notesValue ? 'add' : 'remove']('notes-filled');

Angular2+ using .getElementsByClassName() returns empty selection though existent

I have a fairly simple question maybe, but I can't find an answer to it. I also searched previous questions but it seems not to work....
I have on my template in angular a large amount of text inside a div and some parts are wrapped with a span and those have the class highlight. Now I simply want to select them all when I press on a button. I need all the spans and do sth with them later.
I tried:
const elm = (this.el as any).getElementsByClassName('.highlight');
console.log('elmens: ', elm);
for (let i = 0; i < elm.length; i++) {
console.log('HTML ELM: ', elm[i]);
}
Also with:
const elm = document.getElementsByClassName('.highlight');
This both only returns me an empty selection, although they are existent. I even tried it on the browser console. I know I could use jQuery maybe, but I don't want to include it for such simple tasks.
Maybe you know what I am doing wrong???
I am using:
Angular: 7.0.0
Angular-cli: 7.0.2
Typescript: 3.1.3
I would look to avoid using this technique within the angular framework as it is not recommended to interact with the DOM in this way. They have appropriate alternatives. Interacting with the DOM can introduce Performance implications and is bad practice.
Instead you could look into using #viewchildren for this problem.
Docs here
Which would suggest each element you want to get, in your case the spans
<span #myNewId>text</span>
<span #myNewId>text snippet 2</span>
Could be accessed in the controller with the following
#ViewChildren('myNewId')public mySpans: ElementRef;
This should give you all the same functionality without having to interact directly with the DOM. mySpans will then be an array of the spans marked with the #myNewID.
This should also allow you access your elements in regards to your question, as they are bound the variables in the class.
I would use:
const elements= (<HTMLCollection>document.getElementsByClassName('your_class_name_without_dot'));
console.log(elements)
Maybe your child views are not initialized and you try to play with DOM before elements are rendered to the browser. try to use Angular hooks and then call you code. Like
ngAfterViewChecked() {
...
const elm = (this.el as any).getElementsByClassName('.highlight');
console.log('elmens: ', elm);
for (let i = 0; i < elm.length; i++) {
console.log('HTML ELM: ', elm[i]);
}
...
}

How to extend native DOM elements using "is"?

I am trying to using the custom elements spec to extend native DOM elements using the "is" attribute, but it doesn't seem to be doing anything at all. I am using Google Canary so I am able to create custom elements, but no effect in extending.
In my sample, I am trying to add a caption to the native img tag:
<img is="super-img" src="http://lorempixel.com/400/200/"
caption="This is my custom caption!" />
<script>
document.registerElement('super-img', {
prototype: Object.create(HTMLImageElement.prototype, {
createdCallback: function() {
var caption = this.attributes.getNamedItem('caption').value;
alert(caption);
}
})
});
</script>
http://jsbin.com/OMaPIVoV/3/
The createdCallback never fires. Any ideas on how to accomplish this?
Object.create(HTMLImageElement.prototype, {
createdCallback: function() {…}
})
Object.create does create a map of property descriptors as its second parameter - not plain values - like Object.defineProperties does.
This is also mentioned in the article you found at "Adding JS properties and methods":
Of course there are umpteen thousand ways to construct a prototype. If
you're not a fan of creating prototypes like this, here's a more
condensed version of the same thing:
[…] [This] first format allows for the use of ES5 Object.defineProperty.
The second allows the use of get/set.
(The strike-through was added by me as it's rubbish)
So what you want is either
var SuperImgProto = Object.create(HTMLImageElement.prototype);
SuperImgProto.createdCallback = function() { … };
var SuperImg = document.registerElement('super-img', {prototype: SuperImgProto});
or
document.registerElement('super-img', {
prototype: Object.create(HTMLImageElement.prototype, {
createdCallback: {value: function() { … } }
})
});
looks like you forgot to tell your web component, that it extends the native img element. Here's a running example based on your fiddle but broken down to the important bits: http://jsbin.com/OMaPIVoV/7/edit
hope this helps!

jQuery UI Operator Overloading?

I'm attempting to figure out OOP Javascript, jQuery, and jQuery UI all at the same time. Basically, I want to create a custom "panel" component that I can reuse in various places throughout my web app. The panel consists of a title bar and then content below it.
So I'm using jQuery UI to accomplish this. I want to be able to make the component and then change its attributes (like the title bar text). Here's an example:
$(function()
{
$.widget("custom.ShinyPanel",
{
options: {
css:{},
title:""
},
_create:function()
{
$(this.element).addClass("shinyPanel").disableSelection();
this.titleBar = $(createElement("div")).addClass("shinyPanelTitleBar").appendTo(this.element);
this.topShine = $(createElement("div")).addClass("shinyPanelTopShine").appendTo(this.element);
this.leftShine = $(createElement("div")).addClass("shinyPanelLeftShine").appendTo(this.element);
this.content = $(createElement("div")).addClass("shinyPanelContent").appendTo(this.element);
this._refresh();
},
_refresh:function()
{
if (this.options.hasOwnProperty("title"))
$(this.titleBar).html(this.options.title);
}
});
});
// $("#divShotList").ShinyPanel({title:"Shot List"}); // this works
$("#divShotList").ShinyPanel();
$("#divShotList").title = "Shot List"; // this doesn't work
<div id="divShotList" style="position:absolute; top:5px; bottom:10px; width:250px;"></div>
Is there a way for me to overload the = operator or something to make this work with this syntax? I know that I could probably create an extra function, like setProperty or something, but it would be really cool if I could just keep this syntax and get it to work. Any idea how I can modify the widget to make this happen?
The element or jQuery wrapped element is not your widget:
$("#divShotList").data('ShinyPanel')._setOption('title', 'something');
But it is store in the .data() of the element.
Alternatively:
var shinyPanel = $("#divShotList").ShinyPanel().data('ShinyPanel');
shinyPanel.options.title = 'new title';
shinyPanel.refresh();
would also work.
Final Edit: To answer you question: No.

DOJO: find child

Here is the code:
dojo.query(subNav.navClass).forEach(function(node, index, arr){
if(dojo.style(node, 'display') == 'block'){
"NOW HOW WOULD I FIND CHILDREN????"
});
}
});
By the way I just started working with DOJO, i am primarily working in jQuery.
So now that i have found node that has its display set to block, i want to preform something to its specific children, how would i preform query on children of the node that i just stopped on?
any clarification, suggestion? thank you.
dojo.query('> li .secondary_nav_dropdown', node).style('display', 'none');
The second parameter specifies origin where the query should start from.
Dojo query documentation
U can use array children and mapping like this:
dojo.map(node.children, function(child){
// work with child
})

Categories

Resources