mirror of
https://github.com/home-assistant/frontend.git
synced 2025-09-17 17:09:43 +00:00
Compare commits
2 Commits
reduce-mot
...
fix-naviga
Author | SHA1 | Date | |
---|---|---|---|
![]() |
9a6e48a82b | ||
![]() |
a8b8fb4c30 |
@@ -1,4 +1,5 @@
|
|||||||
FROM mcr.microsoft.com/devcontainers/python:1-3.13
|
# See here for image contents: https://github.com/microsoft/vscode-dev-containers/tree/v0.148.1/containers/python-3/.devcontainer/base.Dockerfile
|
||||||
|
FROM mcr.microsoft.com/devcontainers/python:3.12
|
||||||
|
|
||||||
ENV \
|
ENV \
|
||||||
DEBIAN_FRONTEND=noninteractive \
|
DEBIAN_FRONTEND=noninteractive \
|
||||||
|
4
.github/ISSUE_TEMPLATE/bug_report.yml
vendored
4
.github/ISSUE_TEMPLATE/bug_report.yml
vendored
@@ -7,7 +7,7 @@ body:
|
|||||||
value: |
|
value: |
|
||||||
Make sure you are running the [latest version of Home Assistant][releases] before reporting an issue.
|
Make sure you are running the [latest version of Home Assistant][releases] before reporting an issue.
|
||||||
|
|
||||||
If you have a feature or enhancement request for the frontend, please [start a discussion][fr] instead of creating an issue.
|
If you have a feature or enhancement request for the frontend, please [start an discussion][fr] instead of creating an issue.
|
||||||
|
|
||||||
**Please do not report issues for custom cards.**
|
**Please do not report issues for custom cards.**
|
||||||
|
|
||||||
@@ -74,7 +74,7 @@ body:
|
|||||||
If known, otherwise leave blank.
|
If known, otherwise leave blank.
|
||||||
- type: input
|
- type: input
|
||||||
attributes:
|
attributes:
|
||||||
label: In which browser are you experiencing the issue?
|
label: In which browser are you experiencing the issue with?
|
||||||
placeholder: Google Chrome 88.0.4324.150
|
placeholder: Google Chrome 88.0.4324.150
|
||||||
description: >
|
description: >
|
||||||
Provide the full name and don't forget to add the version!
|
Provide the full name and don't forget to add the version!
|
||||||
|
2
.github/ISSUE_TEMPLATE/config.yml
vendored
2
.github/ISSUE_TEMPLATE/config.yml
vendored
@@ -2,7 +2,7 @@ blank_issues_enabled: false
|
|||||||
contact_links:
|
contact_links:
|
||||||
- name: Request a feature for the UI / Dashboards
|
- name: Request a feature for the UI / Dashboards
|
||||||
url: https://github.com/home-assistant/frontend/discussions/category_choices
|
url: https://github.com/home-assistant/frontend/discussions/category_choices
|
||||||
about: Request a new feature for the Home Assistant frontend.
|
about: Request an new feature for the Home Assistant frontend.
|
||||||
- name: Report a bug that is NOT related to the UI / Dashboards
|
- name: Report a bug that is NOT related to the UI / Dashboards
|
||||||
url: https://github.com/home-assistant/core/issues
|
url: https://github.com/home-assistant/core/issues
|
||||||
about: This is the issue tracker for our frontend. Please report other issues in the backend ("core") repository.
|
about: This is the issue tracker for our frontend. Please report other issues in the backend ("core") repository.
|
||||||
|
38
.github/workflows/ci.yaml
vendored
38
.github/workflows/ci.yaml
vendored
@@ -26,14 +26,20 @@ jobs:
|
|||||||
- name: Check out files from GitHub
|
- name: Check out files from GitHub
|
||||||
uses: actions/checkout@v4.2.2
|
uses: actions/checkout@v4.2.2
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
|
id: setup-node
|
||||||
uses: actions/setup-node@v4.1.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
|
- uses: actions/cache@v4.2.0
|
||||||
|
id: yarn-cache # use this to check for `cache-hit` (`steps.yarn-cache.outputs.cache-hit != 'true'`)
|
||||||
|
with:
|
||||||
|
path: "node_modules"
|
||||||
|
key: ${{ runner.os }}-yarn-${{ hashFiles('.yarnrc.yml') }}-${{ steps.setup-node.outputs.node-version }}-${{ hashFiles('yarn.lock') }}
|
||||||
|
restore-keys: ${{ runner.os }}-yarn-${{ hashFiles('.yarnrc.yml') }}-${{ steps.setup-node.outputs.node-version }}
|
||||||
- name: Install dependencies
|
- name: Install dependencies
|
||||||
|
if: steps.yarn-cache.outputs.cache-hit != 'true'
|
||||||
run: yarn install --immutable
|
run: yarn install --immutable
|
||||||
- name: Check for duplicate dependencies
|
|
||||||
run: yarn dedupe --check
|
|
||||||
- name: Build resources
|
- name: Build resources
|
||||||
run: ./node_modules/.bin/gulp gen-icons-json build-translations build-locale-data gather-gallery-pages
|
run: ./node_modules/.bin/gulp gen-icons-json build-translations build-locale-data gather-gallery-pages
|
||||||
- name: Setup lint cache
|
- name: Setup lint cache
|
||||||
@@ -60,11 +66,19 @@ jobs:
|
|||||||
- name: Check out files from GitHub
|
- name: Check out files from GitHub
|
||||||
uses: actions/checkout@v4.2.2
|
uses: actions/checkout@v4.2.2
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
|
id: setup-node
|
||||||
uses: actions/setup-node@v4.1.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
|
- uses: actions/cache@v4.2.0
|
||||||
|
id: yarn-cache # use this to check for `cache-hit` (`steps.yarn-cache.outputs.cache-hit != 'true'`)
|
||||||
|
with:
|
||||||
|
path: "node_modules"
|
||||||
|
key: ${{ runner.os }}-yarn-${{ hashFiles('.yarnrc.yml') }}-${{ steps.setup-node.outputs.node-version }}-${{ hashFiles('yarn.lock') }}
|
||||||
|
restore-keys: ${{ runner.os }}-yarn-${{ hashFiles('.yarnrc.yml') }}-${{ steps.setup-node.outputs.node-version }}
|
||||||
- name: Install dependencies
|
- name: Install dependencies
|
||||||
|
if: steps.yarn-cache.outputs.cache-hit != 'true'
|
||||||
run: yarn install --immutable
|
run: yarn install --immutable
|
||||||
- name: Build resources
|
- name: Build resources
|
||||||
run: ./node_modules/.bin/gulp gen-icons-json build-translations build-locale-data
|
run: ./node_modules/.bin/gulp gen-icons-json build-translations build-locale-data
|
||||||
@@ -78,18 +92,26 @@ jobs:
|
|||||||
- name: Check out files from GitHub
|
- name: Check out files from GitHub
|
||||||
uses: actions/checkout@v4.2.2
|
uses: actions/checkout@v4.2.2
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
|
id: setup-node
|
||||||
uses: actions/setup-node@v4.1.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
|
- uses: actions/cache@v4.2.0
|
||||||
|
id: yarn-cache # use this to check for `cache-hit` (`steps.yarn-cache.outputs.cache-hit != 'true'`)
|
||||||
|
with:
|
||||||
|
path: "node_modules"
|
||||||
|
key: ${{ runner.os }}-yarn-${{ hashFiles('.yarnrc.yml') }}-${{ steps.setup-node.outputs.node-version }}-${{ hashFiles('yarn.lock') }}
|
||||||
|
restore-keys: ${{ runner.os }}-yarn-${{ hashFiles('.yarnrc.yml') }}-${{ steps.setup-node.outputs.node-version }}
|
||||||
- name: Install dependencies
|
- name: Install dependencies
|
||||||
|
if: steps.yarn-cache.outputs.cache-hit != 'true'
|
||||||
run: yarn install --immutable
|
run: yarn install --immutable
|
||||||
- name: Build Application
|
- name: Build Application
|
||||||
run: ./node_modules/.bin/gulp build-app
|
run: ./node_modules/.bin/gulp build-app
|
||||||
env:
|
env:
|
||||||
IS_TEST: "true"
|
IS_TEST: "true"
|
||||||
- name: Upload bundle stats
|
- name: Upload bundle stats
|
||||||
uses: actions/upload-artifact@v4.6.0
|
uses: actions/upload-artifact@v4.4.3
|
||||||
with:
|
with:
|
||||||
name: frontend-bundle-stats
|
name: frontend-bundle-stats
|
||||||
path: build/stats/*.json
|
path: build/stats/*.json
|
||||||
@@ -102,18 +124,26 @@ jobs:
|
|||||||
- name: Check out files from GitHub
|
- name: Check out files from GitHub
|
||||||
uses: actions/checkout@v4.2.2
|
uses: actions/checkout@v4.2.2
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
|
id: setup-node
|
||||||
uses: actions/setup-node@v4.1.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
|
- uses: actions/cache@v4.2.0
|
||||||
|
id: yarn-cache # use this to check for `cache-hit` (`steps.yarn-cache.outputs.cache-hit != 'true'`)
|
||||||
|
with:
|
||||||
|
path: "node_modules"
|
||||||
|
key: ${{ runner.os }}-yarn-${{ hashFiles('.yarnrc.yml') }}-${{ steps.setup-node.outputs.node-version }}-${{ hashFiles('yarn.lock') }}
|
||||||
|
restore-keys: ${{ runner.os }}-yarn-${{ hashFiles('.yarnrc.yml') }}-${{ steps.setup-node.outputs.node-version }}
|
||||||
- name: Install dependencies
|
- name: Install dependencies
|
||||||
|
if: steps.yarn-cache.outputs.cache-hit != 'true'
|
||||||
run: yarn install --immutable
|
run: yarn install --immutable
|
||||||
- name: Build Application
|
- name: Build Application
|
||||||
run: ./node_modules/.bin/gulp build-hassio
|
run: ./node_modules/.bin/gulp build-hassio
|
||||||
env:
|
env:
|
||||||
IS_TEST: "true"
|
IS_TEST: "true"
|
||||||
- name: Upload bundle stats
|
- name: Upload bundle stats
|
||||||
uses: actions/upload-artifact@v4.6.0
|
uses: actions/upload-artifact@v4.4.3
|
||||||
with:
|
with:
|
||||||
name: supervisor-bundle-stats
|
name: supervisor-bundle-stats
|
||||||
path: build/stats/*.json
|
path: build/stats/*.json
|
||||||
|
6
.github/workflows/nightly.yaml
vendored
6
.github/workflows/nightly.yaml
vendored
@@ -6,7 +6,7 @@ on:
|
|||||||
- cron: "0 1 * * *"
|
- cron: "0 1 * * *"
|
||||||
|
|
||||||
env:
|
env:
|
||||||
PYTHON_VERSION: "3.13"
|
PYTHON_VERSION: "3.12"
|
||||||
NODE_OPTIONS: --max_old_space_size=6144
|
NODE_OPTIONS: --max_old_space_size=6144
|
||||||
|
|
||||||
permissions:
|
permissions:
|
||||||
@@ -57,14 +57,14 @@ jobs:
|
|||||||
run: tar -czvf translations.tar.gz translations
|
run: tar -czvf translations.tar.gz translations
|
||||||
|
|
||||||
- name: Upload build artifacts
|
- name: Upload build artifacts
|
||||||
uses: actions/upload-artifact@v4.6.0
|
uses: actions/upload-artifact@v4.4.3
|
||||||
with:
|
with:
|
||||||
name: wheels
|
name: wheels
|
||||||
path: dist/home_assistant_frontend*.whl
|
path: dist/home_assistant_frontend*.whl
|
||||||
if-no-files-found: error
|
if-no-files-found: error
|
||||||
|
|
||||||
- name: Upload translations
|
- name: Upload translations
|
||||||
uses: actions/upload-artifact@v4.6.0
|
uses: actions/upload-artifact@v4.4.3
|
||||||
with:
|
with:
|
||||||
name: translations
|
name: translations
|
||||||
path: translations.tar.gz
|
path: translations.tar.gz
|
||||||
|
16
.github/workflows/release.yaml
vendored
16
.github/workflows/release.yaml
vendored
@@ -6,7 +6,7 @@ on:
|
|||||||
- published
|
- published
|
||||||
|
|
||||||
env:
|
env:
|
||||||
PYTHON_VERSION: "3.13"
|
PYTHON_VERSION: "3.12"
|
||||||
NODE_OPTIONS: --max_old_space_size=6144
|
NODE_OPTIONS: --max_old_space_size=6144
|
||||||
|
|
||||||
# Set default workflow permissions
|
# Set default workflow permissions
|
||||||
@@ -25,14 +25,14 @@ jobs:
|
|||||||
- name: Checkout the repository
|
- name: Checkout the repository
|
||||||
uses: actions/checkout@v4.2.2
|
uses: actions/checkout@v4.2.2
|
||||||
|
|
||||||
|
- name: Verify version
|
||||||
|
uses: home-assistant/actions/helpers/verify-version@master
|
||||||
|
|
||||||
- name: Set up Python ${{ env.PYTHON_VERSION }}
|
- name: Set up Python ${{ env.PYTHON_VERSION }}
|
||||||
uses: actions/setup-python@v5
|
uses: actions/setup-python@v5
|
||||||
with:
|
with:
|
||||||
python-version: ${{ env.PYTHON_VERSION }}
|
python-version: ${{ env.PYTHON_VERSION }}
|
||||||
|
|
||||||
- name: Verify version
|
|
||||||
uses: home-assistant/actions/helpers/verify-version@master
|
|
||||||
|
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
uses: actions/setup-node@v4.1.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
@@ -55,7 +55,7 @@ jobs:
|
|||||||
script/release
|
script/release
|
||||||
|
|
||||||
- name: Upload release assets
|
- name: Upload release assets
|
||||||
uses: softprops/action-gh-release@v2.2.1
|
uses: softprops/action-gh-release@v2.1.0
|
||||||
with:
|
with:
|
||||||
files: |
|
files: |
|
||||||
dist/*.whl
|
dist/*.whl
|
||||||
@@ -76,7 +76,7 @@ jobs:
|
|||||||
- name: Build wheels
|
- name: Build wheels
|
||||||
uses: home-assistant/wheels@2024.11.0
|
uses: home-assistant/wheels@2024.11.0
|
||||||
with:
|
with:
|
||||||
abi: cp313
|
abi: cp312
|
||||||
tag: musllinux_1_2
|
tag: musllinux_1_2
|
||||||
arch: amd64
|
arch: amd64
|
||||||
wheels-key: ${{ secrets.WHEELS_KEY }}
|
wheels-key: ${{ secrets.WHEELS_KEY }}
|
||||||
@@ -107,7 +107,7 @@ jobs:
|
|||||||
- name: Tar folder
|
- name: Tar folder
|
||||||
run: tar -czf landing-page/home_assistant_frontend_landingpage-${{ github.event.release.tag_name }}.tar.gz -C landing-page/dist .
|
run: tar -czf landing-page/home_assistant_frontend_landingpage-${{ github.event.release.tag_name }}.tar.gz -C landing-page/dist .
|
||||||
- name: Upload release asset
|
- name: Upload release asset
|
||||||
uses: softprops/action-gh-release@v2.2.1
|
uses: softprops/action-gh-release@v2.1.0
|
||||||
with:
|
with:
|
||||||
files: landing-page/home_assistant_frontend_landingpage-${{ github.event.release.tag_name }}.tar.gz
|
files: landing-page/home_assistant_frontend_landingpage-${{ github.event.release.tag_name }}.tar.gz
|
||||||
|
|
||||||
@@ -136,6 +136,6 @@ jobs:
|
|||||||
- name: Tar folder
|
- name: Tar folder
|
||||||
run: tar -czf hassio/home_assistant_frontend_supervisor-${{ github.event.release.tag_name }}.tar.gz -C hassio/build .
|
run: tar -czf hassio/home_assistant_frontend_supervisor-${{ github.event.release.tag_name }}.tar.gz -C hassio/build .
|
||||||
- name: Upload release asset
|
- name: Upload release asset
|
||||||
uses: softprops/action-gh-release@v2.2.1
|
uses: softprops/action-gh-release@v2.1.0
|
||||||
with:
|
with:
|
||||||
files: hassio/home_assistant_frontend_supervisor-${{ github.event.release.tag_name }}.tar.gz
|
files: hassio/home_assistant_frontend_supervisor-${{ github.event.release.tag_name }}.tar.gz
|
||||||
|
File diff suppressed because one or more lines are too long
@@ -6,4 +6,4 @@ enableGlobalCache: false
|
|||||||
|
|
||||||
nodeLinker: node-modules
|
nodeLinker: node-modules
|
||||||
|
|
||||||
yarnPath: .yarn/releases/yarn-4.6.0.cjs
|
yarnPath: .yarn/releases/yarn-4.5.3.cjs
|
||||||
|
@@ -5,7 +5,7 @@ import paths from "../paths.cjs";
|
|||||||
const POLYFILL_DIR = join(paths.polymer_dir, "src/resources/polyfills");
|
const POLYFILL_DIR = join(paths.polymer_dir, "src/resources/polyfills");
|
||||||
|
|
||||||
// List of polyfill keys with supported browser targets for the functionality
|
// List of polyfill keys with supported browser targets for the functionality
|
||||||
const polyfillSupport = {
|
const PolyfillSupport = {
|
||||||
// Note states and shadowRoot properties should be supported.
|
// Note states and shadowRoot properties should be supported.
|
||||||
"element-internals": {
|
"element-internals": {
|
||||||
android: 90,
|
android: 90,
|
||||||
@@ -18,6 +18,17 @@ const polyfillSupport = {
|
|||||||
safari: 17.4,
|
safari: 17.4,
|
||||||
samsung: 15.0,
|
samsung: 15.0,
|
||||||
},
|
},
|
||||||
|
"element-append": {
|
||||||
|
android: 54,
|
||||||
|
chrome: 54,
|
||||||
|
edge: 17,
|
||||||
|
firefox: 49,
|
||||||
|
ios: 10.0,
|
||||||
|
opera: 41,
|
||||||
|
opera_mobile: 41,
|
||||||
|
safari: 10.0,
|
||||||
|
samsung: 6.0,
|
||||||
|
},
|
||||||
"element-getattributenames": {
|
"element-getattributenames": {
|
||||||
android: 61,
|
android: 61,
|
||||||
chrome: 61,
|
chrome: 61,
|
||||||
@@ -40,18 +51,27 @@ const polyfillSupport = {
|
|||||||
safari: 12.0,
|
safari: 12.0,
|
||||||
samsung: 10.0,
|
samsung: 10.0,
|
||||||
},
|
},
|
||||||
// FormatJS polyfill detects fix for https://bugs.chromium.org/p/v8/issues/detail?id=10682,
|
fetch: {
|
||||||
// so adjusted to several months after that was marked fixed
|
android: 42,
|
||||||
|
chrome: 42,
|
||||||
|
edge: 14,
|
||||||
|
firefox: 39,
|
||||||
|
ios: 10.3,
|
||||||
|
opera: 29,
|
||||||
|
opera_mobile: 29,
|
||||||
|
safari: 10.1,
|
||||||
|
samsung: 4.0,
|
||||||
|
},
|
||||||
"intl-getcanonicallocales": {
|
"intl-getcanonicallocales": {
|
||||||
android: 90,
|
android: 54,
|
||||||
chrome: 90,
|
chrome: 54,
|
||||||
edge: 90,
|
edge: 16,
|
||||||
firefox: 48,
|
firefox: 48,
|
||||||
ios: 10.3,
|
ios: 10.3,
|
||||||
opera: 76,
|
opera: 41,
|
||||||
opera_mobile: 64,
|
opera_mobile: 41,
|
||||||
safari: 10.1,
|
safari: 10.1,
|
||||||
samsung: 15.0,
|
samsung: 6.0,
|
||||||
},
|
},
|
||||||
"intl-locale": {
|
"intl-locale": {
|
||||||
android: 74,
|
android: 74,
|
||||||
@@ -67,6 +87,17 @@ const polyfillSupport = {
|
|||||||
"intl-other": {
|
"intl-other": {
|
||||||
// Not specified (i.e. always try polyfill) since compatibility depends on supported locales
|
// Not specified (i.e. always try polyfill) since compatibility depends on supported locales
|
||||||
},
|
},
|
||||||
|
proxy: {
|
||||||
|
android: 49,
|
||||||
|
chrome: 49,
|
||||||
|
edge: 12,
|
||||||
|
firefox: 18,
|
||||||
|
ios: 10.0,
|
||||||
|
opera: 36,
|
||||||
|
opera_mobile: 36,
|
||||||
|
safari: 10.0,
|
||||||
|
samsung: 5.0,
|
||||||
|
},
|
||||||
"resize-observer": {
|
"resize-observer": {
|
||||||
android: 64,
|
android: 64,
|
||||||
chrome: 64,
|
chrome: 64,
|
||||||
@@ -84,6 +115,8 @@ const polyfillSupport = {
|
|||||||
// corresponding polyfill key and actual module to import
|
// corresponding polyfill key and actual module to import
|
||||||
const polyfillMap = {
|
const polyfillMap = {
|
||||||
global: {
|
global: {
|
||||||
|
fetch: { key: "fetch", module: "unfetch/polyfill" },
|
||||||
|
Proxy: { key: "proxy", module: "proxy-polyfill" },
|
||||||
ResizeObserver: {
|
ResizeObserver: {
|
||||||
key: "resize-observer",
|
key: "resize-observer",
|
||||||
module: join(POLYFILL_DIR, "resize-observer.ts"),
|
module: join(POLYFILL_DIR, "resize-observer.ts"),
|
||||||
@@ -95,7 +128,7 @@ const polyfillMap = {
|
|||||||
module: "element-internals-polyfill",
|
module: "element-internals-polyfill",
|
||||||
},
|
},
|
||||||
...Object.fromEntries(
|
...Object.fromEntries(
|
||||||
["getAttributeNames", "toggleAttribute"].map((prop) => {
|
["append", "getAttributeNames", "toggleAttribute"].map((prop) => {
|
||||||
const key = `element-${prop.toLowerCase()}`;
|
const key = `element-${prop.toLowerCase()}`;
|
||||||
return [prop, { key, module: join(POLYFILL_DIR, `${key}.ts`) }];
|
return [prop, { key, module: join(POLYFILL_DIR, `${key}.ts`) }];
|
||||||
})
|
})
|
||||||
@@ -135,7 +168,7 @@ export default defineProvider(
|
|||||||
const resolvePolyfill = createMetaResolver(polyfillMap);
|
const resolvePolyfill = createMetaResolver(polyfillMap);
|
||||||
return {
|
return {
|
||||||
name: "custom-polyfill",
|
name: "custom-polyfill",
|
||||||
polyfills: polyfillSupport,
|
polyfills: PolyfillSupport,
|
||||||
usageGlobal(meta, utils) {
|
usageGlobal(meta, utils) {
|
||||||
const polyfill = resolvePolyfill(meta);
|
const polyfill = resolvePolyfill(meta);
|
||||||
if (polyfill && shouldInjectPolyfill(polyfill.desc.key)) {
|
if (polyfill && shouldInjectPolyfill(polyfill.desc.key)) {
|
||||||
|
@@ -9,7 +9,7 @@ export default [
|
|||||||
"import/extensions": "off",
|
"import/extensions": "off",
|
||||||
"import/no-dynamic-require": "off",
|
"import/no-dynamic-require": "off",
|
||||||
"global-require": "off",
|
"global-require": "off",
|
||||||
"@typescript-eslint/no-require-imports": "off",
|
"@typescript-eslint/no-var-requires": "off",
|
||||||
"prefer-arrow-callback": "off",
|
"prefer-arrow-callback": "off",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
@@ -3,7 +3,6 @@
|
|||||||
import { constants } from "node:zlib";
|
import { constants } from "node:zlib";
|
||||||
import gulp from "gulp";
|
import gulp from "gulp";
|
||||||
import brotli from "gulp-brotli";
|
import brotli from "gulp-brotli";
|
||||||
import zopfli from "gulp-zopfli-green";
|
|
||||||
import paths from "../paths.cjs";
|
import paths from "../paths.cjs";
|
||||||
|
|
||||||
const filesGlob = "*.{js,json,css,svg,xml}";
|
const filesGlob = "*.{js,json,css,svg,xml}";
|
||||||
@@ -13,18 +12,17 @@ const brotliOptions = {
|
|||||||
[constants.BROTLI_PARAM_QUALITY]: constants.BROTLI_MAX_QUALITY,
|
[constants.BROTLI_PARAM_QUALITY]: constants.BROTLI_MAX_QUALITY,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
const zopfliOptions = { threshold: 150 };
|
|
||||||
|
|
||||||
const compressModern = (rootDir, modernDir, compress) =>
|
const compressModern = (rootDir, modernDir) =>
|
||||||
gulp
|
gulp
|
||||||
.src([`${modernDir}/**/${filesGlob}`, `${rootDir}/sw-modern.js`], {
|
.src([`${modernDir}/**/${filesGlob}`, `${rootDir}/sw-modern.js`], {
|
||||||
base: rootDir,
|
base: rootDir,
|
||||||
allowEmpty: true,
|
allowEmpty: true,
|
||||||
})
|
})
|
||||||
.pipe(compress === "zopfli" ? zopfli(zopfliOptions) : brotli(brotliOptions))
|
.pipe(brotli(brotliOptions))
|
||||||
.pipe(gulp.dest(rootDir));
|
.pipe(gulp.dest(rootDir));
|
||||||
|
|
||||||
const compressOther = (rootDir, modernDir, compress) =>
|
const compressOther = (rootDir, modernDir) =>
|
||||||
gulp
|
gulp
|
||||||
.src(
|
.src(
|
||||||
[
|
[
|
||||||
@@ -35,52 +33,21 @@ const compressOther = (rootDir, modernDir, compress) =>
|
|||||||
],
|
],
|
||||||
{ base: rootDir, allowEmpty: true }
|
{ base: rootDir, allowEmpty: true }
|
||||||
)
|
)
|
||||||
.pipe(compress === "zopfli" ? zopfli(zopfliOptions) : brotli(brotliOptions))
|
.pipe(brotli(brotliOptions))
|
||||||
.pipe(gulp.dest(rootDir));
|
.pipe(gulp.dest(rootDir));
|
||||||
|
|
||||||
const compressAppModernBrotli = () =>
|
const compressAppModern = () =>
|
||||||
compressModern(paths.app_output_root, paths.app_output_latest, "brotli");
|
compressModern(paths.app_output_root, paths.app_output_latest);
|
||||||
const compressAppModernZopfli = () =>
|
const compressHassioModern = () =>
|
||||||
compressModern(paths.app_output_root, paths.app_output_latest, "zopfli");
|
compressModern(paths.hassio_output_root, paths.hassio_output_latest);
|
||||||
|
|
||||||
const compressHassioModernBrotli = () =>
|
const compressAppOther = () =>
|
||||||
compressModern(
|
compressOther(paths.app_output_root, paths.app_output_latest);
|
||||||
paths.hassio_output_root,
|
const compressHassioOther = () =>
|
||||||
paths.hassio_output_latest,
|
compressOther(paths.hassio_output_root, paths.hassio_output_latest);
|
||||||
"brotli"
|
|
||||||
);
|
|
||||||
const compressHassioModernZopfli = () =>
|
|
||||||
compressModern(
|
|
||||||
paths.hassio_output_root,
|
|
||||||
paths.hassio_output_latest,
|
|
||||||
"zopfli"
|
|
||||||
);
|
|
||||||
|
|
||||||
const compressAppOtherBrotli = () =>
|
gulp.task("compress-app", gulp.parallel(compressAppModern, compressAppOther));
|
||||||
compressOther(paths.app_output_root, paths.app_output_latest, "brotli");
|
|
||||||
const compressAppOtherZopfli = () =>
|
|
||||||
compressOther(paths.app_output_root, paths.app_output_latest, "zopfli");
|
|
||||||
|
|
||||||
const compressHassioOtherBrotli = () =>
|
|
||||||
compressOther(paths.hassio_output_root, paths.hassio_output_latest, "brotli");
|
|
||||||
const compressHassioOtherZopfli = () =>
|
|
||||||
compressOther(paths.hassio_output_root, paths.hassio_output_latest, "zopfli");
|
|
||||||
|
|
||||||
gulp.task(
|
|
||||||
"compress-app",
|
|
||||||
gulp.parallel(
|
|
||||||
compressAppModernBrotli,
|
|
||||||
compressAppOtherBrotli,
|
|
||||||
compressAppModernZopfli,
|
|
||||||
compressAppOtherZopfli
|
|
||||||
)
|
|
||||||
);
|
|
||||||
gulp.task(
|
gulp.task(
|
||||||
"compress-hassio",
|
"compress-hassio",
|
||||||
gulp.parallel(
|
gulp.parallel(compressHassioModern, compressHassioOther)
|
||||||
compressHassioModernBrotli,
|
|
||||||
compressHassioOtherBrotli,
|
|
||||||
compressHassioModernZopfli,
|
|
||||||
compressHassioOtherZopfli
|
|
||||||
)
|
|
||||||
);
|
);
|
||||||
|
@@ -67,6 +67,12 @@ function copyPolyfills(staticDir) {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function copyLoaderJS(staticDir) {
|
||||||
|
const staticPath = genStaticPath(staticDir);
|
||||||
|
copyFileDir(npmPath("systemjs/dist/s.min.js"), staticPath("js"));
|
||||||
|
copyFileDir(npmPath("systemjs/dist/s.min.js.map"), staticPath("js"));
|
||||||
|
}
|
||||||
|
|
||||||
function copyFonts(staticDir) {
|
function copyFonts(staticDir) {
|
||||||
const staticPath = genStaticPath(staticDir);
|
const staticPath = genStaticPath(staticDir);
|
||||||
// Local fonts
|
// Local fonts
|
||||||
@@ -134,6 +140,8 @@ gulp.task("copy-static-app", async () => {
|
|||||||
const staticDir = paths.app_output_static;
|
const staticDir = paths.app_output_static;
|
||||||
// Basic static files
|
// Basic static files
|
||||||
fs.copySync(polyPath("public"), paths.app_output_root);
|
fs.copySync(polyPath("public"), paths.app_output_root);
|
||||||
|
|
||||||
|
copyLoaderJS(staticDir);
|
||||||
copyPolyfills(staticDir);
|
copyPolyfills(staticDir);
|
||||||
copyFonts(staticDir);
|
copyFonts(staticDir);
|
||||||
copyTranslations(staticDir);
|
copyTranslations(staticDir);
|
||||||
@@ -156,6 +164,8 @@ gulp.task("copy-static-demo", async () => {
|
|||||||
);
|
);
|
||||||
// Copy demo static files
|
// Copy demo static files
|
||||||
fs.copySync(path.resolve(paths.demo_dir, "public"), paths.demo_output_root);
|
fs.copySync(path.resolve(paths.demo_dir, "public"), paths.demo_output_root);
|
||||||
|
|
||||||
|
copyLoaderJS(paths.demo_output_static);
|
||||||
copyPolyfills(paths.demo_output_static);
|
copyPolyfills(paths.demo_output_static);
|
||||||
copyMapPanel(paths.demo_output_static);
|
copyMapPanel(paths.demo_output_static);
|
||||||
copyFonts(paths.demo_output_static);
|
copyFonts(paths.demo_output_static);
|
||||||
@@ -169,6 +179,8 @@ gulp.task("copy-static-cast", async () => {
|
|||||||
fs.copySync(polyPath("public/static"), paths.cast_output_static);
|
fs.copySync(polyPath("public/static"), paths.cast_output_static);
|
||||||
// Copy cast static files
|
// Copy cast static files
|
||||||
fs.copySync(path.resolve(paths.cast_dir, "public"), paths.cast_output_root);
|
fs.copySync(path.resolve(paths.cast_dir, "public"), paths.cast_output_root);
|
||||||
|
|
||||||
|
copyLoaderJS(paths.cast_output_static);
|
||||||
copyPolyfills(paths.cast_output_static);
|
copyPolyfills(paths.cast_output_static);
|
||||||
copyMapPanel(paths.cast_output_static);
|
copyMapPanel(paths.cast_output_static);
|
||||||
copyFonts(paths.cast_output_static);
|
copyFonts(paths.cast_output_static);
|
||||||
|
@@ -1,17 +0,0 @@
|
|||||||
import "./app.js";
|
|
||||||
import "./cast.js";
|
|
||||||
import "./clean.js";
|
|
||||||
import "./compress.js";
|
|
||||||
import "./demo.js";
|
|
||||||
import "./download-translations.js";
|
|
||||||
import "./entry-html.js";
|
|
||||||
import "./fetch-nightly-translations.js";
|
|
||||||
import "./gallery.js";
|
|
||||||
import "./gather-static.js";
|
|
||||||
import "./gen-icons-json.js";
|
|
||||||
import "./hassio.js";
|
|
||||||
import "./landing-page.js";
|
|
||||||
import "./locale-data.js";
|
|
||||||
import "./rspack.js";
|
|
||||||
import "./service-worker.js";
|
|
||||||
import "./translations.js";
|
|
@@ -25,7 +25,7 @@ Home Assistant Cast is made up of two separate applications:
|
|||||||
|
|
||||||
### Setting dev variables
|
### Setting dev variables
|
||||||
|
|
||||||
Open `src/cast/dev_const.ts` and change `CAST_DEV_APP_ID` to the ID of the app you just created. And set the `CAST_DEV_HASS_URL` to the url of your development machine.
|
Open `src/cast/dev_const.ts` and change `CAST_DEV_APP_ID` to the ID of the app you just created. And set the `CAST_DEV_HASS_URL` to the url of you development machine.
|
||||||
|
|
||||||
### Changing configuration
|
### Changing configuration
|
||||||
|
|
||||||
|
@@ -7,6 +7,7 @@
|
|||||||
<%= renderTemplate("../../../src/html/_style_base.html.template") %>
|
<%= renderTemplate("../../../src/html/_style_base.html.template") %>
|
||||||
<style>
|
<style>
|
||||||
body {
|
body {
|
||||||
|
background-color: white;
|
||||||
font-size: initial;
|
font-size: initial;
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
@@ -3,7 +3,7 @@ import "@material/mwc-list/mwc-list";
|
|||||||
import type { ActionDetail } from "@material/mwc-list/mwc-list";
|
import type { ActionDetail } from "@material/mwc-list/mwc-list";
|
||||||
import { mdiCast, mdiCastConnected, mdiViewDashboard } from "@mdi/js";
|
import { mdiCast, mdiCastConnected, mdiViewDashboard } from "@mdi/js";
|
||||||
import type { Auth, Connection } from "home-assistant-js-websocket";
|
import type { Auth, Connection } from "home-assistant-js-websocket";
|
||||||
import type { TemplateResult } from "lit";
|
import type { CSSResultGroup, TemplateResult } from "lit";
|
||||||
import { LitElement, css, html } from "lit";
|
import { LitElement, css, html } from "lit";
|
||||||
import { customElement, property, state } from "lit/decorators";
|
import { customElement, property, state } from "lit/decorators";
|
||||||
import type { CastManager } from "../../../../src/cast/cast_manager";
|
import type { CastManager } from "../../../../src/cast/cast_manager";
|
||||||
@@ -203,12 +203,13 @@ class HcCast extends LitElement {
|
|||||||
}
|
}
|
||||||
this.connection.close();
|
this.connection.close();
|
||||||
location.reload();
|
location.reload();
|
||||||
} catch (_err: any) {
|
} catch (err: any) {
|
||||||
alert("Unable to log out!");
|
alert("Unable to log out!");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
.center-item {
|
.center-item {
|
||||||
display: flex;
|
display: flex;
|
||||||
justify-content: space-around;
|
justify-content: space-around;
|
||||||
@@ -270,6 +271,7 @@ class HcCast extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -13,7 +13,7 @@ import {
|
|||||||
ERR_INVALID_HTTPS_TO_HTTP,
|
ERR_INVALID_HTTPS_TO_HTTP,
|
||||||
getAuth,
|
getAuth,
|
||||||
} from "home-assistant-js-websocket";
|
} from "home-assistant-js-websocket";
|
||||||
import type { TemplateResult } from "lit";
|
import type { CSSResultGroup, TemplateResult } from "lit";
|
||||||
import { css, html, LitElement } from "lit";
|
import { css, html, LitElement } from "lit";
|
||||||
import { customElement, state } from "lit/decorators";
|
import { customElement, state } from "lit/decorators";
|
||||||
import type { CastManager } from "../../../../src/cast/cast_manager";
|
import type { CastManager } from "../../../../src/cast/cast_manager";
|
||||||
@@ -215,7 +215,7 @@ export class HcConnect extends LitElement {
|
|||||||
let url: URL;
|
let url: URL;
|
||||||
try {
|
try {
|
||||||
url = new URL(value);
|
url = new URL(value);
|
||||||
} catch (_err: any) {
|
} catch (err: any) {
|
||||||
this.error = "Invalid URL";
|
this.error = "Invalid URL";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -252,7 +252,7 @@ export class HcConnect extends LitElement {
|
|||||||
this.loading = false;
|
this.loading = false;
|
||||||
return;
|
return;
|
||||||
} finally {
|
} finally {
|
||||||
// Clear url if we have an auth callback in url.
|
// Clear url if we have a auth callback in url.
|
||||||
if (location.search.includes("auth_callback=1")) {
|
if (location.search.includes("auth_callback=1")) {
|
||||||
history.replaceState(null, "", location.pathname);
|
history.replaceState(null, "", location.pathname);
|
||||||
}
|
}
|
||||||
@@ -288,12 +288,13 @@ export class HcConnect extends LitElement {
|
|||||||
try {
|
try {
|
||||||
saveTokens(null);
|
saveTokens(null);
|
||||||
location.reload();
|
location.reload();
|
||||||
} catch (_err: any) {
|
} catch (err: any) {
|
||||||
alert("Unable to log out!");
|
alert("Unable to log out!");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
.card-content a {
|
.card-content a {
|
||||||
color: var(--primary-color);
|
color: var(--primary-color);
|
||||||
}
|
}
|
||||||
@@ -322,6 +323,7 @@ export class HcConnect extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -1,6 +1,6 @@
|
|||||||
import type { Auth, Connection, HassUser } from "home-assistant-js-websocket";
|
import type { Auth, Connection, HassUser } from "home-assistant-js-websocket";
|
||||||
import { getUser } from "home-assistant-js-websocket";
|
import { getUser } from "home-assistant-js-websocket";
|
||||||
import type { TemplateResult } from "lit";
|
import type { CSSResultGroup, TemplateResult } from "lit";
|
||||||
import { css, html, LitElement } from "lit";
|
import { css, html, LitElement } from "lit";
|
||||||
import { customElement, property } from "lit/decorators";
|
import { customElement, property } from "lit/decorators";
|
||||||
import "../../../../src/components/ha-card";
|
import "../../../../src/components/ha-card";
|
||||||
@@ -63,7 +63,8 @@ class HcLayout extends LitElement {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
:host {
|
:host {
|
||||||
display: flex;
|
display: flex;
|
||||||
min-height: 100%;
|
min-height: 100%;
|
||||||
@@ -152,6 +153,7 @@ class HcLayout extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -1,4 +1,4 @@
|
|||||||
import type { TemplateResult } from "lit";
|
import type { CSSResultGroup, TemplateResult } from "lit";
|
||||||
import { css, html, LitElement } from "lit";
|
import { css, html, LitElement } from "lit";
|
||||||
import { customElement, property } from "lit/decorators";
|
import { customElement, property } from "lit/decorators";
|
||||||
import type { HomeAssistant } from "../../../../src/types";
|
import type { HomeAssistant } from "../../../../src/types";
|
||||||
@@ -24,7 +24,8 @@ class HcLaunchScreen extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
:host {
|
:host {
|
||||||
display: block;
|
display: block;
|
||||||
height: 100vh;
|
height: 100vh;
|
||||||
@@ -48,6 +49,7 @@ class HcLaunchScreen extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -1,4 +1,10 @@
|
|||||||
import { css, html, LitElement, type TemplateResult } from "lit";
|
import {
|
||||||
|
css,
|
||||||
|
type CSSResultGroup,
|
||||||
|
html,
|
||||||
|
LitElement,
|
||||||
|
type TemplateResult,
|
||||||
|
} from "lit";
|
||||||
import { customElement, property } from "lit/decorators";
|
import { customElement, property } from "lit/decorators";
|
||||||
import { fireEvent } from "../../../../src/common/dom/fire_event";
|
import { fireEvent } from "../../../../src/common/dom/fire_event";
|
||||||
import type { LovelaceConfig } from "../../../../src/data/lovelace/config/types";
|
import type { LovelaceConfig } from "../../../../src/data/lovelace/config/types";
|
||||||
@@ -8,7 +14,6 @@ import "../../../../src/panels/lovelace/views/hui-view";
|
|||||||
import "../../../../src/panels/lovelace/views/hui-view-container";
|
import "../../../../src/panels/lovelace/views/hui-view-container";
|
||||||
import type { HomeAssistant } from "../../../../src/types";
|
import type { HomeAssistant } from "../../../../src/types";
|
||||||
import "./hc-launch-screen";
|
import "./hc-launch-screen";
|
||||||
import "../../../../src/panels/lovelace/views/hui-view-background";
|
|
||||||
|
|
||||||
(window as any).loadCardHelpers = () =>
|
(window as any).loadCardHelpers = () =>
|
||||||
import("../../../../src/panels/lovelace/custom-card-helpers");
|
import("../../../../src/panels/lovelace/custom-card-helpers");
|
||||||
@@ -52,9 +57,11 @@ class HcLovelace extends LitElement {
|
|||||||
const background = viewConfig.background || this.lovelaceConfig.background;
|
const background = viewConfig.background || this.lovelaceConfig.background;
|
||||||
|
|
||||||
return html`
|
return html`
|
||||||
<hui-view-container .hass=${this.hass} .theme=${viewConfig.theme}>
|
<hui-view-container
|
||||||
<hui-view-background .hass=${this.hass} .background=${background}>
|
.hass=${this.hass}
|
||||||
</hui-view-background>
|
.background=${background}
|
||||||
|
.theme=${viewConfig.theme}
|
||||||
|
>
|
||||||
<hui-view
|
<hui-view
|
||||||
.hass=${this.hass}
|
.hass=${this.hass}
|
||||||
.lovelace=${lovelace}
|
.lovelace=${lovelace}
|
||||||
@@ -111,19 +118,21 @@ class HcLovelace extends LitElement {
|
|||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
hui-view-container {
|
hui-view-container {
|
||||||
display: flex;
|
display: flex;
|
||||||
position: relative;
|
position: relative;
|
||||||
min-height: 100vh;
|
min-height: 100vh;
|
||||||
box-sizing: border-box;
|
box-sizing: border-box;
|
||||||
}
|
}
|
||||||
hui-view-container > * {
|
hui-view {
|
||||||
flex: 1 1 100%;
|
flex: 1 1 100%;
|
||||||
max-width: 100%;
|
max-width: 100%;
|
||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
export interface CastViewChanged {
|
export interface CastViewChanged {
|
||||||
title: string | undefined;
|
title: string | undefined;
|
||||||
|
@@ -3,7 +3,7 @@ import type { Lovelace } from "../../../src/panels/lovelace/types";
|
|||||||
import { energyEntities } from "../stubs/entities";
|
import { energyEntities } from "../stubs/entities";
|
||||||
import type { DemoConfig } from "./types";
|
import type { DemoConfig } from "./types";
|
||||||
|
|
||||||
export const demoConfigs: (() => Promise<DemoConfig>)[] = [
|
export const demoConfigs: Array<() => Promise<DemoConfig>> = [
|
||||||
() => import("./sections").then((mod) => mod.demoSections),
|
() => import("./sections").then((mod) => mod.demoSections),
|
||||||
() => import("./arsaboo").then((mod) => mod.demoArsaboo),
|
() => import("./arsaboo").then((mod) => mod.demoArsaboo),
|
||||||
() => import("./teachingbirds").then((mod) => mod.demoTeachingbirds),
|
() => import("./teachingbirds").then((mod) => mod.demoTeachingbirds),
|
||||||
|
@@ -1,4 +1,5 @@
|
|||||||
import { mdiTelevision } from "@mdi/js";
|
import { mdiTelevision } from "@mdi/js";
|
||||||
|
import type { CSSResultGroup } from "lit";
|
||||||
import { css, html, LitElement, nothing } from "lit";
|
import { css, html, LitElement, nothing } from "lit";
|
||||||
import { customElement, state } from "lit/decorators";
|
import { customElement, state } from "lit/decorators";
|
||||||
import type { CastManager } from "../../../src/cast/cast_manager";
|
import type { CastManager } from "../../../src/cast/cast_manager";
|
||||||
@@ -66,7 +67,8 @@ class CastDemoRow extends LitElement implements LovelaceRow {
|
|||||||
this.style.display = this._castManager ? "" : "none";
|
this.style.display = this._castManager ? "" : "none";
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
:host {
|
:host {
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
@@ -96,6 +98,7 @@ class CastDemoRow extends LitElement implements LovelaceRow {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -32,7 +32,6 @@ export class HADemoCard extends LitElement implements LovelaceCard {
|
|||||||
return this._hidden ? 0 : 2;
|
return this._hidden ? 0 : 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
// eslint-disable-next-line @typescript-eslint/no-empty-function
|
|
||||||
public setConfig(_config: LovelaceCardConfig) {}
|
public setConfig(_config: LovelaceCardConfig) {}
|
||||||
|
|
||||||
protected render() {
|
protected render() {
|
||||||
|
@@ -131,7 +131,6 @@ export const mockHistory = (mockHass: MockHomeAssistant) => {
|
|||||||
});
|
});
|
||||||
}, 1);
|
}, 1);
|
||||||
|
|
||||||
// eslint-disable-next-line @typescript-eslint/no-empty-function
|
|
||||||
return () => {};
|
return () => {};
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
@@ -43,7 +43,7 @@ customElements.whenDefined("hui-root").then(() => {
|
|||||||
const index = (ev as CustomEvent).detail.index;
|
const index = (ev as CustomEvent).detail.index;
|
||||||
try {
|
try {
|
||||||
await setDemoConfig(this.hass, this.lovelace!, index);
|
await setDemoConfig(this.hass, this.lovelace!, index);
|
||||||
} catch (_err: any) {
|
} catch (err: any) {
|
||||||
setDemoConfig(this.hass, this.lovelace!, selectedDemoConfigIndex);
|
setDemoConfig(this.hass, this.lovelace!, selectedDemoConfigIndex);
|
||||||
alert("Failed to switch config :-(");
|
alert("Failed to switch config :-(");
|
||||||
}
|
}
|
||||||
|
@@ -15,7 +15,6 @@ export const mockPersistentNotification = (hass: MockHomeAssistant) => {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
} as PersistentNotificationMessage);
|
} as PersistentNotificationMessage);
|
||||||
// eslint-disable-next-line @typescript-eslint/no-empty-function
|
|
||||||
return () => {};
|
return () => {};
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
@@ -15,7 +15,7 @@ import type { MockHomeAssistant } from "../../../src/fake_data/provide_hass";
|
|||||||
const generateMeanStatistics = (
|
const generateMeanStatistics = (
|
||||||
start: Date,
|
start: Date,
|
||||||
end: Date,
|
end: Date,
|
||||||
// eslint-disable-next-line default-param-last
|
// eslint-disable-next-line @typescript-eslint/default-param-last
|
||||||
period: "5minute" | "hour" | "day" | "month" = "hour",
|
period: "5minute" | "hour" | "day" | "month" = "hour",
|
||||||
initValue: number,
|
initValue: number,
|
||||||
maxDiff: number
|
maxDiff: number
|
||||||
@@ -52,7 +52,7 @@ const generateMeanStatistics = (
|
|||||||
const generateSumStatistics = (
|
const generateSumStatistics = (
|
||||||
start: Date,
|
start: Date,
|
||||||
end: Date,
|
end: Date,
|
||||||
// eslint-disable-next-line default-param-last
|
// eslint-disable-next-line @typescript-eslint/default-param-last
|
||||||
period: "5minute" | "hour" | "day" | "month" = "hour",
|
period: "5minute" | "hour" | "day" | "month" = "hour",
|
||||||
initValue: number,
|
initValue: number,
|
||||||
maxDiff: number
|
maxDiff: number
|
||||||
@@ -89,7 +89,7 @@ const generateSumStatistics = (
|
|||||||
const generateCurvedStatistics = (
|
const generateCurvedStatistics = (
|
||||||
start: Date,
|
start: Date,
|
||||||
end: Date,
|
end: Date,
|
||||||
// eslint-disable-next-line default-param-last
|
// eslint-disable-next-line @typescript-eslint/default-param-last
|
||||||
_period: "5minute" | "hour" | "day" | "month" = "hour",
|
_period: "5minute" | "hour" | "day" | "month" = "hour",
|
||||||
initValue: number,
|
initValue: number,
|
||||||
maxDiff: number,
|
maxDiff: number,
|
||||||
|
@@ -11,7 +11,6 @@ export const mockTemplate = (hass: MockHomeAssistant) => {
|
|||||||
result: msg.template,
|
result: msg.template,
|
||||||
listeners: { all: false, domains: [], entities: [], time: false },
|
listeners: { all: false, domains: [], entities: [], time: false },
|
||||||
});
|
});
|
||||||
// eslint-disable-next-line @typescript-eslint/no-empty-function
|
|
||||||
return () => {};
|
return () => {};
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
@@ -22,6 +22,5 @@ export const mockTodo = (hass: MockHomeAssistant) => {
|
|||||||
},
|
},
|
||||||
] as TodoItem[],
|
] as TodoItem[],
|
||||||
}));
|
}));
|
||||||
// eslint-disable-next-line @typescript-eslint/no-empty-function
|
|
||||||
hass.mockWS("todo/item/subscribe", (_msg, _hass) => () => {});
|
hass.mockWS("todo/item/subscribe", (_msg, _hass) => () => {});
|
||||||
};
|
};
|
||||||
|
@@ -18,9 +18,8 @@ const compat = new FlatCompat({
|
|||||||
export default [
|
export default [
|
||||||
...compat.extends(
|
...compat.extends(
|
||||||
"airbnb-base",
|
"airbnb-base",
|
||||||
|
"airbnb-typescript/base",
|
||||||
"plugin:@typescript-eslint/recommended",
|
"plugin:@typescript-eslint/recommended",
|
||||||
"plugin:@typescript-eslint/strict",
|
|
||||||
"plugin:@typescript-eslint/stylistic",
|
|
||||||
"plugin:wc/recommended",
|
"plugin:wc/recommended",
|
||||||
"plugin:lit/all",
|
"plugin:lit/all",
|
||||||
"plugin:lit-a11y/recommended",
|
"plugin:lit-a11y/recommended",
|
||||||
@@ -51,6 +50,8 @@ export default [
|
|||||||
ecmaFeatures: {
|
ecmaFeatures: {
|
||||||
modules: true,
|
modules: true,
|
||||||
},
|
},
|
||||||
|
|
||||||
|
project: "./tsconfig.json",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|
||||||
@@ -147,15 +148,15 @@ export default [
|
|||||||
},
|
},
|
||||||
],
|
],
|
||||||
|
|
||||||
"@typescript-eslint/no-unused-vars": [
|
"@typescript-eslint/no-unused-vars": "off",
|
||||||
|
|
||||||
|
"unused-imports/no-unused-vars": [
|
||||||
"error",
|
"error",
|
||||||
{
|
{
|
||||||
args: "all",
|
vars: "all",
|
||||||
argsIgnorePattern: "^_",
|
|
||||||
caughtErrors: "all",
|
|
||||||
caughtErrorsIgnorePattern: "^_",
|
|
||||||
destructuredArrayIgnorePattern: "^_",
|
|
||||||
varsIgnorePattern: "^_",
|
varsIgnorePattern: "^_",
|
||||||
|
args: "after-used",
|
||||||
|
argsIgnorePattern: "^_",
|
||||||
ignoreRestSiblings: true,
|
ignoreRestSiblings: true,
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
@@ -173,16 +174,6 @@ export default [
|
|||||||
"lit-a11y/role-has-required-aria-attrs": "error",
|
"lit-a11y/role-has-required-aria-attrs": "error",
|
||||||
"@typescript-eslint/consistent-type-imports": "error",
|
"@typescript-eslint/consistent-type-imports": "error",
|
||||||
"@typescript-eslint/no-import-type-side-effects": "error",
|
"@typescript-eslint/no-import-type-side-effects": "error",
|
||||||
camelcase: "off",
|
|
||||||
"@typescript-eslint/no-dynamic-delete": "off",
|
|
||||||
"@typescript-eslint/no-empty-object-type": [
|
|
||||||
"error",
|
|
||||||
{
|
|
||||||
allowInterfaces: "always",
|
|
||||||
allowObjectTypes: "always",
|
|
||||||
},
|
|
||||||
],
|
|
||||||
"no-use-before-define": "off",
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
@@ -42,7 +42,7 @@ In most cases, Create can be paired with Delete, and Add can be paired with Remo
|
|||||||
|
|
||||||
## Add
|
## Add
|
||||||
|
|
||||||
An already-existing item.
|
An already-exisiting item.
|
||||||
|
|
||||||
For example:
|
For example:
|
||||||
|
|
||||||
|
@@ -177,7 +177,8 @@ export class DemoAutomationDescribeAction extends LitElement {
|
|||||||
this._action = ev.detail.isValid ? ev.detail.value : undefined;
|
this._action = ev.detail.isValid ? ev.detail.value : undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -196,6 +197,7 @@ export class DemoAutomationDescribeAction extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -98,7 +98,8 @@ export class DemoAutomationDescribeCondition extends LitElement {
|
|||||||
this._condition = ev.detail.isValid ? ev.detail.value : undefined;
|
this._condition = ev.detail.isValid ? ev.detail.value : undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -117,6 +118,7 @@ export class DemoAutomationDescribeCondition extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -121,7 +121,8 @@ export class DemoAutomationDescribeTrigger extends LitElement {
|
|||||||
this._trigger = ev.detail.isValid ? ev.detail.value : undefined;
|
this._trigger = ev.detail.isValid ? ev.detail.value : undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -140,6 +141,7 @@ export class DemoAutomationDescribeTrigger extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -58,7 +58,8 @@ export class DemoAutomationTraceTimeline extends LitElement {
|
|||||||
hass.updateTranslations("config", "en");
|
hass.updateTranslations("config", "en");
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px;
|
margin: 24px;
|
||||||
@@ -73,6 +74,7 @@ export class DemoAutomationTraceTimeline extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -68,7 +68,8 @@ export class DemoAutomationTrace extends LitElement {
|
|||||||
this._selected = { ...this._selected, [sampleIdx]: ev.detail.path };
|
this._selected = { ...this._selected, [sampleIdx]: ev.detail.path };
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px;
|
margin: 24px;
|
||||||
@@ -89,6 +90,7 @@ export class DemoAutomationTrace extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -19,7 +19,7 @@ The alert offers four severity levels that set a distinctive icon and color.
|
|||||||
</ha-alert>
|
</ha-alert>
|
||||||
|
|
||||||
<ha-alert alert-type="warning">
|
<ha-alert alert-type="warning">
|
||||||
This is a warning alert — check it out!
|
This is an warning alert — check it out!
|
||||||
</ha-alert>
|
</ha-alert>
|
||||||
|
|
||||||
<ha-alert alert-type="info">
|
<ha-alert alert-type="info">
|
||||||
@@ -27,7 +27,7 @@ The alert offers four severity levels that set a distinctive icon and color.
|
|||||||
</ha-alert>
|
</ha-alert>
|
||||||
|
|
||||||
<ha-alert alert-type="success">
|
<ha-alert alert-type="success">
|
||||||
This is a success alert — check it out!
|
This is an success alert — check it out!
|
||||||
</ha-alert>
|
</ha-alert>
|
||||||
|
|
||||||
**Note:** This component is by <a href="https://mui.com/components/alert/" rel="noopener noreferrer" target="_blank">MUI</a> and is not documented in the <a href="https://material.io" rel="noopener noreferrer" target="_blank">Material Design guidelines</a>.
|
**Note:** This component is by <a href="https://mui.com/components/alert/" rel="noopener noreferrer" target="_blank">MUI</a> and is not documented in the <a href="https://material.io" rel="noopener noreferrer" target="_blank">Material Design guidelines</a>.
|
||||||
@@ -95,7 +95,7 @@ Actions must have a tab index of 0 so that they can be reached by keyboard-only
|
|||||||
</ha-alert>
|
</ha-alert>
|
||||||
|
|
||||||
<ha-alert alert-type="warning">
|
<ha-alert alert-type="warning">
|
||||||
This is a warning alert — check it out!
|
This is an warning alert — check it out!
|
||||||
</ha-alert>
|
</ha-alert>
|
||||||
|
|
||||||
<ha-alert alert-type="info">
|
<ha-alert alert-type="info">
|
||||||
@@ -103,7 +103,7 @@ Actions must have a tab index of 0 so that they can be reached by keyboard-only
|
|||||||
</ha-alert>
|
</ha-alert>
|
||||||
|
|
||||||
<ha-alert alert-type="success">
|
<ha-alert alert-type="success">
|
||||||
This is a success alert — check it out!
|
This is an success alert — check it out!
|
||||||
</ha-alert>
|
</ha-alert>
|
||||||
|
|
||||||
```html
|
```html
|
||||||
@@ -122,37 +122,37 @@ Actions must have a tab index of 0 so that they can be reached by keyboard-only
|
|||||||
The `title ` option should not be used without a description.
|
The `title ` option should not be used without a description.
|
||||||
|
|
||||||
<ha-alert alert-type="success" title="Success">
|
<ha-alert alert-type="success" title="Success">
|
||||||
This is a success alert — check it out!
|
This is an success alert — check it out!
|
||||||
</ha-alert>
|
</ha-alert>
|
||||||
|
|
||||||
```html
|
```html
|
||||||
<ha-alert alert-type="success" title="Success">
|
<ha-alert alert-type="success" title="Success">
|
||||||
This is a success alert — check it out!
|
This is an success alert — check it out!
|
||||||
</ha-alert>
|
</ha-alert>
|
||||||
```
|
```
|
||||||
|
|
||||||
**Dismissable**
|
**Dismissable**
|
||||||
|
|
||||||
<ha-alert alert-type="success" dismissable>
|
<ha-alert alert-type="success" dismissable>
|
||||||
This is a success alert — check it out!
|
This is an success alert — check it out!
|
||||||
</ha-alert>
|
</ha-alert>
|
||||||
|
|
||||||
```html
|
```html
|
||||||
<ha-alert alert-type="success" dismissable>
|
<ha-alert alert-type="success" dismissable>
|
||||||
This is a success alert — check it out!
|
This is an success alert — check it out!
|
||||||
</ha-alert>
|
</ha-alert>
|
||||||
```
|
```
|
||||||
|
|
||||||
**Slotted action**
|
**Slotted action**
|
||||||
|
|
||||||
<ha-alert alert-type="success">
|
<ha-alert alert-type="success">
|
||||||
This is a success alert — check it out!
|
This is an success alert — check it out!
|
||||||
<mwc-button slot="action" label="Undo"></mwc-button>
|
<mwc-button slot="action" label="Undo"></mwc-button>
|
||||||
</ha-alert>
|
</ha-alert>
|
||||||
|
|
||||||
```html
|
```html
|
||||||
<ha-alert alert-type="success">
|
<ha-alert alert-type="success">
|
||||||
This is a success alert — check it out!
|
This is an success alert — check it out!
|
||||||
<mwc-button slot="action" label="Undo"></mwc-button>
|
<mwc-button slot="action" label="Undo"></mwc-button>
|
||||||
</ha-alert>
|
</ha-alert>
|
||||||
```
|
```
|
||||||
|
@@ -177,7 +177,8 @@ export class DemoHaAlert extends LitElement {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
:host {
|
:host {
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: row;
|
flex-direction: row;
|
||||||
@@ -216,6 +217,7 @@ export class DemoHaAlert extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -63,7 +63,8 @@ export class DemoHaBar extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -76,6 +77,7 @@ export class DemoHaBar extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -103,7 +103,8 @@ export class DemoHaChips extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -115,6 +116,7 @@ export class DemoHaChips extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -48,13 +48,15 @@ export class DemoHaCircularProgress extends LitElement {
|
|||||||
></ha-card>`;
|
></ha-card>`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -14,12 +14,12 @@ import "../../../../src/components/ha-card";
|
|||||||
import "../../../../src/components/ha-svg-icon";
|
import "../../../../src/components/ha-svg-icon";
|
||||||
import "../../../../src/components/ha-control-button-group";
|
import "../../../../src/components/ha-control-button-group";
|
||||||
|
|
||||||
interface Button {
|
type Button = {
|
||||||
label: string;
|
label: string;
|
||||||
icon?: string;
|
icon?: string;
|
||||||
class?: string;
|
class?: string;
|
||||||
disabled?: boolean;
|
disabled?: boolean;
|
||||||
}
|
};
|
||||||
|
|
||||||
const buttons: Button[] = [
|
const buttons: Button[] = [
|
||||||
{
|
{
|
||||||
@@ -35,10 +35,10 @@ const buttons: Button[] = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
interface ButtonGroup {
|
type ButtonGroup = {
|
||||||
vertical?: boolean;
|
vertical?: boolean;
|
||||||
class?: string;
|
class?: string;
|
||||||
}
|
};
|
||||||
|
|
||||||
const buttonGroups: ButtonGroup[] = [
|
const buttonGroups: ButtonGroup[] = [
|
||||||
{},
|
{},
|
||||||
@@ -137,7 +137,8 @@ export class DemoHaBarButton extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -183,6 +184,7 @@ export class DemoHaBarButton extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -133,7 +133,8 @@ export class DemoHaCircularSlider extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -165,6 +166,7 @@ export class DemoHaCircularSlider extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -73,7 +73,8 @@ export class DemoHarControlNumberButtons extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -98,6 +99,7 @@ export class DemoHarControlNumberButtons extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -8,19 +8,19 @@ import "../../../../src/components/ha-control-select-menu";
|
|||||||
import "../../../../src/components/ha-list-item";
|
import "../../../../src/components/ha-list-item";
|
||||||
import "../../../../src/components/ha-svg-icon";
|
import "../../../../src/components/ha-svg-icon";
|
||||||
|
|
||||||
interface SelectMenuOptions {
|
type SelectMenuOptions = {
|
||||||
label: string;
|
label: string;
|
||||||
value: string;
|
value: string;
|
||||||
icon?: string;
|
icon?: string;
|
||||||
}
|
};
|
||||||
|
|
||||||
interface SelectMenu {
|
type SelectMenu = {
|
||||||
label: string;
|
label: string;
|
||||||
icon: string;
|
icon: string;
|
||||||
class?: string;
|
class?: string;
|
||||||
disabled?: boolean;
|
disabled?: boolean;
|
||||||
options: SelectMenuOptions[];
|
options: SelectMenuOptions[];
|
||||||
}
|
};
|
||||||
|
|
||||||
const selects: SelectMenu[] = [
|
const selects: SelectMenu[] = [
|
||||||
{
|
{
|
||||||
@@ -112,7 +112,8 @@ export class DemoHaControlSelectMenu extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -137,6 +138,7 @@ export class DemoHaControlSelectMenu extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -168,7 +168,8 @@ export class DemoHaControlSelect extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -203,6 +204,7 @@ export class DemoHaControlSelect extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -131,7 +131,8 @@ export class DemoHaBarSlider extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -167,6 +168,7 @@ export class DemoHaBarSlider extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -99,7 +99,8 @@ export class DemoHaControlSwitch extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -136,6 +137,7 @@ export class DemoHaControlSwitch extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -143,12 +143,14 @@ export class DemoHaExpansionPanel extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-expansion-panel {
|
ha-expansion-panel {
|
||||||
margin: -16px;
|
margin: -16px;
|
||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -20,7 +20,7 @@ export class DemoHaFaded extends LitElement {
|
|||||||
<ha-faded><span>${LONG_TEXT}</span></ha-faded>
|
<ha-faded><span>${LONG_TEXT}</span></ha-faded>
|
||||||
<h3>No text</h3>
|
<h3>No text</h3>
|
||||||
<ha-faded><span></span></ha-faded>
|
<ha-faded><span></span></ha-faded>
|
||||||
<h3>Small text</h3>
|
<h3>Smal text</h3>
|
||||||
<ha-faded><span>${SMALL_TEXT}</span></ha-faded>
|
<ha-faded><span>${SMALL_TEXT}</span></ha-faded>
|
||||||
<h3>Long text in markdown</h3>
|
<h3>Long text in markdown</h3>
|
||||||
<ha-faded>
|
<ha-faded>
|
||||||
@@ -61,13 +61,15 @@ export class DemoHaFaded extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -76,7 +76,7 @@ export class DemoHaHsColorPicker extends LitElement {
|
|||||||
@change=${this._saturationChanged}
|
@change=${this._saturationChanged}
|
||||||
>
|
>
|
||||||
</ha-slider>
|
</ha-slider>
|
||||||
<p>Color Brightness : ${this.brightness}</p>
|
<p>Color Brighness : ${this.brightness}</p>
|
||||||
<ha-slider
|
<ha-slider
|
||||||
labeled
|
labeled
|
||||||
step="1"
|
step="1"
|
||||||
@@ -91,7 +91,8 @@ export class DemoHaHsColorPicker extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -111,6 +112,7 @@ export class DemoHaHsColorPicker extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -95,7 +95,8 @@ export class DemoHaLabelBadge extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
margin: 24px auto;
|
margin: 24px auto;
|
||||||
@@ -113,6 +114,7 @@ export class DemoHaLabelBadge extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -48,7 +48,8 @@ export class DemoHaTip extends LitElement {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
:host {
|
:host {
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: row;
|
flex-direction: row;
|
||||||
@@ -68,6 +69,7 @@ export class DemoHaTip extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -100,7 +100,8 @@ export class DemoDateTimeDateTimeNumeric extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-control-select {
|
ha-control-select {
|
||||||
max-width: 800px;
|
max-width: 800px;
|
||||||
margin: 12px auto;
|
margin: 12px auto;
|
||||||
@@ -125,6 +126,7 @@ export class DemoDateTimeDateTimeNumeric extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -100,7 +100,8 @@ export class DemoDateTimeDateTimeSeconds extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-control-select {
|
ha-control-select {
|
||||||
max-width: 800px;
|
max-width: 800px;
|
||||||
margin: 12px auto;
|
margin: 12px auto;
|
||||||
@@ -125,6 +126,7 @@ export class DemoDateTimeDateTimeSeconds extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -100,7 +100,8 @@ export class DemoDateTimeDateTimeShortYear extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-control-select {
|
ha-control-select {
|
||||||
max-width: 800px;
|
max-width: 800px;
|
||||||
margin: 12px auto;
|
margin: 12px auto;
|
||||||
@@ -125,6 +126,7 @@ export class DemoDateTimeDateTimeShortYear extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -100,7 +100,8 @@ export class DemoDateTimeDateTimeShort extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-control-select {
|
ha-control-select {
|
||||||
max-width: 800px;
|
max-width: 800px;
|
||||||
margin: 12px auto;
|
margin: 12px auto;
|
||||||
@@ -125,6 +126,7 @@ export class DemoDateTimeDateTimeShort extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -100,7 +100,8 @@ export class DemoDateTimeDateTime extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-control-select {
|
ha-control-select {
|
||||||
max-width: 800px;
|
max-width: 800px;
|
||||||
margin: 12px auto;
|
margin: 12px auto;
|
||||||
@@ -125,6 +126,7 @@ export class DemoDateTimeDateTime extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -90,7 +90,8 @@ export class DemoDateTimeDate extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
.header {
|
.header {
|
||||||
font-weight: bold;
|
font-weight: bold;
|
||||||
}
|
}
|
||||||
@@ -111,6 +112,7 @@ export class DemoDateTimeDate extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -100,7 +100,8 @@ export class DemoDateTimeTimeSeconds extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-control-select {
|
ha-control-select {
|
||||||
max-width: 800px;
|
max-width: 800px;
|
||||||
margin: 12px auto;
|
margin: 12px auto;
|
||||||
@@ -125,6 +126,7 @@ export class DemoDateTimeTimeSeconds extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -100,7 +100,8 @@ export class DemoDateTimeTimeWeekday extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-control-select {
|
ha-control-select {
|
||||||
max-width: 800px;
|
max-width: 800px;
|
||||||
margin: 12px auto;
|
margin: 12px auto;
|
||||||
@@ -125,6 +126,7 @@ export class DemoDateTimeTimeWeekday extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -100,7 +100,8 @@ export class DemoDateTimeTime extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-control-select {
|
ha-control-select {
|
||||||
max-width: 800px;
|
max-width: 800px;
|
||||||
margin: 12px auto;
|
margin: 12px auto;
|
||||||
@@ -125,6 +126,7 @@ export class DemoDateTimeTime extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -321,13 +321,13 @@ function createEntity(
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
interface EntityRowData {
|
type EntityRowData = {
|
||||||
stateObj: HassEntity;
|
stateObj: HassEntity;
|
||||||
entity_id: string;
|
entity_id: string;
|
||||||
state: string;
|
state: string;
|
||||||
device_class?: string;
|
device_class?: string;
|
||||||
domain: string;
|
domain: string;
|
||||||
}
|
};
|
||||||
|
|
||||||
function createRowData(stateObj: HassEntity): EntityRowData {
|
function createRowData(stateObj: HassEntity): EntityRowData {
|
||||||
return {
|
return {
|
||||||
@@ -429,7 +429,8 @@ export class DemoEntityState extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
.color {
|
.color {
|
||||||
display: block;
|
display: block;
|
||||||
height: 20px;
|
height: 20px;
|
||||||
@@ -439,6 +440,7 @@ export class DemoEntityState extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -76,13 +76,15 @@ export class DemoMiscMarkdown extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
ha-card {
|
ha-card {
|
||||||
margin: 12px;
|
margin: 12px;
|
||||||
padding: 12px;
|
padding: 12px;
|
||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -135,12 +135,12 @@ const configFlows: DataEntryFlowProgressExtended[] = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
const configEntries: {
|
const configEntries: Array<{
|
||||||
items: ConfigEntryExtended[];
|
items: ConfigEntryExtended[];
|
||||||
is_custom?: boolean;
|
is_custom?: boolean;
|
||||||
disabled?: boolean;
|
disabled?: boolean;
|
||||||
highlight?: string;
|
highlight?: string;
|
||||||
}[] = [
|
}> = [
|
||||||
{ items: [loadedEntry] },
|
{ items: [loadedEntry] },
|
||||||
{ items: [configPanelEntry] },
|
{ items: [configPanelEntry] },
|
||||||
{ items: [optionsFlowEntry] },
|
{ items: [optionsFlowEntry] },
|
||||||
@@ -349,7 +349,8 @@ export class DemoIntegrationCard extends LitElement {
|
|||||||
this.isCloud = !this.isCloud;
|
this.isCloud = !this.isCloud;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
|
return css`
|
||||||
.container {
|
.container {
|
||||||
display: grid;
|
display: grid;
|
||||||
grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));
|
grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));
|
||||||
@@ -368,6 +369,7 @@ export class DemoIntegrationCard extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
14
gulpfile.js
14
gulpfile.js
@@ -1,4 +1,16 @@
|
|||||||
|
import { globIterate } from "glob";
|
||||||
import { availableParallelism } from "node:os";
|
import { availableParallelism } from "node:os";
|
||||||
import "./build-scripts/gulp/index.mjs";
|
|
||||||
|
|
||||||
process.env.UV_THREADPOOL_SIZE = availableParallelism();
|
process.env.UV_THREADPOOL_SIZE = availableParallelism();
|
||||||
|
|
||||||
|
const gulpImports = [];
|
||||||
|
|
||||||
|
for await (const gulpModule of globIterate("build-scripts/gulp/*.?(c|m)js", {
|
||||||
|
dotRelative: true,
|
||||||
|
})) {
|
||||||
|
gulpImports.push(import(gulpModule));
|
||||||
|
}
|
||||||
|
|
||||||
|
// Since all tasks are currently registered with gulp.task(), this is enough
|
||||||
|
// If any are converted to named exports, need to loop and aggregate exports here
|
||||||
|
await Promise.all(gulpImports);
|
||||||
|
@@ -1,7 +1,7 @@
|
|||||||
import type { ActionDetail } from "@material/mwc-list/mwc-list-foundation";
|
import type { ActionDetail } from "@material/mwc-list/mwc-list-foundation";
|
||||||
import "@material/mwc-list/mwc-list-item";
|
import "@material/mwc-list/mwc-list-item";
|
||||||
import { mdiDotsVertical } from "@mdi/js";
|
import { mdiDotsVertical } from "@mdi/js";
|
||||||
import type { PropertyValues, TemplateResult } from "lit";
|
import type { CSSResultGroup, PropertyValues, TemplateResult } from "lit";
|
||||||
import { css, html, LitElement, nothing } from "lit";
|
import { css, html, LitElement, nothing } from "lit";
|
||||||
import { customElement, property, state } from "lit/decorators";
|
import { customElement, property, state } from "lit/decorators";
|
||||||
import memoizeOne from "memoize-one";
|
import memoizeOne from "memoize-one";
|
||||||
@@ -211,7 +211,8 @@ export class HassioAddonStore extends LitElement {
|
|||||||
this._filter = e.detail.value;
|
this._filter = e.detail.value;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
hassio-addon-repository {
|
hassio-addon-repository {
|
||||||
margin-top: 24px;
|
margin-top: 24px;
|
||||||
}
|
}
|
||||||
@@ -239,6 +240,7 @@ export class HassioAddonStore extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -299,7 +299,7 @@ class HassioAddonConfig extends LitElement {
|
|||||||
if (this.addon.schema && this._canShowSchema && !this._yamlMode) {
|
if (this.addon.schema && this._canShowSchema && !this._yamlMode) {
|
||||||
this._valid = true;
|
this._valid = true;
|
||||||
this._configHasChanged = true;
|
this._configHasChanged = true;
|
||||||
this._options = ev.detail.value;
|
this._options! = ev.detail.value;
|
||||||
} else {
|
} else {
|
||||||
this._configHasChanged = true;
|
this._configHasChanged = true;
|
||||||
this._valid = ev.detail.isValid;
|
this._valid = ev.detail.isValid;
|
||||||
|
@@ -151,7 +151,7 @@ class HassioAddonNetwork extends LitElement {
|
|||||||
|
|
||||||
private async _configChanged(ev: CustomEvent): Promise<void> {
|
private async _configChanged(ev: CustomEvent): Promise<void> {
|
||||||
this._configHasChanged = true;
|
this._configHasChanged = true;
|
||||||
this._config = ev.detail.value;
|
this._config! = ev.detail.value;
|
||||||
}
|
}
|
||||||
|
|
||||||
private async _resetTapped(ev: CustomEvent): Promise<void> {
|
private async _resetTapped(ev: CustomEvent): Promise<void> {
|
||||||
|
@@ -1,5 +1,5 @@
|
|||||||
import { mdiHelpCircle } from "@mdi/js";
|
import { mdiHelpCircle } from "@mdi/js";
|
||||||
import type { TemplateResult } from "lit";
|
import type { CSSResultGroup, TemplateResult } from "lit";
|
||||||
import { css, html, LitElement } from "lit";
|
import { css, html, LitElement } from "lit";
|
||||||
import { customElement, property } from "lit/decorators";
|
import { customElement, property } from "lit/decorators";
|
||||||
import "../../../src/components/ha-svg-icon";
|
import "../../../src/components/ha-svg-icon";
|
||||||
@@ -64,7 +64,8 @@ class HassioCardContent extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
:host {
|
:host {
|
||||||
direction: ltr;
|
direction: ltr;
|
||||||
}
|
}
|
||||||
@@ -143,6 +144,7 @@ class HassioCardContent extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -1,7 +1,7 @@
|
|||||||
import { mdiFolderUpload } from "@mdi/js";
|
import { mdiFolderUpload } from "@mdi/js";
|
||||||
import type { TemplateResult } from "lit";
|
import type { TemplateResult } from "lit";
|
||||||
import { html, LitElement } from "lit";
|
import { html, LitElement } from "lit";
|
||||||
import { customElement, property, state } from "lit/decorators";
|
import { customElement, state } from "lit/decorators";
|
||||||
import { fireEvent } from "../../../src/common/dom/fire_event";
|
import { fireEvent } from "../../../src/common/dom/fire_event";
|
||||||
import "../../../src/components/ha-circular-progress";
|
import "../../../src/components/ha-circular-progress";
|
||||||
import "../../../src/components/ha-file-upload";
|
import "../../../src/components/ha-file-upload";
|
||||||
@@ -10,12 +10,10 @@ import { uploadBackup } from "../../../src/data/hassio/backup";
|
|||||||
import { extractApiErrorMessage } from "../../../src/data/hassio/common";
|
import { extractApiErrorMessage } from "../../../src/data/hassio/common";
|
||||||
import { showAlertDialog } from "../../../src/dialogs/generic/show-dialog-box";
|
import { showAlertDialog } from "../../../src/dialogs/generic/show-dialog-box";
|
||||||
import type { HomeAssistant } from "../../../src/types";
|
import type { HomeAssistant } from "../../../src/types";
|
||||||
import type { LocalizeFunc } from "../../../src/common/translations/localize";
|
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HASSDomEvents {
|
interface HASSDomEvents {
|
||||||
"backup-uploaded": { backup: HassioBackup };
|
"backup-uploaded": { backup: HassioBackup };
|
||||||
"backup-cleared": undefined;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -23,8 +21,6 @@ declare global {
|
|||||||
export class HassioUploadBackup extends LitElement {
|
export class HassioUploadBackup extends LitElement {
|
||||||
public hass?: HomeAssistant;
|
public hass?: HomeAssistant;
|
||||||
|
|
||||||
@property({ attribute: false }) public localize?: LocalizeFunc;
|
|
||||||
|
|
||||||
@state() public value: string | null = null;
|
@state() public value: string | null = null;
|
||||||
|
|
||||||
@state() private _uploading = false;
|
@state() private _uploading = false;
|
||||||
@@ -36,26 +32,13 @@ export class HassioUploadBackup extends LitElement {
|
|||||||
.uploading=${this._uploading}
|
.uploading=${this._uploading}
|
||||||
.icon=${mdiFolderUpload}
|
.icon=${mdiFolderUpload}
|
||||||
accept="application/x-tar"
|
accept="application/x-tar"
|
||||||
.label=${this.localize?.(
|
label="Upload backup"
|
||||||
"ui.panel.page-onboarding.restore.upload_backup"
|
supports="Supports .TAR files"
|
||||||
) || "Upload backup"}
|
|
||||||
.supports=${this.localize?.(
|
|
||||||
"ui.panel.page-onboarding.restore.upload_supports"
|
|
||||||
) || "Supports .TAR files"}
|
|
||||||
.secondary=${this.localize?.(
|
|
||||||
"ui.panel.page-onboarding.restore.upload_drop"
|
|
||||||
) || "Or drop your file here"}
|
|
||||||
@file-picked=${this._uploadFile}
|
@file-picked=${this._uploadFile}
|
||||||
@files-cleared=${this._clear}
|
|
||||||
></ha-file-upload>
|
></ha-file-upload>
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
private _clear() {
|
|
||||||
this.value = null;
|
|
||||||
fireEvent(this, "backup-cleared");
|
|
||||||
}
|
|
||||||
|
|
||||||
private async _uploadFile(ev) {
|
private async _uploadFile(ev) {
|
||||||
const file = ev.detail.files[0];
|
const file = ev.detail.files[0];
|
||||||
|
|
||||||
|
@@ -1,5 +1,5 @@
|
|||||||
import { mdiFolder, mdiPuzzle } from "@mdi/js";
|
import { mdiFolder, mdiPuzzle } from "@mdi/js";
|
||||||
import type { TemplateResult } from "lit";
|
import type { CSSResultGroup, TemplateResult } from "lit";
|
||||||
import { LitElement, css, html, nothing } from "lit";
|
import { LitElement, css, html, nothing } from "lit";
|
||||||
import { customElement, property, query } from "lit/decorators";
|
import { customElement, property, query } from "lit/decorators";
|
||||||
import { atLeastVersion } from "../../../src/common/config/version";
|
import { atLeastVersion } from "../../../src/common/config/version";
|
||||||
@@ -65,7 +65,7 @@ const _computeAddons = (addons): AddonCheckboxItem[] =>
|
|||||||
|
|
||||||
@customElement("supervisor-backup-content")
|
@customElement("supervisor-backup-content")
|
||||||
export class SupervisorBackupContent extends LitElement {
|
export class SupervisorBackupContent extends LitElement {
|
||||||
@property({ attribute: false }) public hass?: HomeAssistant;
|
@property({ attribute: false }) public hass!: HomeAssistant;
|
||||||
|
|
||||||
@property({ attribute: false }) public localize?: LocalizeFunc;
|
@property({ attribute: false }) public localize?: LocalizeFunc;
|
||||||
|
|
||||||
@@ -186,13 +186,12 @@ export class SupervisorBackupContent extends LitElement {
|
|||||||
.iconPath=${mdiHomeAssistant}
|
.iconPath=${mdiHomeAssistant}
|
||||||
.version=${this.backup
|
.version=${this.backup
|
||||||
? this.backup.homeassistant
|
? this.backup.homeassistant
|
||||||
: this.hass?.config.version}
|
: this.hass.config.version}
|
||||||
>
|
>
|
||||||
</supervisor-formfield-label>`}
|
</supervisor-formfield-label>`}
|
||||||
>
|
>
|
||||||
<ha-checkbox
|
<ha-checkbox
|
||||||
.checked=${this.onboarding || this.homeAssistant}
|
.checked=${this.homeAssistant}
|
||||||
.disabled=${this.onboarding}
|
|
||||||
@change=${this._toggleHomeAssistant}
|
@change=${this._toggleHomeAssistant}
|
||||||
>
|
>
|
||||||
</ha-checkbox>
|
</ha-checkbox>
|
||||||
@@ -283,7 +282,8 @@ export class SupervisorBackupContent extends LitElement {
|
|||||||
this.homeAssistant = !this.homeAssistant;
|
this.homeAssistant = !this.homeAssistant;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
.partial-picker ha-formfield {
|
.partial-picker ha-formfield {
|
||||||
display: block;
|
display: block;
|
||||||
}
|
}
|
||||||
@@ -327,13 +327,14 @@ export class SupervisorBackupContent extends LitElement {
|
|||||||
margin-top: 8px;
|
margin-top: 8px;
|
||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
|
}
|
||||||
|
|
||||||
public backupDetails():
|
public backupDetails():
|
||||||
| HassioPartialBackupCreateParams
|
| HassioPartialBackupCreateParams
|
||||||
| HassioFullBackupCreateParams {
|
| HassioFullBackupCreateParams {
|
||||||
const data: any = {};
|
const data: any = {};
|
||||||
|
|
||||||
if (!this.backup && this.hass) {
|
if (!this.backup) {
|
||||||
data.name =
|
data.name =
|
||||||
this.backupName ||
|
this.backupName ||
|
||||||
formatDate(new Date(), this.hass.locale, this.hass.config);
|
formatDate(new Date(), this.hass.locale, this.hass.config);
|
||||||
@@ -363,9 +364,7 @@ export class SupervisorBackupContent extends LitElement {
|
|||||||
if (folders?.length) {
|
if (folders?.length) {
|
||||||
data.folders = folders;
|
data.folders = folders;
|
||||||
}
|
}
|
||||||
|
data.homeassistant = this.homeAssistant;
|
||||||
// onboarding needs at least homeassistant to restore
|
|
||||||
data.homeassistant = this.onboarding || this.homeAssistant;
|
|
||||||
|
|
||||||
return data;
|
return data;
|
||||||
}
|
}
|
||||||
@@ -387,7 +386,6 @@ export class SupervisorBackupContent extends LitElement {
|
|||||||
.iconPath=${section === "addons" ? mdiPuzzle : mdiFolder}
|
.iconPath=${section === "addons" ? mdiPuzzle : mdiFolder}
|
||||||
.imageUrl=${section === "addons" &&
|
.imageUrl=${section === "addons" &&
|
||||||
!this.onboarding &&
|
!this.onboarding &&
|
||||||
this.hass &&
|
|
||||||
atLeastVersion(this.hass.config.version, 0, 105) &&
|
atLeastVersion(this.hass.config.version, 0, 105) &&
|
||||||
addons?.get(item.slug)?.icon
|
addons?.get(item.slug)?.icon
|
||||||
? `/api/hassio/addons/${item.slug}/icon`
|
? `/api/hassio/addons/${item.slug}/icon`
|
||||||
|
@@ -1,4 +1,4 @@
|
|||||||
import type { TemplateResult } from "lit";
|
import type { CSSResultGroup, TemplateResult } from "lit";
|
||||||
import { css, html, LitElement } from "lit";
|
import { css, html, LitElement } from "lit";
|
||||||
import { customElement, property } from "lit/decorators";
|
import { customElement, property } from "lit/decorators";
|
||||||
import "../../../src/components/ha-svg-icon";
|
import "../../../src/components/ha-svg-icon";
|
||||||
@@ -30,7 +30,8 @@ class SupervisorFormfieldLabel extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
:host {
|
:host {
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
@@ -52,6 +53,7 @@ class SupervisorFormfieldLabel extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -1,4 +1,4 @@
|
|||||||
import type { TemplateResult } from "lit";
|
import type { CSSResultGroup, TemplateResult } from "lit";
|
||||||
import { css, html, LitElement } from "lit";
|
import { css, html, LitElement } from "lit";
|
||||||
import { customElement, property } from "lit/decorators";
|
import { customElement, property } from "lit/decorators";
|
||||||
import { classMap } from "lit/directives/class-map";
|
import { classMap } from "lit/directives/class-map";
|
||||||
@@ -31,7 +31,8 @@ class SupervisorMetric extends LitElement {
|
|||||||
</ha-settings-row>`;
|
</ha-settings-row>`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
ha-settings-row {
|
ha-settings-row {
|
||||||
padding: 0;
|
padding: 0;
|
||||||
height: 54px;
|
height: 54px;
|
||||||
@@ -44,7 +45,10 @@ class SupervisorMetric extends LitElement {
|
|||||||
justify-content: space-between;
|
justify-content: space-between;
|
||||||
}
|
}
|
||||||
ha-bar {
|
ha-bar {
|
||||||
--ha-bar-primary-color: var(--hassio-bar-ok-color, var(--success-color));
|
--ha-bar-primary-color: var(
|
||||||
|
--hassio-bar-ok-color,
|
||||||
|
var(--success-color)
|
||||||
|
);
|
||||||
}
|
}
|
||||||
.target-warning {
|
.target-warning {
|
||||||
--ha-bar-primary-color: var(
|
--ha-bar-primary-color: var(
|
||||||
@@ -67,6 +71,7 @@ class SupervisorMetric extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -28,7 +28,7 @@ export class DialogHassioBackupUpload
|
|||||||
await this.updateComplete;
|
await this.updateComplete;
|
||||||
}
|
}
|
||||||
|
|
||||||
public closeDialog() {
|
public closeDialog(): void {
|
||||||
if (this._dialogParams && !this._dialogParams.onboarding) {
|
if (this._dialogParams && !this._dialogParams.onboarding) {
|
||||||
if (this._dialogParams.reloadBackup) {
|
if (this._dialogParams.reloadBackup) {
|
||||||
this._dialogParams.reloadBackup();
|
this._dialogParams.reloadBackup();
|
||||||
@@ -36,7 +36,6 @@ export class DialogHassioBackupUpload
|
|||||||
}
|
}
|
||||||
this._dialogParams = undefined;
|
this._dialogParams = undefined;
|
||||||
fireEvent(this, "dialog-closed", { dialog: this.localName });
|
fireEvent(this, "dialog-closed", { dialog: this.localName });
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
protected render() {
|
protected render() {
|
||||||
|
@@ -8,11 +8,9 @@ import { atLeastVersion } from "../../../../src/common/config/version";
|
|||||||
import { fireEvent } from "../../../../src/common/dom/fire_event";
|
import { fireEvent } from "../../../../src/common/dom/fire_event";
|
||||||
import { stopPropagation } from "../../../../src/common/dom/stop_propagation";
|
import { stopPropagation } from "../../../../src/common/dom/stop_propagation";
|
||||||
import { slugify } from "../../../../src/common/string/slugify";
|
import { slugify } from "../../../../src/common/string/slugify";
|
||||||
import "../../../../src/components/ha-md-dialog";
|
import "../../../../src/components/ha-dialog";
|
||||||
import "../../../../src/components/ha-dialog-header";
|
|
||||||
import "../../../../src/components/buttons/ha-progress-button";
|
import "../../../../src/components/buttons/ha-progress-button";
|
||||||
import "../../../../src/components/ha-alert";
|
import "../../../../src/components/ha-alert";
|
||||||
import "../../../../src/components/ha-button";
|
|
||||||
import "../../../../src/components/ha-button-menu";
|
import "../../../../src/components/ha-button-menu";
|
||||||
import "../../../../src/components/ha-header-bar";
|
import "../../../../src/components/ha-header-bar";
|
||||||
import "../../../../src/components/ha-icon-button";
|
import "../../../../src/components/ha-icon-button";
|
||||||
@@ -21,7 +19,6 @@ import type { HassioBackupDetail } from "../../../../src/data/hassio/backup";
|
|||||||
import {
|
import {
|
||||||
fetchHassioBackupInfo,
|
fetchHassioBackupInfo,
|
||||||
removeBackup,
|
removeBackup,
|
||||||
restoreBackup,
|
|
||||||
} from "../../../../src/data/hassio/backup";
|
} from "../../../../src/data/hassio/backup";
|
||||||
import { extractApiErrorMessage } from "../../../../src/data/hassio/common";
|
import { extractApiErrorMessage } from "../../../../src/data/hassio/common";
|
||||||
import {
|
import {
|
||||||
@@ -36,7 +33,6 @@ import "../../components/supervisor-backup-content";
|
|||||||
import type { SupervisorBackupContent } from "../../components/supervisor-backup-content";
|
import type { SupervisorBackupContent } from "../../components/supervisor-backup-content";
|
||||||
import type { HassioBackupDialogParams } from "./show-dialog-hassio-backup";
|
import type { HassioBackupDialogParams } from "./show-dialog-hassio-backup";
|
||||||
import type { BackupOrRestoreKey } from "../../util/translations";
|
import type { BackupOrRestoreKey } from "../../util/translations";
|
||||||
import type { HaMdDialog } from "../../../../src/components/ha-md-dialog";
|
|
||||||
|
|
||||||
@customElement("dialog-hassio-backup")
|
@customElement("dialog-hassio-backup")
|
||||||
class HassioBackupDialog
|
class HassioBackupDialog
|
||||||
@@ -56,20 +52,13 @@ class HassioBackupDialog
|
|||||||
@query("supervisor-backup-content")
|
@query("supervisor-backup-content")
|
||||||
private _backupContent!: SupervisorBackupContent;
|
private _backupContent!: SupervisorBackupContent;
|
||||||
|
|
||||||
@query("ha-md-dialog") private _dialog?: HaMdDialog;
|
|
||||||
|
|
||||||
public async showDialog(dialogParams: HassioBackupDialogParams) {
|
public async showDialog(dialogParams: HassioBackupDialogParams) {
|
||||||
this._dialogParams = dialogParams;
|
|
||||||
this._backup = await fetchHassioBackupInfo(this.hass, dialogParams.slug);
|
this._backup = await fetchHassioBackupInfo(this.hass, dialogParams.slug);
|
||||||
if (!this._backup) {
|
this._dialogParams = dialogParams;
|
||||||
this._error = this._localize("no_backup_found");
|
|
||||||
} else if (this._dialogParams.onboarding && !this._backup.homeassistant) {
|
|
||||||
this._error = this._localize("restore_no_home_assistant");
|
|
||||||
}
|
|
||||||
this._restoringBackup = false;
|
this._restoringBackup = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
private _dialogClosed(): void {
|
public closeDialog() {
|
||||||
this._backup = undefined;
|
this._backup = undefined;
|
||||||
this._dialogParams = undefined;
|
this._dialogParams = undefined;
|
||||||
this._restoringBackup = false;
|
this._restoringBackup = false;
|
||||||
@@ -77,11 +66,6 @@ class HassioBackupDialog
|
|||||||
fireEvent(this, "dialog-closed", { dialog: this.localName });
|
fireEvent(this, "dialog-closed", { dialog: this.localName });
|
||||||
}
|
}
|
||||||
|
|
||||||
public closeDialog() {
|
|
||||||
this._dialog?.close();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
private _localize(key: BackupOrRestoreKey) {
|
private _localize(key: BackupOrRestoreKey) {
|
||||||
return (
|
return (
|
||||||
this._dialogParams!.supervisor?.localize(`backup.${key}`) ||
|
this._dialogParams!.supervisor?.localize(`backup.${key}`) ||
|
||||||
@@ -94,26 +78,52 @@ class HassioBackupDialog
|
|||||||
return nothing;
|
return nothing;
|
||||||
}
|
}
|
||||||
return html`
|
return html`
|
||||||
<ha-md-dialog
|
<ha-dialog
|
||||||
open
|
open
|
||||||
.disableCancelAction=${!this._error}
|
scrimClickAction
|
||||||
@closed=${this._dialogClosed}
|
@closed=${this.closeDialog}
|
||||||
|
.heading=${this._backup.name}
|
||||||
>
|
>
|
||||||
<ha-dialog-header slot="headline">
|
<div slot="heading">
|
||||||
|
<ha-header-bar>
|
||||||
|
<span slot="title">${this._backup.name}</span>
|
||||||
<ha-icon-button
|
<ha-icon-button
|
||||||
slot="navigationIcon"
|
|
||||||
.label=${this._localize("close")}
|
.label=${this._localize("close")}
|
||||||
.path=${mdiClose}
|
.path=${mdiClose}
|
||||||
@click=${this.closeDialog}
|
slot="actionItems"
|
||||||
.disabled=${this._restoringBackup}
|
dialogAction="cancel"
|
||||||
></ha-icon-button>
|
></ha-icon-button>
|
||||||
<span slot="title" .title=${this._backup.name}
|
</ha-header-bar>
|
||||||
>${this._backup.name}</span
|
</div>
|
||||||
|
${this._restoringBackup
|
||||||
|
? html`<ha-circular-progress indeterminate></ha-circular-progress>`
|
||||||
|
: html`
|
||||||
|
<supervisor-backup-content
|
||||||
|
.hass=${this.hass}
|
||||||
|
.supervisor=${this._dialogParams.supervisor}
|
||||||
|
.backup=${this._backup}
|
||||||
|
.onboarding=${this._dialogParams.onboarding || false}
|
||||||
|
.localize=${this._dialogParams.localize}
|
||||||
|
dialogInitialFocus
|
||||||
>
|
>
|
||||||
|
</supervisor-backup-content>
|
||||||
|
`}
|
||||||
|
${this._error
|
||||||
|
? html`<ha-alert alert-type="error">${this._error}</ha-alert>`
|
||||||
|
: nothing}
|
||||||
|
|
||||||
|
<mwc-button
|
||||||
|
.disabled=${this._restoringBackup}
|
||||||
|
slot="secondaryAction"
|
||||||
|
@click=${this._restoreClicked}
|
||||||
|
>
|
||||||
|
${this._localize("restore")}
|
||||||
|
</mwc-button>
|
||||||
|
|
||||||
${!this._dialogParams.onboarding && this._dialogParams.supervisor
|
${!this._dialogParams.onboarding && this._dialogParams.supervisor
|
||||||
? html`<ha-button-menu
|
? html`<ha-button-menu
|
||||||
slot="actionItems"
|
|
||||||
fixed
|
fixed
|
||||||
|
slot="primaryAction"
|
||||||
@action=${this._handleMenuAction}
|
@action=${this._handleMenuAction}
|
||||||
@closed=${stopPropagation}
|
@closed=${stopPropagation}
|
||||||
>
|
>
|
||||||
@@ -136,38 +146,32 @@ class HassioBackupDialog
|
|||||||
>
|
>
|
||||||
</ha-button-menu>`
|
</ha-button-menu>`
|
||||||
: nothing}
|
: nothing}
|
||||||
</ha-dialog-header>
|
</ha-dialog>
|
||||||
<div slot="content">
|
|
||||||
${this._error
|
|
||||||
? html`<ha-alert alert-type="error">${this._error}</ha-alert>`
|
|
||||||
: this._restoringBackup
|
|
||||||
? html`<div class="loading">
|
|
||||||
<ha-circular-progress indeterminate></ha-circular-progress>
|
|
||||||
</div>`
|
|
||||||
: html`
|
|
||||||
<supervisor-backup-content
|
|
||||||
.hass=${this.hass}
|
|
||||||
.supervisor=${this._dialogParams.supervisor}
|
|
||||||
.backup=${this._backup}
|
|
||||||
.onboarding=${this._dialogParams.onboarding || false}
|
|
||||||
.localize=${this._dialogParams.localize}
|
|
||||||
dialogInitialFocus
|
|
||||||
>
|
|
||||||
</supervisor-backup-content>
|
|
||||||
`}
|
|
||||||
</div>
|
|
||||||
<div slot="actions">
|
|
||||||
<ha-button
|
|
||||||
.disabled=${this._restoringBackup || !!this._error}
|
|
||||||
@click=${this._restoreClicked}
|
|
||||||
>
|
|
||||||
${this._localize("restore")}
|
|
||||||
</ha-button>
|
|
||||||
</div>
|
|
||||||
</ha-md-dialog>
|
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static get styles(): CSSResultGroup {
|
||||||
|
return [
|
||||||
|
haStyle,
|
||||||
|
haStyleDialog,
|
||||||
|
css`
|
||||||
|
ha-circular-progress {
|
||||||
|
display: block;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
ha-header-bar {
|
||||||
|
--mdc-theme-on-primary: var(--primary-text-color);
|
||||||
|
--mdc-theme-primary: var(--mdc-theme-surface);
|
||||||
|
flex-shrink: 0;
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
ha-icon-button {
|
||||||
|
color: var(--secondary-text-color);
|
||||||
|
}
|
||||||
|
`,
|
||||||
|
];
|
||||||
|
}
|
||||||
|
|
||||||
private _handleMenuAction(ev: CustomEvent<ActionDetail>) {
|
private _handleMenuAction(ev: CustomEvent<ActionDetail>) {
|
||||||
switch (ev.detail.index) {
|
switch (ev.detail.index) {
|
||||||
case 0:
|
case 0:
|
||||||
@@ -182,7 +186,16 @@ class HassioBackupDialog
|
|||||||
private async _restoreClicked() {
|
private async _restoreClicked() {
|
||||||
const backupDetails = this._backupContent.backupDetails();
|
const backupDetails = this._backupContent.backupDetails();
|
||||||
this._restoringBackup = true;
|
this._restoringBackup = true;
|
||||||
|
this._dialogParams?.onRestoring?.();
|
||||||
|
if (this._backupContent.backupType === "full") {
|
||||||
|
await this._fullRestoreClicked(backupDetails);
|
||||||
|
} else {
|
||||||
|
await this._partialRestoreClicked(backupDetails);
|
||||||
|
}
|
||||||
|
this._restoringBackup = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
private async _partialRestoreClicked(backupDetails) {
|
||||||
const supervisor = this._dialogParams?.supervisor;
|
const supervisor = this._dialogParams?.supervisor;
|
||||||
if (supervisor !== undefined && supervisor.info.state !== "running") {
|
if (supervisor !== undefined && supervisor.info.state !== "running") {
|
||||||
await showAlertDialog(this, {
|
await showAlertDialog(this, {
|
||||||
@@ -191,45 +204,91 @@ class HassioBackupDialog
|
|||||||
state: supervisor.info.state,
|
state: supervisor.info.state,
|
||||||
}),
|
}),
|
||||||
});
|
});
|
||||||
this._restoringBackup = false;
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (
|
if (
|
||||||
!(await showConfirmationDialog(this, {
|
!(await showConfirmationDialog(this, {
|
||||||
title: this._localize(
|
title: this._localize("confirm_restore_partial_backup_title"),
|
||||||
this._backup!.type === "full"
|
text: this._localize("confirm_restore_partial_backup_text"),
|
||||||
? "confirm_restore_full_backup_title"
|
|
||||||
: "confirm_restore_partial_backup_title"
|
|
||||||
),
|
|
||||||
text: this._localize(
|
|
||||||
this._backup!.type === "full"
|
|
||||||
? "confirm_restore_full_backup_text"
|
|
||||||
: "confirm_restore_partial_backup_text"
|
|
||||||
),
|
|
||||||
confirmText: this._localize("restore"),
|
confirmText: this._localize("restore"),
|
||||||
dismissText: this._localize("cancel"),
|
dismissText: this._localize("cancel"),
|
||||||
}))
|
}))
|
||||||
) {
|
) {
|
||||||
this._restoringBackup = false;
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!this._dialogParams?.onboarding) {
|
||||||
try {
|
try {
|
||||||
await restoreBackup(
|
await this.hass!.callApi(
|
||||||
this.hass,
|
"POST",
|
||||||
this._backup!.type,
|
|
||||||
this._backup!.slug,
|
|
||||||
{ ...backupDetails, background: this._dialogParams?.onboarding },
|
|
||||||
!!this.hass && atLeastVersion(this.hass.config.version, 2021, 9)
|
|
||||||
);
|
|
||||||
|
|
||||||
this._dialogParams?.onRestoring?.();
|
`hassio/${
|
||||||
|
atLeastVersion(this.hass!.config.version, 2021, 9)
|
||||||
|
? "backups"
|
||||||
|
: "snapshots"
|
||||||
|
}/${this._backup!.slug}/restore/partial`,
|
||||||
|
backupDetails
|
||||||
|
);
|
||||||
this.closeDialog();
|
this.closeDialog();
|
||||||
} catch (error: any) {
|
} catch (error: any) {
|
||||||
this._error =
|
this._error = error.body.message;
|
||||||
error?.body?.message || this._localize("restore_start_failed");
|
}
|
||||||
} finally {
|
} else {
|
||||||
this._restoringBackup = false;
|
this._dialogParams?.onRestoring?.();
|
||||||
|
await fetch(`/api/hassio/backups/${this._backup!.slug}/restore/partial`, {
|
||||||
|
method: "POST",
|
||||||
|
body: JSON.stringify(backupDetails),
|
||||||
|
});
|
||||||
|
this.closeDialog();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private async _fullRestoreClicked(backupDetails) {
|
||||||
|
const supervisor = this._dialogParams?.supervisor;
|
||||||
|
if (supervisor !== undefined && supervisor.info.state !== "running") {
|
||||||
|
await showAlertDialog(this, {
|
||||||
|
title: supervisor.localize("backup.could_not_restore"),
|
||||||
|
text: supervisor.localize("backup.restore_blocked_not_running", {
|
||||||
|
state: supervisor.info.state,
|
||||||
|
}),
|
||||||
|
});
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (
|
||||||
|
!(await showConfirmationDialog(this, {
|
||||||
|
title: this._localize("confirm_restore_full_backup_title"),
|
||||||
|
text: this._localize("confirm_restore_full_backup_text"),
|
||||||
|
confirmText: this._localize("restore"),
|
||||||
|
dismissText: this._localize("cancel"),
|
||||||
|
}))
|
||||||
|
) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!this._dialogParams?.onboarding) {
|
||||||
|
this.hass!.callApi(
|
||||||
|
"POST",
|
||||||
|
`hassio/${
|
||||||
|
atLeastVersion(this.hass!.config.version, 2021, 9)
|
||||||
|
? "backups"
|
||||||
|
: "snapshots"
|
||||||
|
}/${this._backup!.slug}/restore/full`,
|
||||||
|
backupDetails
|
||||||
|
).then(
|
||||||
|
() => {
|
||||||
|
this.closeDialog();
|
||||||
|
},
|
||||||
|
(error) => {
|
||||||
|
this._error = error.body.message;
|
||||||
|
}
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
this._dialogParams?.onRestoring?.();
|
||||||
|
fetch(`/api/hassio/backups/${this._backup!.slug}/restore/full`, {
|
||||||
|
method: "POST",
|
||||||
|
body: JSON.stringify(backupDetails),
|
||||||
|
});
|
||||||
|
this.closeDialog();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -302,36 +361,7 @@ class HassioBackupDialog
|
|||||||
private get _computeName() {
|
private get _computeName() {
|
||||||
return this._backup
|
return this._backup
|
||||||
? this._backup.name || this._backup.slug
|
? this._backup.name || this._backup.slug
|
||||||
: this._localize("unnamed_backup");
|
: "Unnamed backup";
|
||||||
}
|
|
||||||
|
|
||||||
static get styles(): CSSResultGroup {
|
|
||||||
return [
|
|
||||||
haStyle,
|
|
||||||
haStyleDialog,
|
|
||||||
css`
|
|
||||||
ha-circular-progress {
|
|
||||||
display: block;
|
|
||||||
text-align: center;
|
|
||||||
}
|
|
||||||
ha-header-bar {
|
|
||||||
--mdc-theme-on-primary: var(--primary-text-color);
|
|
||||||
--mdc-theme-primary: var(--mdc-theme-surface);
|
|
||||||
flex-shrink: 0;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
ha-icon-button {
|
|
||||||
color: var(--secondary-text-color);
|
|
||||||
}
|
|
||||||
.loading {
|
|
||||||
width: 100%;
|
|
||||||
display: flex;
|
|
||||||
height: 100%;
|
|
||||||
justify-content: center;
|
|
||||||
align-items: center;
|
|
||||||
}
|
|
||||||
`,
|
|
||||||
];
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -82,11 +82,10 @@ export class DialogHassioNetwork
|
|||||||
await this.updateComplete;
|
await this.updateComplete;
|
||||||
}
|
}
|
||||||
|
|
||||||
public closeDialog() {
|
public closeDialog(): void {
|
||||||
this._params = undefined;
|
this._params = undefined;
|
||||||
this._processing = false;
|
this._processing = false;
|
||||||
fireEvent(this, "dialog-closed", { dialog: this.localName });
|
fireEvent(this, "dialog-closed", { dialog: this.localName });
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
protected render() {
|
protected render() {
|
||||||
|
@@ -92,7 +92,7 @@ class HassioMyRedirect extends LitElement {
|
|||||||
let url: string;
|
let url: string;
|
||||||
try {
|
try {
|
||||||
url = this._createRedirectUrl(redirect);
|
url = this._createRedirectUrl(redirect);
|
||||||
} catch (_err: any) {
|
} catch (err: any) {
|
||||||
this._error = this.supervisor.localize("my.error");
|
this._error = this.supervisor.localize("my.error");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@@ -1,4 +1,4 @@
|
|||||||
import type { TemplateResult } from "lit";
|
import type { CSSResultGroup, TemplateResult } from "lit";
|
||||||
import { css, html, LitElement } from "lit";
|
import { css, html, LitElement } from "lit";
|
||||||
import { customElement, property } from "lit/decorators";
|
import { customElement, property } from "lit/decorators";
|
||||||
import type { Supervisor } from "../../src/data/supervisor/supervisor";
|
import type { Supervisor } from "../../src/data/supervisor/supervisor";
|
||||||
@@ -39,7 +39,8 @@ class HassioPanel extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
:host {
|
:host {
|
||||||
--app-header-background-color: var(--sidebar-background-color);
|
--app-header-background-color: var(--sidebar-background-color);
|
||||||
--app-header-text-color: var(--sidebar-text-color);
|
--app-header-text-color: var(--sidebar-text-color);
|
||||||
@@ -47,6 +48,7 @@ class HassioPanel extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -1,5 +1,5 @@
|
|||||||
import { mdiMenu } from "@mdi/js";
|
import { mdiMenu } from "@mdi/js";
|
||||||
import type { PropertyValues, TemplateResult } from "lit";
|
import type { CSSResultGroup, PropertyValues, TemplateResult } from "lit";
|
||||||
import { css, html, LitElement } from "lit";
|
import { css, html, LitElement } from "lit";
|
||||||
import { customElement, property, state } from "lit/decorators";
|
import { customElement, property, state } from "lit/decorators";
|
||||||
import { fireEvent } from "../../../src/common/dom/fire_event";
|
import { fireEvent } from "../../../src/common/dom/fire_event";
|
||||||
@@ -158,7 +158,7 @@ class HassioIngressView extends LitElement {
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
addon = await fetchHassioAddonInfo(this.hass, addonSlug);
|
addon = await fetchHassioAddonInfo(this.hass, addonSlug);
|
||||||
} catch (_err: any) {
|
} catch (err: any) {
|
||||||
await this.updateComplete;
|
await this.updateComplete;
|
||||||
await showAlertDialog(this, {
|
await showAlertDialog(this, {
|
||||||
text:
|
text:
|
||||||
@@ -219,7 +219,7 @@ class HassioIngressView extends LitElement {
|
|||||||
});
|
});
|
||||||
this._fetchData(addonSlug);
|
this._fetchData(addonSlug);
|
||||||
return;
|
return;
|
||||||
} catch (_err) {
|
} catch (e) {
|
||||||
await showAlertDialog(this, {
|
await showAlertDialog(this, {
|
||||||
text:
|
text:
|
||||||
this.supervisor.localize("ingress.error_starting_addon") ||
|
this.supervisor.localize("ingress.error_starting_addon") ||
|
||||||
@@ -264,7 +264,7 @@ class HassioIngressView extends LitElement {
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
session = await createSessionPromise;
|
session = await createSessionPromise;
|
||||||
} catch (_err: any) {
|
} catch (err: any) {
|
||||||
if (this._sessionKeepAlive) {
|
if (this._sessionKeepAlive) {
|
||||||
clearInterval(this._sessionKeepAlive);
|
clearInterval(this._sessionKeepAlive);
|
||||||
}
|
}
|
||||||
@@ -285,7 +285,7 @@ class HassioIngressView extends LitElement {
|
|||||||
this._sessionKeepAlive = window.setInterval(async () => {
|
this._sessionKeepAlive = window.setInterval(async () => {
|
||||||
try {
|
try {
|
||||||
await validateHassioSession(this.hass, session);
|
await validateHassioSession(this.hass, session);
|
||||||
} catch (_err: any) {
|
} catch (err: any) {
|
||||||
session = await createHassioSession(this.hass);
|
session = await createHassioSession(this.hass);
|
||||||
}
|
}
|
||||||
}, 60000);
|
}, 60000);
|
||||||
@@ -325,7 +325,8 @@ class HassioIngressView extends LitElement {
|
|||||||
fireEvent(this, "hass-toggle-menu");
|
fireEvent(this, "hass-toggle-menu");
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
iframe {
|
iframe {
|
||||||
display: block;
|
display: block;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
@@ -369,6 +370,7 @@ class HassioIngressView extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -33,7 +33,7 @@ class HassioCoreInfo extends LitElement {
|
|||||||
|
|
||||||
@state() private _metrics?: HassioStats;
|
@state() private _metrics?: HassioStats;
|
||||||
|
|
||||||
protected render(): TemplateResult | undefined {
|
protected render(): TemplateResult | void {
|
||||||
const metrics = [
|
const metrics = [
|
||||||
{
|
{
|
||||||
description: this.supervisor.localize("system.core.cpu_usage"),
|
description: this.supervisor.localize("system.core.cpu_usage"),
|
||||||
|
@@ -49,7 +49,7 @@ class HassioHostInfo extends LitElement {
|
|||||||
|
|
||||||
@property({ attribute: false }) public supervisor!: Supervisor;
|
@property({ attribute: false }) public supervisor!: Supervisor;
|
||||||
|
|
||||||
protected render(): TemplateResult | undefined {
|
protected render(): TemplateResult | void {
|
||||||
const primaryIpAddress = this.supervisor.host.features.includes("network")
|
const primaryIpAddress = this.supervisor.host.features.includes("network")
|
||||||
? this._primaryIpAddress(this.supervisor.network!)
|
? this._primaryIpAddress(this.supervisor.network!)
|
||||||
: "";
|
: "";
|
||||||
|
@@ -44,7 +44,7 @@ class HassioSupervisorInfo extends LitElement {
|
|||||||
|
|
||||||
@state() private _metrics?: HassioStats;
|
@state() private _metrics?: HassioStats;
|
||||||
|
|
||||||
protected render(): TemplateResult | undefined {
|
protected render(): TemplateResult | void {
|
||||||
const metrics = [
|
const metrics = [
|
||||||
{
|
{
|
||||||
description: this.supervisor.localize("system.supervisor.cpu_usage"),
|
description: this.supervisor.localize("system.supervisor.cpu_usage"),
|
||||||
|
@@ -65,7 +65,7 @@ class HassioSupervisorLog extends LitElement {
|
|||||||
await this._loadData();
|
await this._loadData();
|
||||||
}
|
}
|
||||||
|
|
||||||
protected render(): TemplateResult | undefined {
|
protected render(): TemplateResult | void {
|
||||||
return html`
|
return html`
|
||||||
<ha-card outlined>
|
<ha-card outlined>
|
||||||
${this._error
|
${this._error
|
||||||
|
@@ -23,7 +23,7 @@ class HassioSystem extends LitElement {
|
|||||||
|
|
||||||
@property({ attribute: false }) public route!: Route;
|
@property({ attribute: false }) public route!: Route;
|
||||||
|
|
||||||
protected render(): TemplateResult | undefined {
|
protected render(): TemplateResult | void {
|
||||||
return html`
|
return html`
|
||||||
<hass-tabs-subpage
|
<hass-tabs-subpage
|
||||||
.hass=${this.hass}
|
.hass=${this.hass}
|
||||||
|
@@ -18,7 +18,10 @@ import "../../../src/components/ha-checkbox";
|
|||||||
import "../../../src/components/ha-faded";
|
import "../../../src/components/ha-faded";
|
||||||
import "../../../src/components/ha-icon-button";
|
import "../../../src/components/ha-icon-button";
|
||||||
import "../../../src/components/ha-markdown";
|
import "../../../src/components/ha-markdown";
|
||||||
|
import "../../../src/components/ha-settings-row";
|
||||||
import "../../../src/components/ha-svg-icon";
|
import "../../../src/components/ha-svg-icon";
|
||||||
|
import "../../../src/components/ha-switch";
|
||||||
|
import type { HaSwitch } from "../../../src/components/ha-switch";
|
||||||
import type { HassioAddonDetails } from "../../../src/data/hassio/addon";
|
import type { HassioAddonDetails } from "../../../src/data/hassio/addon";
|
||||||
import {
|
import {
|
||||||
fetchHassioAddonChangelog,
|
fetchHassioAddonChangelog,
|
||||||
@@ -160,6 +163,19 @@ class UpdateAvailableCard extends LitElement {
|
|||||||
)}
|
)}
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
|
${["core", "addon"].includes(this._updateType)
|
||||||
|
? html`
|
||||||
|
<hr />
|
||||||
|
<ha-settings-row>
|
||||||
|
<span slot="heading">
|
||||||
|
${this.supervisor.localize(
|
||||||
|
"update_available.create_backup"
|
||||||
|
)}
|
||||||
|
</span>
|
||||||
|
<ha-switch id="create_backup" checked></ha-switch>
|
||||||
|
</ha-settings-row>
|
||||||
|
`
|
||||||
|
: nothing}
|
||||||
`
|
`
|
||||||
: html`<ha-circular-progress
|
: html`<ha-circular-progress
|
||||||
aria-label="Updating"
|
aria-label="Updating"
|
||||||
@@ -227,6 +243,19 @@ class UpdateAvailableCard extends LitElement {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
get _shouldCreateBackup(): boolean {
|
||||||
|
if (this._updateType && !["core", "addon"].includes(this._updateType)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
const createBackupSwitch = this.shadowRoot?.getElementById(
|
||||||
|
"create-backup"
|
||||||
|
) as HaSwitch;
|
||||||
|
if (createBackupSwitch) {
|
||||||
|
return createBackupSwitch.checked;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
get _version(): string {
|
get _version(): string {
|
||||||
return this._updateType
|
return this._updateType
|
||||||
? this._updateType === "addon"
|
? this._updateType === "addon"
|
||||||
@@ -341,14 +370,23 @@ class UpdateAvailableCard extends LitElement {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async _update() {
|
private async _update() {
|
||||||
|
if (this._shouldCreateBackup && this.supervisor.info.state === "freeze") {
|
||||||
|
this._error = this.supervisor.localize("backup.backup_already_running");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
this._error = undefined;
|
this._error = undefined;
|
||||||
this._updating = true;
|
this._updating = true;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
if (this._updateType === "addon") {
|
if (this._updateType === "addon") {
|
||||||
await updateHassioAddon(this.hass, this.addonSlug!);
|
await updateHassioAddon(
|
||||||
|
this.hass,
|
||||||
|
this.addonSlug!,
|
||||||
|
this._shouldCreateBackup
|
||||||
|
);
|
||||||
} else if (this._updateType === "core") {
|
} else if (this._updateType === "core") {
|
||||||
await updateCore(this.hass);
|
await updateCore(this.hass, this._shouldCreateBackup);
|
||||||
} else if (this._updateType === "os") {
|
} else if (this._updateType === "os") {
|
||||||
await updateOS(this.hass);
|
await updateOS(this.hass);
|
||||||
} else if (this._updateType === "supervisor") {
|
} else if (this._updateType === "supervisor") {
|
||||||
@@ -398,6 +436,11 @@ class UpdateAvailableCard extends LitElement {
|
|||||||
padding-bottom: 8px;
|
padding-bottom: 8px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ha-settings-row {
|
||||||
|
padding: 0;
|
||||||
|
margin-bottom: -16px;
|
||||||
|
}
|
||||||
|
|
||||||
hr {
|
hr {
|
||||||
border-color: var(--divider-color);
|
border-color: var(--divider-color);
|
||||||
border-bottom: none;
|
border-bottom: none;
|
||||||
|
@@ -1,4 +1,4 @@
|
|||||||
import type { TemplateResult } from "lit";
|
import type { CSSResultGroup, TemplateResult } from "lit";
|
||||||
import { css, html, LitElement } from "lit";
|
import { css, html, LitElement } from "lit";
|
||||||
import { customElement, property } from "lit/decorators";
|
import { customElement, property } from "lit/decorators";
|
||||||
import type { Supervisor } from "../../../src/data/supervisor/supervisor";
|
import type { Supervisor } from "../../../src/data/supervisor/supervisor";
|
||||||
@@ -38,7 +38,8 @@ class UpdateAvailableDashboard extends LitElement {
|
|||||||
history.back();
|
history.back();
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
|
return css`
|
||||||
hass-subpage {
|
hass-subpage {
|
||||||
--app-header-background-color: var(--primary-background-color);
|
--app-header-background-color: var(--primary-background-color);
|
||||||
--app-header-text-color: var(--sidebar-text-color);
|
--app-header-text-color: var(--sidebar-text-color);
|
||||||
@@ -51,6 +52,7 @@ class UpdateAvailableDashboard extends LitElement {
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
interface HTMLElementTagNameMap {
|
interface HTMLElementTagNameMap {
|
||||||
|
@@ -230,7 +230,7 @@ class LandingPageLogs extends LitElement {
|
|||||||
this._startLogStream();
|
this._startLogStream();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
} catch (_err) {
|
} catch (err) {
|
||||||
// ignore and continue with observer logs
|
// ignore and continue with observer logs
|
||||||
}
|
}
|
||||||
this._loadObserverLogs();
|
this._loadObserverLogs();
|
||||||
|
@@ -126,7 +126,7 @@ class HaLandingPage extends LandingPageBaseElement {
|
|||||||
"selectedLanguage",
|
"selectedLanguage",
|
||||||
JSON.stringify(language)
|
JSON.stringify(language)
|
||||||
);
|
);
|
||||||
} catch (_err: any) {
|
} catch (err: any) {
|
||||||
// Ignore
|
// Ignore
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
100
package.json
100
package.json
@@ -27,24 +27,24 @@
|
|||||||
"type": "module",
|
"type": "module",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@babel/runtime": "7.26.0",
|
"@babel/runtime": "7.26.0",
|
||||||
"@braintree/sanitize-url": "7.1.1",
|
"@braintree/sanitize-url": "7.1.0",
|
||||||
"@codemirror/autocomplete": "6.18.4",
|
"@codemirror/autocomplete": "6.18.3",
|
||||||
"@codemirror/commands": "6.8.0",
|
"@codemirror/commands": "6.7.1",
|
||||||
"@codemirror/language": "6.10.8",
|
"@codemirror/language": "6.10.6",
|
||||||
"@codemirror/legacy-modes": "6.4.2",
|
"@codemirror/legacy-modes": "6.4.2",
|
||||||
"@codemirror/search": "6.5.8",
|
"@codemirror/search": "6.5.8",
|
||||||
"@codemirror/state": "6.5.1",
|
"@codemirror/state": "6.4.1",
|
||||||
"@codemirror/view": "6.36.2",
|
"@codemirror/view": "6.35.2",
|
||||||
"@egjs/hammerjs": "2.0.17",
|
"@egjs/hammerjs": "2.0.17",
|
||||||
"@formatjs/intl-datetimeformat": "6.17.2",
|
"@formatjs/intl-datetimeformat": "6.16.6",
|
||||||
"@formatjs/intl-displaynames": "6.8.9",
|
"@formatjs/intl-displaynames": "6.8.6",
|
||||||
"@formatjs/intl-durationformat": "0.7.2",
|
"@formatjs/intl-durationformat": "0.6.5",
|
||||||
"@formatjs/intl-getcanonicallocales": "2.5.4",
|
"@formatjs/intl-getcanonicallocales": "2.5.3",
|
||||||
"@formatjs/intl-listformat": "7.7.9",
|
"@formatjs/intl-listformat": "7.7.6",
|
||||||
"@formatjs/intl-locale": "4.2.9",
|
"@formatjs/intl-locale": "4.2.6",
|
||||||
"@formatjs/intl-numberformat": "8.15.2",
|
"@formatjs/intl-numberformat": "8.14.6",
|
||||||
"@formatjs/intl-pluralrules": "5.4.2",
|
"@formatjs/intl-pluralrules": "5.3.6",
|
||||||
"@formatjs/intl-relativetimeformat": "11.4.9",
|
"@formatjs/intl-relativetimeformat": "11.4.6",
|
||||||
"@fullcalendar/core": "6.1.15",
|
"@fullcalendar/core": "6.1.15",
|
||||||
"@fullcalendar/daygrid": "6.1.15",
|
"@fullcalendar/daygrid": "6.1.15",
|
||||||
"@fullcalendar/interaction": "6.1.15",
|
"@fullcalendar/interaction": "6.1.15",
|
||||||
@@ -55,7 +55,7 @@
|
|||||||
"@lit-labs/context": "0.4.1",
|
"@lit-labs/context": "0.4.1",
|
||||||
"@lit-labs/motion": "1.0.7",
|
"@lit-labs/motion": "1.0.7",
|
||||||
"@lit-labs/observers": "2.0.4",
|
"@lit-labs/observers": "2.0.4",
|
||||||
"@lit-labs/virtualizer": "2.0.15",
|
"@lit-labs/virtualizer": "2.0.14",
|
||||||
"@lrnwebcomponents/simple-tooltip": "8.0.2",
|
"@lrnwebcomponents/simple-tooltip": "8.0.2",
|
||||||
"@material/chips": "=14.0.0-canary.53b3cad2f.0",
|
"@material/chips": "=14.0.0-canary.53b3cad2f.0",
|
||||||
"@material/data-table": "=14.0.0-canary.53b3cad2f.0",
|
"@material/data-table": "=14.0.0-canary.53b3cad2f.0",
|
||||||
@@ -91,19 +91,20 @@
|
|||||||
"@polymer/polymer": "3.5.2",
|
"@polymer/polymer": "3.5.2",
|
||||||
"@replit/codemirror-indentation-markers": "6.5.3",
|
"@replit/codemirror-indentation-markers": "6.5.3",
|
||||||
"@thomasloven/round-slider": "0.6.0",
|
"@thomasloven/round-slider": "0.6.0",
|
||||||
"@vaadin/combo-box": "24.6.2",
|
"@vaadin/combo-box": "24.5.5",
|
||||||
"@vaadin/vaadin-themable-mixin": "24.6.2",
|
"@vaadin/vaadin-themable-mixin": "24.5.5",
|
||||||
"@vibrant/color": "4.0.0",
|
"@vibrant/color": "3.2.1-alpha.1",
|
||||||
|
"@vibrant/core": "3.2.1-alpha.1",
|
||||||
|
"@vibrant/quantizer-mmcq": "3.2.1-alpha.1",
|
||||||
"@vue/web-component-wrapper": "1.3.0",
|
"@vue/web-component-wrapper": "1.3.0",
|
||||||
"@webcomponents/scoped-custom-element-registry": "0.0.9",
|
"@webcomponents/scoped-custom-element-registry": "0.0.9",
|
||||||
"@webcomponents/webcomponentsjs": "2.8.0",
|
"@webcomponents/webcomponentsjs": "2.8.0",
|
||||||
"app-datepicker": "5.1.1",
|
"app-datepicker": "5.1.1",
|
||||||
"barcode-detector": "2.3.1",
|
"barcode-detector": "2.3.1",
|
||||||
"chart.js": "4.4.7",
|
"chart.js": "4.4.7",
|
||||||
"chartjs-plugin-zoom": "2.2.0",
|
|
||||||
"color-name": "2.0.0",
|
"color-name": "2.0.0",
|
||||||
"comlink": "4.4.2",
|
"comlink": "4.4.2",
|
||||||
"core-js": "3.40.0",
|
"core-js": "3.39.0",
|
||||||
"cropperjs": "1.6.2",
|
"cropperjs": "1.6.2",
|
||||||
"date-fns": "4.1.0",
|
"date-fns": "4.1.0",
|
||||||
"date-fns-tz": "3.2.0",
|
"date-fns-tz": "3.2.0",
|
||||||
@@ -113,20 +114,20 @@
|
|||||||
"element-internals-polyfill": "1.3.12",
|
"element-internals-polyfill": "1.3.12",
|
||||||
"fuse.js": "7.0.0",
|
"fuse.js": "7.0.0",
|
||||||
"google-timezones-json": "1.2.0",
|
"google-timezones-json": "1.2.0",
|
||||||
"gulp-zopfli-green": "6.0.2",
|
|
||||||
"hls.js": "patch:hls.js@npm%3A1.5.7#~/.yarn/patches/hls.js-npm-1.5.7-f5bbd3d060.patch",
|
"hls.js": "patch:hls.js@npm%3A1.5.7#~/.yarn/patches/hls.js-npm-1.5.7-f5bbd3d060.patch",
|
||||||
"home-assistant-js-websocket": "9.4.0",
|
"home-assistant-js-websocket": "9.4.0",
|
||||||
"idb-keyval": "6.2.1",
|
"idb-keyval": "6.2.1",
|
||||||
"intl-messageformat": "10.7.11",
|
"intl-messageformat": "10.7.8",
|
||||||
"js-yaml": "4.1.0",
|
"js-yaml": "4.1.0",
|
||||||
"leaflet": "1.9.4",
|
"leaflet": "1.9.4",
|
||||||
"leaflet-draw": "patch:leaflet-draw@npm%3A1.0.4#./.yarn/patches/leaflet-draw-npm-1.0.4-0ca0ebcf65.patch",
|
"leaflet-draw": "patch:leaflet-draw@npm%3A1.0.4#./.yarn/patches/leaflet-draw-npm-1.0.4-0ca0ebcf65.patch",
|
||||||
"lit": "2.8.0",
|
"lit": "2.8.0",
|
||||||
"lit-html": "2.8.0",
|
"lit-html": "2.8.0",
|
||||||
"luxon": "3.5.0",
|
"luxon": "3.5.0",
|
||||||
"marked": "15.0.6",
|
"marked": "15.0.3",
|
||||||
"memoize-one": "6.0.0",
|
"memoize-one": "6.0.0",
|
||||||
"node-vibrant": "4.0.1",
|
"node-vibrant": "3.2.1-alpha.1",
|
||||||
|
"proxy-polyfill": "0.3.2",
|
||||||
"punycode": "2.3.1",
|
"punycode": "2.3.1",
|
||||||
"qr-scanner": "1.4.2",
|
"qr-scanner": "1.4.2",
|
||||||
"qrcode": "1.5.4",
|
"qrcode": "1.5.4",
|
||||||
@@ -138,7 +139,8 @@
|
|||||||
"tinykeys": "3.0.0",
|
"tinykeys": "3.0.0",
|
||||||
"tsparticles-engine": "2.12.0",
|
"tsparticles-engine": "2.12.0",
|
||||||
"tsparticles-preset-links": "2.12.0",
|
"tsparticles-preset-links": "2.12.0",
|
||||||
"ua-parser-js": "2.0.0",
|
"ua-parser-js": "1.0.39",
|
||||||
|
"unfetch": "5.0.0",
|
||||||
"vis-data": "7.1.9",
|
"vis-data": "7.1.9",
|
||||||
"vis-network": "9.1.9",
|
"vis-network": "9.1.9",
|
||||||
"vue": "2.7.16",
|
"vue": "2.7.16",
|
||||||
@@ -160,13 +162,13 @@
|
|||||||
"@babel/preset-env": "7.26.0",
|
"@babel/preset-env": "7.26.0",
|
||||||
"@babel/preset-typescript": "7.26.0",
|
"@babel/preset-typescript": "7.26.0",
|
||||||
"@bundle-stats/plugin-webpack-filter": "4.17.0",
|
"@bundle-stats/plugin-webpack-filter": "4.17.0",
|
||||||
"@lokalise/node-api": "13.0.0",
|
"@lokalise/node-api": "12.8.0",
|
||||||
"@octokit/auth-oauth-device": "7.1.2",
|
"@octokit/auth-oauth-device": "7.1.1",
|
||||||
"@octokit/plugin-retry": "7.1.3",
|
"@octokit/plugin-retry": "7.1.2",
|
||||||
"@octokit/rest": "21.1.0",
|
"@octokit/rest": "21.0.2",
|
||||||
"@rsdoctor/rspack-plugin": "0.4.13",
|
"@rsdoctor/rspack-plugin": "0.4.11",
|
||||||
"@rspack/cli": "1.1.8",
|
"@rspack/cli": "1.1.5",
|
||||||
"@rspack/core": "1.1.8",
|
"@rspack/core": "1.1.5",
|
||||||
"@types/babel__plugin-transform-runtime": "7.9.5",
|
"@types/babel__plugin-transform-runtime": "7.9.5",
|
||||||
"@types/chromecast-caf-receiver": "6.0.20",
|
"@types/chromecast-caf-receiver": "6.0.20",
|
||||||
"@types/chromecast-caf-sender": "1.0.11",
|
"@types/chromecast-caf-sender": "1.0.11",
|
||||||
@@ -174,27 +176,29 @@
|
|||||||
"@types/glob": "8.1.0",
|
"@types/glob": "8.1.0",
|
||||||
"@types/html-minifier-terser": "7.0.2",
|
"@types/html-minifier-terser": "7.0.2",
|
||||||
"@types/js-yaml": "4.0.9",
|
"@types/js-yaml": "4.0.9",
|
||||||
"@types/leaflet": "1.9.16",
|
"@types/leaflet": "1.9.15",
|
||||||
"@types/leaflet-draw": "1.0.11",
|
"@types/leaflet-draw": "1.0.11",
|
||||||
"@types/lodash.merge": "4.6.9",
|
"@types/lodash.merge": "4.6.9",
|
||||||
"@types/luxon": "3.4.2",
|
"@types/luxon": "3.4.2",
|
||||||
"@types/mocha": "10.0.10",
|
"@types/mocha": "10.0.10",
|
||||||
"@types/qrcode": "1.5.5",
|
"@types/qrcode": "1.5.5",
|
||||||
|
"@types/serve-handler": "6.1.4",
|
||||||
"@types/sortablejs": "1.15.8",
|
"@types/sortablejs": "1.15.8",
|
||||||
"@types/tar": "6.1.13",
|
"@types/tar": "6.1.13",
|
||||||
"@types/ua-parser-js": "0.7.39",
|
"@types/ua-parser-js": "0.7.39",
|
||||||
"@types/webspeechapi": "0.0.29",
|
"@types/webspeechapi": "0.0.29",
|
||||||
"@typescript-eslint/eslint-plugin": "8.20.0",
|
"@typescript-eslint/eslint-plugin": "7.18.0",
|
||||||
"@typescript-eslint/parser": "8.20.0",
|
"@typescript-eslint/parser": "7.18.0",
|
||||||
"@vitest/coverage-v8": "2.1.8",
|
"@vitest/coverage-v8": "2.1.8",
|
||||||
"babel-loader": "9.2.1",
|
"babel-loader": "9.2.1",
|
||||||
"babel-plugin-template-html-minifier": "4.1.0",
|
"babel-plugin-template-html-minifier": "4.1.0",
|
||||||
"browserslist-useragent-regexp": "4.1.3",
|
"browserslist-useragent-regexp": "4.1.3",
|
||||||
"del": "8.0.0",
|
"del": "8.0.0",
|
||||||
"eslint": "9.18.0",
|
"eslint": "9.16.0",
|
||||||
"eslint-config-airbnb-base": "15.0.0",
|
"eslint-config-airbnb-base": "15.0.0",
|
||||||
|
"eslint-config-airbnb-typescript": "18.0.0",
|
||||||
"eslint-config-prettier": "9.1.0",
|
"eslint-config-prettier": "9.1.0",
|
||||||
"eslint-import-resolver-webpack": "0.13.10",
|
"eslint-import-resolver-webpack": "0.13.9",
|
||||||
"eslint-plugin-import": "2.31.0",
|
"eslint-plugin-import": "2.31.0",
|
||||||
"eslint-plugin-lit": "1.15.0",
|
"eslint-plugin-lit": "1.15.0",
|
||||||
"eslint-plugin-lit-a11y": "4.1.4",
|
"eslint-plugin-lit-a11y": "4.1.4",
|
||||||
@@ -202,29 +206,33 @@
|
|||||||
"eslint-plugin-wc": "2.2.0",
|
"eslint-plugin-wc": "2.2.0",
|
||||||
"fancy-log": "2.0.0",
|
"fancy-log": "2.0.0",
|
||||||
"fs-extra": "11.2.0",
|
"fs-extra": "11.2.0",
|
||||||
"glob": "11.0.1",
|
"glob": "11.0.0",
|
||||||
"gulp": "5.0.0",
|
"gulp": "5.0.0",
|
||||||
"gulp-brotli": "3.0.0",
|
"gulp-brotli": "3.0.0",
|
||||||
"gulp-json-transform": "0.5.0",
|
"gulp-json-transform": "0.5.0",
|
||||||
"gulp-rename": "2.0.0",
|
"gulp-rename": "2.0.0",
|
||||||
"html-minifier-terser": "7.2.0",
|
"html-minifier-terser": "7.2.0",
|
||||||
"husky": "9.1.7",
|
"husky": "9.1.7",
|
||||||
"jsdom": "26.0.0",
|
"jsdom": "25.0.1",
|
||||||
"jszip": "3.10.1",
|
"jszip": "3.10.1",
|
||||||
"lint-staged": "15.3.0",
|
"lint-staged": "15.2.10",
|
||||||
"lit-analyzer": "2.0.3",
|
"lit-analyzer": "2.0.3",
|
||||||
"lodash.merge": "4.6.2",
|
"lodash.merge": "4.6.2",
|
||||||
"lodash.template": "4.5.0",
|
"lodash.template": "4.5.0",
|
||||||
|
"magic-string": "0.30.14",
|
||||||
"map-stream": "0.0.7",
|
"map-stream": "0.0.7",
|
||||||
"object-hash": "3.0.0",
|
"object-hash": "3.0.0",
|
||||||
|
"open": "10.1.0",
|
||||||
"pinst": "3.0.0",
|
"pinst": "3.0.0",
|
||||||
"prettier": "3.4.2",
|
"prettier": "3.4.2",
|
||||||
"rspack-manifest-plugin": "5.0.3",
|
"rspack-manifest-plugin": "5.0.2",
|
||||||
|
"serve-handler": "6.1.6",
|
||||||
"sinon": "19.0.2",
|
"sinon": "19.0.2",
|
||||||
|
"systemjs": "6.15.1",
|
||||||
"tar": "7.4.3",
|
"tar": "7.4.3",
|
||||||
"terser-webpack-plugin": "5.3.11",
|
"terser-webpack-plugin": "5.3.10",
|
||||||
"ts-lit-plugin": "2.0.2",
|
"ts-lit-plugin": "2.0.2",
|
||||||
"typescript": "5.7.3",
|
"typescript": "5.7.2",
|
||||||
"vitest": "2.1.8",
|
"vitest": "2.1.8",
|
||||||
"webpack-stats-plugin": "1.1.3",
|
"webpack-stats-plugin": "1.1.3",
|
||||||
"webpackbar": "7.0.0",
|
"webpackbar": "7.0.0",
|
||||||
@@ -239,7 +247,7 @@
|
|||||||
"clean-css": "5.3.3",
|
"clean-css": "5.3.3",
|
||||||
"@lit/reactive-element": "1.6.3",
|
"@lit/reactive-element": "1.6.3",
|
||||||
"@fullcalendar/daygrid": "6.1.15",
|
"@fullcalendar/daygrid": "6.1.15",
|
||||||
"globals": "15.14.0"
|
"globals": "15.13.0"
|
||||||
},
|
},
|
||||||
"packageManager": "yarn@4.6.0"
|
"packageManager": "yarn@4.5.3"
|
||||||
}
|
}
|
||||||
|
@@ -4,14 +4,14 @@ build-backend = "setuptools.build_meta"
|
|||||||
|
|
||||||
[project]
|
[project]
|
||||||
name = "home-assistant-frontend"
|
name = "home-assistant-frontend"
|
||||||
version = "20241224.0"
|
version = "20241127.0"
|
||||||
license = {text = "Apache-2.0"}
|
license = {text = "Apache-2.0"}
|
||||||
description = "The Home Assistant frontend"
|
description = "The Home Assistant frontend"
|
||||||
readme = "README.md"
|
readme = "README.md"
|
||||||
authors = [
|
authors = [
|
||||||
{name = "The Home Assistant Authors", email = "hello@home-assistant.io"}
|
{name = "The Home Assistant Authors", email = "hello@home-assistant.io"}
|
||||||
]
|
]
|
||||||
requires-python = ">=3.13.0"
|
requires-python = ">=3.11.0"
|
||||||
|
|
||||||
[project.urls]
|
[project.urls]
|
||||||
"Homepage" = "https://github.com/home-assistant/frontend"
|
"Homepage" = "https://github.com/home-assistant/frontend"
|
||||||
|
@@ -1,4 +1,4 @@
|
|||||||
/* eslint-disable @typescript-eslint/no-require-imports */
|
/* eslint-disable @typescript-eslint/no-var-requires */
|
||||||
// Needs to remain CommonJS until eslint-import-resolver-webpack supports ES modules
|
// Needs to remain CommonJS until eslint-import-resolver-webpack supports ES modules
|
||||||
const rspack = require("./build-scripts/rspack.cjs");
|
const rspack = require("./build-scripts/rspack.cjs");
|
||||||
const env = require("./build-scripts/env.cjs");
|
const env = require("./build-scripts/env.cjs");
|
||||||
|
@@ -30,7 +30,7 @@ set -e
|
|||||||
|
|
||||||
cd "$(dirname "$0")/.."
|
cd "$(dirname "$0")/.."
|
||||||
|
|
||||||
# parse input parameters
|
# parse input paramters
|
||||||
if [ -n "$DEVCONTAINER" ]; then
|
if [ -n "$DEVCONTAINER" ]; then
|
||||||
frontendPort=8123
|
frontendPort=8123
|
||||||
else
|
else
|
||||||
|
@@ -232,7 +232,7 @@ export class HaAuthorize extends litLocalizeLiteMixin(LitElement) {
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
url = new URL(this.redirectUri);
|
url = new URL(this.redirectUri);
|
||||||
} catch (_err) {
|
} catch (err) {
|
||||||
this._error = "Invalid redirect URI";
|
this._error = "Invalid redirect URI";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -328,7 +328,7 @@ export class HaAuthorize extends litLocalizeLiteMixin(LitElement) {
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
window.localStorage.setItem("selectedLanguage", JSON.stringify(language));
|
window.localStorage.setItem("selectedLanguage", JSON.stringify(language));
|
||||||
} catch (_err: any) {
|
} catch (err: any) {
|
||||||
// Ignore
|
// Ignore
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -32,7 +32,7 @@ export class CastManager {
|
|||||||
// If the cast connection is connected to our Hass.
|
// If the cast connection is connected to our Hass.
|
||||||
public status?: ReceiverStatusMessage;
|
public status?: ReceiverStatusMessage;
|
||||||
|
|
||||||
private _eventListeners: Record<string, CastEventListener[]> = {};
|
private _eventListeners: { [event: string]: CastEventListener[] } = {};
|
||||||
|
|
||||||
constructor(auth?: Auth) {
|
constructor(auth?: Auth) {
|
||||||
this.auth = auth;
|
this.auth = auth;
|
||||||
|
@@ -1,20 +1,14 @@
|
|||||||
type NonNullUndefined<T> = T extends undefined
|
type NonUndefined<T> = T extends undefined ? never : T;
|
||||||
? never
|
|
||||||
: T extends null
|
|
||||||
? never
|
|
||||||
: T;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Ensure that the input is an array or wrap it in an array
|
* Ensure that the input is an array or wrap it in an array
|
||||||
* @param value - The value to ensure is an array
|
* @param value - The value to ensure is an array
|
||||||
*/
|
*/
|
||||||
export function ensureArray(value: undefined): undefined;
|
export function ensureArray(value: undefined): undefined;
|
||||||
export function ensureArray(value: null): null;
|
export function ensureArray<T>(value: T | T[]): NonUndefined<T>[];
|
||||||
export function ensureArray<T>(
|
export function ensureArray<T>(value: T | readonly T[]): NonUndefined<T>[];
|
||||||
value: T | T[] | readonly T[]
|
|
||||||
): NonNullUndefined<T>[];
|
|
||||||
export function ensureArray(value) {
|
export function ensureArray(value) {
|
||||||
if (value === undefined || value === null || Array.isArray(value)) {
|
if (value === undefined || Array.isArray(value)) {
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
return [value];
|
return [value];
|
||||||
|
@@ -66,7 +66,7 @@ export function loadTokens() {
|
|||||||
} else {
|
} else {
|
||||||
tokenCache.tokens = null;
|
tokenCache.tokens = null;
|
||||||
}
|
}
|
||||||
} catch (_err: any) {
|
} catch (err: any) {
|
||||||
tokenCache.tokens = null;
|
tokenCache.tokens = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -90,9 +90,9 @@ export const lab2rgb = (
|
|||||||
x = Xn * lab_xyz(x);
|
x = Xn * lab_xyz(x);
|
||||||
z = Zn * lab_xyz(z);
|
z = Zn * lab_xyz(z);
|
||||||
|
|
||||||
const r = Math.round(xyz_rgb(3.2404542 * x - 1.5371385 * y - 0.4985314 * z)); // D65 -> sRGB
|
const r = xyz_rgb(3.2404542 * x - 1.5371385 * y - 0.4985314 * z); // D65 -> sRGB
|
||||||
const g = Math.round(xyz_rgb(-0.969266 * x + 1.8760108 * y + 0.041556 * z));
|
const g = xyz_rgb(-0.969266 * x + 1.8760108 * y + 0.041556 * z);
|
||||||
const b_ = Math.round(xyz_rgb(0.0556434 * x - 0.2040259 * y + 1.0572252 * z));
|
const b_ = xyz_rgb(0.0556434 * x - 0.2040259 * y + 1.0572252 * z);
|
||||||
|
|
||||||
return [r, g, b_];
|
return [r, g, b_];
|
||||||
};
|
};
|
||||||
|
@@ -8,9 +8,9 @@ export const temperature2rgb = (
|
|||||||
): [number, number, number] => {
|
): [number, number, number] => {
|
||||||
const value = temperature / 100;
|
const value = temperature / 100;
|
||||||
return [
|
return [
|
||||||
Math.round(temperatureRed(value)),
|
temperatureRed(value),
|
||||||
Math.round(temperatureGreen(value)),
|
temperatureGreen(value),
|
||||||
Math.round(temperatureBlue(value)),
|
temperatureBlue(value),
|
||||||
];
|
];
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -59,10 +59,10 @@ const matchMaxScale = (
|
|||||||
};
|
};
|
||||||
|
|
||||||
export const mired2kelvin = (miredTemperature: number) =>
|
export const mired2kelvin = (miredTemperature: number) =>
|
||||||
miredTemperature === 0 ? 1000000 : Math.floor(1000000 / miredTemperature);
|
Math.floor(1000000 / miredTemperature);
|
||||||
|
|
||||||
export const kelvin2mired = (kelvinTemperature: number) =>
|
export const kelvin2mired = (kelvintTemperature: number) =>
|
||||||
kelvinTemperature === 0 ? 1000000 : Math.floor(1000000 / kelvinTemperature);
|
Math.floor(1000000 / kelvintTemperature);
|
||||||
|
|
||||||
export const rgbww2rgb = (
|
export const rgbww2rgb = (
|
||||||
rgbww: [number, number, number, number, number],
|
rgbww: [number, number, number, number, number],
|
||||||
|
@@ -14,8 +14,8 @@ export const hexBlend = (c1: string, c2: string, blend = 50): string => {
|
|||||||
c1 = expandHex(c1);
|
c1 = expandHex(c1);
|
||||||
c2 = expandHex(c2);
|
c2 = expandHex(c2);
|
||||||
for (let i = 0; i <= 5; i += 2) {
|
for (let i = 0; i <= 5; i += 2) {
|
||||||
const h1 = parseInt(c1.substring(i, i + 2), 16);
|
const h1 = parseInt(c1.substr(i, 2), 16);
|
||||||
const h2 = parseInt(c2.substring(i, i + 2), 16);
|
const h2 = parseInt(c2.substr(i, 2), 16);
|
||||||
let hex = Math.floor(h2 + (h1 - h2) * (blend / 100)).toString(16);
|
let hex = Math.floor(h2 + (h1 - h2) * (blend / 100)).toString(16);
|
||||||
while (hex.length < 2) hex = "0" + hex;
|
while (hex.length < 2) hex = "0" + hex;
|
||||||
color += hex;
|
color += hex;
|
||||||
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user