source: t29-www/shared/js-v6/modules/menu.js @ 276

Last change on this file since 276 was 276, checked in by sven, 12 years ago

Weitere Fixes in den Geräteseiten:

  • Univac-Geräteseiten konvertiert
  • Interlang-System verbessert (bessere Ausgabe bei nicht existierenden Interlang-Links)
File size: 10.2 KB
Line 
1/**
2 * t29v6 Menu
3 *
4 * Features:
5 *  - Collapsable (can be expanded by button)
6 *  - Scrollable (can be maked position:fixed by button)
7 *  - Guide beam (footer clone of navigation in a fancy beam like way)
8 *
9 * Language-specific strings are taken from t29.msg.
10 *
11 * (c) 2012 Sven Koeppel <sven@tech..29.de>
12 * Licensed under GPL
13 **/
14
15if(!t29) window.t29 = {}; // the t29 namespace
16 
17t29.menu = { collapsed:{}, scroll:{}, guide:{} }; // mit Unterklassen
18t29.menu.setup = function() {
19        t29.menu.side = $("nav.side");   // Hauptseitennavigation
20        t29.menu.beam = $("nav.guide");  // Strahlnavigation/Guide (Kopie von side)
21        t29.menu.rel = $("nav.rel");     // relative navigation im footer (vor/zurück)
22        t29.menu.collapsed.setup();
23        t29.menu.scroll.setup();
24        t29.menu.guide.setup();
25};
26
27//////////////////////////// Menu Collapsed System.
28/**
29 * Menu ein- oder ausklappen.
30 * @param target_state  true: Eingeklappt, false: ausgeklappt
31 * @param quick  true=keine Animation, false/undefined=Animation
32 **/
33t29.menu.collapsed.set = function(collapse, quick) {
34        if(collapse==undefined) collapse = !t29.menu.collapsed.is();
35        log("Collapse zu "+(collapse?"KLEIN":"GROß")+" quick="+quick);
36        if(quick) collapse ? t29.menu.collapsed.lists.hide() : t29.menu.collapsed.lists.show();
37        else      collapse ? t29.menu.collapsed.lists.slideUp() : t29.menu.collapsed.lists.slideDown();
38        t29.menu.collapsed.but.text(t29._(collapse ? "js-menu-collapse-out" : "js-menu-collapse-in"));
39        collapse ? $("html").addClass("collapsed-menu") : $("html").removeClass("collapsed-menu");
40}
41// returns whether menu is collapsed (boolean).
42t29.menu.collapsed.is = function() { return $("html").hasClass("collapsed-menu"); };
43t29.menu.collapsed.setup = function() {
44        t29.menu.collapsed.but = $('<span class="button collapse-menu"></span>').appendTo("nav.side");
45        t29.menu.collapsed.lists = $("nav.side .u3").not("nav.side li.active > .u3"); // ein/auszuklappende Listen
46        t29.menu.collapsed.set(true, true); // initial state
47        t29.menu.collapsed.but.click(function(){ t29.menu.collapsed.set(); });
48};
49
50//////////////////////////// Menu Scroll System
51// enums, die CSS-Klassen im <html> entsprechen:
52t29.menu.scroll.States = Object.freeze({STATIC:"static-menu",FIX:"fixed-menu",STICK_TOP:"stick-top-menu",STICK_BOTTOM:"stick-bottom-menu"});
53/**
54 * Menuezustand beim Scrollen umschalten.
55 * @param target_state Zustand aus scroll.States-Enum
56 * @param
57 *
58 **/
59t29.menu.scroll.set = function(target_state) {
60        old_state = t29.menu.scroll.state;
61        t29.menu.scroll.state = target_state;
62        $("html").removeClass("static-menu fixed-menu stick-top-menu stick-bottom-menu").addClass(t29.menu.scroll.state);
63       
64        // Aufraeumen nach altem Status:
65        switch(old_state) {
66                case t29.menu.scroll.States.STICK_BOTTOM:
67                        t29.menu.side.attr("style",""); // reset css "top" value for positioning
68                        break;
69        }
70       
71        // Einrichten des neuen Status:
72        log("Gehe in Scroll-Zustand "+target_state);
73        switch(target_state) {
74                case t29.menu.scroll.States.STICK_TOP:
75                        // Menue schlaegt obene an. Prinzipiell Gleicher Zustand wie STATIC. Weiter.
76                case t29.menu.scroll.States.STATIC:
77                        // die CSS-Klassen regeln eigentlich alles.
78                        t29.menu.collapsed.but.show();
79                        t29.menu.scroll.but.text(t29._("js-menu-scroll-show"));
80                        t29.menu.side.show();
81                        break;
82                case t29.menu.scroll.States.FIX:
83                        // checken ob fixing ueberhaupt geht
84                        /*
85                        if( !t29.menu.collapsed.is() && t29.menu.side.height() > $(window).height()) {
86                                // Navi ist gerade ausgeklappt und zu groß fuer Bildschirm. Probiere Einklappen:
87                                t29.menu.collapsed.set(true, true);
88                                if(t29.menu.side.height() > $(window).height()) {
89                                        // Navi ist auch eingeklappt noch zu groß!
90                                        log("Navi ist auch eingeklappt zu groß zum fixen!");
91                                        // eingeklappt lassen. Weitermachen.
92                                        // hier noch was ueberlegen: Bei zu kleinem Bildschirm
93                                        // sollte der Button gar nicht erst angezeigt werden.
94                                        // dazu braucht man einen resize-Listener, der aber im
95                                        // ausgeklappten zustand jedesmal checken müsste, ob das
96                                        // eingeklappte menue reinpasst. (werte muss man cachen)
97                                        // Ziemlich doofe Aufgabe.
98                                }
99                        }*/
100
101                        t29.menu.collapsed.set(true, true); // Sicherstellen, dass Navi eingeklappt.
102                        t29.menu.collapsed.but.hide(); // Ausgeklappte Navi passt auf keinen Bildschirm.
103                        t29.menu.scroll.but.text(t29._("js-menu-scroll-hide"));
104                        break;
105                case t29.menu.scroll.States.STICK_BOTTOM:
106                        // Position absolute; Top-Position manuell setzen.
107                        t29.menu.side.css({top: t29.menu.scroll.stick_bottom });
108                        break;
109                default:
110                        log("Schlechter Zustand: "+target_state);
111        }
112}
113
114t29.menu.scroll.setup = function() {
115        t29.menu.scroll.but = $('<span class="button get-menu"></span>').appendTo("section.sidebar");
116        t29.menu.scroll.set(t29.menu.scroll.States.STATIC); // initial state
117       
118        t29.menu.scroll.but.click(function(){
119                switch(t29.menu.scroll.state) {
120                        case t29.menu.scroll.States.STATIC:
121                                // zu Fix uebergehen, mit Animation.
122                                t29.menu.side.hide();
123                                t29.menu.scroll.set(t29.menu.scroll.States.FIX);
124                                t29.menu.side.fadeIn();
125                                break;
126                        case t29.menu.scroll.States.FIX:
127                        case t29.menu.scroll.States.STICK_BOTTOM:
128                                // zu Static uebergehen, mit Animation.
129                                t29.menu.side.fadeOut(function(){
130                                        t29.menu.scroll.set(t29.menu.scroll.States.STATIC); });
131                                break;
132                        case t29.menu.scroll.States.STICK_TOP:
133                        default:
134                                // diese Faelle sollten nicht vorkommen.
135                                log("Get-Menu Scroll-Button gedrückt obwohl unmöglich; state="+t29.menu.scroll.state);
136                }
137        }); // end event t29.menu.scroll.but.click.
138       
139        // nun ein paar Y-Koordinaten. berechnet mit dem Ausgangs-menu.side (STATIC).
140        t29.menu.scroll.origin_top = t29.menu.side.offset().top;
141        t29.menu.scroll.max_bottom = $("footer").offset().top - t29.menu.side.height();
142        t29.menu.scroll.stick_bottom = $("footer").offset().top - t29.menu.side.height() - $("#background-color-container").offset().top;
143        t29.menu.scroll.button_max_bottom = $("footer").offset().top;
144        //t29.menu.scroll.max_bottom - $("#background-color-container").offset().top;
145
146        $(window).scroll(function(){
147                var y = $(this).scrollTop();
148
149                switch(t29.menu.scroll.state) {
150                        case t29.menu.scroll.States.STATIC: break; // System inaktiv.
151                        case t29.menu.scroll.States.FIX: 
152                                if(y < t29.menu.scroll.origin_top)
153                                        t29.menu.scroll.set(t29.menu.scroll.States.STICK_TOP);
154                                else if(y > t29.menu.scroll.max_bottom)
155                                        t29.menu.scroll.set(t29.menu.scroll.States.STICK_BOTTOM);
156                                break;
157                        case t29.menu.scroll.States.STICK_TOP:
158                                if(y > t29.menu.scroll.origin_top) {
159                                        // wir sind wieder weiter runter gescrollt.
160                                        if(t29.menu.collapsed.is())
161                                                // und der Benutzer hat zwischenzeitlich nicht das Menue ausgeklappt
162                                                t29.menu.scroll.set(t29.menu.scroll.States.FIX);
163                                        else
164                                                // der Benutzer hat zwischenzeitlich ausgeklappt. Schalte fixing aus.
165                                                t29.menu.scroll.set(t29.menu.scroll.States.STATIC);
166                                }
167                                break;
168                        case t29.menu.scroll.States.STICK_BOTTOM:
169                                if(y < t29.menu.scroll.max_bottom) {
170                                        // wir sind wieder weiter hoch gescrollt. Entcollapsen bieten wir ganz
171                                        // unten nicht an. Ergo: Fixing wieder einschalten.
172                                        t29.menu.scroll.set(t29.menu.scroll.States.FIX);
173                                }
174                                break;
175                }
176
177                // Sichtbarkeit des Fixed-Buttons am unteren Seitenrand
178                // festlegen:
179                if(y + $(window).height() > t29.menu.scroll.button_max_bottom) {
180                        $("html").addClass('button-stick-bottom');
181                } else if($("html").hasClass('button-stick-bottom')) {
182                        $("html").removeClass('button-stick-bottom');
183                }
184        }); // end event window.scroll.
185}; // end t29.menu.scroll.setup.
186
187
188//////////////////////////// Footer Guided Tour System (auch Menu)
189t29.menu.guide.setup = function() {
190        // Zentraler Hauptschritt: Das Menue ab oberster Ebene klonen und im Footer dranhaengen,
191        // ausserdem ein paar Ummodellierungen.
192        g = t29.menu.beam;
193        t29.menu.side.find(".u1").clone().appendTo(g);
194        g.find("ul").show(); // durch t29.menu.collapse.setup wurden die .u3er auf hide gesetzt. Revert!
195        g.find(".geraete").remove(); // geraete-Links nicht anzeigen
196       
197
198        // Texte ersetzen durch laengere verstaendlichere Beschreibungen im title
199        g.find("a[title]").each(function(){
200                $(this).text( $(this).attr('title') );
201        });
202
203        // Abkuerzungen und Wrappings
204        a = g.find("a"); li = g.find("li");
205        a.wrapInner("<span class='text'/>").append("<span class='bullet'/>");
206
207        // Punkte aequidistant verteilen
208        count = a.length;
209        bwidth = $(".bullet",g).outerWidth();
210        each_width = (g.width() + bwidth*2) / count;
211        a.width(Math.floor(each_width));
212        // text-Label zentriert darstellen um den Punkt
213        $(".text", a).css("left", function(){return(bwidth - $(this).width())/2; });
214       
215        default_visibles = g.find(".start, .end, .current");
216        default_visibles.addClass("visible"); //.find("a").css("z-index",0);
217        default_visibles = default_visibles.find("a:first-child"); // von li auf a
218       
219        // Overlappings finden
220        // left,right: Funktionen geben links/rechts-Offset des Objekts wieder
221        left = function($o) { return $o.offset().left; }
222        right = function($o) { return $o.offset().left + $o.width(); }
223        edges = default_visibles.map(function(){
224                t = $(".text", this);
225                return {'left': left(t), 'right': right(t) };
226        });
227        min_left = Math.min.apply(null, edges.map(function(){ return this.left }));
228        max_right = Math.max.apply(null, edges.map(function(){ return this.right; }));
229        a.not(default_visibles).each(function(){
230                t = $(".text", this); this_a = $(this);
231                l = left(t); r = right(t);
232                edges.each(function(i){
233                        if((l < this.right && l > this.left) || // rechte kante drin
234                           (r > this.left && r < this.right) || // linke kante drin
235                           (l < this.right && l < min_left)  ||
236                           (r > this.left && r > max_right)) {
237                                        this_a.addClass("higher-text");
238                        }
239                });
240        });
241       
242        // Split position for relative navigation
243        // 20px von nav.side margin left; 40px = 4*10px padding left von nav.rel a
244        ///// 22.04.2012: Deaktiviert, weil anderes Design vor Augen.
245        /*
246        split = $(".current a",g).offset().left - g.offset().left + bwidth/2;
247        rest = $("#content").outerWidth() - split - 40;
248        t29.menu.rel.find(".prev a").width(split);
249        t29.menu.rel.find(".next a").width(rest);
250        */
251};
252
253$(t29.menu.setup);
Note: See TracBrowser for help on using the repository browser.
© 2008 - 2013 technikum29 • Sven Köppel • Some rights reserved
Powered by Trac
Expect where otherwise noted, content on this site is licensed under a Creative Commons 3.0 License