Pomoc - Szukaj - Użytkownicy - Kalendarz
Pełna wersja: wywołanie funkcji
Forum PHP.pl > Forum > Po stronie przeglądarki > JavaScript
SaMi
Witam, mam mały problem i najprawdopodobniej jest to banał. Mianowicie gdy tworzę zewnetrzny plik js poprzez utworzenie tagu <script> w DOMie i wywoluję zawartą w nim funkcje uzyskuję komunikat ReferenceError: user is not defined. natomiast jeśli załaduję klasycznie w htmlu ten sam plik wszystko działa bez problemu.
  1. <script type="text/javascript">
  2. (function(d,s){
  3. var js,jsr = d.getElementsByTagName(s)[0];
  4. js = d.createElement(s);
  5. js.src = '//www.mojadomena.pl/js/iframe.js';
  6. jsr.parentNode.insertBefore(js,jsr);
  7. }(document,'script'));
  8.  
  9. user.setAccount(['12345']);

iframe.js w wielkim uproszczeniu
  1. // (function(w){ - tego tu miało tu nie być
  2. var user = user || (function(){
  3. _args = {};
  4.  
  5. return {
  6. setAccount: function(a){
  7. _args = a;
  8. },
  9. key: function(){
  10. return _args[0];
  11. }
  12. };
  13. }());
lukasz1985
Odpowiedź kryje się w tej całej ceregieli, którą wykonujesz żeby oszczędzić globalną przestrzeń nazw.
Zmienna "user" to zmienna lokalna anonimowej funkcji w iframe.js. Domyślam się, ze chciałeś przesłać do tej funkcji zmienną window (po literce "w" w argumencie) i tam przypisać ją w następujący sposób na końcu:

[JAVASCRIPT] pobierz, plaintext
  1. w.user = user
[JAVASCRIPT] pobierz, plaintext


Poza tym, po co takie kombinacje? Po co do funkcji anonimowej przesyłać zmienną document, skoro to zmienna globalna zawsze widoczna w każdym zasięgu?

Przerost formy nad treścią. Proponowałbym zacząć od importowania skryptów zwykłym znacznikiem <script> , a potem interesować się jakimis tam formami usprawniania tego procesu.

Sprawdziłbym jeszcze czy nie lepiej byłoby użyć append zamiast insertBefore. Tutaj specjalistą nie jestem jednak myślę, że problemem może być to, że skrypty są zaimportowane w złej kolejności.
SaMi
zakradł się mały błąd który skorygowałem.
Jest to implementacja wyszukiwarki którą pośrednicy zamieszczają na swoich stronach. Na dzień dzisiejszy eksperymentuję i uczę się, także proszę o wyrozumiałość i ewentualne rady smile.gif
lukasz1985
[JAVASCRIPT] pobierz, plaintext
  1. function(d,s){
  2.  
  3. var js,jsr = d.getElementsByTagName(s)[0];
  4.  
  5. js = d.createElement(s);
  6.  
  7. js.src = '//www.mojadomena.pl/js/iframe.js';
  8.  
  9. jsr.parentNode.insertBefore(js,jsr);
  10.  
  11. }(document,'script')); // Zupełnie nie potrzebne
  12.  
[JAVASCRIPT] pobierz, plaintext



[JAVASCRIPT] pobierz, plaintext
  1. function(){
  2.  
  3. var js,jsr = document.getElementsByTagName(s)[0];
  4.  
  5. js = document.createElement("script");
  6.  
  7. js.src = '//www.mojadomena.pl/js/iframe.js';
  8.  
  9. jsr.parentNode.insertBefore(js,jsr);
  10.  
  11. }();
  12.  
[JAVASCRIPT] pobierz, plaintext



Poza tym proponowałbym - zamiast używania anonimowych funkcji do korzystania z "przestrzeni nazw":

[JAVASCRIPT] pobierz, plaintext
  1. var mojmodul = {};
  2. mojmodul.zrobCos = function(){
  3.  
  4. var js,jsr = document.getElementsByTagName(s)[0];
  5.  
  6. js = document.createElement("script");
  7.  
  8. js.src = '//www.mojadomena.pl/js/iframe.js';
  9.  
  10. jsr.parentNode.insertBefore(js,jsr);
  11.  
  12. };
  13.  
  14. mojmodul.zrobCos();
  15.  
[JAVASCRIPT] pobierz, plaintext



Anonimowe funkcje są fajne - dla małych fragmentów kodu - przynajmniej takie moje zdanie po tym jak potrafią one namieszać w kodzie, który w ostateczności staje się jednym wielkim śmietnikiem. Moduły w dużym stopniu elminują konieczność ich używania jeśli chodzi o moduły. W kodzie czysto obiektowym potrzebne jest już zupełnie inne podejście do tematu.
SaMi
Zmieniłem na przestrzenie nazw faktycznie łatwiej to ogarnać. Aczkolwiek moje pytanie z pierwszego posta jest nadal aktualne.
lukasz1985
Odpowiedź na Twoje pytanie jest dość prosta. Otóż tworząc z poziomu JavaScript tag "script" i ustawiając jego źródło informujesz tym samym przeglądarkę, że ma wykonać kolejne zapytanie pod podane źródło, a więc robiąc tak:

[JAVASCRIPT] pobierz, plaintext
  1.  
  2. var js = ddocument.createElement("script");
  3. js.src = "iframe.js";
  4. document.body.appendChild(js);
  5. user.setAccount("213");
[JAVASCRIPT] pobierz, plaintext


przeglądarka zacznie wgrywać nowy adres, w tym przypadku plik skryptu znajdującego się pod ścieżką "iframe.js".

Tak się składa, że nie dzieje się to natychmiast, a ładowanie następuje asynchronicznie, w tle, tak jak w przypadku XHR (XmlHttpRequest, czy krócej "AJAX"). Oznacza to, że zmienna "user" zdefiniowana w tamtym pliku nie pojawi się natychmiast, a dopiero po wykonaniu całego procesu: pobrania pliku js i wrzucenia go w dokument.

Aby wykonać kod po załadowaniu tego dokumentu należy się posłużyć funkcją zwrotną ("callback'iem"):


[JAVASCRIPT] pobierz, plaintext
  1.  
  2. var js = ddocument.createElement("script");
  3. js.src = "iframe.js";
  4. document.body.appendChild(js);
  5.  
  6. js.onload = function() {
  7. user.setAccount("213");
  8. }
  9.  
[JAVASCRIPT] pobierz, plaintext
To jest wersja lo-fi głównej zawartości. Aby zobaczyć pełną wersję z większą zawartością, obrazkami i formatowaniem proszę kliknij tutaj.
Invision Power Board © 2001-2025 Invision Power Services, Inc.