mirror of
https://github.com/home-assistant/frontend.git
synced 2025-07-22 16:56:35 +00:00
Lovelace: Allow press-and-hold on picture-elements elements. (#1745)
* Allow press-and-hold on picture-elements elements.
This commit is contained in:
parent
1f642f436a
commit
f146a1d80f
@ -17,6 +17,7 @@
|
|||||||
"author": "Paulus Schoutsen <Paulus@PaulusSchoutsen.nl> (http://paulusschoutsen.nl)",
|
"author": "Paulus Schoutsen <Paulus@PaulusSchoutsen.nl> (http://paulusschoutsen.nl)",
|
||||||
"license": "Apache-2.0",
|
"license": "Apache-2.0",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
|
"@material/mwc-ripple": "^0.3.1",
|
||||||
"@mdi/svg": "^2.7.94",
|
"@mdi/svg": "^2.7.94",
|
||||||
"@polymer/app-layout": "^3.0.1",
|
"@polymer/app-layout": "^3.0.1",
|
||||||
"@polymer/app-localize-behavior": "^3.0.1",
|
"@polymer/app-localize-behavior": "^3.0.1",
|
||||||
|
@ -22,9 +22,6 @@ class HuiPictureElementsCard extends PolymerElement {
|
|||||||
position: absolute;
|
position: absolute;
|
||||||
transform: translate(-50%, -50%);
|
transform: translate(-50%, -50%);
|
||||||
}
|
}
|
||||||
hui-image-element {
|
|
||||||
overflow-y: hidden;
|
|
||||||
}
|
|
||||||
</style>
|
</style>
|
||||||
|
|
||||||
<ha-card header="[[_config.title]]">
|
<ha-card header="[[_config.title]]">
|
||||||
|
@ -13,13 +13,13 @@ class HuiIconElement extends ElementClickMixin(PolymerElement) {
|
|||||||
return html`
|
return html`
|
||||||
<style>
|
<style>
|
||||||
:host {
|
:host {
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
<ha-icon
|
<ha-icon
|
||||||
icon="[[_config.icon]]"
|
icon="[[_config.icon]]"
|
||||||
title$="[[computeTooltip(hass, _config)]]"
|
title$="[[computeTooltip(hass, _config)]]"
|
||||||
></ha-icon>
|
></ha-icon>
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -32,9 +32,7 @@ class HuiIconElement extends ElementClickMixin(PolymerElement) {
|
|||||||
|
|
||||||
ready() {
|
ready() {
|
||||||
super.ready();
|
super.ready();
|
||||||
this.addEventListener("click", () =>
|
this.registerMouse(this._config);
|
||||||
this.handleClick(this.hass, this._config)
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
setConfig(config) {
|
setConfig(config) {
|
||||||
|
@ -14,9 +14,11 @@ class HuiImageElement extends ElementClickMixin(PolymerElement) {
|
|||||||
<style>
|
<style>
|
||||||
:host(.clickable) {
|
:host(.clickable) {
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
|
-webkit-touch-callout: none !important;
|
||||||
}
|
}
|
||||||
hui-image {
|
hui-image {
|
||||||
overflow-y: hidden;
|
overflow-y: hidden;
|
||||||
|
-webkit-user-select: none !important;
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
<hui-image
|
<hui-image
|
||||||
@ -42,9 +44,7 @@ class HuiImageElement extends ElementClickMixin(PolymerElement) {
|
|||||||
|
|
||||||
ready() {
|
ready() {
|
||||||
super.ready();
|
super.ready();
|
||||||
this.addEventListener("click", () =>
|
this.registerMouse(this._config);
|
||||||
this.handleClick(this.hass, this._config)
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
setConfig(config) {
|
setConfig(config) {
|
||||||
|
@ -13,13 +13,13 @@ class HuiStateIconElement extends ElementClickMixin(PolymerElement) {
|
|||||||
return html`
|
return html`
|
||||||
<style>
|
<style>
|
||||||
:host {
|
:host {
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
<state-badge
|
<state-badge
|
||||||
state-obj="[[_stateObj]]"
|
state-obj="[[_stateObj]]"
|
||||||
title$="[[computeTooltip(hass, _config)]]"
|
title$="[[computeTooltip(hass, _config)]]"
|
||||||
></state-badge>
|
></state-badge>
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -36,9 +36,7 @@ class HuiStateIconElement extends ElementClickMixin(PolymerElement) {
|
|||||||
|
|
||||||
ready() {
|
ready() {
|
||||||
super.ready();
|
super.ready();
|
||||||
this.addEventListener("click", () =>
|
this.registerMouse(this._config);
|
||||||
this.handleClick(this.hass, this._config)
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
setConfig(config) {
|
setConfig(config) {
|
||||||
|
@ -45,9 +45,7 @@ class HuiStateLabelElement extends LocalizeMixin(
|
|||||||
|
|
||||||
ready() {
|
ready() {
|
||||||
super.ready();
|
super.ready();
|
||||||
this.addEventListener("click", () =>
|
this.registerMouse(this._config);
|
||||||
this.handleClick(this.hass, this._config)
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
setConfig(config) {
|
setConfig(config) {
|
||||||
|
@ -3,6 +3,7 @@ import toggleEntity from "../common/entity/toggle-entity.js";
|
|||||||
import NavigateMixin from "../../../mixins/navigate-mixin";
|
import NavigateMixin from "../../../mixins/navigate-mixin";
|
||||||
import EventsMixin from "../../../mixins/events-mixin.js";
|
import EventsMixin from "../../../mixins/events-mixin.js";
|
||||||
import computeStateName from "../../../common/entity/compute_state_name";
|
import computeStateName from "../../../common/entity/compute_state_name";
|
||||||
|
import "@material/mwc-ripple";
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* @polymerMixin
|
* @polymerMixin
|
||||||
@ -12,8 +13,87 @@ import computeStateName from "../../../common/entity/compute_state_name";
|
|||||||
export default dedupingMixin(
|
export default dedupingMixin(
|
||||||
(superClass) =>
|
(superClass) =>
|
||||||
class extends NavigateMixin(EventsMixin(superClass)) {
|
class extends NavigateMixin(EventsMixin(superClass)) {
|
||||||
handleClick(hass, config) {
|
registerMouse(config) {
|
||||||
const tapAction = config.tap_action || "more-info";
|
var isTouch =
|
||||||
|
"ontouchstart" in window ||
|
||||||
|
navigator.MaxTouchPoints > 0 ||
|
||||||
|
navigator.msMaxTouchPoints > 0;
|
||||||
|
|
||||||
|
let ripple = null;
|
||||||
|
const rippleWrapper = document.createElement("div");
|
||||||
|
this.shadowRoot.appendChild(rippleWrapper);
|
||||||
|
Object.assign(rippleWrapper.style, {
|
||||||
|
position: "absolute",
|
||||||
|
width: isTouch ? "100px" : "50px",
|
||||||
|
height: isTouch ? "100px" : "50px",
|
||||||
|
top: "50%",
|
||||||
|
left: "50%",
|
||||||
|
transform: "translate(-50%, -50%)",
|
||||||
|
pointerEvents: "none",
|
||||||
|
});
|
||||||
|
|
||||||
|
const loadRipple = () => {
|
||||||
|
if (ripple) return;
|
||||||
|
ripple = document.createElement("mwc-ripple");
|
||||||
|
rippleWrapper.appendChild(ripple);
|
||||||
|
ripple.unbounded = true;
|
||||||
|
ripple.primary = true;
|
||||||
|
};
|
||||||
|
const startAnimation = () => {
|
||||||
|
ripple.style.visibility = "visible";
|
||||||
|
ripple.disabled = false;
|
||||||
|
ripple.active = true;
|
||||||
|
};
|
||||||
|
const stopAnimation = () => {
|
||||||
|
if (ripple) {
|
||||||
|
ripple.active = false;
|
||||||
|
ripple.disabled = true;
|
||||||
|
ripple.style.visibility = "hidden";
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
var mouseDown = isTouch ? "touchstart" : "mousedown";
|
||||||
|
var mouseOut = isTouch ? "touchcancel" : "mouseout";
|
||||||
|
var click = isTouch ? "touchend" : "click";
|
||||||
|
|
||||||
|
var timer = null;
|
||||||
|
var held = false;
|
||||||
|
var holdTime = config.hold_time || 500;
|
||||||
|
|
||||||
|
this.addEventListener(mouseDown, () => {
|
||||||
|
held = false;
|
||||||
|
loadRipple();
|
||||||
|
timer = setTimeout(() => {
|
||||||
|
startAnimation();
|
||||||
|
held = true;
|
||||||
|
}, holdTime);
|
||||||
|
});
|
||||||
|
|
||||||
|
this.addEventListener(click, () => {
|
||||||
|
stopAnimation();
|
||||||
|
this.handleClick(this.hass, config, held);
|
||||||
|
});
|
||||||
|
|
||||||
|
[
|
||||||
|
mouseOut,
|
||||||
|
"mouseup",
|
||||||
|
"touchmove",
|
||||||
|
"mousewheel",
|
||||||
|
"wheel",
|
||||||
|
"scroll",
|
||||||
|
].forEach((ev) => {
|
||||||
|
document.addEventListener(ev, () => {
|
||||||
|
clearTimeout(timer);
|
||||||
|
stopAnimation();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
handleClick(hass, config, held = false) {
|
||||||
|
let tapAction = config.tap_action || "more-info";
|
||||||
|
if (held) {
|
||||||
|
tapAction = config.hold_action || "none";
|
||||||
|
}
|
||||||
if (tapAction === "none") return;
|
if (tapAction === "none") return;
|
||||||
|
|
||||||
switch (tapAction) {
|
switch (tapAction) {
|
||||||
|
42
yarn.lock
42
yarn.lock
@ -1266,6 +1266,48 @@
|
|||||||
dependencies:
|
dependencies:
|
||||||
base64-js "^1.3.0"
|
base64-js "^1.3.0"
|
||||||
|
|
||||||
|
"@material/animation@^0.40.1":
|
||||||
|
version "0.40.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/@material/animation/-/animation-0.40.1.tgz#c5ff31e7d7e17324a0045e889d3530b150b9fcec"
|
||||||
|
integrity sha512-HtxFUw04EHg4S6pXfTA3Z0wKxnNDNcDhe1Np2Y2geo+lAk2Hb7m8yCL/GaL9o2I/eRYsgUXC0U7+Mk74GCz3zw==
|
||||||
|
|
||||||
|
"@material/base@^0.40.1":
|
||||||
|
version "0.40.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/@material/base/-/base-0.40.1.tgz#a0d8e19cee98dae0f96dbf0887a14b3f7acd2aac"
|
||||||
|
integrity sha512-vrbOK8hONVCYgURQ9h7nkXvMdYnZVVNmAfFFijF8fbWQdwnoPcNTdqV6RoQlhBEqHYHQqLNfdUDlznAPKLclGQ==
|
||||||
|
|
||||||
|
"@material/mwc-base@^0.3.1":
|
||||||
|
version "0.3.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/@material/mwc-base/-/mwc-base-0.3.1.tgz#5e1440aa09e0a83633be36eb8102ff88d3fddae8"
|
||||||
|
integrity sha512-7AdcBu6rxARcUteEBNSJKCen3hP47T/NRsfw+RMn6IedHlEGp2GKwF6YqYDCVSsQbm0IjsJ4ft4+nVXlFVYO2g==
|
||||||
|
dependencies:
|
||||||
|
"@polymer/lit-element" "^0.6.2"
|
||||||
|
lit-html "^0.12.0"
|
||||||
|
|
||||||
|
"@material/mwc-ripple@^0.3.1":
|
||||||
|
version "0.3.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/@material/mwc-ripple/-/mwc-ripple-0.3.1.tgz#da812516d0bd0b15b0c4793b783fbdb9e04cd7a0"
|
||||||
|
integrity sha512-pOdBkP6NJyGz9UftvKjrx8sXvz+yIXMC8q6Qx/LgGw67tgU4qM/1Hy22iePiw1UFNhlqD8ZwtdPLXKVaisGauQ==
|
||||||
|
dependencies:
|
||||||
|
"@material/mwc-base" "^0.3.1"
|
||||||
|
"@material/ripple" "^0.40.0"
|
||||||
|
"@polymer/lit-element" "^0.6.2"
|
||||||
|
lit-html "^0.12.0"
|
||||||
|
|
||||||
|
"@material/ripple@^0.40.0":
|
||||||
|
version "0.40.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/@material/ripple/-/ripple-0.40.1.tgz#57cbc689303b48282229cb9b62556af7442e852a"
|
||||||
|
integrity sha512-sndeTS4VHa0v1UGj7MNcxMCuO9LJ1DjoL1EjE6BH3Lm3M1MnXJHdsBo2CgPbU/FI84tt6+eyHGOYPdPrEDJhCA==
|
||||||
|
dependencies:
|
||||||
|
"@material/animation" "^0.40.1"
|
||||||
|
"@material/base" "^0.40.1"
|
||||||
|
"@material/theme" "^0.40.1"
|
||||||
|
|
||||||
|
"@material/theme@^0.40.1":
|
||||||
|
version "0.40.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/@material/theme/-/theme-0.40.1.tgz#3cc3f1bf87ee9581df03e347a1979e53ae617221"
|
||||||
|
integrity sha512-cH1CsGIDisEQ2oroZhLTypV0Ir00x3WIwFXnPo7qv3832tuIDkZY623U3rUax6KNPz4Hh1j0tNpTwgrNZwvwWA==
|
||||||
|
|
||||||
"@mdi/svg@^2.7.94":
|
"@mdi/svg@^2.7.94":
|
||||||
version "2.8.94"
|
version "2.8.94"
|
||||||
resolved "https://registry.yarnpkg.com/@mdi/svg/-/svg-2.8.94.tgz#574da5953fb8ccd58b660d95061d43add53f5704"
|
resolved "https://registry.yarnpkg.com/@mdi/svg/-/svg-2.8.94.tgz#574da5953fb8ccd58b660d95061d43add53f5704"
|
||||||
|
Loading…
x
Reference in New Issue
Block a user