source: tailbone/tailbone/templates/themes/bobcat/base.mako @ c1eaf28

Last change on this file since c1eaf28 was c1eaf28, checked in by Lance Edgar <lance@…>, 15 months ago

Add support for top-level links for simple menus

also add 'messaging_enabled' to global template context, so can include (or
not) that stuff in the user menu

  • Property mode set to 100644
File size: 10.2 KB
Line 
1## -*- coding: utf-8; -*-
2<%namespace file="/grids/nav.mako" import="grid_index_nav" />
3<%namespace file="/feedback_dialog.mako" import="feedback_dialog" />
4<%namespace name="base_meta" file="/base_meta.mako" />
5<!DOCTYPE html>
6<html lang="en">
7  <head>
8    <meta http-equiv="content-type" content="text/html; charset=UTF-8" />
9    <title>${base_meta.global_title()} &raquo; ${capture(self.title)|n}</title>
10    ${base_meta.favicon()}
11    ${self.header_core()}
12
13    % if not request.rattail_config.production():
14        <style type="text/css">
15          body { background-image: url(${request.static_url('tailbone:static/img/testing.png')}); }
16        </style>
17    % endif
18
19    ${self.head_tags()}
20  </head>
21
22  <body>
23    <header>
24
25      <nav class="navbar" role="navigation" aria-label="main navigation">
26        <div class="navbar-menu">
27          <div class="navbar-start">
28
29            % for topitem in menus:
30                % if topitem.is_link:
31                    ${h.link_to(topitem.title, topitem.url, target=topitem.target, class_='navbar-item')}
32                % else:
33                    <div class="navbar-item has-dropdown is-hoverable">
34                      <a class="navbar-link">${topitem.title}</a>
35                      <div class="navbar-dropdown">
36                        % for subitem in topitem.items:
37                            % if subitem.is_sep:
38                                <hr class="navbar-divider">
39                            % else:
40                                ${h.link_to(subitem.title, subitem.url, class_='navbar-item', target=subitem.target)}
41                            % endif
42                        % endfor
43                      </div>
44                    </div>
45                % endif
46            % endfor
47
48          </div><!-- navbar-start -->
49          <div class="navbar-end">
50
51            ## User Menu
52            % if request.user:
53                <div class="navbar-item has-dropdown is-hoverable">
54                  % if messaging_enabled:
55                      <a class="navbar-link ${'root-user' if request.is_root else ''}">${request.user}${" ({})".format(inbox_count) if inbox_count else ''}</a>
56                  % else:
57                      <a class="navbar-link ${'root-user' if request.is_root else ''}">${request.user}</a>
58                  % endif
59                  <div class="navbar-dropdown">
60                    % if request.is_root:
61                        ${h.link_to("Stop being root", url('stop_root'), class_='navbar-item root-user')}
62                    % elif request.is_admin:
63                        ${h.link_to("Become root", url('become_root'), class_='navbar-item root-user')}
64                    % endif
65                    % if messaging_enabled:
66                        ${h.link_to("Messages{}".format(" ({})".format(inbox_count) if inbox_count else ''), url('messages.inbox'), class_='navbar-item')}
67                    % endif
68                    ${h.link_to("Change Password", url('change_password'), class_='navbar-item')}
69                    ${h.link_to("Logout", url('logout'), class_='navbar-item')}
70                  </div>
71                </div>
72            % else:
73                ${h.link_to("Login", url('login'), class_='navbar-item')}
74            % endif
75
76          </div><!-- navbar-end -->
77        </div>
78      </nav>
79
80      <nav class="level">
81        <div class="level-left">
82
83          ## App Logo / Name
84          <div class="level-item">
85            <a class="home" href="${url('home')}">
86              <div id="header-logo">${base_meta.header_logo()}</div>
87              <span class="global-title">${base_meta.global_title()}</span>
88            </a>
89          </div>
90
91          ## Current Context
92          <div id="current-context" class="level-item">
93            % if master:
94                <span>&raquo;</span>
95                % if master.listing:
96                    <span>${index_title}</span>
97                % else:
98                    ${h.link_to(index_title, index_url)}
99                    % if parent_url is not Undefined:
100                        <span>&raquo;</span>
101                        ${h.link_to(parent_title, parent_url)}
102                    % elif instance_url is not Undefined:
103                        <span>&raquo;</span>
104                        ${h.link_to(instance_title, instance_url)}
105                    % endif
106                    % if master.viewing and grid_index:
107                        ${grid_index_nav()}
108                    % endif
109                % endif
110            % elif index_title:
111                <span>&raquo;</span>
112                <span>${index_title}</span>
113            % endif
114          </div>
115
116        </div><!-- level-left -->
117        <div class="level-right">
118
119          ## Theme Picker
120          % if expose_theme_picker and request.has_perm('common.change_app_theme'):
121              <div class="level-item">
122                ${h.form(url('change_theme'), method="post")}
123                ${h.csrf_token(request)}
124                Theme:
125                <div class="theme-picker">
126                  <div class="select">
127                    ${h.select('theme', theme, options=theme_picker_options, id='theme-picker')}
128                  </div>
129                </div>
130                ${h.end_form()}
131              </div>
132          % endif
133
134          ## Help Button
135          % if help_url is not Undefined and help_url:
136              <div class="level-item">
137                ${h.link_to("Help", help_url, target='_blank', class_='button')}
138              </div>
139          % endif
140
141          ## Feedback Button
142          <div class="level-item">
143            <button type="button" class="button is-primary" id="feedback">Feedback</button>
144          </div>
145
146        </div><!-- level-right -->
147      </nav><!-- level -->
148    </header>
149
150    ## Page Title
151    <section id="content-title" class="hero is-primary">
152      <div class="container">
153        ${self.content_title()}
154      </div>
155    </section>
156
157    ## Page Body
158    <section id="page-body">
159
160      % if request.session.peek_flash('error'):
161          % for error in request.session.pop_flash('error'):
162              <div class="notification is-warning">
163                <!-- <button class="delete"></button> -->
164                ${error}
165              </div>
166          % endfor
167      % endif
168
169      % if request.session.peek_flash():
170          % for msg in request.session.pop_flash():
171              <div class="notification is-info">
172                <!-- <button class="delete"></button> -->
173                ${msg}
174              </div>
175          % endfor
176      % endif
177
178      ${self.body()}
179    </section>
180
181    ## Feedback Dialog
182    ${feedback_dialog()}
183
184    ## Footer
185    <footer class="footer">
186      <div class="content">
187        ${base_meta.footer()}
188      </div>
189    </footer>
190
191  </body>
192</html>
193
194<%def name="title()"></%def>
195
196<%def name="content_title()">
197  <h1 class="title">${self.title()}</h1>
198</%def>
199
200<%def name="header_core()">
201
202  ${self.core_javascript()}
203  ${self.extra_javascript()}
204  ${self.core_styles()}
205  ${self.extra_styles()}
206
207  ## TODO: should this be elsewhere / more customizable?
208  % if dform is not Undefined:
209      <% resources = dform.get_widget_resources() %>
210      % for path in resources['js']:
211          ${h.javascript_link(request.static_url(path))}
212      % endfor
213      % for path in resources['css']:
214          ${h.stylesheet_link(request.static_url(path))}
215      % endfor
216  % endif
217</%def>
218
219<%def name="core_javascript()">
220  ${self.jquery()}
221  ${h.javascript_link(request.static_url('tailbone:static/js/lib/jquery.loadmask.min.js'))}
222  ${h.javascript_link(request.static_url('tailbone:static/js/lib/jquery.ui.timepicker.js'))}
223  <script type="text/javascript">
224    var session_timeout = ${request.get_session_timeout() or 'null'};
225    var logout_url = '${request.route_url('logout')}';
226    var noop_url = '${request.route_url('noop')}';
227    % if expose_theme_picker and request.has_perm('common.change_app_theme'):
228        $(function() {
229            $('#theme-picker').change(function() {
230                $(this).parents('form:first').submit();
231            });
232        });
233    % endif
234  </script>
235  ${h.javascript_link(request.static_url('tailbone:static/js/tailbone.js') + '?ver={}'.format(tailbone.__version__))}
236  ${h.javascript_link(request.static_url('tailbone:static/js/tailbone.feedback.js') + '?ver={}'.format(tailbone.__version__))}
237  ${h.javascript_link(request.static_url('tailbone:static/js/jquery.ui.tailbone.js') + '?ver={}'.format(tailbone.__version__))}
238</%def>
239
240<%def name="jquery()">
241  ${h.javascript_link('https://code.jquery.com/jquery-1.12.4.min.js')}
242  ${h.javascript_link('https://code.jquery.com/ui/{}/jquery-ui.min.js'.format(request.rattail_config.get('tailbone', 'jquery_ui.version', default='1.11.4')))}
243</%def>
244
245<%def name="extra_javascript()"></%def>
246
247<%def name="core_styles()">
248
249  ${h.stylesheet_link('https://cdnjs.cloudflare.com/ajax/libs/bulma/0.7.2/css/bulma.min.css')}
250
251  ${self.jquery_theme()}
252  ${h.stylesheet_link(request.static_url('tailbone:static/css/jquery.loadmask.css'))}
253  ${h.stylesheet_link(request.static_url('tailbone:static/css/jquery.ui.timepicker.css'))}
254  ${h.stylesheet_link(request.static_url('tailbone:static/css/jquery.ui.tailbone.css') + '?ver={}'.format(tailbone.__version__))}
255
256  ${h.stylesheet_link(request.static_url('tailbone:static/themes/bobcat/css/base.css') + '?ver={}'.format(tailbone.__version__))}
257  ${h.stylesheet_link(request.static_url('tailbone:static/themes/bobcat/css/layout.css') + '?ver={}'.format(tailbone.__version__))}
258  ${h.stylesheet_link(request.static_url('tailbone:static/css/grids.css') + '?ver={}'.format(tailbone.__version__))}
259  ${h.stylesheet_link(request.static_url('tailbone:static/css/filters.css') + '?ver={}'.format(tailbone.__version__))}
260  ${h.stylesheet_link(request.static_url('tailbone:static/themes/bobcat/css/forms.css') + '?ver={}'.format(tailbone.__version__))}
261  ${h.stylesheet_link(request.static_url('tailbone:static/css/diffs.css') + '?ver={}'.format(tailbone.__version__))}
262</%def>
263
264<%def name="jquery_theme()">
265  ${h.stylesheet_link('https://code.jquery.com/ui/1.11.4/themes/dark-hive/jquery-ui.css')}
266</%def>
267
268<%def name="extra_styles()"></%def>
269
270<%def name="head_tags()"></%def>
271
272<%def name="wtfield(form, name, **kwargs)">
273  <div class="field-wrapper${' error' if form[name].errors else ''}">
274    <label for="${name}">${form[name].label}</label>
275    <div class="field">
276      ${form[name](**kwargs)}
277    </div>
278  </div>
279</%def>
Note: See TracBrowser for help on using the repository browser.