2009-11-19 8 views
16

Non so se ciò che sto cercando di realizzare è possibile. Vorrei sovrascrivere il comportamento predefinito per tutti gli oggetti di ancoraggio (tag A) per una determinata pagina HTML. So che posso scorrere tutti gli elementi A e aggiungere dinamicamente una chiamata onclick a ognuno di essi dal metodo body body onload, ma sto cercando una soluzione più assoluta. Che cosa ho bisogno è che tutti A gli elementi vengono assegnati un onclick azione che chiama un metodo che passa la proprietà elemento href come argomento, quindi il seguente:Ignora comportamento predefinito per gli oggetti di collegamento ('a') in Javascript

<a href="http://domain.tld/page.html"> 

diventa dinamico:

<a href="http://domain.tld/page.html" onclick="someMethodName('http://domain.tld/page.html'); return false;"> 

Come ho detto, il modo ideale per fare questo sarebbe in qualche modo scavalcare la classe Anchor quando il documento viene caricato. Se non è possibile, ricorro al metodo degli elementi loop-through-A (che so già come fare).

+0

Bene, con la delega degli eventi non tutti hanno bisogno di avere l'evento attaccato su di loro. Vedi "Live" in jQuery, per esempio. O leggi sulla delega degli eventi JavaScript. – Nosredna

+0

In genere questo dovrebbe essere fatto al codice HTML prima che raggiunga il client. Se la tua pagina è complessa potresti incontrare molti programmi con delega degli eventi. – Ben

+0

In realtà, per l'evento "clic" mi aspetterei meno problemi con la delega.È cose come rintracciare il topo che ti ucciderà. – Nosredna

risposta

30

Se non si desidera iterare su tutti gli elementi di ancoraggio, si può utilizzare semplicemente event delegation, ad esempio:

document.onclick = function (e) { 
    e = e || window.event; 
    var element = e.target || e.srcElement; 

    if (element.tagName == 'A') { 
    someFunction(element.href); 
    return false; // prevent default action and stop event propagation 
    } 
}; 

Controllare l'esempio precedente here.

+0

What'd dici che il vantaggio di non iterare sugli elementi di ancoraggio? In un certo modo questo è il metodo più invadente, poiché significa reindirizzare * tutti * i clic nel documento! –

+4

La domanda menziona esplicitamente di non iterare sugli elementi di ancoraggio. – Ben

+0

Ed è anche più efficiente quando non devi prima passare attraverso gli elementi. – jtbandes

2
window.onload = function() { 
    var anchorElements = document.getElementsByTagName('a'); 
    for (var i in anchorElements) 
     anchorElements[i].onclick = function() { 
      alert(this.href); 
      return false; 
     } 
} 

Questo è il modo più semplice per farlo. Avvolgi in <script type="text/javascript">...</script> nella testina del documento e verrà eseguito al caricamento della pagina.

0

Non è possibile sovrascrivere tutti gli eventi onlick degli elementi di ancoraggio. È possibile aggiungere un onclick al corpo del documento e disporre della logica per vedere se il pari viene propagato da un elemento di ancoraggio ed eseguire l'evento in quel caso, ma questa soluzione potrebbe causare problemi se la pagina è complessa e non sta propagando i clic in alcuni casi.

Rimanerei con la soluzione getElementsByTagName se possibile.

7

utilizzando jQuery:

$(function() { 
    $("a").click(function() { 
     return someMethodName($(this).attr('href')); 
    }); 
}); 

function someMethodName(href) 
{ 
    console.log(href); 
    return false; 
} 
0

Non usare un caso se ci sono più eventi che è necessario gestire. Usa invece la composizione a stringa per costruire il percorso della funzione che deve essere chiamata. Ciò richiede che un prototipo venga aggiunto agli elementi "A" che definiscono il valore predefinito e la stringa da comporre. Un attributo dati sull'elemento dovrebbe essere in grado di ignorare il valore predefinito. In sostanza, vogliamo solo che un messaggio e un'azione vengano passati per impostazione predefinita e modificati in modo dichiarativo nel markup. L'azione specificata dovrebbe essere pubblicata da qualche parte come API o altra funzione di libreria accessibile ed essere richiamabile da lib ['funName']. Dagli un attributo, nessuna preoccupazione per nome o id. Il prototipo e l'attributo saranno utili per il debounce, perché dovrai rimbalzare.

0

Simile alla risposta di Benji XVI, ma utilizzando querySelectorAll, all'interno di un contenitore div con classe 'contenitore' e utilizzando es6.

const $elems = document.querySelectorAll('.container a') 
var elems = Array.from($elems) 
elems.map(a => { 
    a.onclick = (e) => { 
    e.preventDefault() 
    window.alert('Clicking external links is disabled') 
    } 
}) 
Problemi correlati