Avatar billede spiri Nybegynder
21. juli 2001 - 01:56 Der er 20 kommentarer og
1 løsning

globale variabler i functioner

Er det muligt at angive en variabel inde i en function, for så senere at bruge den i en anden?

Jeg har snuset mig frem til at hvis en variabel bliver sat således:

variabelnavn = værdi;

...inde i en function, burde den være global, hvorimod:
var variabelnavn = værdi;

...inde i en function er en lokal.


Men det virke bare ikke.

Nogen bud...
Avatar billede jakobandersen Nybegynder
21. juli 2001 - 01:59 #1
var ting;

function doting(){
ting = 1
}

document.write ting;
Avatar billede spiri Nybegynder
21. juli 2001 - 02:01 #2
jamen, det funker ikke...
Avatar billede jakoba Nybegynder
21. juli 2001 - 02:49 #3
for at gøre en variabel global skal du definere den i en script sektion i dokumentets head.

i head:
<script language=\'javascript\'>

var enGlobalEn = 25:      // denne kan ses fra enhver funktion

function dummy() {
  var lokalIFunktion = 30;  // denne forsvinder såsnart funktionen returnerer.
};

hvis du definerer en variabel i dokumentets <body vil den variabel kunne nås igennem:

document.variabelnavn

Desværre er IE ret ligeglad med reglerne. \"der er da bedre jo nemmere det er for folk at find deres variable\". så de har en tenden til at gøre alting globalt hvis det overhovedet er muligt. selv en variabel skabt indeni en funktion vil blive kusket og du kan aflæse værdien i den. Det kan nogen gang give nogen ubehagelige konsekvenser når man prøver at debugge.
Men hvis du husker ALTID at definere lokale variable i funktioner med  var foran kan du regne med at de bliver nedlagt igen ved funktionens afslutning sådan som de bør.

mvh JakobA
Avatar billede jakoba Nybegynder
21. juli 2001 - 02:50 #4
Ups. kusket -> husket
Avatar billede jakoba Nybegynder
21. juli 2001 - 09:33 #5
Sorry, det var da vist slet ikke det du spurgte om :(

Ja det kan du. opret den blit i sidens window-del:

function derLaverEnGlobal( ) {
  window.nyVar = \"Hej med dig\";  // opretter nyVar i window
  setTimeout( \"alert(nyVar);\", 2000);
};

mvh JakobA
Avatar billede roenving Novice
21. juli 2001 - 10:06 #6
jakoba<<
Va er det ikke sådan, at man kan se en global variabel oprettet i det yderste html-lag overalt?

Dvs. at man i den typiske situation kunne definere i en Head på det første frameset-dokument?

Og hvis man så fik brug for det i en underside kunne bruge dit forslag om window.variabelnavn?

Altså f.eks

<HTML>
<HEAD>
<Title>Globale variable</TITLE>
<SCRIPT language=\"Javascript\">
var DetSkalJegHuske    //Denne her kan ses af alt alle steder
</SCRIPT>
</HEAD>
<BODY>
<FRAMESET rows=\"120,*\">
  <FRAME SRC=\"Menu.html\"></FRAME>
  <FRAME SRC=\"Main.html\"></FRAME>
</FRAMESET>
</BODY></HTML>


<HTML>
<HEAD>
<Title>Main Frame</TITLE>
<SCRIPT language=\"Javascript\">
var LokalGlobal      //Denne her kan ses overalt i Main-Frame, men ikke i Menu-Frame
function derLaverEnGlobal( ) {
  window.nyVar = \"Hej med dig\";  // opretter nyVar i window
  setTimeout( \"alert(nyVar);\", 2000); //Også denne her kan ses overalt
};
</SCRIPT>
</HEAD>
<BODY>
<FRAMESET cols=\"10%,*\">
  <FRAME SRC=\"MenuMain.html\"></FRAME>
  <FRAME SRC=\"Content.html\"></FRAME>
</FRAMESET>
</BODY></HTML>

?~]

jes
Avatar billede jakoba Nybegynder
21. juli 2001 - 10:21 #7
roenving >> Jeg tror det ikke.

den reelle udstrækning af \"globalt\" er \"overalt i siden der er loadet i dette vindue\". hvis andre vinduer/rammer er åbne samtidigt kan man adressere sig hen til dem. Men kun hvis man:
1) kender vejen i form af opener, parent, rammenavn og popopvinduesnavn
2) dokumenterne i begge winduer er loadet fra samme domæne.

Det ville give alvorlige sikkerheds-risici at lave et \"rigtigt\" globalt område man kunne gemme vaiable og funktioner i.

Det nærmeste der er er \'cookies\', men mange vælger at slå dem fra, netop på grund af sikkerhedsrisikoen (den er eller minimal for cookies).

mvh JakobA
Avatar billede roenving Novice
21. juli 2001 - 10:24 #8
>>jakoba

OK, men jeg var også kun inde på om man ikke selv kunne have sine egne globale, jeg er nemlig helt enig i, at den slags sikkerheds-problemer næsten for enhver pris skal undgås.

;~}
jes
Avatar billede spiri Nybegynder
21. juli 2001 - 10:52 #9
Hold da op, der sker en masse når man sover. Jeg kigger lige på det.

2 min...
Avatar billede spiri Nybegynder
21. juli 2001 - 11:12 #10
Nu har jeg prøvet lidt af hvert, og kan stadig ikke få det til at funke.

Det er en menu fra www.bratta.com, jeg er ved at ændre lidt på.

Den er bygget op af en masse layers, som jeg gerne skulle have højden på.

Det virker også fint inde i den function der bygger menuen, men jeg kan som sagt ikke få fat i den uden for functionen (til at angive højden på et baggrundslayer).

Jeg har lagt skidtet her: http://www.emusikskolen.dk/test.htm

Den først alertboks skulle være variablen UDEN for functionen, og den anden alertboks er inde i functionen.


Jeg ved godt der er en masse rod i resten af scriptet, men det jo kun halvfærdigt:)
Avatar billede jakoba Nybegynder
21. juli 2001 - 11:24 #11
Jeg satte lidt ekstra information ind i dine alerts:

alert(\"TopLayerHeight: \" +this.TopLayerHeight);
alert(\"GlobaltSkrammel: \" +window.GloaltSkrammel);

Så er det nemt at se hvad der sker. Du kalder nr 2 alert først. før variabelen GlobaltSkrammel har fået en værdi.

mvh JakobA
Avatar billede jakoba Nybegynder
21. juli 2001 - 11:31 #12
Ups. og der skulle være et b i Globalt, men det er underordnet når den alligevel ikke har fået en værdi.
Avatar billede spiri Nybegynder
21. juli 2001 - 11:33 #13
Ja, det er rigtigt, men jeg kalder jo functionen FØR, den \"første\" alertboks!

Men, nu er jeg en absolut rookie til det her, og ved ikke hvordan den behandler koden.

Men hvordan får jeg så kørt functionen igennem, FØR jeg skal bruge min værdi?


Gav dette overhovedet mening??

Altså jeg skal ha\' printet et nyt layer med TopLayerHeight som højden. F.eks:

document.write(\"<div \\\"id=et_eller_andet\\\" style=\\\"{height:\" + TopLayerHeight +\"\\\"><div>\");

eller noget i den stil.

Men hvor skal den printes, for at jeg kan være sikker på at værdien er blevet tildelt?
Avatar billede jakoba Nybegynder
21. juli 2001 - 12:07 #14
når du definerer en funktion med fx:

function en_ny_funktion( ) {
  alert( \"Her er funktionen \'en_ny_funktion\'.\" );
};

så findes funktionen. men den bliver ikke udført før du kalder den:

en_ny_funktion();

omvendt vil det gå galt hvis du prøver at kalde den før den er defineret.

Siden JavaScript er et \"dynamisk\" sprog hvor du nårsomhelst kan oprette nye funktioner eller ændre dem der allerede findes kan det ofte være ret besværligt at holde rede i den rækkefælge der er i programmet.

i dit program ved vi at GlobaltSkrammel får sin værdi i funktionen init(), og vi må så sørge for at vi ikke prøver at bruge GlobaltSkrammel før init() er kørt.
så vi kikker efter hvor init() bliver kaldt. og finder:
        //Initiating the menus onload, if it\'s a 4.x+ browser.
        if(bw.bw)onload=init;
der bliver init gjort til \"den funktion der skal kaldes onload\", dvs når hele siden engang er blevet hentet. og det er svært at gætte på hvornår er.

For at teste at det virker det her med globale variable kan du evt lave et lille testlink:

<a href=\"java script:void();\"
  onclick=\'alert(\"GlobaltSkrammel: \" +window.GlobaltSkrammel);\'>test</a>
når siden er hentet vil det link virke og give en alert med værdien i.

men det vil ikke hjælpe dig med at lave den ændring i menuen du ønsker.

------

men mon ikke du skal bygge ændringen ind i funktionen init(), og så blot sørge for at ændringen kommer efter den anden alert (altså den der står i init() ).

mvh JakobA
Avatar billede spiri Nybegynder
21. juli 2001 - 12:23 #15
Nu dæmrer det. Det er jo klart.

Men er det ikke lidt catch 22(i mangel af bedre, og knap så snobbet ord), functionen init() skal jo først kørers når siden er læst ind, da den først skal vide hvilke layers, den skal arbejde med. Samtidig skal jeg bruge højde af samtlige layers, for at kunne gøre højden på baggrundslayeret(den blå) dynamisk, efter hvor mange menupunkter der er(samt fontsize osv).

Men dette layer skulle jo meget gerne være en del af helesiden der bliver loadet, hvorved init endnu ikke er kørt!!!!!

Findes der en function der kan checke om init(eller en hvilken som helst function er blevet kørt), så jeg kan køre en ny function, der tegner dette bglayer?

Eller et helt andet forslag måske...

Jeg skal nok hamre flere point af til dig, da dette vist er lidt mere kompleks end jeg troede.
Avatar billede spiri Nybegynder
21. juli 2001 - 12:25 #16
Forøvrigt, virker det måske lidt \"overkill-agtigt\" at lave det dynamisk, men det skal bruges i en større sammenhæng, på flere forskellige sites.
Avatar billede jakoba Nybegynder
21. juli 2001 - 12:33 #17
I IE (og kun IE) kan det gøres, da du nårsomhelst kan gå ind og ændre højden på et layer, også efter siden er loadet.
Så bliver siden blot gentegnet med den nye højde (og uden at scriptet kører igen).
men html-standarden siger ret udtrykkeligt at reight skal være read-only, og at det ikke er noget man skal kunne.
Nok netop fordi det som du siger en en hønen eller ægget situation. Det kan meget nemt gå i en uendelig løkke hvor feedback fra hønen ændrer ægget, der så giver feedback tilbage til en lidt anderledes høne, osv osv.

men hvis du er sikker på at det ikke vil gå galt her, kan du altså bare ændre højden på laget efter det er blevet tegnet.

mvh JakobA
Avatar billede jakoba Nybegynder
21. juli 2001 - 12:35 #18
Ups. reight -> height
Avatar billede spiri Nybegynder
21. juli 2001 - 12:49 #19
Den med hønen og ægget er sgu\' alle de point værd. Griner sammenligning.

Det holder jo desværre ikke kun med IE, så jeg må nok tage den irriterende vej og lave det i php, hvilket dog også bliver en halv løsning, men kan til nød bruges.

Men mange tak for hjælpen, i det mindste fik jeg styr på en del ting.
Avatar billede spiri Nybegynder
21. juli 2001 - 13:16 #20
Lige en sidste ting.

Nu har jeg fået det lavet, så det funker med JS.

Istedet for at gøre sådan:
onload=init;

...kalder jeg nu bare init(), nederst på siden. Derved kan jeg nu tegne mit layer.

Det virker i IE5.0 og NS4.76

Jeg kan dog ikke lige overskue om der skulle være problemer med at gøre sådan. Det er ret vigtigt at init først bliver kaldt, når inholdet i de forskellige layers er læst.

Findes der browserer/situationer hvor ovenstående ikke holder?

Avatar billede jakoba Nybegynder
21. juli 2001 - 13:36 #21
Logisk burde det virke allevegne med reækkefølgen:
  tegn indholdsceller / initier og mål indholdslag / tegn underliggende rammelag
men jeg kender ikke brattas meny godt nok til at turde love dig det.

mvh JakobA
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Vi tilbyder markedets bedste kurser inden for webudvikling

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester