wake-up-neo.com

Funktion ruft nicht innerhalb eines Onclick-Ereignisses auf

Ich möchte am Ende jedes Youtube-Links etwas HTML hinzufügen, um den Player in einer Litebox zu öffnen. Dies ist mein Code bisher:

$(document).ready(function() {
  var valid_url = new RegExp('youtube\.com\/.*v=([a-zA-Z0-9_-]+)');
  var image_data = 'base64 encoded image';

  init();

  function init() {
    $('a').each(function() {
      if (valid_url.test($(this).attr('href'))) {
        $(this).after( ' <img src="' + image_data + '" onclick="open_litebox(\'hi\');" />' );
      }
    });
  }

  function open_litebox(param) {
    alert(param);
  }
});

Es funktioniert bis zu dem Punkt, an dem nach dem Youtube-Link etwas HTML-Code eingefügt wird:

<img src="base 64 data" onclick="open_litebox('hi')">

Aber wenn ich darauf klicke, wird die Funktion open_litebox() nicht aufgerufen. Wenn ich in der Fehlerkonsole schaue, kann ich einen Fehler sehen, der open_litebox is not defined sagt, aber ich habe ihn definiert.

Ich bin ziemlich ahnungslos, was hier schief läuft. Kann mir jemand helfen?

Vielen Dank.

27
Wen

Dies ist ein häufiges Problem, wenn Sie zum ersten Mal mit jQuery arbeiten. Das Problem hierbei ist, dass Sie die Funktion innerhalb des jQuery-Bereichs definiert haben. Dies bedeutet, dass Sie nicht darauf zugreifen können, indem Sie sie wie eine normale Funktion aufrufen. Eine Lösung für Ihr Problem besteht darin, Ihre Funktionsdefinition außerhalb der anonymen Bereitschaftsfunktion zu verschieben, die Sie geschrieben haben.

$(document).ready(function() {

    // do your stuff here

});

// define your functions here 
function my_func() {

}

Oh, und ich würde vorschlagen, dasselbe für Ihre Variablen zu tun, die Sie definiert haben. Verschieben Sie sie auch außerhalb Ihrer Ready-Funktion, da Sie dieselben Probleme haben werden wie mit Ihren Funktionen.

45
Simon H

Ihre open_litebox-Funktion befindet sich im Bereich einer anderen Funktion und ist daher nicht global sichtbar. Versuchen Sie stattdessen, .click() zu verwenden:

Etwas in diese Richtung:

$(this).after( ' <img src="' + image_data + '" id='abc' />' );
$('#abc').click(open_litebox);

Sie müssen auf diese Weise separate IDs für jeden der Links generieren. Sie können also jeden <img>-Tag über ein bekanntes class-Attribut verfügen und dieses dann mit $('.abc') (wenn abc) anstelle von $('#abc') auswählen in einem Schritt (dh als separater Anruf nach Ihrer $('a').each).

10
icyrock.com

Die anderen Antworten sind insofern korrekt, als das Verschieben Ihrer my_func-Deklaration außerhalb von $(document).ready() Ihr Problem lösen wird. Ich möchte jedoch die Begründung erläutern, da sie nichts mit jQuery zu tun hat.

$(document).ready() ist ein Ereignishandler, an den Sie eine anonyme Funktion als Rückruf übergeben, die ausgeführt werden sollte, wenn der Browser Sie benachrichtigt, dass das Dokument bereit ist. 

Da Sie my_func in der Rückruffunktion definiert haben, ist es nicht im globalen Gültigkeitsbereich sichtbar und kann daher nicht über die onclick-Eigenschaft des img-Elements Ihrer Seite aufgerufen werden.

In JavaScript liegt der Gültigkeitsbereich auf der Funktionsebene. Alles, was sich nicht in einer Funktion befindet, wird im globalen Bereich zusammengefasst.

10
Rob Sobers

Der Grund ist, dass open_litebox() in der document.ready-Funktion deklariert ist und daher nicht aus einem globalen Bereich heraus zugänglich ist.

Sie können die Funktion außerhalb von document.ready verschieben oder den Code so ändern, dass der Onclick-Handler mithilfe von jQuery (der die Funktion direkt referenziert) angehängt wird:

var link = $(' <img src="' + image_data + '" />' ).click(function () {
   open_litebox('hi');
});
$(this).after(link);
2
David Tang

Es gibt eine viel schönere und jQuery-Methode zum Zuweisen der Klickaktion.

function init() {
    $('a').each(function() {
        if(valid_url.test($(this).attr('href'))){
            $(this).click( function() { open_litebox('hi'); });
        }
    });
}

Dies löst das Umfangsproblem, wie in den anderen Antworten beschrieben. Wenn Sie open_litebox () mit Parametern aufrufen müssen, wickeln Sie es wie ich in eine anonyme Funktion ein. Andernfalls wird die Funktion aufgerufen und der Rückgabewert wird an die Klickaktion übergeben. Andernfalls ist die Zuweisung einfacher, wenn keine Parameter übergeben werden müssen:

$(this).click( open_litebox );
0
Surreal Dreams