summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorJo-Philipp Wich <jo@mein.io>2018-10-18 16:14:35 +0200
committerJo-Philipp Wich <jo@mein.io>2018-11-05 11:01:45 +0100
commit7f613be5000e753e99ce5b829748fb43fca78754 (patch)
treea9615767db020a857f4b71e25632c236f7248bfd
parent31bce2455fdeacefbb837d6abb95584df66c36a2 (diff)
luci-base, themes: add tooltip helpers & styles
Add the required JS and CSS infrastructure to support rich hover/focus tooltips for element. Signed-off-by: Jo-Philipp Wich <jo@mein.io>
-rw-r--r--modules/luci-base/htdocs/luci-static/resources/cbi.js52
-rw-r--r--themes/luci-theme-bootstrap/htdocs/luci-static/bootstrap/cascade.css19
-rw-r--r--themes/luci-theme-freifunk-generic/htdocs/luci-static/freifunk-generic/cascade.css13
-rw-r--r--themes/luci-theme-material/htdocs/luci-static/material/cascade.css6
-rw-r--r--themes/luci-theme-openwrt/htdocs/luci-static/openwrt.org/cascade.css16
5 files changed, 93 insertions, 13 deletions
diff --git a/modules/luci-base/htdocs/luci-static/resources/cbi.js b/modules/luci-base/htdocs/luci-static/resources/cbi.js
index b1fc26c74..b92b86f52 100644
--- a/modules/luci-base/htdocs/luci-static/resources/cbi.js
+++ b/modules/luci-base/htdocs/luci-static/resources/cbi.js
@@ -2191,6 +2191,58 @@ function cbi_update_table(table, data, placeholder) {
});
}
+var tooltipDiv = null, tooltipTimeout = null;
+
+function showTooltip(ev) {
+ if (!matchesElem(ev.target, '[data-tooltip]'))
+ return;
+
+ if (tooltipTimeout !== null) {
+ window.clearTimeout(tooltipTimeout);
+ tooltipTimeout = null;
+ }
+
+ var rect = ev.target.getBoundingClientRect(),
+ x = rect.left + window.pageXOffset,
+ y = rect.top + rect.height + window.pageYOffset;
+
+ tooltipDiv.className = 'cbi-tooltip';
+ tooltipDiv.innerHTML = '▲ ';
+ tooltipDiv.firstChild.data += ev.target.getAttribute('data-tooltip');
+
+ if (ev.target.hasAttribute('data-tooltip-style'))
+ tooltipDiv.classList.add(ev.target.getAttribute('data-tooltip-style'));
+
+ if ((y + tooltipDiv.offsetHeight) > (window.innerHeight + window.pageYOffset)) {
+ y -= (tooltipDiv.offsetHeight + ev.target.offsetHeight);
+ tooltipDiv.firstChild.data = '▼ ' + tooltipDiv.firstChild.data.substr(2);
+ }
+
+ tooltipDiv.style.top = y + 'px';
+ tooltipDiv.style.left = x + 'px';
+ tooltipDiv.style.opacity = 1;
+}
+
+function hideTooltip(ev) {
+ if (ev.target === tooltipDiv || ev.relatedTarget === tooltipDiv)
+ return;
+
+ if (tooltipTimeout !== null) {
+ window.clearTimeout(tooltipTimeout);
+ tooltipTimeout = null;
+ }
+
+ tooltipDiv.style.opacity = 0;
+ tooltipTimeout = window.setTimeout(function() { tooltipDiv.removeAttribute('style'); }, 250);
+}
+
document.addEventListener('DOMContentLoaded', function() {
+ tooltipDiv = document.body.appendChild(E('div', { 'class': 'cbi-tooltip' }));
+
+ document.addEventListener('mouseover', showTooltip, true);
+ document.addEventListener('mouseout', hideTooltip, true);
+ document.addEventListener('focus', showTooltip, true);
+ document.addEventListener('blur', hideTooltip, true);
+
document.querySelectorAll('.table').forEach(cbi_update_table);
});
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 a30dc45b7..690fd2ad4 100644
--- a/themes/luci-theme-bootstrap/htdocs/luci-static/bootstrap/cascade.css
+++ b/themes/luci-theme-bootstrap/htdocs/luci-static/bootstrap/cascade.css
@@ -1168,7 +1168,8 @@ footer {
.btn.info,
.alert-message.info,
.btn.info:hover,
-.alert-message.info:hover {
+.alert-message.info:hover,
+.cbi-tooltip.error, .cbi-tooltip.success, .cbi-tooltip.info {
color: #fff;
}
@@ -1180,25 +1181,26 @@ footer {
.btn.danger,
.alert-message.danger,
.btn.error,
-.alert-message.error {
+.alert-message.error,
+.cbi-tooltip.error {
background: linear-gradient(to bottom, #ee5f5b, #c43c35) repeat-x;
text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25);
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
}
-.btn.success, .alert-message.success {
+.btn.success, .alert-message.success, .cbi-tooltip.success {
background: linear-gradient(to bottom, #62c462, #57a957) repeat-x;
text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25);
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
}
-.btn.info, .alert-message.info {
+.btn.info, .alert-message.info, .cbi-tooltip.info {
background: linear-gradient(to bottom, #5bc0de, #339bb9) repeat-x;
text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25);
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
}
-.alert-message.notice {
+.alert-message.notice, .cbi-tooltip.notice {
background: linear-gradient(to bottom, #efefef, #fefefe) repeat-x;
text-shadow: 0 -1px 0 rgba(255, 255, 255, 0.25);
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
@@ -1491,8 +1493,13 @@ select + .cbi-button {
position: absolute;
z-index: 1000;
left: -1000px;
+ box-shadow: 0 0 2px #ccc;
+ border-radius: 3px;
+ background: #fff;
+ white-space: pre;
+ padding: 2px 5px;
opacity: 0;
- transition: opacity .25s ease-out;
+ transition: opacity .25s ease-in;
}
.cbi-tooltip-container:hover .cbi-tooltip:not(:empty) {
diff --git a/themes/luci-theme-freifunk-generic/htdocs/luci-static/freifunk-generic/cascade.css b/themes/luci-theme-freifunk-generic/htdocs/luci-static/freifunk-generic/cascade.css
index 3e1b1cd2f..b9ac0f033 100644
--- a/themes/luci-theme-freifunk-generic/htdocs/luci-static/freifunk-generic/cascade.css
+++ b/themes/luci-theme-freifunk-generic/htdocs/luci-static/freifunk-generic/cascade.css
@@ -156,12 +156,17 @@ a img {
color: #000;
}
-.alert-message.notice {
+.alert-message, .cbi-tooltip.error {
+ background: #fee;
+ color: #a22;
+}
+
+.alert-message.notice, .cbi-tooltip.notice {
background: linear-gradient(#ccc 0%, #eee 100%);
color: #4a6b7c;
}
-.alert-message.warning {
+.alert-message.warning, .cbi-tooltip.warning {
background: linear-gradient(#dda 0%, #dd8 100%);
color: #c00;
}
@@ -1354,6 +1359,10 @@ td.cbi-value-error {
position: absolute;
z-index: 1000;
left: -1000px;
+ border-radius: 3px;
+ background: #fff;
+ padding: 2px 5px;
+ white-space: pre;
opacity: 0;
transition: opacity .25s ease-out;
pointer-events: none;
diff --git a/themes/luci-theme-material/htdocs/luci-static/material/cascade.css b/themes/luci-theme-material/htdocs/luci-static/material/cascade.css
index 6961bfe2d..a4d71eeb6 100644
--- a/themes/luci-theme-material/htdocs/luci-static/material/cascade.css
+++ b/themes/luci-theme-material/htdocs/luci-static/material/cascade.css
@@ -291,7 +291,7 @@ header {
}
header > .fill > .container {
- padding-top: 0.25rem;
+ padding-top: 0.25rem;
padding-right: 1rem;
padding-bottom: 0.25rem;
display: flex;
@@ -1481,6 +1481,10 @@ small {
position: absolute;
z-index: 1000;
left: -1000px;
+ border-radius: 3px;
+ background: #fff;
+ padding: 2px 5px;
+ white-space: pre;
opacity: 0;
transition: opacity .25s ease-out;
pointer-events: none;
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 5becfc5ba..94d6b5729 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
@@ -231,18 +231,22 @@ hr {
padding: .5em;
border-radius: 3px;
border: 1px solid #a22;
- color: #a22;
- background: #fee;
margin: 0 0 .5em 0;
}
-.alert-message.notice {
+.alert-message, .cbi-tooltip.error {
+ border-color: #a22;
+ background: #fee;
+ color: #a22;
+}
+
+.alert-message.notice, .cbi-tooltip.notice {
border-color: #15a;
background: #e6f6ff;
color: #15a;
}
-.alert-message.warning {
+.alert-message.warning, .cbi-tooltip.warning {
border-color: #ed5;
background: #fe9;
color: #650;
@@ -1173,6 +1177,10 @@ select + .cbi-button {
position: absolute;
z-index: 1000;
left: -1000px;
+ border-radius: 3px;
+ background: #fff;
+ padding: 2px 5px;
+ white-space: pre;
opacity: 0;
transition: opacity .25s ease-out;
pointer-events: none;