Currently looking to take an OOP style approach with javascript, as I am a beginner level programmer looking to take my javascript skills up a notch. The code I have seems not to be working at all, and I have tried differed solutions for a few hours now.
My Goal
I would like to accomplish the action of creating click functionality on a page. Where a user clicks on a link and it adds the CSS class .active to the link (and of course not adding the class to other links when clicked on).And finally would like when a suer clicks on the same link(active link with the class) again for the class to remove itself and return to its normal state.
Thank you for the help!
Javascript
var activeState = $(".category-tree-with-article .article-list > li > a, .content-left-bottom li a, .content-right-bottom li a");
function clickState () {
this.initEvent();
clickState.prototype = {
initEvent: function() {
activeState.on('click', function (event) {
event.preventDefault();
var el = $(this);
// For class changes
activeState.toggleClass('active');
el.addClass('active');
});
}
}//prototype inherit
} //end function
clickState();
CSS
a.active {
color:red;
font-family:"Prime";
}
I'd say you should probably stop using your "OOP" style coding
var activeState = $(".category-tree-with-article .article-list > li > a, .content-left-bottom li a, .content-right-bottom li a");
activeState.on('click', function (event) {
event.preventDefault();
activeState.not(this).removeClass('active');
$(this).toggleClass('active');
});
Related
I'm trying to make it so that when you scroll on my HTML page when you reach a certain section, that respective section should become active,
for example:
<nav class="scrollmenu">
<ul>
<li class="starters">STARTERS</li>
<li class="ramen">RAMEN</li>
</ul>
</nav>
starters should become active when you reach this section on the page:
<section id="starters" class="foodgrid">...</section>
I'm trying to do this with this JS code:
const sections = document.querySelectorAll("section");
const navLi = document.querySelectorAll("nav ul li");
window.addEventListener("scroll", () => {
let current = " ";
sections.forEach((section) => {
const sectionTop = section.offsetTop;
const sectionHeight = section.clientHeight;
if (scrollY >= sectionTop) {
current = section.getAttribute("id");
}
});
navLi.forEach((li) => {
li.classList.remove("active");
if (li.classList.contains(current)) {
li.classList.add("active");
}
});
});
I'm still going to expand on this JS code to make it work better but if I'm not mistaken it should already make the class visually active when I'm on the right section.
In case you are wondering my CSS looks like this for the time being:
nav ul li:active {
background-color: blue;
}
what happens here is that you are attaching a class name which is active and you are not declaring that class, you just have the event :active that is triggered when you click on the element, so you must do this
.active {
background-color: blue;
}
and that will work when you set the class and remove it, also leaving the css code as you have it will make that when the html li element is clicked it changes it background and then changes to the normal color, try it and let me know if it works, if it doesn't is something about your js and then ill check it
running into issues of trying to have only 1 div toggle instead of them all toggle. I've tried using next() and setting the selector to the children as opposed to the parent element, but then it won't toggle open at all.
FIDDLE:
http://jsfiddle.net/L415g07n/2/
What I am specifically trying to accomplish?
Have the selected div toggle when .toggle is clicked instead of all of them being toggled at once.
var c1 = $("#o");
var c2 = $("#t");
var c3 = $("#th");
$(document).ready(function () {
$(c1).hide(0).delay(500).fadeIn(1500);
$(c2).hide(0).delay(1500).fadeIn(1500);
$(c3).hide(0).delay(2500).fadeIn(1500);
});
var content = $("#main .column .body");
$(content).hide();
var t1 = $(".toggle");
$(t1).click(function () {
$(content).slideToggle('slow');
$(t1).toggleClass("toggle");
$(t1).toggleClass("toggle-d");
});
Try to use this object and traverse to the required nodes,
$(t1).click(function () {
$(this).toggleClass("toggle")
.toggleClass("toggle-d")
.parent().next('.body').slideToggle('slow');
});
DEMO
jQuery's $(this) alows you to apply your effects on the current element. Here's the correct, shorter and simpler version of your code:
$(document).ready(function () {
$(".column, .body").hide(); // you should put this in your CSS ( .column, .body { display: none; } )
$(".column").each(function(index) {
$(this).delay(400*index).fadeIn(300);
});
$(".toggle").click(function () {
$(this).toggleClass("toggle").toggleClass("toggle-d").parent().next(".body").slideToggle();
});
});
Notice, how you can even improve the part when your divs fade in, by reffering to them with a class name instead of id by using $(this) and .each().
I think w3schools explains $(this) quite nicely.
My website is a parallax one page scrolling website, so all my nav links are directed to ids nested within that page...
For example:
<ul class="clearfix">
<li>Home</li>
<li>Work</li>
<li>About</li>
<li>Contact</li>
</ul>
So How would I tell my html that when someone clicks on one of these links and directs them to the corresponding ID on the page, to take on the class active? And the link that was active to turn back to the regular styling?
Assuming your link elements are contained in an element with class nav, and you're using jQuery, you could do the following:
$('.nav a').on('click', function(event) {
$('.nav a.active').removeClass('active');
$(this).addClass('active');
});
fiddle
You will have to use JavaScript to add that functionality into your application. Everytime a link is clicked, add the 'active' class to the triggering element, and remove it from all others. This is straightforward if you can use jQuery (jsFiddle with jQuery), and only a little more tedious otherwise.
$(function() {
$("ul.clearfix > li > a").click(function() {
$("a.active").removeClass("active");
$(this).addClass("active");
});
});
If you're only using native JS, you can try something along the lines of the below (jsFiddle using vanilla JS):
var links = document.getElementsByTagName("a"); // more specific selector if other links
for (var i = 0; i < links.length; i++) {
var link = links[i];
link.onclick = function () {
var prev = document.getElementsByClassName("active");
if (prev && prev[0]) {
prev[0].className = ""; // if using other classes, filter better
}
this.className += " active";
};
}
This second solution needs to be adapted to fit your particular application/DOM structure, since it's not quite as flexible as the first.
jQuery
$('ul a').on('click', function(event) {
$('a').removeClass("active");
$(this).addClass("active");
});
Replace ul a with something more specific like .nav a
I am using the following js which works great for hiding and showing content when one of 5 tabs is clicked. Works great but my question is, how could i adjust the code so that when a tab's content is currently being displayed, the tab has an active class. The hover class works well and so does everything else besides the active class. Any help is hugely appreciated:
$(window).ready(function() {
$('#infotab').click(function() {
$(document).find('.tabcontent').hide();
$('.infotabcontent').show();
$(document).find('.top-nav2-menu li').removeClass('tabactive');
$('#infotab').addClass('tabactive');
$('#reviewtab').removeClass('tabactivelast');
});
$('#findingtab').click(function() {
$(document).find('.tabcontent').hide();
$('.findingtabcontent').show();
$(document).find('.top-nav2-menu li').removeClass('tabactive');
$('#findingtab').addClass('tabactive');
$('#reviewtab').removeClass('tabactivelast');
document.getElementById('frame1').contentDocument.location.reload(true);
});
$('#streetviewtab').click(function() {
$(document).find('.tabcontent').hide();
$('.streetviewtabcontent').show();
$(document).find('.top-nav2-menu li').removeClass('tabactive');
$('#streetviewtab').addClass('tabactive');
$('#reviewtab').removeClass('tabactivelast');
document.getElementById('frame2').contentDocument.location.reload(true);
});
$('#videotab').click(function() {
$(document).find('.tabcontent').hide();
$('.videotabcontent').show();
$(document).find('.top-nav2-menu li').removeClass('tabactive');
$('#videotab').addClass('tabactive');
$('#reviewtab').removeClass('tabactivelast');
});
$('#reviewtab').click(function() {
$(document).find('.tabcontent').hide();
$('.reviewtabcontent').show();
$(document).find('.top-nav2-menu li').removeClass('tabactive');
$('#reviewtab').addClass('tabactivelast');
});
});
Your code is a pain ...
$(window).ready(function() { should be $(function() {
which is a shorthand for $(document).ready(function(){
In your HTML assign a class class="tab" to all your id="***tab" elements
Cache your elements collections $('.tabcontent') and $('.top-nav2-menu li')
use the $(this) selector
Than this is all you need:
$(function(){ // DOM is now ready
// Cache your selectors
var $tabCont = $(".tabcontent"),
$topNavLi = $(".top-nav-menu li"),
$tabRev = $('#reviewtab');
$('.tab').click(function() {
var myId = this.id;
if(myId=="findingtab"){
$('#frame1')[0].contentDocument.location.reload(true);
}
if(myId=="streetviewtab"){
$('#frame2')[0].contentDocument.location.reload(true);
}
$tabCont.hide();
$("."+ myId +"content").show();
$(this).addClass('tabactive').siblings().removeClass('tabactive');
$tabRev.removeClass('tabactivelast');
if(myId=="reviewtab"){
$(this).addClass('tabactivelast');
}
});
});
With something like:
function deactivateAllTabs(){
$('#infotab, #findingtab, #streetviewtab, #videotab, #reviewtab').removeClass('tabactive');
}
Then, prior to adding your tabactive class you'd call this method:
So, for example, instead of:
$('#infotab').addClass('tabactive');
do this:
deactivateAllTabs();
$('#infotab').addClass('tabactive');
repeate this for all your click handlerss
This way, the active tab will always have a tabactive class
I don't know your DOM structure, since you didn't post it, but I'm assuming that every tab has an identical class, "tabcontent", from what you've posted. If so, you could do something like this inside your function:
$('.tabcontent').removeClass('.tabactive'); // removes class from all tabs
$('#sometab').addClass('.tabactive'); // adds class to specific tab
Then you could show or hide using just some CSS, like this:
.tabcontent { display: none; }
.tabactive { display: block; }
IMHO you'd also be better off using a single function for all of your tabs so they get the same treatment. Easier to maintain. e.g. Give each tab bar item that you click on to see the tab a data attribute with the id of the div you want to display, and you could expand on something like this (untested but hopefully you get the gist):
$('.tab').click(function() {
$('.tabcontent').removeClass('.tabactive');
$($(this).data('tabcontent')).addClass('.tabactive');
});
i have a little jquery script :
$('.product_types > li').click(function() {
$(this)
.css('backgroundColor','#EE178C')
.siblings()
.css('backgroundColor','#ffffff');
// $('.product_types > li').removeClass(backgroundColor);
});
that colors me a div onclick. The problem is that i want only the last element clicked to be colored. And i dont know can i remove the style (the css style) after every click ?
thank you
I would use a css class like .lastClicked and using jquery to remove all instances of .lastClicked when a new element is clicked.
.lastClicked{ background-color:#EE178C; }
.lastClicked (siblingName) { background-color: #ffffff; }
your jquery code would look something like:
$('.product_types > li').click(function() {
$(".lastClicked").removeClass("lastClicked");
$(this).addClass("lastClicked");});
You can store lastly clicked element in global variable, and on click reset its color :
var lastElm = null
$('.product_types > li').click(function() {
if( lastElm ) $(lastElm).css('backgroundColor','#[Your original color]')
lastElm = this;
$(this)
.css('backgroundColor','#EE178C')
.siblings()
.css('backgroundColor','#ffffff');
// $('.product_types > li').removeClass(backgroundColor);
});
You need a variable that store the actual colored div and remove style on it. Something like this (not tested) should do the trick :
(function(){
var coloredDiv = null;
$('.product_types > li').click(function() {
var item = $(this);
if(coloredDiv != null) coloredDiv.removeClass('someCSSClassThatColorMyDiv');
item.addClass('someCSSClassThatColorMyDiv');
coloredDiv = item;
});
})();
NB: I also suggest to use CSS class instead of manualy set the CSS property in the Javascript. This leads to better separating of the code logic and displaying.
I also put the whole stuff in a closure so the variable cannot be overriden by some other script by mistake.