diff --git a/applications/luci-app-firewall/luasrc/view/firewall/cbi_addforward.htm b/applications/luci-app-firewall/luasrc/view/firewall/cbi_addforward.htm index 279b6e06d6..f48599b505 100644 --- a/applications/luci-app-firewall/luasrc/view/firewall/cbi_addforward.htm +++ b/applications/luci-app-firewall/luasrc/view/firewall/cbi_addforward.htm @@ -18,95 +18,91 @@ vals[#vals+1] = '%s (%s)' %{ ip, name } end) -%> -
-
-
-
-
<%:New port forward%>:
+ +

<%:New port forward%>

+
+
+
<%:Name%>
+
<%:Protocol%>
+
<%:External zone%>
+
<%:External port%>
+
<%:Internal zone%>
+
<%:Internal IP address%>
+
<%:Internal port%>
+
+
+
+
+
-
-
<%:Name%>
-
<%:Protocol%>
-
<%:External zone%>
-
<%:External port%>
-
<%:Internal zone%>
-
<%:Internal IP address%>
-
<%:Internal port%>
-
+
+
-
-
- -
-
- -
-
- -
-
- -
-
- -
-
- 0, "data-choices", {keys, vals}) - %>/> -
-
- -
-
- -
+
+ +
+
+ +
+
+ +
+
+ 0, "data-choices", {keys, vals}) + %>/> +
+
+ +
+
+
- -
+ + diff --git a/applications/luci-app-firewall/luasrc/view/firewall/cbi_addrule.htm b/applications/luci-app-firewall/luasrc/view/firewall/cbi_addrule.htm index c99ecaca37..273675cd30 100644 --- a/applications/luci-app-firewall/luasrc/view/firewall/cbi_addrule.htm +++ b/applications/luci-app-firewall/luasrc/view/firewall/cbi_addrule.htm @@ -5,112 +5,105 @@ local zones = fw:get_zones() %> -
- <% if wz then %> -
-
-
-
<%:Open ports on router%>:
+<% if wz then %> +

<%:Open ports on router%>

+
+
+
<%:Name%>
+
<%:Protocol%>
+
<%:External port%>
+
+
+
+
+
-
-
<%:Name%>
-
<%:Protocol%>
-
<%:External port%>
-
+
+
-
-
- -
-
- -
-
- -
-
- -
+
+ +
+
+
- <% end %> - <% if #zones > 1 then %> -
-
-

<%:New forward rule%>:
+
+<% end %> +<% if #zones > 1 then %> +

<%:New forward rule%>

+
+
+
<%:Name%>
+
<%:Source zone%>
+
<%:Destination zone%>
+
+
+
+
+
-
-
<%:Name%>
-
<%:Source zone%>
-
<%:Destination zone%>
-
+
+
-
-
- -
-
- -
-
- -
-
- -
+
+ +
+
+
- <% else %> - - <% end %> +
+<% else %> + +<% end %> - <% if wz then %> - - <% end %> -
+ cbi_validate_field('cbi.cts.<%=self.config%>.<%=self.sectiontype%>.<%=section%>', true, 'uciname'); + //]]> +<% end %> diff --git a/applications/luci-app-firewall/luasrc/view/firewall/cbi_addsnat.htm b/applications/luci-app-firewall/luasrc/view/firewall/cbi_addsnat.htm index b2775cf694..0b4774ccc0 100644 --- a/applications/luci-app-firewall/luasrc/view/firewall/cbi_addsnat.htm +++ b/applications/luci-app-firewall/luasrc/view/firewall/cbi_addsnat.htm @@ -12,53 +12,48 @@ end %> -
- <% if #zones > 1 then %> -
-
-
-
<%:New source NAT%>:
+<% if #zones > 1 then %> +

<%:New source NAT%>

+
+
+
<%:Name%>
+
<%:Source zone%>
+
<%:Destination zone%>
+
<%:To source IP%>
+
<%:To source port%>
+
+
+
+
+
-
-
<%:Name%>
-
<%:Source zone%>
-
<%:Destination zone%>
-
<%:To source IP%>
-
<%:To source port%>
-
+
+
-
-
- -
-
- -
-
- -
-
- 0, "data-choices", { keys, vals }) - %> /> -
-
- -
-
- -
+
+ +
+
+ 0, "data-choices", { keys, vals }) + %> /> +
+
+ +
+
+
- <% else %> - - <% end %> -
+
+<% else %> + +<% end %> diff --git a/applications/luci-app-shadowsocks-libev/luasrc/view/shadowsocks-libev/add_instance.htm b/applications/luci-app-shadowsocks-libev/luasrc/view/shadowsocks-libev/add_instance.htm index 80b95564dd..f016dd47e6 100644 --- a/applications/luci-app-shadowsocks-libev/luasrc/view/shadowsocks-libev/add_instance.htm +++ b/applications/luci-app-shadowsocks-libev/luasrc/view/shadowsocks-libev/add_instance.htm @@ -1,24 +1,17 @@
-
-
-
-
- -
-
- -
-
- -
-
+
+
+
+ +
+
+
<%=translatef("Provides an overview of all configured uplinks for the travelmate interface (%s). You can edit, delete or re-order existing uplinks or scan for a new one. The currently used uplink is emphasized in blue.", trmiface)%>
-
-
+
+
-
<%:Device%>
-
<%:SSID%>
-
<%:BSSID%>
-
<%:Encryption%>
-
<%:Actions%>
+
<%:Device%>
+
<%:SSID%>
+
<%:BSSID%>
+
<%:Encryption%>
+
 
<% uci:foreach("wireless", "wifi-iface", function(s) @@ -45,11 +47,9 @@ This is free software, licensed under the Apache License, Version 2.0
<%=ssid%>
<%=bssid%>
<%=encryption%>
-
- - -
-
+
+ +
@@ -59,7 +59,7 @@ This is free software, licensed under the Apache License, Version 2.0 end) %>
-
+
<% uci:foreach("wireless", "wifi-device", function(s) @@ -68,7 +68,7 @@ This is free software, licensed under the Apache License, Version 2.0
- +
<% end) diff --git a/applications/luci-app-travelmate/luasrc/view/travelmate/wifi_scan.htm b/applications/luci-app-travelmate/luasrc/view/travelmate/wifi_scan.htm index 81182b99b4..57efd97376 100644 --- a/applications/luci-app-travelmate/luasrc/view/travelmate/wifi_scan.htm +++ b/applications/luci-app-travelmate/luasrc/view/travelmate/wifi_scan.htm @@ -39,31 +39,33 @@ This is free software, licensed under the Apache License, Version 2.0 <%+header%> + +

<%:Wireless Scan%>

-
-
+
+
-
<%:Uplink SSID%>
-
<%:Uplink BSSID%>
-
<%:Encryption%>
-
<%:Signal strength%>
+
<%:Uplink SSID%>
+
<%:Uplink BSSID%>
+
<%:Encryption%>
+
<%:Signal strength%>
<% for i, net in ipairs(iw.scanlist or { }) do %>
-
+
<%=net.ssid and utl.pcdata(net.ssid) or "%s" % translate("hidden")%>
-
+
<%=net.bssid and utl.pcdata(net.bssid)%>
-
+
<%=format_wifi_encryption(net.encryption)%>
-
+
<%=percent_wifi_signal(net)%> %
-
+
@@ -80,16 +82,16 @@ This is free software, licensed under the Apache License, Version 2.0
<% end %>
-
+
+ + +
-
- -
diff --git a/applications/luci-app-upnp/luasrc/view/upnp_status.htm b/applications/luci-app-upnp/luasrc/view/upnp_status.htm index 1e09225793..459c63c1d7 100644 --- a/applications/luci-app-upnp/luasrc/view/upnp_status.htm +++ b/applications/luci-app-upnp/luasrc/view/upnp_status.htm @@ -16,40 +16,39 @@ var tb = document.getElementById('upnp_status_table'); if (st && tb) { - /* clear all rows */ - while (tb.firstElementChild !== tb.lastElementChild) - tb.removeChild(tb.lastElementChild); + var rows = []; for (var i = 0; i < st.length; i++) - tb.appendChild(E('
'.format((i % 2) + 1), [ - E('
', st[i].proto), - E('
', st[i].extport), - E('
', st[i].intaddr), - E('
', st[i].intport), - E('
', st[i].descr), - E(''.format(st[i].num)) - ])); + rows.push([ + st[i].proto, + st[i].extport, + st[i].intaddr, + st[i].intport, + st[i].descr, + E(''.format(st[i].num)) + ]); - if (tb.firstElementChild === tb.lastElementChild) - tb.appendChild(E('

<%:There are no active redirects.%>
')); + cbi_update_table(tb, rows, '<%:There are no active redirects.%>'); } } ); //]]> -
+
<%:Active UPnP Redirects%> -
-
-
<%:Protocol%>
-
<%:External Port%>
-
<%:Client Address%>
-
<%:Client Port%>
-
<%:Description%>
-
 
-
-
-

<%:Collecting data...%>
+
+
+
+
<%:Protocol%>
+
<%:External Port%>
+
<%:Client Address%>
+
<%:Client Port%>
+
<%:Description%>
+
 
+
+
+
<%:Collecting data...%>
+
-
+
diff --git a/modules/luci-base/htdocs/luci-static/resources/cbi.js b/modules/luci-base/htdocs/luci-static/resources/cbi.js index a7f999d876..6a487366f8 100644 --- a/modules/luci-base/htdocs/luci-static/resources/cbi.js +++ b/modules/luci-base/htdocs/luci-static/resources/cbi.js @@ -620,7 +620,11 @@ function cbi_init() { } document.querySelectorAll('.cbi-dropdown').forEach(function(s) { - cbi_dropdown_init(s); + cbi_dropdown_init(s); + }); + + document.querySelectorAll('.cbi-tooltip:not(:empty)').forEach(function(s) { + s.parentNode.classList.add('cbi-tooltip-container'); }); cbi_d_update(); @@ -1232,14 +1236,13 @@ function cbi_validate_field(cbid, optional, type) function cbi_row_swap(elem, up, store) { - var tr = elem.parentNode; - - while (tr && !tr.classList.contains('cbi-section-table-row')) - tr = tr.parentNode; + var tr = findParent(elem.parentNode, '.cbi-section-table-row'); if (!tr) return false; + tr.classList.remove('flash'); + if (up) { var prev = tr.previousElementSibling; @@ -1277,6 +1280,9 @@ function cbi_row_swap(elem, up, store) if (input) input.value = ids.join(' '); + window.scrollTo(0, tr.offsetTop); + window.setTimeout(function() { tr.classList.add('flash'); }, 1); + return false; } @@ -1522,6 +1528,19 @@ function toElem(s) return elem || null; } +function findParent(node, selector) +{ + while (node) + if (node.msMatchesSelector && node.msMatchesSelector(selector)) + return node; + else if (node.matches && node.matches(selector)) + return node; + else + node = node.parentNode; + + return null; +} + function E() { var html = arguments[0], @@ -1541,7 +1560,7 @@ function E() if (attr) for (var key in attr) - if (attr.hasOwnProperty(key)) + if (attr.hasOwnProperty(key) && attr[key] !== null && attr[key] !== undefined) elem.setAttribute(key, attr[key]); if (typeof(data) === 'function') @@ -1818,18 +1837,6 @@ CBIDropdown = { document.querySelectorAll('.cbi-dropdown[open]').forEach(function(s) { s.dispatchEvent(new CustomEvent('cbi-dropdown-close', {})); }); - }, - - findParent: function(node, selector) { - while (node) - if (node.msMatchesSelector && node.msMatchesSelector(selector)) - return node; - else if (node.matches && node.matches(selector)) - return node; - else - node = node.parentNode; - - return null; } }; @@ -1908,7 +1915,7 @@ function cbi_dropdown_init(sb) { sbox.openDropdown(this); } else { - var li = sbox.findParent(ev.target, 'li'); + var li = findParent(ev.target, 'li'); if (li && li.parentNode.classList.contains('dropdown')) sbox.toggleItem(this, li); } @@ -1933,7 +1940,7 @@ function cbi_dropdown_init(sb) { } else { - var active = sbox.findParent(document.activeElement, 'li'); + var active = findParent(document.activeElement, 'li'); switch (ev.keyCode) { case 27: @@ -1986,7 +1993,7 @@ function cbi_dropdown_init(sb) { if (!this.hasAttribute('open')) return; - var li = sbox.findParent(ev.target, 'li'); + var li = findParent(ev.target, 'li'); if (li) { if (li.parentNode.classList.contains('dropdown')) sbox.setFocus(this, li); @@ -2023,18 +2030,18 @@ function cbi_dropdown_init(sb) { }); create.addEventListener('focus', function(ev) { - var cbox = sbox.findParent(this, 'li').querySelector('input[type="checkbox"]'); + var cbox = findParent(this, 'li').querySelector('input[type="checkbox"]'); if (cbox) cbox.checked = true; sb.setAttribute('locked-in', ''); }); create.addEventListener('blur', function(ev) { - var cbox = sbox.findParent(this, 'li').querySelector('input[type="checkbox"]'); + var cbox = findParent(this, 'li').querySelector('input[type="checkbox"]'); if (cbox) cbox.checked = false; sb.removeAttribute('locked-in'); }); - var li = sbox.findParent(create, 'li'); + var li = findParent(create, 'li'); li.setAttribute('unselectable', ''); li.addEventListener('click', function(ev) { @@ -2044,3 +2051,77 @@ function cbi_dropdown_init(sb) { } cbi_dropdown_init.prototype = CBIDropdown; + +function cbi_update_table(table, data, placeholder) { + target = isElem(table) ? table : document.querySelector(table); + + if (!isElem(target)) + return; + + target.querySelectorAll('.tr.table-titles, .cbi-section-table-titles').forEach(function(thead) { + var titles = []; + + thead.querySelectorAll('.th').forEach(function(th) { + titles.push(th); + }); + + if (Array.isArray(data)) { + var n = 0, rows = target.querySelectorAll('.tr'); + + data.forEach(function(row) { + var trow = E('div', { 'class': 'tr' }); + + for (var i = 0; i < titles.length; i++) { + var text = titles[i].innerText; + var td = trow.appendChild(E('div', { + 'class': titles[i].className, + 'data-title': text ? text.trim() : null + }, row[i] || '')); + + td.classList.remove('th'); + td.classList.add('td'); + } + + trow.classList.add('cbi-rowstyle-%d'.format((n++ % 2) ? 2 : 1)); + + if (rows[n]) + target.replaceChild(trow, rows[n]); + else + target.appendChild(trow); + }); + + while (rows[++n]) + target.removeChild(rows[n]); + + if (placeholder && target.firstElementChild === target.lastElementChild) { + var trow = target.appendChild(E('div', { 'class': 'tr placeholder' })); + var td = trow.appendChild(E('div', { 'class': titles[0].className }, placeholder)); + + td.classList.remove('th'); + td.classList.add('td'); + } + } + else { + thead.parentNode.style.display = 'none'; + + thead.parentNode.querySelectorAll('.tr, .cbi-section-table-row').forEach(function(trow) { + if (trow !== thead) { + var n = 0; + trow.querySelectorAll('.th, .td').forEach(function(td) { + if (n < titles.length) { + var text = (titles[n++].innerText || '').trim(); + if (text !== '') + td.setAttribute('data-title', text); + } + }); + } + }); + + thead.parentNode.style.display = ''; + } + }); +} + +document.addEventListener('DOMContentLoaded', function() { + document.querySelectorAll('.table').forEach(cbi_update_table); +}); diff --git a/modules/luci-base/luasrc/view/cbi/apply_widget.htm b/modules/luci-base/luasrc/view/cbi/apply_widget.htm index 702512f495..e3090da656 100644 --- a/modules/luci-base/luasrc/view/cbi/apply_widget.htm +++ b/modules/luci-base/luasrc/view/cbi/apply_widget.htm @@ -47,7 +47,7 @@ } - + -
-
-
-
-
- ? -
-
- <%:Collecting data...%> -
-
-
+ + + + <%:Collecting data...%> + + <%+cbi/valuefooter%> diff --git a/modules/luci-mod-admin-full/luasrc/view/admin_network/lease_status.htm b/modules/luci-mod-admin-full/luasrc/view/admin_network/lease_status.htm index 9005279a4e..a1b2c8454d 100644 --- a/modules/luci-mod-admin-full/luasrc/view/admin_network/lease_status.htm +++ b/modules/luci-mod-admin-full/luasrc/view/admin_network/lease_status.htm @@ -34,7 +34,7 @@ else timestr = String.format('%t', st[0][i].expires); - tb.appendChild(E('
'.format((i % 2) + 1), [ + tb.appendChild(E('
'.format((i % 2) + 1), [ E('
', st[0][i].hostname || '?'), E('
', st[0][i].ipaddr), E('
', st[0][i].macaddr), @@ -43,7 +43,7 @@ } if (tb.firstElementChild === tb.lastElementChild) - tb.appendChild(E('

<%:There are no active leases.%>
')); + tb.appendChild(E('

<%:There are no active leases.%>
')); } var tb6 = document.getElementById('lease6_status_table'); @@ -79,8 +79,8 @@ hint = host.name; } - tb6.appendChild(E('
'.format((i % 2) + 1), [ - E('
', hint ? '
%h (%h)
'.format(name || '?', hint) : (name || '?')), + tb6.appendChild(E('
'.format((i % 2) + 1), [ + E('
', hint ? '%h (%h)'.format(name || '?', hint) : (name || '?')), E('
', st[1][i].ip6addr), E('
', st[1][i].duid), E('
', timestr) @@ -88,7 +88,7 @@ } if (tb6.firstElementChild === tb6.lastElementChild) - tb6.appendChild(E('

<%:There are no active leases.%>
')); + tb6.appendChild(E('

<%:There are no active leases.%>
')); } } ); @@ -96,14 +96,14 @@
<%:Active DHCP Leases%> -
-
-
<%:Hostname%>
-
<%:IPv4-Address%>
-
<%:MAC-Address%>
-
<%:Leasetime remaining%>
+
+
+
<%:Hostname%>
+
<%:IPv4-Address%>
+
<%:MAC-Address%>
+
<%:Leasetime remaining%>
-
+

<%:Collecting data...%>
@@ -111,14 +111,14 @@
-
+
<%:IPv6 Neighbours%> -
-
-
-
<%:IPv6-Address%>
-
<%:MAC-Address%>
-
<%:Interface%>
+
+
+
<%:IPv6-Address%>
+
<%:MAC-Address%>
+
<%:Interface%>
<% for _, v in ipairs(ip.neighbors({ family = 6 })) do if v.dest and not v.dest:is6linklocal() and v.mac then %> -
-
<%=v.dest%>
-
<%=v.mac%>
-
<%=luci.tools.webadmin.iface_get_network(v.dev) or '(' .. v.dev .. ')'%>
+
+
<%=v.dest%>
+
<%=v.mac%>
+
<%=luci.tools.webadmin.iface_get_network(v.dev) or '(' .. v.dev .. ')'%>
<% style = not style @@ -154,8 +150,7 @@ %>
-
-
+
<% end %>
diff --git a/modules/luci-mod-admin-full/luasrc/view/admin_system/flashops.htm b/modules/luci-mod-admin-full/luasrc/view/admin_system/flashops.htm index b32ef78263..9eec012547 100644 --- a/modules/luci-mod-admin-full/luasrc/view/admin_system/flashops.htm +++ b/modules/luci-mod-admin-full/luasrc/view/admin_system/flashops.htm @@ -13,84 +13,78 @@
  • <%:Configuration%>
  • -
    - -
    - <%:Backup / Restore%> -
    <%:Click "Generate archive" to download a tar archive of the current configuration files. To reset the firmware to its initial state, click "Perform reset" (only possible with squashfs images).%>
    -
    -
    - -
    - -
    - -
    +
    + <%:Backup / Restore%> +
    <%:Click "Generate archive" to download a tar archive of the current configuration files. To reset the firmware to its initial state, click "Perform reset" (only possible with squashfs images).%>
    +
    + + +
    + +
    +
    - - <% if reset_avail then %> -
    - -
    - -
    - -
    -
    -
    - <% end %> -
    -
    -
    <%:To restore configuration files, you can upload a previously generated backup archive here.%>
    -
    -
    -
    - -
    - - - -
    -
    -
    -
    +
    + <% if reset_avail then %> -
    <%:Custom files (certificates, scripts) may remain on the system. To prevent this, perform a factory-reset first.%>
    +
    + +
    + +
    + +
    +
    +
    <% end %> -
    - +

    +
    <%:To restore configuration files, you can upload a previously generated backup archive here.%>
    +
    +
    +
    + +
    + + + +
    +
    +
    +
    + <% if reset_avail then %> +
    <%:Custom files (certificates, scripts) may remain on the system. To prevent this, perform a factory-reset first.%>
    + <% end %> +
    -
    - <%:Flash new firmware image%> - <% if upgrade_avail then %> -
    - -
    <%:Upload a sysupgrade-compatible image here to replace the running firmware. Check "Keep settings" to retain the current configuration (requires a compatible firmware image).%>
    -
    -
    - -
    - -
    -
    -
    - -
    - - -
    +
    + <%:Flash new firmware image%> + <% if upgrade_avail then %> + + +
    <%:Upload a sysupgrade-compatible image here to replace the running firmware. Check "Keep settings" to retain the current configuration (requires a compatible firmware image).%>
    +
    +
    + +
    +
    - <% if image_invalid then %> -
    <%:The uploaded image file does not contain a supported format. Make sure that you choose the generic image format for your platform. %>
    - <% end %> - - <% else %> -
    <%:Sorry, there is no sysupgrade support present; a new firmware image must be flashed manually. Please refer to the wiki for device specific install instructions.%>
    - <% end %> -
    - - +
    + +
    + + +
    +
    +
    + <% if image_invalid then %> +
    <%:The uploaded image file does not contain a supported format. Make sure that you choose the generic image format for your platform. %>
    + <% end %> + + <% else %> +
    <%:Sorry, there is no sysupgrade support present; a new firmware image must be flashed manually. Please refer to the wiki for device specific install instructions.%>
    + <% end %> +
    <%+footer%> diff --git a/modules/luci-mod-admin-full/luasrc/view/admin_system/packages.htm b/modules/luci-mod-admin-full/luasrc/view/admin_system/packages.htm index 4944a232b2..ef13a91672 100644 --- a/modules/luci-mod-admin-full/luasrc/view/admin_system/packages.htm +++ b/modules/luci-mod-admin-full/luasrc/view/admin_system/packages.htm @@ -44,6 +44,8 @@ end <%+header%> + +

    <%:Software%>

    @@ -57,8 +59,8 @@ end -
    -
    +
    +
    <% if (install and next(install)) or (remove and next(remove)) or update or upgrade then %>
    <% if #stdout > 0 then %>
    <%=pcdata(stdout)%>
    <% end %> @@ -91,18 +93,18 @@ end
     
    -
    +

    -
    +
    - +
    @@ -110,11 +112,11 @@ end
    - +
    -
    - +
    +
    @@ -122,90 +124,90 @@ end <% if display ~= "available" then %> -
    -
    -
    -
     
    -
    <%:Package name%>
    -
    <%:Version%>
    -
    - <% local empty = true; luci.model.ipkg.list_installed(querypat, function(n, v, s, d) empty = false; filter[n] = true %> -
    -
    -
    - - - - <%:Remove%> -
    +
    +
    +
    +
    +
    <%:Package name%>
    +
    <%:Version%>
    +
     
    -
    <%=luci.util.pcdata(n)%>
    -
    <%=luci.util.pcdata(v)%>
    + <% local empty = true; luci.model.ipkg.list_installed(querypat, function(n, v, s, d) empty = false; filter[n] = true %> +
    +
    <%=luci.util.pcdata(n)%>
    +
    <%=luci.util.pcdata(v)%>
    +
    +
    + + + + +
    +
    +
    + <% end) %> + <% if empty then %> +
    +
     
    +
    <%:none%>
    +
    <%:none%>
    +
    + <% end %>
    - <% end) %> - <% if empty then %> -
    -
     
    -
    <%:none%>
    -
    <%:none%>
    -
    - <% end %>
    -
    +
    <% else %> -
    +
    <% if not querypat then %> -
      + -
      <% end %> -
      -
      -
       
      -
      <%:Package name%>
      -
      <%:Version%>
      -
      <%:Size (.ipk)%>
      -
      <%:Description%>
      -
      - <% local empty = true; opkg_list(querypat or letterpat, function(n, v, s, d) if filter[n] then return end; empty = false %> -
      -
      -
      - - - - <%:Install%> -
      +
      +
      +
      +
      <%:Package name%>
      +
      <%:Version%>
      +
      <%:Size (.ipk)%>
      +
      <%:Description%>
      +
       
      -
      <%=luci.util.pcdata(n)%>
      -
      <%=luci.util.pcdata(v)%>
      -
      <%=luci.util.pcdata(s)%>
      -
      <%=luci.util.pcdata(d)%>
      + <% local empty = true; opkg_list(querypat or letterpat, function(n, v, s, d) if filter[n] then return end; empty = false %> +
      +
      <%=luci.util.pcdata(n)%>
      +
      <%=luci.util.pcdata(v)%>
      +
      <%=luci.util.pcdata(s)%>
      +
      <%=luci.util.pcdata(d)%>
      +
      +
      + + + + +
      +
      +
      + <% end) %> + <% if empty then %> +
      +
       
      +
      <%:none%>
      +
      <%:none%>
      +
      <%:none%>
      +
      <%:none%>
      +
      + <% end %>
      - <% end) %> - <% if empty then %> -
      -
       
      -
      <%:none%>
      -
      <%:none%>
      -
      <%:none%>
      -
      <%:none%>
      -
      - <% end %>
      - <% if not querypat then %> -
      - <% end %> -
    +
    <% end %>
    diff --git a/modules/luci-mod-admin-full/luasrc/view/admin_system/reboot.htm b/modules/luci-mod-admin-full/luasrc/view/admin_system/reboot.htm index c9551804d2..6ec2b310d2 100644 --- a/modules/luci-mod-admin-full/luasrc/view/admin_system/reboot.htm +++ b/modules/luci-mod-admin-full/luasrc/view/admin_system/reboot.htm @@ -7,7 +7,6 @@ <%+header%>

    <%:Reboot%>

    -

    <%:Reboots the operating system of your device%>

    @@ -49,7 +48,7 @@ } //]]> - +
    +
    <%:Legend:%>
      <%:Section added%>
    @@ -32,9 +32,11 @@ ret[#ret+1] = "
    %s.%s.%s+=%s" %{ r, s, o, util.pcdata(v[i]) } end - else + elseif v ~= "" then ret[#ret+1] = "
    %s.%s.%s=%s" %{ r, s, o, util.pcdata(v) } + else + ret[#ret+1] = "
    %s.%s.%s" %{ r, s, o } end end end @@ -57,7 +59,7 @@ ret[#ret+1] = "%s.%s.%s+=%s
    " %{ r, s, o, util.pcdata(v[i]) } end - + else ret[#ret+1] = "%s.%s.%s=%s
    " %{ r, s, o, util.pcdata(v) } @@ -75,5 +77,5 @@ write(table.concat(ret)) %>
    -
    +
    <%- end) %> diff --git a/modules/luci-mod-admin-full/luasrc/view/admin_uci/changes.htm b/modules/luci-mod-admin-full/luasrc/view/admin_uci/changes.htm index c69ec1215a..6282244757 100644 --- a/modules/luci-mod-admin-full/luasrc/view/admin_uci/changes.htm +++ b/modules/luci-mod-admin-full/luasrc/view/admin_uci/changes.htm @@ -27,21 +27,17 @@
    <% if redir_url then %> -
    -
    - -
    -
    +
    + +
    <% end %> -
    - -
    "> - - " /> - -
    -
    + +
    "> + + " /> + +
    <%+footer%> diff --git a/themes/luci-theme-bootstrap/htdocs/luci-static/bootstrap/cascade.css b/themes/luci-theme-bootstrap/htdocs/luci-static/bootstrap/cascade.css index 4a40f6d680..b54510876e 100644 --- a/themes/luci-theme-bootstrap/htdocs/luci-static/bootstrap/cascade.css +++ b/themes/luci-theme-bootstrap/htdocs/luci-static/bootstrap/cascade.css @@ -215,7 +215,8 @@ a:hover { * ---------------------------------------------------------------------------------------- */ p, .cbi-map-descr, -.cbi-section-descr { +.cbi-section-descr, +.table .tr.cbi-section-table-descr .th { font-size: 13px; font-weight: normal; line-height: 18px; @@ -229,7 +230,7 @@ p small { h1, h2, -h3, +h3, legend, h4, h5, h6 { @@ -265,14 +266,14 @@ h2 small { font-size: 14px; } -h3, +h3, legend, h4, h5, h6 { line-height: 36px; } -h3 { +h3, legend { font-size: 18px; } @@ -645,6 +646,26 @@ textarea[readonly] { border-color: #ddd; } +.cbi-optionals, +.cbi-section-create { + padding: 0 0 10px 10px; +} + +.cbi-section-create { + margin: -3px; + display: inline-flex; + align-items: center; +} + +.cbi-section-create > * { + margin: 3px; + flex: 1 1 auto; +} + +.cbi-section-create > * > input { + width: 100%; +} + .actions, .cbi-page-actions { background: #f5f5f5; @@ -706,6 +727,7 @@ textarea[readonly] { padding: 0; font-size: 13px; border-collapse: collapse; + position: relative; } .table .th, .table .td { @@ -732,6 +754,19 @@ textarea[readonly] { vertical-align: top; } +.tr.placeholder { + height: calc(3em + 20px); +} + +.tr.placeholder > .td { + position: absolute; + left: 0; + right: 0; + bottom: 0; + text-align: center; + line-height: 3em; +} + /* Patterns.less * Repeatable UI elements outside the base styles provided from the scaffolding * ---------------------------------------------------------------------------- */ @@ -1244,99 +1279,67 @@ footer { outline: 1px dotted #666; } -.btn.primary, -.cbi-page-actions .cbi-button-apply, -.cbi-page-actions .cbi-button-save, -.cbi-page-actions .cbi-button-reset { - color: #ffffff; - padding: 5px 14px 6px; - background-color: #0064cd; - background-repeat: repeat-x; - background-image: linear-gradient(to bottom, #049cdb, #0064cd); - text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25); - border-color: #0064cd #0064cd #003f81; - border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25); -} - .cbi-input-invalid, .cbi-value-error input { color: #FF0000; border-color: #FF0000; } -.cbi-button-up, -.cbi-input-up { - background-position: center center; - background-image: url('../resources/cbi/up.gif'), linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); -} - -.cbi-button-down, -.cbi-input-down { - background-position: center center; - background-image: url('../resources/cbi/down.gif'), linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); -} - -.cbi-button-find, -.cbi-input-find { - background-position: 6px center, left top; - padding-left: 28px; - background-image: url('../resources/cbi/find.gif'), linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); -} - +.cbi-button-positive, +.cbi-button-fieldadd, .cbi-button-add, -.cbi-input-add { - background-position: 6px center, left top; - padding-left: 28px; - background-image: url('../resources/cbi/add.gif'), linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); -} - -.cbi-button-apply, -.cbi-input-apply { - background-position: 6px center, left top; - padding-left: 28px; - background-image: url('../resources/cbi/apply.gif'), linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); -} - -.cbi-button-reset, -.cbi-input-reset { - background-position: 6px center, left top; - padding-left: 28px; - background-image: url('../resources/cbi/reset.gif'), linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); -} - -.cbi-button-edit, -.cbi-input-edit { - background-position: 6px center, left top; - padding-left: 28px; - background-image: url('../resources/cbi/edit.gif'), linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); -} - -.cbi-button-remove, -.cbi-input-remove { - background-position: 6px center, left top; - padding-left: 28px; - background-image: url('../resources/cbi/remove.gif'), linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); -} - -.cbi-button-reload, -.cbi-input-reload { - background-position: 6px center, left top; - padding-left: 28px; - background-image: url('../resources/cbi/reload.gif'), linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); -} - -.cbi-button-link, -.cbi-input-link { - background-position: 6px center, left top; - padding-left: 28px; - background-image: url('../resources/cbi/link.gif'), linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); +.cbi-button-save { + border-color: #4a4; + color: #4a4; } +.cbi-button-neutral, .cbi-button-download, -.cbi-input-download { - background-position: 6px center, left top; - padding-left: 28px; - background-image: url('../resources/cbi/download.gif'), linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); +.cbi-button-find, +.cbi-button-link, +.cbi-button-up, +.cbi-button-down { + border-color: #444; + color: #444; +} + +.btn.primary, +.cbi-button-action, +.cbi-button-apply, +.cbi-button-reload, +.cbi-button-edit { + border-color: #0069d6; + color: #0069d6; +} + +.cbi-button-negative, +.cbi-section-remove .cbi-button, +.cbi-button-reset, +.cbi-button-remove { + border-color: #c44; + color: #c44; +} + +.btn.primary, +.cbi-button-action.important, +.cbi-page-actions .cbi-button-apply, +.cbi-section-actions .cbi-button-edit { + color: #fff; + background: #0069d6; + text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25); +} + +.cbi-button-positive.important, +.cbi-page-actions .cbi-button-save { + color: #fff; + background: #4a4; + text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25); +} + +.cbi-page-actions .cbi-button-apply + .cbi-button-save { + background: linear-gradient(#ffffff, #ffffff 25%, #e6e6e6); + text-shadow: 0 -1px 0 rgba(255, 255, 255, 0.75); + color: #4a4; } .cbi-dropdown { @@ -1492,6 +1495,58 @@ footer { opacity: .6; } +.cbi-tooltip-container { + cursor: help; +} + +.cbi-tooltip { + position: absolute; + z-index: 1000; + left: -1000px; + opacity: 0; + transition: opacity .25s ease-out; +} + +.cbi-tooltip-container:hover .cbi-tooltip:not(:empty) { + left: auto; + opacity: 1; + transition: opacity .25s ease-in; +} + +.zonebadge .cbi-tooltip { + padding: 1px; + background: inherit; + margin: -1.6em 0 0 -5px; + border-radius: 3px; + pointer-events: none; + box-shadow: 0 0 3px #444; +} + +.zonebadge .cbi-tooltip > * { + margin: 1px; +} + +.zone-forwards { + display: flex; + flex-wrap: wrap; +} + +.zone-forwards > * { + flex: 1 1 40%; + padding: 1px; +} + +.zone-forwards > span { + flex-basis: 10%; + text-align: center; +} + +.zone-forwards .zone-src, +.zone-forwards .zone-dest { + display: flex; + flex-direction: column; +} + .btn.active, .btn:active { box-shadow: inset 0 2px 4px rgba(0, 0, 0, 0.25), 0 1px 2px rgba(0, 0, 0, 0.05); } @@ -1751,9 +1806,13 @@ table table td, vertical-align: middle; } -.cbi-value-description { display: inline; } - -.cbi-value-description img { vertical-align: middle; } +.cbi-value-description { + background-image: url(/luci-static/resources/cbi/help.gif); + background-position: .25em .2em; + background-repeat: no-repeat; + margin: .25em 0 0 0; + padding: 0 0 0 1.7em; +} .cbi-section-error { border: 1px solid #FF0000; @@ -1852,6 +1911,7 @@ table table td, flex-wrap: wrap; } +.ifacebadge.large, .network-status-table .ifacebox-body .ifacebadge { flex: 1; margin: .5em .25em 0 .25em; @@ -1866,7 +1926,6 @@ table table td, white-space: nowrap; color: #666666; text-shadow: 0 1px 1px rgba(255, 255, 255, 0.75); - cursor: pointer; } .zonebadge > em, diff --git a/themes/luci-theme-material/htdocs/luci-static/material/css/style.css b/themes/luci-theme-material/htdocs/luci-static/material/css/style.css index a9585cf40e..03a82b656a 100755 --- a/themes/luci-theme-material/htdocs/luci-static/material/css/style.css +++ b/themes/luci-theme-material/htdocs/luci-static/material/css/style.css @@ -32,8 +32,8 @@ font-style: normal; } -.table { display: table; } -.tr { display: table-row; } +.table { display: table; position: relative; } +.tr { display: table-row; } .thead { display: table-header-group; } .tbody { display: table-row-group; } .tfoot { display: table-footer-group; } @@ -48,6 +48,19 @@ font-weight: bold; } +.tr.placeholder { + height: 4em; +} + +.tr.placeholder > .td { + position: absolute; + left: 0; + right: 0; + bottom: 0; + text-align: center; + line-height: 3em; +} + .table[width="33%"], .th[width="33%"], .td[width="33%"] { width: 33%; } .table[width="100%"], .th[width="100%"], .td[width="100%"] { width: 100%; } @@ -442,10 +455,12 @@ h3 { } h4 { - + margin: 2rem 0 0 0; + font-size: 1.2rem; + padding-bottom: 10px; } -fieldset { +.cbi-section { margin: 2rem 0 0 0; padding: 2rem; border: 0; @@ -465,7 +480,7 @@ fieldset { margin-top: 1rem; } -fieldset > legend { +.cbi-section > legend { display: none !important; } @@ -486,10 +501,12 @@ fieldset > fieldset { border-bottom: 1px solid #eee; } -table, -.table { +table { border-spacing: 0; border-collapse: collapse; +} + +table, .table { width: 100%; border: 1px solid #eee; } @@ -501,21 +518,75 @@ table > tbody > tr > td, table > tbody > tr > th, table > tfoot > tr > td, table white-space: nowrap; } +.td.cbi-value-field, .cbi-section-table-cell { text-align: center; + display: inline-block; + flex: 10; +} + +.cbi-section-table-cell { + white-space: nowrap; + align-self: flex-end; + flex: 1; +} + +.td.cbi-value-field[data-title]::before { + content: attr(data-title); + padding: .5rem; + display: block; + white-space: nowrap; +} + +.cbi-section-table { + border: none; +} + +.cbi-section-table-titles, +.cbi-section-table-descr { + display: none; } .cbi-section-table-row { text-align: center; + display: flex; + flex-wrap: wrap; + flex-direction: row; + justify-content: space-between; + margin-bottom: 1rem; + background: #f4f4f4; + box-shadow: 0 2px 2px 0 rgba(0, 0, 0, .16), 0 0 2px 0 rgba(0, 0, 0, .12); } -fieldset > table > tbody > tr:nth-of-type(2n), -fieldset > .table > .tbody > .tr:nth-of-type(2n) { +.cbi-section-table-row:last-child { + margin-bottom: 0; +} + +.cbi-section-table-row[data-title]::before { + content: attr(data-title); + display: block; + width: 100%; + margin: .25rem; + padding: .25rem .25rem .5rem .25rem; + border-bottom: 1px solid rgba(0, 0, 0, .26); + text-align: center; + font-size: 1rem; +} + +.cbi-section-table-row > .cbi-value-field .cbi-input-select, +.cbi-section-table-row > .cbi-value-field .cbi-input-text, +.cbi-section-table-row > .cbi-value-field .cbi-input-password, +.cbi-section-table-row > .cbi-value-field .cbi-dropdown { + width: 100%; +} + +div > table > tbody > tr:nth-of-type(2n), +div > .table > .tbody > .tr:nth-of-type(2n) { background-color: #f9f9f9; } -fieldset > table > tbody > tr:nth-of-type(2n), -fieldset > .table > .tbody > .tr:nth-of-type(2n) { +div > table > tbody > tr:nth-of-type(2n), +div > .table > .tbody > .tr:nth-of-type(2n) { background-color: #f9f9f9; } @@ -1029,7 +1100,7 @@ td > .ifacebadge, .ifacebadge > img { display: inline-block; margin: 0 .2rem; - align-self: start; + align-self: flex-start; } .ifacebadge > img + img { @@ -1206,10 +1277,9 @@ td > .ifacebadge, .zonebadge { padding: 0.2rem 0.5rem; display: inline-block; - cursor: pointer; } -.zonebadge > .ifacebadge { +.zonebadge .ifacebadge { padding: .2rem .3rem; margin: 0.1rem 0.2rem; border: 1px solid #6C6C6C; @@ -1255,11 +1325,13 @@ td > .ifacebadge, min-width: 7rem; } -.cbi-section-table-row > .cbi-value-field .cbi-input-select { - width: 7rem; +.cbi-section-create { + margin: .5rem -3px; + display: inline-flex; + align-items: center; } -.cbi-section-create > .cbi-button-add { +.cbi-section-create > * { margin: 0.5rem; } @@ -1291,6 +1363,62 @@ small { border-top: 1px solid #CCC; } +.cbi-dropdown-container { + position: relative; +} + +.cbi-tooltip-container { + cursor: help; +} + +.cbi-tooltip { + position: absolute; + z-index: 1000; + left: -1000px; + opacity: 0; + transition: opacity .25s ease-out; + pointer-events: none; + box-shadow: 0 0 2px #444; +} + +.cbi-tooltip-container:hover .cbi-tooltip { + left: auto; + opacity: 1; + transition: opacity .25s ease-in; +} + +.zonebadge .cbi-tooltip { + padding: .25rem; + background: inherit; + margin: -1.5rem 0 0 -.5rem; +} + +.zonebadge-empty { + background: repeating-linear-gradient(45deg,rgba(204,204,204,0.5),rgba(204,204,204,0.5) 5px,rgba(255,255,255,0.5) 5px,rgba(255,255,255,0.5) 10px); + color: #404040; +} + +.zone-forwards { + display: flex; + min-width: 10rem; +} + +.zone-forwards > * { + flex: 1 1 45%; +} + +.zone-forwards > span { + flex-basis: 10%; + text-align: center; + padding: 0 .25rem; +} + +.zone-forwards .zone-src, +.zone-forwards .zone-dest { + display: flex; + flex-direction: column; +} + #diag-rc-output > pre { background-color: #f5f5f5; display: block; @@ -1475,11 +1603,6 @@ header > .container > .pull-right > * { margin-top: 0; } -/* fix network firewall*/ -.node-network-firewall > .main .cbi-section-table-row > .cbi-value-field .cbi-input-select { - min-width: 4rem; -} - .node-status-iptables fieldset, .node-system-packages fieldset, .node-system-flashops fieldset { @@ -1669,6 +1792,26 @@ body.lang_pl.node-main-login .cbi-value-title { .node-main-login > .main .cbi-value-title { text-align: left; } + + .tr { + display: flex; + flex-direction: row; + flex-wrap: wrap; + } + + .th, .td { + flex: 1; + flex-basis: 33%; + overflow: hidden; + text-overflow: ellipsis; + } + + .th.cbi-value-field, + .td.cbi-value-field, + .th.cbi-section-table-cell, + .td.cbi-section-table-cell { + flex-basis: auto; + } } @media screen and (max-width: 480px) { @@ -1803,6 +1946,14 @@ body.lang_pl.node-main-login .cbi-value-title { .node-status-iptables > .main div > .cbi-map > form input[type="submit"] + input[type="submit"] { margin-top: 1rem; } + + .th, .td { + flex-basis: 50%; + } + + .td.cbi-value-field { + flex-basis: 100%; + } } @media screen and (min-width: 992px) { diff --git a/themes/luci-theme-openwrt/htdocs/luci-static/openwrt.org/cascade.css b/themes/luci-theme-openwrt/htdocs/luci-static/openwrt.org/cascade.css index 1d5ac8ab24..926e8cbfb2 100644 --- a/themes/luci-theme-openwrt/htdocs/luci-static/openwrt.org/cascade.css +++ b/themes/luci-theme-openwrt/htdocs/luci-static/openwrt.org/cascade.css @@ -18,8 +18,8 @@ body { background-color: #4a6b7c; background-position: bottom center; background-repeat: repeat-x; - font-family: Verdana, Arial, sans-serif; - font-size: 11pt; + font-family: Arial, Verdana, sans-serif; + font-size: 16px; line-height: 100%; padding-bottom: 1.5em; } @@ -30,7 +30,7 @@ body { box-sizing: border-box; } -.table { display: table; } +.table { display: table; width: 100%; position: relative; } .tr { display: table-row; } .thead { display: table-header-group; } .tbody { display: table-row-group; } @@ -41,6 +41,30 @@ body { .table[width="33%"], .th[width="33%"], .td[width="33%"] { width: 33%; } .table[width="100%"], .th[width="100%"], .td[width="100%"] { width: 100%; } +.col-1 { flex: 1 1 30px !important; -webkit-flex: 1 1 30px !important; } +.col-2 { flex: 2 2 60px !important; -webkit-flex: 2 2 60px !important; } +.col-3 { flex: 3 3 90px !important; -webkit-flex: 3 3 90px !important; } +.col-4 { flex: 4 4 120px !important; -webkit-flex: 4 4 120px !important; } +.col-5 { flex: 5 5 150px !important; -webkit-flex: 5 5 150px !important; } +.col-6 { flex: 6 6 180px !important; -webkit-flex: 6 6 180px !important; } +.col-7 { flex: 7 7 210px !important; -webkit-flex: 7 7 210px !important; } +.col-8 { flex: 8 8 240px !important; -webkit-flex: 8 8 240px !important; } +.col-9 { flex: 9 9 270px !important; -webkit-flex: 9 9 270px !important; } +.col-10 { flex: 10 10 300px !important; -webkit-flex: 10 10 300px !important; } + +.tr.placeholder { + height: 3.5em; +} + +.tr.placeholder > .td { + position: absolute; + left: 0; + right: 0; + bottom: 0; + text-align: center; + line-height: 3em; +} + .nowrap { white-space: nowrap; } @@ -50,81 +74,95 @@ a img { text-decoration: none; } -ul.tabmenu { - margin: 0; - clear: both; - display: block; - vertical-align: bottom; - font-size: 10pt; - padding: 5px 0 0 5px; +#maincontainer { + display: flex; } -div.tabmenu2 { - background-color: #AAAAAA; - background-image: url(tabbg.png); - background-repeat: repeat-x; - margin-top: -1px; - border: 1px solid #444444; - border-bottom: none; +#maincontent { + flex-basis: 100%; } -div.tabmenu3, -div.tabmenu4, -div.tabmenu5 { - background-color: #AAAAAA; - background-image: url(tabbg.png); - background-repeat: repeat-x; - border: none; -} - -ul.tabmenu li { - float: left; - display: block; - overflow: hidden; -} - -.lang_he ul.tabmenu li { - float: right; -} - -ul.tabmenu li a { - text-decoration: none; - color: #444444; - display: block; - padding: 3px 8px; - margin: 0 2px; - line-height: 1.3em; - border: 1px solid transparent; - border-bottom: none; - font-size: 85%; -} - -ul.tabmenu li.active a { - font-weight: bold; - color: #000000; +#mainmenu { + max-width: 200px; background: #f5f5f5; - border: 1px solid #AAAAAA; - border-bottom: none; + border: 1px solid #444; + border-width: 0 0 1px 1px; + font-size: 85%; + padding-bottom: 1em; } -ul.tabmenu li a:hover { - color: #444444; - border-color: #444444; +#mainmenu ul { + display: block; + margin: 0; + padding: 0; } -ul.l1 li a { - background-color: #AAAAAA; - background-image: url(tabbg.png); - background-repeat: repeat-x; - border-color: #444444; +#mainmenu ul li { + display: block; + white-space: nowrap; } -ul.l1 li.tabmenu-item-logout a { - margin-left: 30px; +#mainmenu ul li > a { + display: block; + color: #444; + padding: .4em .5em; + text-decoration: none; } -.lang_he ul.l1 li.tabmenu-item-logout a { - margin-right: 30px; +#mainmenu ul li.selected > a { + background: #fff; + color: #59d; + border: 1px dotted #444; + border-width: 1px 0; +} + +#mainmenu ul li.selected:first-child > a { + border-top: none; +} + +#mainmenu ul li li > a { + font-size: 85%; + padding-left: 1.5em; +} + +#mainmenu ul li > ul { + flex-basis: 100%; + max-height: 0; + visibility: hidden; + transition: max-height .15s; +} + +#mainmenu ul:not(.active) li.selected > ul, +#mainmenu ul li.active > ul { + max-height: 1000px; + visibility: visible; + transition: max-height .25s; +} + +#mainmenu ul li.mainmenu-item-logout { + margin-top: 15%; +} + +#tabmenu { + padding: 0; + margin: -.5em -.5em 1em -.5em; + background: #bbb; +} + +#tabmenu ul { + border-color: #444; + padding-top: .5em; + flex-wrap: wrap; + background: repeating-linear-gradient(#f5f5f5, #bbb 2.4em, #f5f5f5 2.4em, #bbb); + line-height: 1em; +} + +#tabmenu ul li { + border-color: #444; +} + +#tabmenu ul li.cbi-tab { + background: #f5f5f5; } abbr, @@ -151,6 +189,13 @@ code { white-space: pre; } +hr { + margin: .5em 0; + padding: 0; + border: 1px solid #444; + border-width: 0 0 1px 0; +} + #maincontent ul { margin-left: 2em; } @@ -183,7 +228,6 @@ code { } .alert-message { - font-size: 9pt; font-weight: normal; padding: .5em; border-radius: 3px; @@ -206,7 +250,6 @@ code { .alert-message > h4 { font-weight: bold; - font-size: 10pt; } div.hostinfo { @@ -348,56 +391,35 @@ textarea#syslog { direction: rtl; } -#maincontent h2 { +h2, h3, h4, legend { font-size: 150%; font-family: Trebuchet MS, Verdana, sans-serif; font-weight: bold; - margin: 0.25em 0 0.7em 0; + margin: .25em 0 .5em 0; border-bottom: 1px solid; - padding-top: 10px; padding-bottom: 4px; + display: block; + width: 100%; } -#maincontent h3 { - margin: 0.5em 0 1.1em 0; +h3, legend { font-size: 125%; - font-weight: bold; - font-style: italic; - font-family: Trebuchet MS, Verdana, sans-serif; - color: #27408B; } +h4 { + font-size: 112%; +} + +fieldset > legend { float: left; } +fieldset > legend + * { clear: both; } + #maincontent p { margin-bottom: 1em; } .cbi-section { - margin-bottom: 0.5em; - padding: 0.5em 1em; - border: 1px dotted #555555; - background-color: #ffffff; - color: #000000; -} - -.cbi-section legend { - font-size: 110%; - font-weight: bold; - height: 1em; - padding: 0 0.25em; - background-color: transparent; - color: #555555; -} - -.cbi-section h2 { - margin: 0em 0 0.5em -0.5em !important; -} - -.cbi-section h3 { - text-decoration: none !important; - font-weight: bold !important; - color: #555555 !important; - margin: 0.25em !important; - font-size: 100% !important; + padding: .5em; + margin-top: .5em; } .cbi-section-descr { @@ -405,6 +427,10 @@ textarea#syslog { font-size: 95%; } +.cbi-section-descr:empty { + display: none; +} + .cbi-title-ref { color: inherit; text-decoration: none; @@ -450,7 +476,7 @@ input[type=image] { } input:focus, -input:hover, +input:not(.cbi-button):hover, select:focus, select:hover { background-color: #ffffff; @@ -459,21 +485,34 @@ select:hover { input[type=text], input[type=password] { - padding: 1px 3px; + padding: 0 3px; } select, input[type=text], input[type=password] { - font-size: inherit; width: 20em; + font-size: inherit; + line-height: 13pt; + height: 14pt; +} + +input[type=radio], +input[type=checkbox], +[data-dynlist] > input + img, +input.cbi-input-password + img { + vertical-align: middle; } .td select, .td .cbi-dropdown, -.td input[type=text], -.td input[type=password] { - width: 99%; +.td input[type=text] { + width: 100%; +} + +.td [data-dynlist] > input, +.td input.cbi-input-password { + width: calc(100% - 20px); } img.cbi-image-button { @@ -483,18 +522,23 @@ img.cbi-image-button { } .btn, .cbi-button { - padding: 2px; + padding: 0 .5em; border-radius: 3px; border: 1px solid #aaa; - background: #eee 1px center no-repeat; text-decoration: none; color: #000; display: inline-block; + font-size: inherit; + -webkit-appearance: none; + background: #fff; + text-align: center; + font-weight: bold; + line-height: 13pt; + height: 14pt; } .btn:hover, .cbi-button:hover { - border-color: #4a6b7c; - background-color: #fff; + box-shadow: 0 0 3px #59d; } .btn[disabled], @@ -503,153 +547,59 @@ img.cbi-image-button { .cbi-button[disabled]:hover { opacity: .6; cursor: default; - border-color: inherit; - background-color: inherit; + pointer-events: none; } -input.cbi-input-user { - background-image: url('../resources/cbi/user.gif'); - background-repeat: no-repeat; - background-position: 1px center; - color: #000000; - text-indent: 17px; +.cbi-button-positive, +.cbi-button-fieldadd, +.cbi-button-add, +.cbi-button-save { + border-color: #7b7; + color: #7b7; } -input.cbi-input-password { - background-image: url('../resources/cbi/key.gif'); - background-repeat: no-repeat; - background-position: 1px center; - color: #000000; - text-indent: 17px; +.cbi-button-neutral, +.cbi-button-reset, +.cbi-button-download, +.cbi-button-find, +.cbi-button-link, +.cbi-button-up, +.cbi-button-down { + border-color: #444; + color: #444; } -input.cbi-input-find, -input.cbi-button-find { - background-image: url('../resources/cbi/find.gif'); - color: #000000; - padding-left: 17px; +.cbi-button-action, +.cbi-button-apply, +.cbi-button-reload, +.cbi-button-edit { + border-color: #59d; + color: #59d; } -input.cbi-input-reload { - background-image: url('../resources/cbi/reload.gif'); - color: #000000; - padding-left: 17px; +.cbi-button-negative, +.cbi-section-remove .cbi-button, +.cbi-button-remove { + border-color: #b77; + color: #b77; } -input.cbi-input-add, -input.cbi-button-add { - background-image: url('../resources/cbi/add.gif'); - color: #000000; - padding-left: 17px; - padding-right: 1px; +.cbi-button-action.important, +.cbi-page-actions .cbi-button-apply, +.cbi-section-actions .cbi-button-edit { + color: #fff; + background: #59d; } -input.cbi-input-fieldadd, -input.cbi-button-fieldadd { - background-image: url(../resources/cbi/fieldadd.gif); - color: #000000; - padding-left: 17px; +.cbi-button-positive.important, +.cbi-page-actions .cbi-button-save { + color: #fff; + background: #7b7; } -input.cbi-input-reset, -input.cbi-button-reset { - background-image: url('../resources/cbi/reset.gif'); - color: #000000; - padding-left: 17px; - padding-right: 1px; -} - -input.cbi-input-save, -input.cbi-button-save { - background-image: url('../resources/cbi/save.gif'); - color: #000000; - padding-left: 17px; - padding-right: 1px; -} - -/* -input.cbi-input-apply, -input.cbi-button-apply { - background-image: url('../resources/cbi/apply.gif'); - color: #000000; - padding-left: 17px; - padding-right: 1px; -} -*/ - -input.cbi-input-apply:before, -input.cbi-button-apply:before { - background-image: url('../resources/cbi/apply.gif'); - border: 2px solid red; - width: 100px; - height: 100px; - content: "."; - display: block; - position: absolute; -} - -input.cbi-input-link, -input.cbi-button-link { - background-image: url('../resources/cbi/link.gif'); - color: #000000; - padding-left: 17px; - padding-right: 1px; -} - -input.cbi-input-download, -input.cbi-button-download { - background-image: url('../resources/cbi/download.gif'); - color: #000000; - padding-left: 17px; - padding-right: 1px; -} - -input.cbi-input-remove, -div.cbi-section-remove input { - background-image: url('../resources/cbi/remove.gif'); - color: #000000; - padding-left: 17px; - padding-right: 1px; -} - -input.cbi-button-up { - background-image: url('../resources/cbi/up.gif'); - padding-left: 11px; - padding-right: 1px; -} - -input.cbi-button-down { - background-image: url('../resources/cbi/down.gif'); - padding-left: 11px; - padding-right: 1px; -} - -input.cbi-button-edit { - background-image: url('../resources/cbi/edit.gif'); - color: #000000; - padding-left: 17px; - padding-right: 1px; -} - -input.cbi-button-reload { - background-image: url('../resources/cbi/reload.gif'); - color: #000000; - padding-left: 17px; - padding-right: 1px; -} - -input.cbi-button-reset { - background-image: url('../resources/cbi/reset.gif'); - color: #000000; - padding-left: 17px; - padding-right: 1px; -} - -input.cbi-button-remove { - background-image: url('../resources/cbi/remove.gif'); - color: #000000; - padding-left: 17px; - padding-right: 1px; +.cbi-page-actions .cbi-button-apply + .cbi-button-save { + background: #fff; + color: #7b7; } .cbi-input-invalid { @@ -660,30 +610,13 @@ input.cbi-button-remove { border-color: #FF0000; } -div.cbi-section-remove input { - border-bottom: none; -} - -textarea { - margin-left: -1px; - margin-bottom: 0.5em; -} - -form > div > input[type=submit], -form > div > input[type=reset] { - float: right; - margin-left: 0.5em; -} - table td, table th { color: #000000; } .table .td, .table .th { color: #000000; - padding: .25em 0; - text-align: center; - vertical-align: middle; + padding: .25em; } .table.smalltext { @@ -716,39 +649,23 @@ table td, table th { border-left: 1px solid #666666; } -.table.cbi-section-table .cbi-rowstyle-1 { +.cbi-rowstyle-1 { background-color: #eeeeff; color: #000000; } -.table.cbi-section-table .cbi-rowstyle-1:hover, -.table.cbi-section-table .cbi-rowstyle-2:hover { - background-color: #b2c8d4; - color: #000000; -} - -.table.cbi-section-table .cbi-section-table-cell { - padding: 3px; - white-space: nowrap; -} - -.cbi-section .cbi-rowstyle-1 h3 { - background-color: #eeeeff; - color: #555555; -} - .cbi-rowstyle-2 { color: #000000; } -div.cbi-value { +.cbi-value { clear: left; vertical-align: middle; padding: 0.25em 0.6em; border-bottom: 1px dotted #bbbbbb; } -div.cbi-value:hover { +.cbi-value:hover { background: #f8f8f8; color: #000000; } @@ -759,35 +676,49 @@ div.cbi-value:hover { line-height: 1.8em; } -div.cbi-value-field { +.cbi-value-field { width: 58%; margin-left: 40%; padding: 0.25em 0; } -div.td.cbi-value-field { +.td.cbi-value-field { width: auto; - vertical-align: middle; + margin-left: 0; + align-self: center; } -div.cbi-value-description { - font-size: 90%; - display: inline; +.cbi-value-description { + background-image: url(/luci-static/resources/cbi/help.gif); + background-position: .25em .25em; + background-repeat: no-repeat; + margin: .25em 0 0 0; + padding: .25em .25em .25em 1.75em; } -div.cbi-section-create { - clear: left; - white-space: nowrap; - vertical-align: top; +.cbi-section-create { + padding: 0 0 .25em 0; + margin: -3px; + display: inline-flex; + align-items: center; } -div.cbi-section-create .btn, -div.cbi-section-create .cbi-button { - margin: 0.25em; +.cbi-section-create > * { + margin: 3px; + flex: 1 1 auto; } -input.cbi-section-create-name { - margin-right: -0.25em; +.cbi-section-create > * > input { + width: 100%; +} + +.cbi-section-remove > .cbi-button { + margin-bottom: -1px; + border-radius: 3px 3px 0 0; +} + +.cbi-section-node + .cbi-section-create { + padding-top: 0; } div.cbi-map-descr { @@ -799,43 +730,39 @@ div.cbi-optionals { border-bottom: 1px dotted #bbbbbb; } -div.cbi-section-remove { - float: right; -} - .cbi-section-node { clear: both; - border: 1px solid #BBBBBB; - border-radius: 3px; padding-bottom: 0; position: relative; + border: 1px dotted #555; + background: #fff; + margin-bottom: 5px; } .cbi-section-node-tabbed { - border-top-left-radius: 0; + border-top: none; } -.cbi-section-node .cbi-value-last { +.cbi-section-node .cbi-value:last-child { border-bottom: none; } -.cbi-section-node .table div { - padding-bottom: 0; - border-bottom: none; -} - -.cbi-section-node div.cbi-section-table-row { - margin: 0.25em; -} - .table.cbi-section-table { width: 100%; font-size: 95%; + border: 1px dotted #444; + background: #fff; + margin: 0 0 .5em 0; } -.table.cbi-section-table .th, -.table.cbi-section-table .td { - text-align: center; +@keyframes flash { + 0% { opacity: 1; } + 50% { opacity: .5; } + 100% { opacity: 1; } +} + +.tr.cbi-section-table-row.flash { + animation: flash .35s; } .tr.cbi-section-table-descr .th { @@ -849,6 +776,93 @@ div.cbi-section-remove { padding-top: 1em; } +.th.cbi-section-actions, +.td.cbi-section-actions { + display: flex; + justify-content: flex-end; + flex-direction: row; + flex: 1 1 150px; + margin: auto -1px auto auto; +} + +.td.cbi-section-actions > form { + display: flex; +} + +.td.cbi-section-actions > *, +.td.cbi-section-actions > form > * { + flex: 1 1 4em; + margin: 1px; +} + +.cbi-page-actions { + display: flex; + justify-content: flex-end; + margin: -3px; + padding: 0 .25em .25em .25em; +} + +.cbi-page-actions > form { + display: flex; +} + +.cbi-page-actions > * { + flex: 0 1 auto; + margin: 3px; +} + +.cbi-page-actions > form > * { + flex: 1; + margin: 0 3px 0 0; +} + +.cbi-page-actions > .cbi-button-link, +.cbi-page-actions > form[method="get"]:first-child { + margin-right: auto; +} + + +.th[data-type="button"], .td[data-type="button"], +.th[data-type="fvalue"], .td[data-type="fvalue"] { + flex: 1 1 2em; + text-align: center; +} + +#cbi-network-switch_vlan .th, +#cbi-network-switch_vlan .td { + flex-basis: 12%; +} + +#cbi-wireless-overview .td:first-child { + align-self: center; +} + +.td[data-title]::before { + content: attr(data-title) ":\20"; + font-weight: bold; + text-align: left; + display: none; + padding: 1px; + white-space: nowrap; +} + +.tr.placeholder .td[data-title]::before { + display: none; +} + +.tr[data-title]::before, +.tr.cbi-section-table-titles.named::before { + content: attr(data-title) "\20"; + font-weight: bold; + text-align: left; + display: inline-block; + align-self: center; + flex: 1 1 5%; + padding: .25em; + white-space: normal; + word-wrap: break-word; +} + .cbi-value-helpicon img { vertical-align: bottom; } @@ -877,55 +891,54 @@ div.cbi-section-remove { } ul.cbi-tabmenu { - padding: 3px 0; - margin-left: 0 !important; list-style-type: none; - position: relative; - z-index: 10; - top: 4px; - line-height: 20px; + display: flex; + margin: 0 !important; + padding: 0 0 0 5px; + border-bottom: 1px solid #bbb; } -ul.cbi-tabmenu li.cbi-tab, -ul.cbi-tabmenu li.cbi-tab-disabled { - display: inline; - margin: 0; -} - -ul.cbi-tabmenu li.cbi-tab a, -ul.cbi-tabmenu li.cbi-tab-disabled a { - text-decoration: none; - padding: 3px 7px; - margin-right: 3px; - border: 1px solid #BBBBBB; +ul.cbi-tabmenu li { + display: inline-flex; + margin: 0 5px -1px 0; + flex: 0 1 auto; + border: 1px solid #bbb; border-bottom: none; border-radius: 3px 3px 0 0; - background-color: #EEEEEE; - color: #BBBBBB; -} - -ul.cbi-tabmenu li.cbi-tab-highlighted a { - color: #000000; - background-color: #FFEEAA; + background: linear-gradient(#ddd 90%, #aaa 100%); + color: #888; + overflow: hidden; + text-overflow: ellipsis; + word-wrap: break-word; } +ul.cbi-tabmenu li a, ul.cbi-tabmenu li a:hover { - color: #000000; + text-decoration: none; + color: inherit; + padding: 5px; + flex: 1; + width: 100%; + height: 100%; } -ul.cbi-tabmenu li.cbi-tab a { - padding-top: 4px; - color: #000000; - background-color: #FFFFFF; +ul.cbi-tabmenu li.cbi-tab-highlighted { + color: #000; + background: #fea; } -div.cbi-tab-descr { +ul.cbi-tabmenu li.cbi-tab { + color: #000; + background: #fff; +} + +.cbi-tab-descr { background-image: url(/luci-static/resources/cbi/help.gif); - background-position: 0.25em 50%; + background-position: .25em 50%; background-repeat: no-repeat; - border-bottom: 1px solid #CCCCCC; - margin: 0.25em 0.25em 2em; - padding: 0.5em 0.5em 0.5em 2em; + border-bottom: 1px solid #ccc; + margin: 0 .25em .25em .25em; + padding: .5em .5em .5em 2em; } @@ -938,6 +951,7 @@ div.cbi-tab-descr { padding: 0; color: #000; min-width: 20em; + max-width: 100%; } .cbi-dropdown:hover { @@ -1091,18 +1105,79 @@ div.cbi-tab-descr { } -.left { +.cbi-tooltip-container { + cursor: help; +} + +.cbi-tooltip { + position: absolute; + z-index: 1000; + left: -1000px; + opacity: 0; + transition: opacity .25s ease-out; + pointer-events: none; + box-shadow: 0 0 2px #444; +} + +.cbi-tooltip-container:hover .cbi-tooltip { + left: auto; + opacity: 1; + transition: opacity .25s ease-in; +} + +.zonebadge .cbi-tooltip { + padding: 1px; + background: inherit; + margin: -1.6em 0 0 -5px; +} + + +.zone-forwards { + display: flex; + flex-wrap: wrap; +} + +.zone-forwards > * { + flex: 1 1 45%; + padding: 1px; +} + +.zone-forwards > span { + flex-basis: 10%; + text-align: center; +} + +.zone-forwards .zone-src, +.zone-forwards .zone-dest { + display: flex; + flex-direction: column; +} + + +.left, .left::before { text-align: left !important; } -.right { +.right, .right::before { text-align: right !important; } -.center { +.center, .center::before { text-align: center !important; } +.td.bottom { + align-self: flex-end; +} + +.td.top { + align-self: flex-start; +} + +.td.middle { + align-self: center; +} + .luci { position: absolute; bottom: 0; @@ -1154,10 +1229,13 @@ div.cbi-tab-descr { align-items: center; } +.ifacebadge > * { + align-self: flex-start; +} + .ifacebadge > img, .ifacebadge > em { margin-right: 5px; - align-self: start; display: inline-block; height: 16px; } @@ -1169,15 +1247,21 @@ div.cbi-tab-descr { .ifacebox { flex-direction: column; - margin: 0 10px; + margin: 0; padding: 0; min-width: 100px; + text-align: center; } .ifacebox > * { padding: 2px; } +.td > .ifacebadge, +.td > .zonebadge { + margin: 0; + vertical-align: top; +} .network-status-table { display: flex; @@ -1205,6 +1289,7 @@ div.cbi-tab-descr { flex-wrap: wrap; } +.ifacebadge.large, .network-status-table .ifacebox-body .ifacebadge { flex: 1; margin: .5em .25em .25em .25em; @@ -1218,7 +1303,6 @@ div.cbi-tab-descr { padding: 2px; display: inline-block; white-space: nowrap; - cursor: pointer; border-radius: 3px; } @@ -1234,7 +1318,7 @@ div.cbi-tab-descr { .zonebadge .ifacebadge, .cbi-dropdown .ifacebadge { - margin: 0 .125em; + margin: 1px; } .zonebadge .ifacebadge img, @@ -1322,3 +1406,313 @@ div.cbi-tab-descr { } + +@media screen and (max-width: 992px) { + body { + -webkit-text-size-adjust: 100%; + } + + #maincontainer { + flex-direction: column; + width: 100%; + } + + #maincontent { + width: 96%; + margin: auto; + } + + #mainmenu { + border: none; + border-radius: 0; + max-width: none; + background: #000; + box-shadow: 0 0 2px #444; + padding: 0; + border-top: 1px solid #444; + position: relative; + } + + #mainmenu ul > li.selected > a { + background: #444; + color: #fff; + border-top: none; + } + + #mainmenu ul > li.selected:not(.active) > ul { + max-height: 0; + visibility: hidden; + } + + #mainmenu ul > li > a { + flex: 1; + color: #fff; + border: 1px solid #444; + border-width: 0 0 1px 1px; + } + + #mainmenu ul.l1 { + display: flex; + flex-direction: row; + flex-wrap: wrap; + position: relative; + margin-left: -1px; + width: 100%; + } + + #mainmenu ul.l1 > li { + display: inline-flex; + flex: 1 1 auto; + position: relative; + height: 2em; + } + + #mainmenu ul.l1 ul.l2 { + position: absolute; + top: 2em; + right: 0; + z-index: 1000; + background: #000; + box-shadow: 0 0 2px #444; + min-width: 120px; + display: block; + } + + #mainmenu ul.l1 ul.l2.align-left { + right: auto; + left: 0; + } + + #mainmenu ul.l2 > li { + display: block; + } + + #mainmenu ul.l2 > li > a { + padding: .5em; + } + + #mainmenu ul li.mainmenu-item-logout { + margin-top: 0; + margin-left: auto; + } + + #mainmenu ul li.mainmenu-item-logout::before { + content: "\0a"; + flex: 10; + border: 1px solid #444; + border-width: 0 0 1px 1px; + } + + .table { + display: flex; + flex-direction: column; + width: 100%; + } + + .tr { + display: flex; + flex-direction: row; + flex-wrap: wrap; + align-items: flex-end; + } + + .th, .td { + flex: 2 2 25%; + align-self: flex-start; + overflow: hidden; + text-overflow: ellipsis; + word-wrap: break-word; + display: inline-block; + } + + .td select { + word-wrap: normal; + } + + .td[data-type="button"], + .td[data-type="fvalue"] { + flex: 1 1 12.5%; + text-align: left; + } + + .td.cbi-value-field { + align-self: flex-start; + } + + .td.cbi-value-field .cbi-button { + width: 100%; + } + + .table.cbi-section-table { + border: none; + background: none; + margin: 0; + } + + .tr.table-titles, + .cbi-section-table-titles, + .cbi-section-table-descr { + display: none; + } + + .cbi-section-table-row { + display: flex; + flex-direction: row; + flex-wrap: wrap; + border: 1px dotted #444; + margin: 0 0 .5em 0; + background: #fff; + } + + .cbi-section-table-row:hover { + border: 1px solid #4a6b7c; + } + + .cbi-section-table + .cbi-section-create { + padding-top: 0; + } + + .tr[data-title]::before { + display: block; + flex: 1 1 100%; + background: #eef; + } + + .td[data-title]::before { + display: block; + } + + .td.cbi-section-actions { + flex-basis: 100%; + margin: auto -1px 0 auto; + } + + .td.cbi-section-actions > *, + .td.cbi-section-actions > form > * { + flex: 0 1 100%; + max-width: 150px; + } + + .hide-sm, + .hide-xs { + display: none; + } +} + +@media screen and (max-width: 480px) { + body { + font-size: 12pt; + } + + input, textarea, select { + font-size: 12pt !important; + line-height: 1.4em; + } + + select, input[type="text"], input[type="password"] { + width: 100%; + height: 1.4em; + } + + [data-dynlist] > input, + input.cbi-input-password { + width: calc(100% - 20px); + } + + .cbi-dropdown { + min-width: 100%; + } + + .btn, .cbi-button { + font-size: 9pt !important; + line-height: 11pt; + } + + #maincontent { + padding: .25em; + } + + #tabmenu { + margin: -.25em -.25em 1em -.25em; + } + + .th, .td { + flex: 2 2 50%; + } + + .td.cbi-value-field { + flex-basis: 100%; + } + + .td.cbi-value-field[data-type="dvalue"] { + flex-basis: 50%; + } + + .td.cbi-value-field[data-type="button"], + .td.cbi-value-field[data-type="fvalue"] { + flex-basis: 25%; + text-align: left; + } + + .cbi-section { + padding: .25em; + } + + .cbi-value-title { + float: none; + font-weight: bold; + } + + .cbi-value-field { + width: 100%; + margin: 0; + } + + .cbi-value-description { + margin-top: 5px; + display: block; + } + + .cbi-section-create { + margin-bottom: 1em; + } + + .cbi-page-actions { + flex-wrap: wrap; + } + + .cbi-page-actions > .cbi-button-link { + flex-basis: 100%; + margin-right: 2px; + } + + .cbi-page-actions > * { + flex: 1 1 auto; + margin: 2px; + } + + ul.cbi-tabmenu { + padding: 0 3px; + } + + ul.cbi-tabmenu li { + font-size: 90%; + margin: 0 1px -1px 0; + } + + .hide-xs { + display: none; + } + + #cbi-network .td[id] > strong { + display: block; + } + + #cbi-network-switch_vlan .td.cbi-section-actions { + flex-basis: 100%; + } + + .network-status-table .ifacebox { + margin: 0 0 .5em 0; + } +} diff --git a/themes/luci-theme-openwrt/luasrc/view/themes/openwrt.org/header.htm b/themes/luci-theme-openwrt/luasrc/view/themes/openwrt.org/header.htm index cbf02a76cd..773cf1f82e 100644 --- a/themes/luci-theme-openwrt/luasrc/view/themes/openwrt.org/header.htm +++ b/themes/luci-theme-openwrt/luasrc/view/themes/openwrt.org/header.htm @@ -56,9 +56,39 @@ local childs = disp.node_childs(node) if #childs > 0 then - write('
      ' %{ - level, level - }) + write('') + end + end + + local function render_tabmenu(prefix, node, level) + if not level then + level = 1 + end + + local childs = disp.node_childs(node) + if #childs > 0 then + if level > 2 then + write('
        ') + end local selected_node local selected_name @@ -71,20 +101,22 @@ selected_name = v end - write('
      • %s
      • ' %{ - v, (nnode._menu_selected or (node.leaf and v == leaf)) and 'active' or '', - nodeurl(prefix, v, nnode.query), - striptags(translate(nnode.title)) - }) + if level > 2 then + write('
      • %s
      • ' %{ + v, (nnode._menu_selected or (node.leaf and v == leaf)) and 'cbi-tab' or '', + nodeurl(prefix, v, nnode.query), + striptags(translate(nnode.title)) + }) + end end - write('

      ') + if level > 2 then + write('
    ') + end if selected_node then - render_menu(prefix .. "/" .. selected_name, selected_node, level + 1) + render_tabmenu(prefix .. "/" .. selected_name, selected_node, level + 1) end - - write('
    ') end end @@ -116,6 +148,7 @@ + <% if node and node.css then %> @@ -125,6 +158,47 @@ <% end -%> + <%=striptags( (boardinfo.hostname or "?") .. ( (node and node.title) and ' - ' .. translate(node.title) or '')) %> - LuCI @@ -161,11 +235,15 @@
    -
    +
    +
    + <% if category then render_tabmenu(category, cattree) end %> +
    +