Avatar billede exp Juniormester
30. december 2013 - 23:09 Der er 4 kommentarer og
1 løsning

Udtræk og print header-tags fra div

Hej JS-wizards!

Jeg leger lidt med at bygge mig simpel tekst-editor og i den forbindelse vil jeg gerne lave et felt i sidebaren, der automatisk opdateres med header-strukturen (h1, h2, h3, h4, h5, h6) fra en given <div>. Strukturen vises som en simpel ordered list (<ol>), hvor headertags er nested under hinanden - ligesom Outline-funktionen i W3's validator.

Jeg tænker at struktur-funktionen kører fx 3 sekunder efter seneste tastatur-tryk, så den ikke konstant skal stå og trække ressourcer...

Kan dette overhovedet lade sig gøre? Og i givet fald, hvordan gør jeg så?

Bemærk, at mine javascript-evner begrænser sig til copy/paste, men jeg vil gerne lære :-)
Avatar billede anri Novice
02. januar 2014 - 18:50 #1
Hmm..
Det lader til at du må give et mere konkret eksempel på problemstillingen.
Jeg forstår i hvert fald ikke hvad du mener, og siden der ikke er nogen andre der svarer, så er det nok ikke fordi jeg er dummere end gennemsnittet.
Avatar billede exp Juniormester
03. januar 2014 - 20:45 #2
Hej anri,

jeg vil prøve at komme med et eksempel :-)

Jeg har et content-felt, der ændrer sig dynamisk. Det kunne fx se således ud:

<div id="content">
    <h1># H1 overskrift</h1>
    <p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Fusce felis dui, elementum nec velit quis, pulvinar feugiat ante. Nam pulvinar est turpis, feugiat facilisis est cursus et. Nullam imperdiet gravida pretium.</p>
    <h2>## H2 overskrift</h2>
    <p>Aliquam eu ullamcorper erat. Maecenas vulputate, mauris at placerat imperdiet, purus ante porttitor tortor, vitae vehicula nibh libero quis nisi. Duis sed ultricies tortor, ut sagittis ligula. Nulla eget elit fermentum eros congue sollicitudin sit amet vel neque.</p>
    <h3>### H3 overskrift</h3>
    <p>Nullam id ornare mi. Curabitur ac elementum leo. Quisque ac lorem quam. Cras vel urna at urna faucibus accumsan. Nulla suscipit tristique eros, at dapibus felis fringilla sed. Morbi volutpat massa in orci mattis posuere. Sed at convallis risus.</p>
    <h3>### H3 overskrift</h3>
    <p>Etiam interdum nunc nisi, non auctor arcu tristique et. Suspendisse potenti. Praesent sollicitudin non felis nec posuere. Suspendisse posuere ultricies leo id feugiat. Donec sed libero lobortis, euismod odio quis, blandit velit.</p>
    <h2>### H2 overskrift</h2>
    <p>Pellentesque sit amet nisi eu leo aliquam interdum quis at mauris. Proin dignissim arcu id sem sagittis rhoncus. Aenean quis laoreet magna. Praesent quis tortor in dolor blandit varius quis tempus lorem. Mauris condimentum quam vitae augue aliquam blandit.</p>
</div>

Det jeg søger er en javascript-funktion, der trækker indholdet af alle <Hx>-tags ud, og outputter en outline, fx således (på baggrund af ovenstående eksempel):

<ul>
    <li class="h1"># H1 overskrift
        <ul>
            <li class="h2">## H2 overskrift
                <ul>
                    <li class="h3">### H3 overskrift</li>
                    <li class="h3">### H3 overskrift</li>
                </ul>
            </li>
            <li class="h2">### H2 overskrift</li>
        </ul>
    </li>
</ul>

Hvis den kan køre fx hver 5. sekund, så kunne det være topfedt.

Håber det giver mening :-)

/exp
Avatar billede anri Novice
03. januar 2014 - 23:57 #3
Understående kode kan gøre det. I stedet for at køre hele koden hvert 5 sekund, så ville jeg hooke mig op på onkeypress eventet og så sætte et flag der indikerer at brugeren har ændret noget.
Hvis det flag ikke er sat, venter man bare yderligere 5 sekunder.

<html>
    <head>
        <script type="text/javascript">
            function MakeIndex() {
                var contentList = document.querySelectorAll(".content h1,.content h2,.content h3,.content h4");

                var currentLevel = 0;
                var indexString = '';

                for (var i = 0; i < contentList.length; i++) {
                    var newLevel = contentList[i].nodeName.charAt(1);
                    if (newLevel > currentLevel) {
                        for(var o=currentLevel;o<newLevel;o++)
                            indexString += "<ul>";
                    } else if (newLevel < currentLevel) {
                        for (var o = currentLevel; o > newLevel; o--)
                            indexString += "</ul>";
                    }

                    indexString += "<li>" + contentList[i].innerHTML + "</li>";
                    currentLevel = newLevel;
                }

                document.getElementById("indexHolder").innerHTML = indexString;
            }
        </script>
    </head>
    <body>
        <div class="content" >
            <h1>
                # H1 overskrift</h1>
            <p>
                Lorem ipsum dolor sit amet, consectetur adipiscing elit. Fusce felis dui, elementum
                nec velit quis, pulvinar feugiat ante. Nam pulvinar est turpis, feugiat facilisis
                est cursus et. Nullam imperdiet gravida pretium.</p>
            <h2>
                ## H2 overskrift</h2>
            <p>
                Aliquam eu ullamcorper erat. Maecenas vulputate, mauris at placerat imperdiet, purus
                ante porttitor tortor, vitae vehicula nibh libero quis nisi. Duis sed ultricies
                tortor, ut sagittis ligula. Nulla eget elit fermentum eros congue sollicitudin sit
                amet vel neque.</p>
            <h3>
                ### H3 overskrift</h3>
            <p>
                Nullam id ornare mi. Curabitur ac elementum leo. Quisque ac lorem quam. Cras vel
                urna at urna faucibus accumsan. Nulla suscipit tristique eros, at dapibus felis
                fringilla sed. Morbi volutpat massa in orci mattis posuere. Sed at convallis risus.</p>
            <h3>
                ### H3 overskrift</h3>
            <p>
                Etiam interdum nunc nisi, non auctor arcu tristique et. Suspendisse potenti. Praesent
                sollicitudin non felis nec posuere. Suspendisse posuere ultricies leo id feugiat.
                Donec sed libero lobortis, euismod odio quis, blandit velit.</p>
            <h2>
                ### H2 overskrift</h2>
            <p>
                Pellentesque sit amet nisi eu leo aliquam interdum quis at mauris. Proin dignissim arcu id sem sagittis rhoncus. Aenean quis laoreet magna. Praesent quis tortor in dolor blandit varius quis tempus lorem. Mauris condimentum quam vitae augue aliquam blandit.</p>
        </div>
        <input id="Button1" type="button" value="button" onclick="MakeIndex();" />
       
        <div id="indexHolder"></div>
    </body>
</html>
Avatar billede exp Juniormester
04. januar 2014 - 22:13 #4
Hej anri,

super fedt!

Din løsning med at lytte på tastetryk ligger på linje med, hvad jeg selv havde forestillet mig. Kan du guide mig i retning mod, hvordan man gør?

/exp
Avatar billede anri Novice
05. januar 2014 - 14:42 #5
Jeg ville gøre således :

var inputChanged = false;

window.onload = function(){
  setInterval(MakeIndex, 5000); //Kald MakeIndex hvert 5. sekund.
}


og i starten af MakeIndex :
function MakeIndex() {
  if (!inputChanged) return;
....


I slutningen af MakeIndex:
  inputChanged = false;
}


Og til sidst skal du lave en funktion der sætter inputChanged  ved tastetryk i content-div'en:
<div tabindex="1" onkeypress="DivKeyPressed" >

og så DivKeyPressed funktionen:
function DivKeyPressed(){
  inputChanged = true;
}


Der skal en tabindex attribut på Div'en for at den reagerer på tastetryk i alle browsere.
..afhængigt af hvordan din side bruges kan du overveje kun at starte setInterval når div'en får fokus, og stoppe den igen når den mister fokus (onfocus & onblur events).
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

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