2014-09-12 130 views
1

我有以下菜單,我想爲最後點擊的鏈接添加一個「活動」類。使用原生JavaScript而不是使用JQuery。使用javascript更改班級

首先,我從所有鏈接刪除活動,然後嘗試添加「主動」,以點擊鏈接

這裏就是我想只是簡單做什麼:

<a href="#" class="menu active" onclick="changeClass()">test 1</a> 
<a href="#" class="menu" onclick="changeClass()">test 2</a> 
<a href="#" class="menu" onclick="changeClass()">test 3</a> 

function changeClass() { 
    document.getElementsByClassName('menu').classList.remove('active'); 
    this.className('menu active'); 
} 

Here's a fiddle to have a look at but not if jsfiddle is working correctly

+0

這個答案嘗試相同/相似的問題 HTTP: //sackoverflow.com/questions/195951/change-an-elements-css-class-with-javascript – Noreen 2014-09-12 12:57:45

+0

[用JavaScript更改元素的類]的可能重複(https://stackoverflow.com/questions/195 951/change-an-elements-class-with-javascript) – jhpratt 2017-08-27 17:06:20

回答

3

className不是一個函數,所以這行:

this.className('menu active'); 

使你可以在Web控制檯容易看到一個錯誤。

當你使用classList其他地方,你可以這樣做:

this.classList.add('active'); 

或者,完全覆蓋類:

this.className = 'menu active'; 

(請注意,舊的瀏覽器不具備classList,所以他們你需要一個墊片,如果你依靠它。)

另外,this在你的功能將不會是eleme nt被點擊,因爲你有事件處理程序掛鉤的方式。你可以確保它是this使用call變化最小:

<a href="#" class="menu active" onclick="changeClass.call(this)">test 1</a> 
<a href="#" class="menu" onclick="changeClass.call(this)">test 2</a> 
<a href="#" class="menu" onclick="changeClass.call(this)">test 3</a> 

你甚至可能想通過事件:

<a href="#" class="menu active" onclick="changeClass.call(this, event)">test 1</a> 
<a href="#" class="menu" onclick="changeClass.call(this, event)">test 2</a> 
<a href="#" class="menu" onclick="changeClass.call(this, event)">test 3</a> 

或課程用現代的手法掛鉤的處理程序,而不是的屬性。

+2

「this'真的會起作用嗎? – Pointy 2014-09-12 12:56:46

+1

@Pointy:很好!不,它不是。 *更新*:我已經更新了處理這個問題的答案,很好。 – 2014-09-12 12:57:14

1

className是屬性,而不是方法,因此您應該使用它,如下所示:

this.className = 'menu active' 

並注意classList在IE10 +中工作,而不在下面。

0

你需要傳遞的元素有關的onclick事件,然後使用更改類的.className

HTML代碼

<a href="#" class="menu active" onclick="changeClass(this)">test 1</a> 
<a href="#" class="menu" onclick="changeClass(this)">test 2</a> 
<a href="#" class="menu" onclick="changeClass(this)">test 3</a> 

JS代碼

function changeClass(elm) { 
    var elements = document.getElementsByClassName('active'); 
    elements[0].className = "menu"; 
    elm.className = 'menu active'; 
} 
1

有一對夫婦的你的代碼有問題。

document.getElementsByClassName確實返回單個元件,而是一個HTMLCollection,它基本上是具有附加屬性的陣列。這意味着您必須遍歷它才能從所有包含元素的類列表中刪除「活動」。

var collection = document.getElementsByClassName("menu"), 
    i; 

for (i = 0; i < collection.length; i++) { 
    collection[i].classList.remove("active"); 
} 

this指向你所點擊的元素,但到窗口對象。爲了在函數中使用事件目標,必須將它作爲HTML代碼中的參數傳遞,並在函數中使用此參數。

<a href="#" class="menu active" onclick="changeClass(this)">test 1</a> 
... 

function changeClass(target) { 
    ... 
    target.classList.add("active"); 
} 

正如你可以在上面的代碼中看到,你也可以使用Element.classList.add一類添加到您的元素。如果在一種情況下使用classList,則應該在所有情況下使用它。不過,舊款瀏覽器不支持此功能。如果您想寫入向後兼容的代碼,則可以使用className屬性。

collection[i].className = "menu"; // Removing the action class 

target.className = "menu active"; // Adding the action class 
1

你有幾個問題:

document. getElementsByClassName()返回HTMLCollection它沒有classList財產。你要訪問集合中的項目,以獲得他們的性能,即:

document.getElementsByClassName('menu')[0].classList = "foo";

2.Element. className是一個屬性,而不是功能。您必須分配一個值,像這樣:

this.className = 'menu active';

3.當您使用內聯標記,即:<a onclick="foo()">this(在foo的上下文中)是不是引發事件的元素附加的處理程序;這是全球性的對象,window。你可能會考慮附加的處理程序,而不是(fiddle):

function menuClickHandler(e) { 
    // on click... 
    // if the event target is already active, return 
    if (this.classList.contains("active")) return; 
    // if the event target is not already active... 
    // get an element that has both menu and active classes 
    // apparently only one item is active at any time 
    var active = document.querySelector(".menu.active"); 
    // did we find an item? remove the active class 
    active && active.classList.remove("active"); 
    // add the active class to the event target, "this" 
    // which is actually the appropriate element now 
    this.classList.add("active"); 
} 
// iterate over all menu items 
[...document.querySelectorAll(".menu")].forEach(item => 
    // add a click handler to each item 
    item.addEventListener("click", menuClickHandler) 
); 

參見:document. querySelector()document. querySelectorAll()Array.prototype. forEach()EventTarget. addEventListener()