<script>
$(document).ready(function(){
$("tr :odd").attr("class" : "dark"),
$("tr :even").attr("class" : "light")
});
</script>
This is the code I am using to give classes to rows in a table.
For some reason, It keeps throwing Uncaught SyntaxError: missing ) after argument list
It is a really good practice to end every sentence with a semicolon.
The problem is that you use attr function wrong.
It takes two plain values (key and value) or a JS object as a single argument.
Key-value:
$("tr :odd").attr("class", "dark");
$("tr :even").attr("class", "light");
Object:
$("tr :odd").attr({"class": "dark"}); // Usually for multiple values
$("tr :even").attr({"class": "light"}); // Usually for multiple values
Moreover, changing class through attr is a really bad practice.
Use jQuery addClass and removeClass functions:
$("tr:odd").addClass("dark");
$("tr:even").addClass("light");
And, finally, are you sure you really need this?
You have CSS like:
.dark
{
background-color: #333333;
}
.light
{
background-color: #CCCCCC;
}
You can do it this way:
.tr:nth-chlid(odd)
{
background-color: #333333;
}
.tr:nth-chlid(even)
{
background-color: #CCCCCC;
}
It is great to avoid using scripts whenever it is possible.
You should do it like this (using an object literal):
$(selector).attr({"class": "dark"})
or
$(selector).attr("class", "dark")
Related
I need to be able to change out the css applied to the <body> on the fly. How, using javascript, could this be accomplished?
My css is stored as a string in a Javascript variable. I am not working with css files. The css consists of around 50 classes, so it doesn't make sense to apply them one-by-one. I know how this could be accomplished by changing the lowest class, but I'm just trying to see if it's possible to do using Javascript commands and variables.
Pseudo Code
var x = "#nav-bar-wrapper {
background-color: #4a3e7d;
padding: 20px 0;
}
#header-nav {
display: flex;
justify-content: center;
}...";
function changeCss() {
var el = $('myelement');
SomeJavaScriptFunction(el, x);
}
As #evolutionbox pointed out, it looks like you want to add new styles to the page. If so, just add them as text content in a style element:
const css = '#nav-bar-wrapper { ... }'
function changeCss() {
const el = document.createElement('style')
el.textContent = css
document.head.appendChild(el)
}
One easy way of doing it would be:
document.querySelector("yourElement").style.cssText += "Your super long string will go here and itll work"
Although, I dont think theres a way of giving different elements a uniqe style all in one line other than appending a style tag to the html. To use the method above, you'd have to separate #nav-bar-wrapper and #header-nav
Just keep in mind to use `` rather than "" to make the string go onto multiple lines
Here's a more JavaScript-y method than using hacky style tags.
const button = document.getElementById('button');
button.onclick = () => {
[
[ 'background', 'black' ],
[ 'color', 'white' ]
].map(([ prop, val ]) => {
button.style[prop] = val;
});
};
<button id="button">Hello there</button>
You could also try out https://cssinjs.org, which also works great in React.
Perhaps using jQuery's .css() function is worthy too: https://api.jquery.com/css/. It can take an object of CSS properties and apply them to an element.
$('#button').on('click', () => {
$('#button').css({ background: 'black', color: 'white' });
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
<button id="button">Hi there</button>
You could also create a new style tag and append it to the body as many people have said. You can even append an external link rel="stylesheet" tag to the header to dynamically add a stylesheet from another URL! An alternative to this would be using the fetch API/jQuery AJAX/xmlhttprequest plus the code below:
$('#button').on('click', () => {
$('body').append('<style>#button { background: black; color: white; }</style>');
});
<body>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
<button id="button">Hi there</button>
</body>
Another approach is using classes that you can dynamically add in JavaScript.
$('button').on('click', () => $('#button').addClass('clicked'));
.clicked {
background: black;
color: white;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
<button id="button">Hi there</button>
You need to get a reference of your html element and after manipulate the DOM, here is an example:
document.getElementById('yourElementIdHere').style.color = 'red';
If you want to get your body reference to manipulate the DOM, you can do it. After this, you can change the style of your body using the style property, and use your string with your css.
document.querySelector("body").style = yourCssStringVar;
This link can help you, too:
JavaScript HTML DOM - Changing CSS
I have this code
The problem is I need to toggle class on click. I have classes
.col
.col-1 / .col-2 / col-3 etc.
and I need to apply on click to the right .col-1 / col-2 an expand class, so it would like
.col .col-1 .col-1--expand
.col .col-2 .col-2--expand
Before I had this on hover in CSS and it works, but make it on click is little problematic. I searched whole day Javascript and jQuery cases, but I haven't found any right solution to it.
What I learned, I must use forEach function in Javascript, but a solution in jQuery is also what I want.
I tried something like this on my project, but I'm still bad at Javascript :(
if (document.querySelector('.slider__col')) {
const expandElement = element.querySelectorAll('.slider__col')
expandElement.forEach(element => {
element.addEventListener('click', function() {
element.classList.toggle("");
})
})
You can use a regular expression to match element classes and toggle the expand class on that element when clicked.
var matched = this.className.match(/col-\d{1,2}/);
This will find any classes in your element's class attribute that contains col- followed by any numbers up to two digits so you can cater for 1-99.
matched.length && (matched = matched.pop())
.match() returns an array of matches so you can determine if any matches were found and pop the first match off of the array.
var expandClass = matched + '--expand';
Because you're matching, for example, col-1 you can use this string and append --expand to make col-1--expand.
$(this).toggleClass(expandClass);
You can use jQuery's toggleClass to add/remove the expandClass depending on the class's presence. See col-3 for demonstration.
$(document).on('click', '.col', function () {
var matched = this.className.match(/col-\d{1,2}/);
if (matched.length && (matched = matched.pop())) {
var expandClass = matched + '--expand';
$(this).toggleClass(expandClass);
}
});
.col {
background-color: blue;
color: white;
padding: .25rem 1rem;
margin: .25rem 0;
}
.col-1--expand,
.col-2--expand,
.col-3--expand,
.col-4--expand,
.col-5--expand,
.col-6--expand {
background-color: green;
padding-top: 1rem;
padding-bottom: 1rem;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="grid">
<div class="col col-1">1</div>
<div class="col col-2">2</div>
<div class="col col-3 col-3--expand">3</div>
<div class="col col-4">4</div>
<div class="col col-5">5</div>
<div class="col col-6">6</div>
</div>
Welcome to StackOverflow! Since you want a solution in jQuery, let me give you some guidance.
1. The forEach function is in jQuery available as the
.each() method. Making your code:
// Select your classes, for each of them run a function
$('.col-1').each(function() { });
2. To make something happen on a click, jQuery has a .click() method available, it will call a function on click. Making your code:
$('.col-1').each(function() {
// Click method:
$(this).click(function() { } );
});
// Or just do:
$('.col-1').click(function() { });
jQuery does not need a loop and can bind the click method to all classes by itself. There are cases where it still might be useful, but let's keep it basic for now and get your code working!
3. Adding the new CSS class. In jQuery there are many methods you can use for it. In this case you are probably looking for the .toggleClass() method. Other useful ones might me .addClass() and .removeClass(). Making your code:
$('.col-1').click(function() {
$(this).toggleClass("col-1--expand");
});
// Or just add it:
$('.col-1').click(function() {
$(this).addClass("col-1--expand");
});
Done, repeat for other classes where you want to do some magic. Next time try spending a day on the jQuery API Documentation. All the methods are there, with great examples included! Best of luck with it.
I know I'm overlooking something but I'm stuck on knowing what I'm doing wrong. Can't seem to get the console to print out ( I'm eventually working on adding a box to the screen). I'm using Chrome btw:
HTML
<button id="1" class="hot"></button>
JS
function addBox() {
console.log("hello");
}
var clickBox = document.getElementById("1");
clickBox.onClick = addBox;
DOM properties are case sensitive (unlike HTML attributes) and the correct name of the property is onclick:
clickBox.onclick = addBox;
Learn more about the different ways of binding event handlers.
function addBox() {
console.log("hello");
}
var clickBox = document.getElementById("1");
clickBox.onclick = addBox;
.hot {
width: 100px;
height: 100px;
border: 3px solid black;
background-color: pink;
}
<button id="1" class="hot"></button>
Try
clickBox.onclick = addBox;
or
clickBox.addEventListener('click', addBox);
I do not know of any native onClick method for DOM elements in JavaScript.
You could do an event attribute in your HTML <button onclick="addBox()">.
Or you could do clickBox.addEventListener('click', addBox);.
this this code javascript :
var clickBox = document.getElementById("1");
clickBox.onclick=addBox;
function addBox() {
console.log("hello");
}
First, your ID should begin with a letter (if you plan to have HTML4 compatibility). Second, if you want to define an event using JS (without a library such as jQuery), you should use addEventListener. Or you can simply go the route of adding onclick directly to the element (onclick="addBox()"). Finally your onclick should all be lowercase (as JS property keys are case sensitive).
Try giving all the javascript within window.onload tags
Like the following:
window.onload = function(){
//Your Code Here
}
having a problem, I have a javascript content switcher on a page, but I can't seem to get one thing working - how to make a clicked button stay active after it's clicked?
Here's a code:
JS
<script type="text/javascript">
function switch1(div) {
var option=['one','two','three'];
for(var i=0; i<option.length; i++) {
if (document.getElementById(option[i])) {
obj=document.getElementById(option[i]);
obj.style.display=(option[i]==div)? "block" : "none";
}
}
}
window.onload=function () {switch1('one');}
</script>
CSS
#switchables li a {
color: #262626;
text-decoration: none;
display: inline-block;
padding-top: 14px;
padding-right: 34px;
padding-bottom: 10px;
padding-left: 33px;
background-image: url(img/catButBcgr.jpg);
border-right-width: 1px;
border-left-width: 1px;
border-right-style: solid;
border-left-style: none;
border-right-color: #E1E1E1;
border-left-color: #FFF;
}
#switchables li a:hover {
background-image: url(img/catButBcgrH.jpg);
}
#switchables li a:active {
background-image: url(img/catButBcgrA.jpg);
}
HTML
<ul id="switchables">
<li><a class="active" href="javascript:void[0];" onclick="switch1('one');">OVERVIEW</a></li>
<li><a class="active" href="javascript:void[0];" onclick="switch1('two');">CATEGORY</a></li>
<li><a class="active" href="javascript:void[0];" onclick="switch1('three');">CATEGORY</a></li>
</ul>
You need to make an "Active" class and add it to the button when clicked.
#switchables a:active, #switchables a.active {
background-image: url(img/catButBcgrA.jpg);
}
It's easy using jQuery:
$(document).ready(function() {
myInit()
})
function myInit() {
$('#switchables a').click(function() {
$('#switchables a').removeClass('active')
$(this).addClass('active')
})
}
This is a nice opportunity to learn. Diodeus' answer is completely right, but his jQuery code does horrible things on the background, see the comments:
$(document).ready(function() {
myInit()
})
function myInit() {
// on the following line, jQuery creates an array of objects (a tags)
// (costly operation!) and adds click listener to each of them
$('#switchables a').click(function() {
// on the following line, jQuery creates the crazy God object again
// and throws it off after this command
// for each a tag and tries to remove class active from it
// in only one case it actually does something - mere class removal
// btw removeClass is ridiculous function if you dig into jQuery 1.10 source
$('#switchables a').removeClass('active')
// this = the source of click event, not jQuery object
$(this).addClass('active')
})
}
This is just a very short code, now imagine you write whole web this style. It will be observably slower, consuming much more resources.
If you insist on jQuery, try to write reusable code a little:
function myInit() {
// jQuery object is created only once
var $anchors = $('#switchables a');
$anchors.click(function() {
// ...and reused here
$anchors.removeClass('active')
$(this).addClass('active')
});
}
But you'd do much better job using native javascript
var items = document.querySelectorAll("#switchables a");
var prev = items[0];
[].forEach.call(items,function(item) {
item.addEventListener("click",function() {
// no need to loop every a tag here
prev.classList.remove("active");
item.classList.add("active");
// remember previous active a tag
prev = item;
});
});
document.querySelectorAll is a live collection which is something that can't be achieved by any javascript library, it is implemented in underlying and more effective code of the browser.
Advice Don't use jQuery until you know Javascript well. Without that knowledge, you will be able to implement just basic animations, copy&paste some plugins and nothing more. And when you know Javascript on some level, you will probably see very little reason to use jQuery anymore.
In the code above, jQuery can be easily removed:
1: $(document).ready(handler) -> document.addEventListener("readystatechange",handler);
2: $('#switchables a') -> document.querySelectorAll("#switchables a");
3: $(nodeList).click(handler) ->
[].forEach.call(nodeList,function(node) {
// you can reuse node here, unlike the jQuery
node.addEventListener("click",handler);
});
4: $(node).removeClass(className) -> node.classList.remove(className)
5: $(node).addClass(className) -> node.classList.add(className)
It is a few chars longer. But it is more reusable, readable, effective and it is not God object or Cargo cult programming.
The native codes above are javascript standards and are supported in any decent browser. Three years ago, when Diodeus provided his answer, IE8 was an issue here. But it is dead now (under 2% worldwide according to gs.statcounter). Help it die completely by not supporting it.
I have some icons that the user is picking with his mouse.
I have this series of icons where I can select and set their border. I am limiting the number of chosen icons to 5. The first selected would become a yellow border one. The next 4 would be black border.
On document.ready, I do:
$('img.selectable').click(function(){
image_click(this); });
For the CSS:
.selectable {
border: 3px solid #ebe6b3;
float:left;
margin:1px;
}
For the HTML:
<img class="selectable" src="img/first_icon.png">
I have this function:
function image_click(e)
{
if($(e).data("clicked")=="yes")
{
images_selected--;
$(e).data("clicked","no").css('border','3px solid ' + NEUTRAL_COLOR);
if(images_selected==1)
{
$('img.selectable').not( e ).filter(function() {
return $( this ).data("clicked")=="yes";
}).css('border','3px solid ' + YELLOW_COLOR);
}
}
else
{
if (images_selected<5)
{
images_selected++;
if(images_selected==1)
{
$(e).data("clicked","yes").css('border','3px solid ' YELLOW_COLOR);
}
else
{
$(e).data("clicked","yes").css('border','3px solid ' + BLACK_COLOR);
}
}
}
};
There has to be a first icon, which will be yellow all the time. I was thinking of doing it with an order array, which stores the order of the objects.
The thing is I didn't seem to be able to call an object from the array and still preserve it's css function.
I was thinking of something like:
var x=[];
inside image_click(e){..
at some point I store the object:
$(e).data("order",clicked_img);
x[clicked_img]=e;
and when I pop it out:
alert(x[clicked_img].data("order"));
...}
BUT....
Seems like I have no acces to the data anymore. Like when the object left the jQuery realm it has lost it's civil rights. I don't know how to access it's data variables.
Help please!
Thanks!
You saved the DOM element, not the jQuery object. It should be
x[clicked_img]=$(e);
not
x[clicked_img]=e;
Like when the object left the jQuery realm it has lost it's civil
rights.
Simple solution: put it back in the jQuery realm. You have a couple options:
x[clicked_img] = $(e);
// ...
alert(x[clicked_img].data("order"));
or:
x[clicked_img] = e;
// ...
alert($(x[clicked_img]).data("order"));
or:
x[clicked_img] = e; // assuming e is the DOM element, not the event
// ...
alert(x[clicked_img].dataset.order);
The latter is not recommended for now as I'm unsure of the cross-browser implications, but in any case, that's how you do it in "regular" JavaScript.
I'd suggest the first method, in which case you should also be assigning $(e) to a variable at the beginning of image_click so it doesn't rebuild the jQuery object every time.