mirror of
https://github.com/home-assistant/frontend.git
synced 2025-10-29 21:49:45 +00:00
Compare commits
1 Commits
20250430.1
...
fix_new_sc
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
637eb6e894 |
@@ -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 \
|
||||||
|
|||||||
@@ -5,15 +5,12 @@
|
|||||||
"context": ".."
|
"context": ".."
|
||||||
},
|
},
|
||||||
"appPort": "8124:8123",
|
"appPort": "8124:8123",
|
||||||
"postCreateCommand": "./.devcontainer/post_create.sh",
|
"postCreateCommand": "sudo apt update && sudo apt upgrade -y && sudo apt install -y libpcap-dev",
|
||||||
"postStartCommand": "script/bootstrap",
|
"postStartCommand": "script/bootstrap",
|
||||||
"containerEnv": {
|
"containerEnv": {
|
||||||
"DEV_CONTAINER": "1",
|
"DEV_CONTAINER": "1",
|
||||||
"WORKSPACE_DIRECTORY": "${containerWorkspaceFolder}"
|
"WORKSPACE_DIRECTORY": "${containerWorkspaceFolder}"
|
||||||
},
|
},
|
||||||
"remoteEnv": {
|
|
||||||
"NODE_OPTIONS": "--max_old_space_size=8192"
|
|
||||||
},
|
|
||||||
"customizations": {
|
"customizations": {
|
||||||
"vscode": {
|
"vscode": {
|
||||||
"extensions": [
|
"extensions": [
|
||||||
@@ -21,8 +18,7 @@
|
|||||||
"esbenp.prettier-vscode",
|
"esbenp.prettier-vscode",
|
||||||
"runem.lit-plugin",
|
"runem.lit-plugin",
|
||||||
"github.vscode-pull-request-github",
|
"github.vscode-pull-request-github",
|
||||||
"eamodio.gitlens",
|
"eamodio.gitlens"
|
||||||
"yeion7.styled-global-variables-autocomplete"
|
|
||||||
],
|
],
|
||||||
"settings": {
|
"settings": {
|
||||||
"files.eol": "\n",
|
"files.eol": "\n",
|
||||||
|
|||||||
@@ -1,22 +0,0 @@
|
|||||||
#!/bin/bash
|
|
||||||
|
|
||||||
# This script will run after the container is created
|
|
||||||
|
|
||||||
# add github cli
|
|
||||||
(type -p wget >/dev/null || (sudo apt update && sudo apt-get install wget -y)) \
|
|
||||||
&& sudo mkdir -p -m 755 /etc/apt/keyrings \
|
|
||||||
&& out=$(mktemp) && wget -nv -O$out https://cli.github.com/packages/githubcli-archive-keyring.gpg \
|
|
||||||
&& cat $out | sudo tee /etc/apt/keyrings/githubcli-archive-keyring.gpg > /dev/null \
|
|
||||||
&& sudo chmod go+r /etc/apt/keyrings/githubcli-archive-keyring.gpg \
|
|
||||||
&& echo "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/githubcli-archive-keyring.gpg] https://cli.github.com/packages stable main" | sudo tee /etc/apt/sources.list.d/github-cli.list > /dev/null
|
|
||||||
|
|
||||||
# Update package lists
|
|
||||||
sudo apt-get update
|
|
||||||
|
|
||||||
sudo apt upgrade -y
|
|
||||||
|
|
||||||
# Install necessary packages
|
|
||||||
sudo apt-get install -y libpcap-dev gh
|
|
||||||
|
|
||||||
# Display a message
|
|
||||||
echo "Post-create script has been executed successfully."
|
|
||||||
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.
|
||||||
|
|||||||
14
.github/workflows/cast_deployment.yaml
vendored
14
.github/workflows/cast_deployment.yaml
vendored
@@ -26,7 +26,7 @@ jobs:
|
|||||||
ref: dev
|
ref: dev
|
||||||
|
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
uses: actions/setup-node@v4.4.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
@@ -41,8 +41,9 @@ jobs:
|
|||||||
|
|
||||||
- name: Deploy to Netlify
|
- name: Deploy to Netlify
|
||||||
id: deploy
|
id: deploy
|
||||||
run: |
|
uses: netlify/actions/cli@master
|
||||||
npx -y netlify-cli deploy --dir=cast/dist --alias dev
|
with:
|
||||||
|
args: deploy --dir=cast/dist --alias dev
|
||||||
env:
|
env:
|
||||||
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
||||||
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_CAST_SITE_ID }}
|
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_CAST_SITE_ID }}
|
||||||
@@ -61,7 +62,7 @@ jobs:
|
|||||||
ref: master
|
ref: master
|
||||||
|
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
uses: actions/setup-node@v4.4.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
@@ -76,8 +77,9 @@ jobs:
|
|||||||
|
|
||||||
- name: Deploy to Netlify
|
- name: Deploy to Netlify
|
||||||
id: deploy
|
id: deploy
|
||||||
run: |
|
uses: netlify/actions/cli@master
|
||||||
npx -y netlify-cli deploy --dir=cast/dist --prod
|
with:
|
||||||
|
args: deploy --dir=cast/dist --prod
|
||||||
env:
|
env:
|
||||||
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
||||||
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_CAST_SITE_ID }}
|
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_CAST_SITE_ID }}
|
||||||
|
|||||||
48
.github/workflows/ci.yaml
vendored
48
.github/workflows/ci.yaml
vendored
@@ -26,18 +26,24 @@ 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
|
||||||
uses: actions/setup-node@v4.4.0
|
id: setup-node
|
||||||
|
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
|
||||||
uses: actions/cache@v4.2.3
|
uses: actions/cache@v4.2.0
|
||||||
with:
|
with:
|
||||||
path: |
|
path: |
|
||||||
node_modules/.cache/prettier
|
node_modules/.cache/prettier
|
||||||
@@ -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
|
||||||
uses: actions/setup-node@v4.4.0
|
id: setup-node
|
||||||
|
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
|
||||||
uses: actions/setup-node@v4.4.0
|
id: setup-node
|
||||||
|
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.2
|
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
|
||||||
uses: actions/setup-node@v4.4.0
|
id: setup-node
|
||||||
|
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.2
|
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
|
||||||
|
|||||||
14
.github/workflows/demo_deployment.yaml
vendored
14
.github/workflows/demo_deployment.yaml
vendored
@@ -27,7 +27,7 @@ jobs:
|
|||||||
ref: dev
|
ref: dev
|
||||||
|
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
uses: actions/setup-node@v4.4.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
@@ -42,8 +42,9 @@ jobs:
|
|||||||
|
|
||||||
- name: Deploy to Netlify
|
- name: Deploy to Netlify
|
||||||
id: deploy
|
id: deploy
|
||||||
run: |
|
uses: netlify/actions/cli@master
|
||||||
npx -y netlify-cli deploy --dir=demo/dist --prod
|
with:
|
||||||
|
args: deploy --dir=demo/dist --prod
|
||||||
env:
|
env:
|
||||||
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
||||||
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_DEMO_DEV_SITE_ID }}
|
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_DEMO_DEV_SITE_ID }}
|
||||||
@@ -62,7 +63,7 @@ jobs:
|
|||||||
ref: master
|
ref: master
|
||||||
|
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
uses: actions/setup-node@v4.4.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
@@ -77,8 +78,9 @@ jobs:
|
|||||||
|
|
||||||
- name: Deploy to Netlify
|
- name: Deploy to Netlify
|
||||||
id: deploy
|
id: deploy
|
||||||
run: |
|
uses: netlify/actions/cli@master
|
||||||
npx -y netlify-cli deploy --dir=demo/dist --prod
|
with:
|
||||||
|
args: deploy --dir=demo/dist --prod
|
||||||
env:
|
env:
|
||||||
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
||||||
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_DEMO_SITE_ID }}
|
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_DEMO_SITE_ID }}
|
||||||
|
|||||||
7
.github/workflows/design_deployment.yaml
vendored
7
.github/workflows/design_deployment.yaml
vendored
@@ -19,7 +19,7 @@ jobs:
|
|||||||
uses: actions/checkout@v4.2.2
|
uses: actions/checkout@v4.2.2
|
||||||
|
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
uses: actions/setup-node@v4.4.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
@@ -34,8 +34,9 @@ jobs:
|
|||||||
|
|
||||||
- name: Deploy to Netlify
|
- name: Deploy to Netlify
|
||||||
id: deploy
|
id: deploy
|
||||||
run: |
|
uses: netlify/actions/cli@master
|
||||||
npx -y netlify-cli deploy --dir=gallery/dist --prod
|
with:
|
||||||
|
args: deploy --dir=gallery/dist --prod
|
||||||
env:
|
env:
|
||||||
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
||||||
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_GALLERY_SITE_ID }}
|
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_GALLERY_SITE_ID }}
|
||||||
|
|||||||
11
.github/workflows/design_preview.yaml
vendored
11
.github/workflows/design_preview.yaml
vendored
@@ -24,7 +24,7 @@ jobs:
|
|||||||
uses: actions/checkout@v4.2.2
|
uses: actions/checkout@v4.2.2
|
||||||
|
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
uses: actions/setup-node@v4.4.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
@@ -39,14 +39,13 @@ jobs:
|
|||||||
|
|
||||||
- name: Deploy preview to Netlify
|
- name: Deploy preview to Netlify
|
||||||
id: deploy
|
id: deploy
|
||||||
run: |
|
uses: netlify/actions/cli@master
|
||||||
npx -y netlify-cli deploy --dir=gallery/dist --alias "deploy-preview-${{ github.event.number }}" \
|
with:
|
||||||
--json > deploy_output.json
|
args: deploy --dir=gallery/dist --alias "deploy-preview-${{ github.event.number }}"
|
||||||
env:
|
env:
|
||||||
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
NETLIFY_AUTH_TOKEN: ${{ secrets.NETLIFY_AUTH_TOKEN }}
|
||||||
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_GALLERY_SITE_ID }}
|
NETLIFY_SITE_ID: ${{ secrets.NETLIFY_GALLERY_SITE_ID }}
|
||||||
|
|
||||||
- name: Generate summary
|
- name: Generate summary
|
||||||
run: |
|
run: |
|
||||||
NETLIFY_LIVE_URL=$(jq -r '.deploy_url' deploy_output.json)
|
echo "${{ steps.deploy.outputs.NETLIFY_LIVE_URL || steps.deploy.outputs.NETLIFY_URL }}" >> "$GITHUB_STEP_SUMMARY"
|
||||||
echo "$NETLIFY_LIVE_URL" >> "$GITHUB_STEP_SUMMARY"
|
|
||||||
|
|||||||
8
.github/workflows/nightly.yaml
vendored
8
.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:
|
||||||
@@ -28,7 +28,7 @@ jobs:
|
|||||||
python-version: ${{ env.PYTHON_VERSION }}
|
python-version: ${{ env.PYTHON_VERSION }}
|
||||||
|
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
uses: actions/setup-node@v4.4.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
@@ -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.2
|
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.2
|
uses: actions/upload-artifact@v4.4.3
|
||||||
with:
|
with:
|
||||||
name: translations
|
name: translations
|
||||||
path: translations.tar.gz
|
path: translations.tar.gz
|
||||||
|
|||||||
2
.github/workflows/relative-ci.yaml
vendored
2
.github/workflows/relative-ci.yaml
vendored
@@ -17,7 +17,7 @@ jobs:
|
|||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
steps:
|
steps:
|
||||||
- name: Send bundle stats and build information to RelativeCI
|
- name: Send bundle stats and build information to RelativeCI
|
||||||
uses: relative-ci/agent-action@v2.2.0
|
uses: relative-ci/agent-action@v2.1.14
|
||||||
with:
|
with:
|
||||||
key: ${{ secrets[format('RELATIVE_CI_KEY_{0}_{1}', matrix.bundle, matrix.build)] }}
|
key: ${{ secrets[format('RELATIVE_CI_KEY_{0}_{1}', matrix.bundle, matrix.build)] }}
|
||||||
token: ${{ github.token }}
|
token: ${{ github.token }}
|
||||||
|
|||||||
2
.github/workflows/release-drafter.yaml
vendored
2
.github/workflows/release-drafter.yaml
vendored
@@ -18,6 +18,6 @@ jobs:
|
|||||||
pull-requests: read
|
pull-requests: read
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
steps:
|
steps:
|
||||||
- uses: release-drafter/release-drafter@v6.1.0
|
- uses: release-drafter/release-drafter@v6.0.0
|
||||||
env:
|
env:
|
||||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||||
|
|||||||
24
.github/workflows/release.yaml
vendored
24
.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,16 +25,16 @@ 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.4.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
@@ -55,7 +55,7 @@ jobs:
|
|||||||
script/release
|
script/release
|
||||||
|
|
||||||
- name: Upload release assets
|
- name: Upload release assets
|
||||||
uses: softprops/action-gh-release@v2.2.2
|
uses: softprops/action-gh-release@v2.1.0
|
||||||
with:
|
with:
|
||||||
files: |
|
files: |
|
||||||
dist/*.whl
|
dist/*.whl
|
||||||
@@ -74,9 +74,9 @@ jobs:
|
|||||||
echo "home-assistant-frontend==$version" > ./requirements.txt
|
echo "home-assistant-frontend==$version" > ./requirements.txt
|
||||||
|
|
||||||
- name: Build wheels
|
- name: Build wheels
|
||||||
uses: home-assistant/wheels@2025.03.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 }}
|
||||||
@@ -92,7 +92,7 @@ jobs:
|
|||||||
- name: Checkout the repository
|
- name: Checkout the repository
|
||||||
uses: actions/checkout@v4.2.2
|
uses: actions/checkout@v4.2.2
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
uses: actions/setup-node@v4.4.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
@@ -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.2
|
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
|
||||||
|
|
||||||
@@ -121,7 +121,7 @@ jobs:
|
|||||||
- name: Checkout the repository
|
- name: Checkout the repository
|
||||||
uses: actions/checkout@v4.2.2
|
uses: actions/checkout@v4.2.2
|
||||||
- name: Setup Node
|
- name: Setup Node
|
||||||
uses: actions/setup-node@v4.4.0
|
uses: actions/setup-node@v4.1.0
|
||||||
with:
|
with:
|
||||||
node-version-file: ".nvmrc"
|
node-version-file: ".nvmrc"
|
||||||
cache: yarn
|
cache: yarn
|
||||||
@@ -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.2
|
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
|
||||||
|
|||||||
2
.github/workflows/stale.yml
vendored
2
.github/workflows/stale.yml
vendored
@@ -10,7 +10,7 @@ jobs:
|
|||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
steps:
|
steps:
|
||||||
- name: 90 days stale policy
|
- name: 90 days stale policy
|
||||||
uses: actions/stale@v9.1.0
|
uses: actions/stale@v9.0.0
|
||||||
with:
|
with:
|
||||||
repo-token: ${{ secrets.GITHUB_TOKEN }}
|
repo-token: ${{ secrets.GITHUB_TOKEN }}
|
||||||
days-before-stale: 90
|
days-before-stale: 90
|
||||||
|
|||||||
3
.vscode/extensions.json
vendored
3
.vscode/extensions.json
vendored
@@ -5,7 +5,6 @@
|
|||||||
"runem.lit-plugin",
|
"runem.lit-plugin",
|
||||||
"github.vscode-pull-request-github",
|
"github.vscode-pull-request-github",
|
||||||
"eamodio.gitlens",
|
"eamodio.gitlens",
|
||||||
"vitest.explorer",
|
"vitest.explorer"
|
||||||
"yeion7.styled-global-variables-autocomplete"
|
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|||||||
42
.vscode/tasks.json
vendored
42
.vscode/tasks.json
vendored
@@ -1,42 +1,6 @@
|
|||||||
{
|
{
|
||||||
"version": "2.0.0",
|
"version": "2.0.0",
|
||||||
"tasks": [
|
"tasks": [
|
||||||
{
|
|
||||||
"label": "Develop and serve Frontend",
|
|
||||||
"type": "shell",
|
|
||||||
"command": "script/develop_and_serve -c ${input:coreUrl}",
|
|
||||||
// Sync changes here to other tasks until issue resolved
|
|
||||||
// https://github.com/Microsoft/vscode/issues/61497
|
|
||||||
"problemMatcher": {
|
|
||||||
"owner": "ha-build",
|
|
||||||
"source": "ha-build",
|
|
||||||
"fileLocation": "absolute",
|
|
||||||
"severity": "error",
|
|
||||||
"pattern": [
|
|
||||||
{
|
|
||||||
"regexp": "(SyntaxError): (.+): (.+) \\((\\d+):(\\d+)\\)",
|
|
||||||
"severity": 1,
|
|
||||||
"file": 2,
|
|
||||||
"message": 3,
|
|
||||||
"line": 4,
|
|
||||||
"column": 5
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"background": {
|
|
||||||
"activeOnStart": true,
|
|
||||||
"beginsPattern": "Changes detected. Starting compilation",
|
|
||||||
"endsPattern": "Build done @"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"isBackground": true,
|
|
||||||
"group": {
|
|
||||||
"kind": "build",
|
|
||||||
"isDefault": true
|
|
||||||
},
|
|
||||||
"runOptions": {
|
|
||||||
"instanceLimit": 1
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
"label": "Develop Frontend",
|
"label": "Develop Frontend",
|
||||||
"type": "gulp",
|
"type": "gulp",
|
||||||
@@ -277,12 +241,6 @@
|
|||||||
"id": "supervisorToken",
|
"id": "supervisorToken",
|
||||||
"type": "promptString",
|
"type": "promptString",
|
||||||
"description": "The token for the Remote API proxy add-on"
|
"description": "The token for the Remote API proxy add-on"
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "coreUrl",
|
|
||||||
"type": "promptString",
|
|
||||||
"description": "The URL of the Home Assistant Core instance",
|
|
||||||
"default": "http://127.0.0.1:8123"
|
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,22 +0,0 @@
|
|||||||
diff --git a/mwc-formfield-base.js b/mwc-formfield-base.js
|
|
||||||
index 7b763326d7d51835ad52646bfbc80fe21989abd3..f2baa8224e6d03df1fdb0b9fd03f5c6d77fc8747 100644
|
|
||||||
--- a/mwc-formfield-base.js
|
|
||||||
+++ b/mwc-formfield-base.js
|
|
||||||
@@ -9,7 +9,7 @@ import { BaseElement } from '@material/mwc-base/base-element.js';
|
|
||||||
import { FormElement } from '@material/mwc-base/form-element.js';
|
|
||||||
import { observer } from '@material/mwc-base/observer.js';
|
|
||||||
import { html } from 'lit';
|
|
||||||
-import { property, query, queryAssignedNodes } from 'lit/decorators.js';
|
|
||||||
+import { property, query, queryAssignedElements } from 'lit/decorators.js';
|
|
||||||
import { classMap } from 'lit/directives/class-map.js';
|
|
||||||
export class FormfieldBase extends BaseElement {
|
|
||||||
constructor() {
|
|
||||||
@@ -96,7 +96,7 @@ __decorate([
|
|
||||||
query('.mdc-form-field')
|
|
||||||
], FormfieldBase.prototype, "mdcRoot", void 0);
|
|
||||||
__decorate([
|
|
||||||
- queryAssignedNodes('', true, '*')
|
|
||||||
+ queryAssignedElements({ slot: "", flatten: true, selector: "*" })
|
|
||||||
], FormfieldBase.prototype, "slottedInputs", void 0);
|
|
||||||
__decorate([
|
|
||||||
query('label')
|
|
||||||
@@ -1,26 +0,0 @@
|
|||||||
diff --git a/mwc-list-base.js b/mwc-list-base.js
|
|
||||||
index 1ba95b6a01dcecea4d85b5cbbbcc3dfb04c40d5f..dced13fdb7929c490d6661b1bbe7e9f96dcd2285 100644
|
|
||||||
--- a/mwc-list-base.js
|
|
||||||
+++ b/mwc-list-base.js
|
|
||||||
@@ -11,7 +11,7 @@ import { BaseElement } from '@material/mwc-base/base-element.js';
|
|
||||||
import { observer } from '@material/mwc-base/observer.js';
|
|
||||||
import { deepActiveElementPath, doesElementContainFocus, isNodeElement } from '@material/mwc-base/utils.js';
|
|
||||||
import { html } from 'lit';
|
|
||||||
-import { property, query, queryAssignedNodes } from 'lit/decorators.js';
|
|
||||||
+import { property, query, queryAssignedElements } from 'lit/decorators.js';
|
|
||||||
import { ifDefined } from 'lit/directives/if-defined.js';
|
|
||||||
import MDCListFoundation, { isIndexSet } from './mwc-list-foundation.js';
|
|
||||||
export { createSetFromIndex, isEventMulti, isIndexSet } from './mwc-list-foundation.js';
|
|
||||||
@@ -425,10 +425,10 @@ __decorate([
|
|
||||||
query('.mdc-deprecated-list')
|
|
||||||
], ListBase.prototype, "mdcRoot", void 0);
|
|
||||||
__decorate([
|
|
||||||
- queryAssignedNodes('', true, '*')
|
|
||||||
+ queryAssignedElements({ flatten: true, selector: "*" })
|
|
||||||
], ListBase.prototype, "assignedElements", void 0);
|
|
||||||
__decorate([
|
|
||||||
- queryAssignedNodes('', true, '[tabindex="0"]')
|
|
||||||
+ queryAssignedElements({ flatten: true, selector: '[tabindex="0"]' })
|
|
||||||
], ListBase.prototype, "tabbableElements", void 0);
|
|
||||||
__decorate([
|
|
||||||
property({ type: Boolean }),
|
|
||||||
34
.yarn/patches/@polymer/polymer/pr-5569.patch
Normal file
34
.yarn/patches/@polymer/polymer/pr-5569.patch
Normal file
@@ -0,0 +1,34 @@
|
|||||||
|
diff --git a/lib/legacy/class.js b/lib/legacy/class.js
|
||||||
|
index aee2511be1cd9bf900ee552bc98190c1631c57c0..f2f499d68bf52034cac9c28307c99e8ce6b8417d 100644
|
||||||
|
--- a/lib/legacy/class.js
|
||||||
|
+++ b/lib/legacy/class.js
|
||||||
|
@@ -304,17 +304,23 @@ function GenerateClassFromInfo(info, Base, behaviors) {
|
||||||
|
// only proceed if the generated class' prototype has not been registered.
|
||||||
|
const generatedProto = PolymerGenerated.prototype;
|
||||||
|
if (!generatedProto.hasOwnProperty(JSCompiler_renameProperty('__hasRegisterFinished', generatedProto))) {
|
||||||
|
- generatedProto.__hasRegisterFinished = true;
|
||||||
|
+ // make sure legacy lifecycle is called on the *element*'s prototype
|
||||||
|
+ // and not the generated class prototype; if the element has been
|
||||||
|
+ // extended, these are *not* the same.
|
||||||
|
+ const proto = Object.getPrototypeOf(this);
|
||||||
|
+ // Only set flag when generated prototype itself is registered,
|
||||||
|
+ // as this element may be extended from, and needs to run `registered`
|
||||||
|
+ // on all behaviors on the subclass as well.
|
||||||
|
+ if (proto === generatedProto) {
|
||||||
|
+ generatedProto.__hasRegisterFinished = true;
|
||||||
|
+ }
|
||||||
|
// ensure superclass is registered first.
|
||||||
|
super._registered();
|
||||||
|
// copy properties onto the generated class lazily if we're optimizing,
|
||||||
|
- if (legacyOptimizations) {
|
||||||
|
+ if (legacyOptimizations && !Object.hasOwnProperty(generatedProto, '__hasCopiedProperties')) {
|
||||||
|
+ generatedProto.__hasCopiedProperties = true;
|
||||||
|
copyPropertiesToProto(generatedProto);
|
||||||
|
}
|
||||||
|
- // make sure legacy lifecycle is called on the *element*'s prototype
|
||||||
|
- // and not the generated class prototype; if the element has been
|
||||||
|
- // extended, these are *not* the same.
|
||||||
|
- const proto = Object.getPrototypeOf(this);
|
||||||
|
let list = lifecycle.beforeRegister;
|
||||||
|
if (list) {
|
||||||
|
for (let i=0; i < list.length; i++) {
|
||||||
934
.yarn/releases/yarn-4.5.3.cjs
vendored
Executable file
934
.yarn/releases/yarn-4.5.3.cjs
vendored
Executable file
File diff suppressed because one or more lines are too long
948
.yarn/releases/yarn-4.9.1.cjs
vendored
948
.yarn/releases/yarn-4.9.1.cjs
vendored
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.9.1.cjs
|
yarnPath: .yarn/releases/yarn-4.5.3.cjs
|
||||||
|
|||||||
@@ -2,10 +2,10 @@ import defineProvider from "@babel/helper-define-polyfill-provider";
|
|||||||
import { join } from "node:path";
|
import { join } from "node:path";
|
||||||
import paths from "../paths.cjs";
|
import paths from "../paths.cjs";
|
||||||
|
|
||||||
const POLYFILL_DIR = join(paths.root_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)) {
|
||||||
|
|||||||
@@ -18,18 +18,30 @@ module.exports.sourceMapURL = () => {
|
|||||||
module.exports.ignorePackages = () => [];
|
module.exports.ignorePackages = () => [];
|
||||||
|
|
||||||
// Files from NPM packages that we should replace with empty file
|
// Files from NPM packages that we should replace with empty file
|
||||||
module.exports.emptyPackages = ({ isHassioBuild }) =>
|
module.exports.emptyPackages = ({ latestBuild, isHassioBuild }) =>
|
||||||
[
|
[
|
||||||
|
// Contains all color definitions for all material color sets.
|
||||||
|
// We don't use it
|
||||||
|
require.resolve("@polymer/paper-styles/color.js"),
|
||||||
|
require.resolve("@polymer/paper-styles/default-theme.js"),
|
||||||
|
// Loads stuff from a CDN
|
||||||
|
require.resolve("@polymer/font-roboto/roboto.js"),
|
||||||
require.resolve("@vaadin/vaadin-material-styles/typography.js"),
|
require.resolve("@vaadin/vaadin-material-styles/typography.js"),
|
||||||
require.resolve("@vaadin/vaadin-material-styles/font-icons.js"),
|
require.resolve("@vaadin/vaadin-material-styles/font-icons.js"),
|
||||||
|
// Compatibility not needed for latest builds
|
||||||
|
latestBuild &&
|
||||||
|
// wrapped in require.resolve so it blows up if file no longer exists
|
||||||
|
require.resolve(
|
||||||
|
path.resolve(paths.polymer_dir, "src/resources/compatibility.ts")
|
||||||
|
),
|
||||||
// Icons in supervisor conflict with icons in HA so we don't load.
|
// Icons in supervisor conflict with icons in HA so we don't load.
|
||||||
isHassioBuild &&
|
isHassioBuild &&
|
||||||
require.resolve(
|
require.resolve(
|
||||||
path.resolve(paths.root_dir, "src/components/ha-icon.ts")
|
path.resolve(paths.polymer_dir, "src/components/ha-icon.ts")
|
||||||
),
|
),
|
||||||
isHassioBuild &&
|
isHassioBuild &&
|
||||||
require.resolve(
|
require.resolve(
|
||||||
path.resolve(paths.root_dir, "src/components/ha-icon-picker.ts")
|
path.resolve(paths.polymer_dir, "src/components/ha-icon-picker.ts")
|
||||||
),
|
),
|
||||||
].filter(Boolean);
|
].filter(Boolean);
|
||||||
|
|
||||||
@@ -43,9 +55,8 @@ module.exports.definedVars = ({ isProdBuild, latestBuild, defineOverlay }) => ({
|
|||||||
__STATIC_PATH__: "/static/",
|
__STATIC_PATH__: "/static/",
|
||||||
__HASS_URL__: `\`${
|
__HASS_URL__: `\`${
|
||||||
"HASS_URL" in process.env
|
"HASS_URL" in process.env
|
||||||
? process.env.HASS_URL
|
? process.env["HASS_URL"]
|
||||||
: // eslint-disable-next-line no-template-curly-in-string
|
: "${location.protocol}//${location.host}"
|
||||||
"${location.protocol}//${location.host}"
|
|
||||||
}\``,
|
}\``,
|
||||||
"process.env.NODE_ENV": JSON.stringify(
|
"process.env.NODE_ENV": JSON.stringify(
|
||||||
isProdBuild ? "production" : "development"
|
isProdBuild ? "production" : "development"
|
||||||
@@ -73,19 +84,6 @@ module.exports.terserOptions = ({ latestBuild, isTestBuild }) => ({
|
|||||||
sourceMap: !isTestBuild,
|
sourceMap: !isTestBuild,
|
||||||
});
|
});
|
||||||
|
|
||||||
/** @type {import('@rspack/core').SwcLoaderOptions} */
|
|
||||||
module.exports.swcOptions = () => ({
|
|
||||||
jsc: {
|
|
||||||
loose: true,
|
|
||||||
externalHelpers: true,
|
|
||||||
target: "ES2021",
|
|
||||||
parser: {
|
|
||||||
syntax: "typescript",
|
|
||||||
decorators: true,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
});
|
|
||||||
|
|
||||||
module.exports.babelOptions = ({
|
module.exports.babelOptions = ({
|
||||||
latestBuild,
|
latestBuild,
|
||||||
isProdBuild,
|
isProdBuild,
|
||||||
@@ -110,6 +108,7 @@ module.exports.babelOptions = ({
|
|||||||
shippedProposals: true,
|
shippedProposals: true,
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
|
"@babel/preset-typescript",
|
||||||
],
|
],
|
||||||
plugins: [
|
plugins: [
|
||||||
[
|
[
|
||||||
@@ -146,6 +145,12 @@ module.exports.babelOptions = ({
|
|||||||
"@babel/plugin-transform-runtime",
|
"@babel/plugin-transform-runtime",
|
||||||
{ version: dependencies["@babel/runtime"] },
|
{ version: dependencies["@babel/runtime"] },
|
||||||
],
|
],
|
||||||
|
// Transpile decorators (still in TC39 process)
|
||||||
|
// Modern browsers support class fields and private methods, but transform is required with the older decorator version dictated by Lit
|
||||||
|
[
|
||||||
|
"@babel/plugin-proposal-decorators",
|
||||||
|
{ version: "2018-09", decoratorsBeforeExport: true },
|
||||||
|
],
|
||||||
"@babel/plugin-transform-class-properties",
|
"@babel/plugin-transform-class-properties",
|
||||||
"@babel/plugin-transform-private-methods",
|
"@babel/plugin-transform-private-methods",
|
||||||
].filter(Boolean),
|
].filter(Boolean),
|
||||||
@@ -165,7 +170,7 @@ module.exports.babelOptions = ({
|
|||||||
],
|
],
|
||||||
],
|
],
|
||||||
exclude: [
|
exclude: [
|
||||||
path.join(paths.root_dir, "src/resources/polyfills"),
|
path.join(paths.polymer_dir, "src/resources/polyfills"),
|
||||||
...[
|
...[
|
||||||
"@formatjs/(?:ecma402-abstract|intl-\\w+)",
|
"@formatjs/(?:ecma402-abstract|intl-\\w+)",
|
||||||
"@lit-labs/virtualizer/polyfills",
|
"@lit-labs/virtualizer/polyfills",
|
||||||
@@ -183,7 +188,6 @@ module.exports.babelOptions = ({
|
|||||||
include: /\/node_modules\//,
|
include: /\/node_modules\//,
|
||||||
exclude: [
|
exclude: [
|
||||||
"element-internals-polyfill",
|
"element-internals-polyfill",
|
||||||
"@shoelace-style",
|
|
||||||
"@?lit(?:-labs|-element|-html)?",
|
"@?lit(?:-labs|-element|-html)?",
|
||||||
].map((p) => new RegExp(`/node_modules/${p}/`)),
|
].map((p) => new RegExp(`/node_modules/${p}/`)),
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -21,7 +21,7 @@ module.exports = {
|
|||||||
},
|
},
|
||||||
version() {
|
version() {
|
||||||
const version = fs
|
const version = fs
|
||||||
.readFileSync(path.resolve(paths.root_dir, "pyproject.toml"), "utf8")
|
.readFileSync(path.resolve(paths.polymer_dir, "pyproject.toml"), "utf8")
|
||||||
.match(/version\W+=\W"(\d{8}\.\d(?:\.dev)?)"/);
|
.match(/version\W+=\W"(\d{8}\.\d(?:\.dev)?)"/);
|
||||||
if (!version) {
|
if (!version) {
|
||||||
throw Error("Version not found");
|
throw Error("Version not found");
|
||||||
|
|||||||
@@ -1,16 +1,16 @@
|
|||||||
// @ts-check
|
|
||||||
|
|
||||||
import tseslint from "typescript-eslint";
|
|
||||||
import rootConfig from "../eslint.config.mjs";
|
import rootConfig from "../eslint.config.mjs";
|
||||||
|
|
||||||
export default tseslint.config(...rootConfig, {
|
export default [
|
||||||
rules: {
|
...rootConfig,
|
||||||
"no-console": "off",
|
{
|
||||||
"import/no-extraneous-dependencies": "off",
|
rules: {
|
||||||
"import/extensions": "off",
|
"no-console": "off",
|
||||||
"import/no-dynamic-require": "off",
|
"import/no-extraneous-dependencies": "off",
|
||||||
"global-require": "off",
|
"import/extensions": "off",
|
||||||
"@typescript-eslint/no-require-imports": "off",
|
"import/no-dynamic-require": "off",
|
||||||
"prefer-arrow-callback": "off",
|
"global-require": "off",
|
||||||
|
"@typescript-eslint/no-var-requires": "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,74 +12,29 @@ 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 compressDistBrotli = (rootDir, modernDir, compressServiceWorker = true) =>
|
||||||
gulp
|
|
||||||
.src([`${modernDir}/**/${filesGlob}`, `${rootDir}/sw-modern.js`], {
|
|
||||||
base: rootDir,
|
|
||||||
allowEmpty: true,
|
|
||||||
})
|
|
||||||
.pipe(compress === "zopfli" ? zopfli(zopfliOptions) : brotli(brotliOptions))
|
|
||||||
.pipe(gulp.dest(rootDir));
|
|
||||||
|
|
||||||
const compressOther = (rootDir, modernDir, compress) =>
|
|
||||||
gulp
|
gulp
|
||||||
.src(
|
.src(
|
||||||
[
|
[
|
||||||
`${rootDir}/**/${filesGlob}`,
|
`${modernDir}/**/${filesGlob}`,
|
||||||
`!${modernDir}/**/${filesGlob}`,
|
compressServiceWorker ? `${rootDir}/sw-modern.js` : undefined,
|
||||||
`!${rootDir}/{sw-modern,service_worker}.js`,
|
].filter(Boolean),
|
||||||
`${rootDir}/{authorize,onboarding}.html`,
|
{
|
||||||
],
|
base: rootDir,
|
||||||
{ 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 compressAppBrotli = () =>
|
||||||
compressModern(paths.app_output_root, paths.app_output_latest, "brotli");
|
compressDistBrotli(paths.app_output_root, paths.app_output_latest);
|
||||||
const compressAppModernZopfli = () =>
|
const compressHassioBrotli = () =>
|
||||||
compressModern(paths.app_output_root, paths.app_output_latest, "zopfli");
|
compressDistBrotli(
|
||||||
|
|
||||||
const compressHassioModernBrotli = () =>
|
|
||||||
compressModern(
|
|
||||||
paths.hassio_output_root,
|
paths.hassio_output_root,
|
||||||
paths.hassio_output_latest,
|
paths.hassio_output_latest,
|
||||||
"brotli"
|
false
|
||||||
);
|
|
||||||
const compressHassioModernZopfli = () =>
|
|
||||||
compressModern(
|
|
||||||
paths.hassio_output_root,
|
|
||||||
paths.hassio_output_latest,
|
|
||||||
"zopfli"
|
|
||||||
);
|
);
|
||||||
|
|
||||||
const compressAppOtherBrotli = () =>
|
gulp.task("compress-app", compressAppBrotli);
|
||||||
compressOther(paths.app_output_root, paths.app_output_latest, "brotli");
|
gulp.task("compress-hassio", compressHassioBrotli);
|
||||||
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(
|
|
||||||
"compress-hassio",
|
|
||||||
gulp.parallel(
|
|
||||||
compressHassioModernBrotli,
|
|
||||||
compressHassioOtherBrotli,
|
|
||||||
compressHassioModernZopfli,
|
|
||||||
compressHassioOtherZopfli
|
|
||||||
)
|
|
||||||
);
|
|
||||||
|
|||||||
@@ -56,7 +56,6 @@ const getCommonTemplateVars = () => {
|
|||||||
);
|
);
|
||||||
return {
|
return {
|
||||||
modernRegex: compileRegex(browserRegexes.concat(haMacOSRegex)).toString(),
|
modernRegex: compileRegex(browserRegexes.concat(haMacOSRegex)).toString(),
|
||||||
hassUrl: process.env.HASS_URL || "",
|
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -169,14 +168,14 @@ const APP_PAGE_ENTRIES = {
|
|||||||
|
|
||||||
gulp.task(
|
gulp.task(
|
||||||
"gen-pages-app-dev",
|
"gen-pages-app-dev",
|
||||||
genPagesDevTask(APP_PAGE_ENTRIES, paths.root_dir, paths.app_output_root)
|
genPagesDevTask(APP_PAGE_ENTRIES, paths.polymer_dir, paths.app_output_root)
|
||||||
);
|
);
|
||||||
|
|
||||||
gulp.task(
|
gulp.task(
|
||||||
"gen-pages-app-prod",
|
"gen-pages-app-prod",
|
||||||
genPagesProdTask(
|
genPagesProdTask(
|
||||||
APP_PAGE_ENTRIES,
|
APP_PAGE_ENTRIES,
|
||||||
paths.root_dir,
|
paths.polymer_dir,
|
||||||
paths.app_output_root,
|
paths.app_output_root,
|
||||||
paths.app_output_latest,
|
paths.app_output_latest,
|
||||||
paths.app_output_es5
|
paths.app_output_es5
|
||||||
|
|||||||
@@ -6,8 +6,8 @@ import path from "path";
|
|||||||
import paths from "../paths.cjs";
|
import paths from "../paths.cjs";
|
||||||
|
|
||||||
const npmPath = (...parts) =>
|
const npmPath = (...parts) =>
|
||||||
path.resolve(paths.root_dir, "node_modules", ...parts);
|
path.resolve(paths.polymer_dir, "node_modules", ...parts);
|
||||||
const polyPath = (...parts) => path.resolve(paths.root_dir, ...parts);
|
const polyPath = (...parts) => path.resolve(paths.polymer_dir, ...parts);
|
||||||
|
|
||||||
const copyFileDir = (fromFile, toDir) =>
|
const copyFileDir = (fromFile, toDir) =>
|
||||||
fs.copySync(fromFile, path.join(toDir, path.basename(fromFile)));
|
fs.copySync(fromFile, path.join(toDir, path.basename(fromFile)));
|
||||||
@@ -59,11 +59,6 @@ function copyPolyfills(staticDir) {
|
|||||||
npmPath("@webcomponents/webcomponentsjs/webcomponents-bundle.js.map"),
|
npmPath("@webcomponents/webcomponentsjs/webcomponents-bundle.js.map"),
|
||||||
staticPath("polyfills/")
|
staticPath("polyfills/")
|
||||||
);
|
);
|
||||||
// Lit polyfill support
|
|
||||||
fs.copySync(
|
|
||||||
npmPath("lit/polyfill-support.js"),
|
|
||||||
path.join(staticPath("polyfills/"), "lit-polyfill-support.js")
|
|
||||||
);
|
|
||||||
|
|
||||||
// dialog-polyfill css
|
// dialog-polyfill css
|
||||||
copyFileDir(
|
copyFileDir(
|
||||||
@@ -72,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
|
||||||
@@ -95,10 +96,6 @@ function copyMapPanel(staticDir) {
|
|||||||
npmPath("leaflet/dist/leaflet.css"),
|
npmPath("leaflet/dist/leaflet.css"),
|
||||||
staticPath("images/leaflet/")
|
staticPath("images/leaflet/")
|
||||||
);
|
);
|
||||||
copyFileDir(
|
|
||||||
npmPath("leaflet.markercluster/dist/MarkerCluster.css"),
|
|
||||||
staticPath("images/leaflet/")
|
|
||||||
);
|
|
||||||
fs.copySync(
|
fs.copySync(
|
||||||
npmPath("leaflet/dist/images"),
|
npmPath("leaflet/dist/images"),
|
||||||
staticPath("images/leaflet/images/")
|
staticPath("images/leaflet/images/")
|
||||||
@@ -143,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);
|
||||||
@@ -165,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);
|
||||||
@@ -178,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";
|
|
||||||
@@ -4,7 +4,7 @@ import gulp from "gulp";
|
|||||||
import { join, resolve } from "node:path";
|
import { join, resolve } from "node:path";
|
||||||
import paths from "../paths.cjs";
|
import paths from "../paths.cjs";
|
||||||
|
|
||||||
const formatjsDir = join(paths.root_dir, "node_modules", "@formatjs");
|
const formatjsDir = join(paths.polymer_dir, "node_modules", "@formatjs");
|
||||||
const outDir = join(paths.build_dir, "locale-data");
|
const outDir = join(paths.build_dir, "locale-data");
|
||||||
|
|
||||||
const INTL_POLYFILLS = {
|
const INTL_POLYFILLS = {
|
||||||
|
|||||||
@@ -40,17 +40,20 @@ class CustomJSON extends Transform {
|
|||||||
this._reviver = reviver;
|
this._reviver = reviver;
|
||||||
}
|
}
|
||||||
|
|
||||||
// eslint-disable-next-line @typescript-eslint/naming-convention
|
|
||||||
async _transform(file, _, callback) {
|
async _transform(file, _, callback) {
|
||||||
let obj = JSON.parse(file.contents.toString(), this._reviver);
|
try {
|
||||||
if (this._func) obj = this._func(obj, file.path);
|
let obj = JSON.parse(file.contents.toString(), this._reviver);
|
||||||
for (const [outObj, dir] of Array.isArray(obj) ? obj : [[obj, ""]]) {
|
if (this._func) obj = this._func(obj, file.path);
|
||||||
const outFile = file.clone({ contents: false });
|
for (const [outObj, dir] of Array.isArray(obj) ? obj : [[obj, ""]]) {
|
||||||
outFile.contents = Buffer.from(JSON.stringify(outObj));
|
const outFile = file.clone({ contents: false });
|
||||||
outFile.dirname += `/${dir}`;
|
outFile.contents = Buffer.from(JSON.stringify(outObj));
|
||||||
this.push(outFile);
|
outFile.dirname += `/${dir}`;
|
||||||
|
this.push(outFile);
|
||||||
|
}
|
||||||
|
callback(null);
|
||||||
|
} catch (err) {
|
||||||
|
callback(err);
|
||||||
}
|
}
|
||||||
callback(null);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -65,19 +68,25 @@ class MergeJSON extends Transform {
|
|||||||
this._reviver = reviver;
|
this._reviver = reviver;
|
||||||
}
|
}
|
||||||
|
|
||||||
// eslint-disable-next-line @typescript-eslint/naming-convention
|
|
||||||
async _transform(file, _, callback) {
|
async _transform(file, _, callback) {
|
||||||
this._objects.push(JSON.parse(file.contents.toString(), this._reviver));
|
try {
|
||||||
if (!this._outFile) this._outFile = file.clone({ contents: false });
|
this._objects.push(JSON.parse(file.contents.toString(), this._reviver));
|
||||||
callback(null);
|
if (!this._outFile) this._outFile = file.clone({ contents: false });
|
||||||
|
callback(null);
|
||||||
|
} catch (err) {
|
||||||
|
callback(err);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// eslint-disable-next-line @typescript-eslint/naming-convention
|
|
||||||
async _flush(callback) {
|
async _flush(callback) {
|
||||||
const mergedObj = merge(this._startObj, ...this._objects);
|
try {
|
||||||
this._outFile.contents = Buffer.from(JSON.stringify(mergedObj));
|
const mergedObj = merge(this._startObj, ...this._objects);
|
||||||
this._outFile.stem = this._stem;
|
this._outFile.contents = Buffer.from(JSON.stringify(mergedObj));
|
||||||
callback(null, this._outFile);
|
this._outFile.stem = this._stem;
|
||||||
|
callback(null, this._outFile);
|
||||||
|
} catch (err) {
|
||||||
|
callback(err);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -16,7 +16,6 @@ const detailsClose = "</details>\n";
|
|||||||
|
|
||||||
const dummyAPI = {
|
const dummyAPI = {
|
||||||
version: babelVersion,
|
version: babelVersion,
|
||||||
// eslint-disable-next-line @typescript-eslint/no-empty-function
|
|
||||||
assertVersion: () => {},
|
assertVersion: () => {},
|
||||||
caller: (callback) =>
|
caller: (callback) =>
|
||||||
callback({
|
callback({
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
const path = require("path");
|
const path = require("path");
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
root_dir: path.resolve(__dirname, ".."),
|
polymer_dir: path.resolve(__dirname, ".."),
|
||||||
|
|
||||||
build_dir: path.resolve(__dirname, "../build"),
|
build_dir: path.resolve(__dirname, "../build"),
|
||||||
app_output_root: path.resolve(__dirname, "../hass_frontend"),
|
app_output_root: path.resolve(__dirname, "../hass_frontend"),
|
||||||
|
|||||||
@@ -1,17 +1,12 @@
|
|||||||
const { existsSync } = require("fs");
|
const { existsSync } = require("fs");
|
||||||
const path = require("path");
|
const path = require("path");
|
||||||
const rspack = require("@rspack/core");
|
const rspack = require("@rspack/core");
|
||||||
// eslint-disable-next-line @typescript-eslint/naming-convention
|
|
||||||
const { RsdoctorRspackPlugin } = require("@rsdoctor/rspack-plugin");
|
const { RsdoctorRspackPlugin } = require("@rsdoctor/rspack-plugin");
|
||||||
// eslint-disable-next-line @typescript-eslint/naming-convention
|
|
||||||
const { StatsWriterPlugin } = require("webpack-stats-plugin");
|
const { StatsWriterPlugin } = require("webpack-stats-plugin");
|
||||||
const filterStats = require("@bundle-stats/plugin-webpack-filter");
|
const filterStats = require("@bundle-stats/plugin-webpack-filter").default;
|
||||||
// eslint-disable-next-line @typescript-eslint/naming-convention
|
|
||||||
const TerserPlugin = require("terser-webpack-plugin");
|
const TerserPlugin = require("terser-webpack-plugin");
|
||||||
// eslint-disable-next-line @typescript-eslint/naming-convention
|
|
||||||
const { WebpackManifestPlugin } = require("rspack-manifest-plugin");
|
const { WebpackManifestPlugin } = require("rspack-manifest-plugin");
|
||||||
const log = require("fancy-log");
|
const log = require("fancy-log");
|
||||||
// eslint-disable-next-line @typescript-eslint/naming-convention
|
|
||||||
const WebpackBar = require("webpackbar/rspack");
|
const WebpackBar = require("webpackbar/rspack");
|
||||||
const paths = require("./paths.cjs");
|
const paths = require("./paths.cjs");
|
||||||
const bundle = require("./bundle.cjs");
|
const bundle = require("./bundle.cjs");
|
||||||
@@ -65,26 +60,19 @@ const createRspackConfig = ({
|
|||||||
rules: [
|
rules: [
|
||||||
{
|
{
|
||||||
test: /\.m?js$|\.ts$/,
|
test: /\.m?js$|\.ts$/,
|
||||||
exclude: /node_modules[\\/]core-js/,
|
use: (info) => ({
|
||||||
use: (info) => [
|
loader: "babel-loader",
|
||||||
{
|
options: {
|
||||||
loader: "babel-loader",
|
...bundle.babelOptions({
|
||||||
options: {
|
latestBuild,
|
||||||
...bundle.babelOptions({
|
isProdBuild,
|
||||||
latestBuild,
|
isTestBuild,
|
||||||
isProdBuild,
|
sw: info.issuerLayer === "sw",
|
||||||
isTestBuild,
|
}),
|
||||||
sw: info.issuerLayer === "sw",
|
cacheDirectory: !isProdBuild,
|
||||||
}),
|
cacheCompression: false,
|
||||||
cacheDirectory: !isProdBuild,
|
|
||||||
cacheCompression: false,
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
{
|
}),
|
||||||
loader: "builtin:swc-loader",
|
|
||||||
options: bundle.swcOptions(),
|
|
||||||
},
|
|
||||||
],
|
|
||||||
resolve: {
|
resolve: {
|
||||||
fullySpecified: false,
|
fullySpecified: false,
|
||||||
},
|
},
|
||||||
@@ -143,8 +131,7 @@ const createRspackConfig = ({
|
|||||||
// calling define.amd will call require("!!webpack amd options")
|
// calling define.amd will call require("!!webpack amd options")
|
||||||
resource.startsWith("!!webpack") ||
|
resource.startsWith("!!webpack") ||
|
||||||
// loaded by webpack dev server but doesn't exist.
|
// loaded by webpack dev server but doesn't exist.
|
||||||
resource === "webpack/hot" ||
|
resource === "webpack/hot"
|
||||||
resource.startsWith("@swc/helpers")
|
|
||||||
) {
|
) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -168,8 +155,10 @@ const createRspackConfig = ({
|
|||||||
},
|
},
|
||||||
}),
|
}),
|
||||||
new rspack.NormalModuleReplacementPlugin(
|
new rspack.NormalModuleReplacementPlugin(
|
||||||
new RegExp(bundle.emptyPackages({ isHassioBuild }).join("|")),
|
new RegExp(
|
||||||
path.resolve(paths.root_dir, "src/util/empty.js")
|
bundle.emptyPackages({ latestBuild, isHassioBuild }).join("|")
|
||||||
|
),
|
||||||
|
path.resolve(paths.polymer_dir, "src/util/empty.js")
|
||||||
),
|
),
|
||||||
!isProdBuild && new LogStartCompilePlugin(),
|
!isProdBuild && new LogStartCompilePlugin(),
|
||||||
isProdBuild &&
|
isProdBuild &&
|
||||||
@@ -203,7 +192,6 @@ const createRspackConfig = ({
|
|||||||
"lit/directives/if-defined$": "lit/directives/if-defined.js",
|
"lit/directives/if-defined$": "lit/directives/if-defined.js",
|
||||||
"lit/directives/guard$": "lit/directives/guard.js",
|
"lit/directives/guard$": "lit/directives/guard.js",
|
||||||
"lit/directives/cache$": "lit/directives/cache.js",
|
"lit/directives/cache$": "lit/directives/cache.js",
|
||||||
"lit/directives/join$": "lit/directives/join.js",
|
|
||||||
"lit/directives/repeat$": "lit/directives/repeat.js",
|
"lit/directives/repeat$": "lit/directives/repeat.js",
|
||||||
"lit/directives/live$": "lit/directives/live.js",
|
"lit/directives/live$": "lit/directives/live.js",
|
||||||
"lit/directives/keyed$": "lit/directives/keyed.js",
|
"lit/directives/keyed$": "lit/directives/keyed.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>
|
||||||
|
|||||||
@@ -1,3 +1,3 @@
|
|||||||
import "./layout/hc-connect";
|
import "./layout/hc-connect";
|
||||||
|
|
||||||
import("../../../src/resources/append-ha-style");
|
import("../../../src/resources/ha-style");
|
||||||
|
|||||||
@@ -1,9 +1,9 @@
|
|||||||
import "@material/mwc-button/mwc-button";
|
import "@material/mwc-button/mwc-button";
|
||||||
|
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";
|
||||||
@@ -19,8 +19,6 @@ import {
|
|||||||
import { atLeastVersion } from "../../../../src/common/config/version";
|
import { atLeastVersion } from "../../../../src/common/config/version";
|
||||||
import { toggleAttribute } from "../../../../src/common/dom/toggle_attribute";
|
import { toggleAttribute } from "../../../../src/common/dom/toggle_attribute";
|
||||||
import "../../../../src/components/ha-icon";
|
import "../../../../src/components/ha-icon";
|
||||||
import "../../../../src/components/ha-list";
|
|
||||||
import "../../../../src/components/ha-list-item";
|
|
||||||
import "../../../../src/components/ha-svg-icon";
|
import "../../../../src/components/ha-svg-icon";
|
||||||
import {
|
import {
|
||||||
getLegacyLovelaceCollection,
|
getLegacyLovelaceCollection,
|
||||||
@@ -31,6 +29,7 @@ import type { LovelaceViewConfig } from "../../../../src/data/lovelace/config/vi
|
|||||||
import "../../../../src/layouts/hass-loading-screen";
|
import "../../../../src/layouts/hass-loading-screen";
|
||||||
import { generateDefaultViewConfig } from "../../../../src/panels/lovelace/common/generate-lovelace-config";
|
import { generateDefaultViewConfig } from "../../../../src/panels/lovelace/common/generate-lovelace-config";
|
||||||
import "./hc-layout";
|
import "./hc-layout";
|
||||||
|
import "../../../../src/components/ha-list-item";
|
||||||
|
|
||||||
@customElement("hc-cast")
|
@customElement("hc-cast")
|
||||||
class HcCast extends LitElement {
|
class HcCast extends LitElement {
|
||||||
@@ -86,7 +85,7 @@ class HcCast extends LitElement {
|
|||||||
`
|
`
|
||||||
: html`
|
: html`
|
||||||
<div class="section-header">PICK A VIEW</div>
|
<div class="section-header">PICK A VIEW</div>
|
||||||
<ha-list @action=${this._handlePickView} activatable>
|
<mwc-list @action=${this._handlePickView} activatable>
|
||||||
${(
|
${(
|
||||||
this.lovelaceViews ?? [
|
this.lovelaceViews ?? [
|
||||||
generateDefaultViewConfig({}, {}, {}, {}, () => ""),
|
generateDefaultViewConfig({}, {}, {}, {}, () => ""),
|
||||||
@@ -114,7 +113,7 @@ class HcCast extends LitElement {
|
|||||||
></ha-svg-icon>`}
|
></ha-svg-icon>`}
|
||||||
</ha-list-item>
|
</ha-list-item>
|
||||||
`
|
`
|
||||||
)}</ha-list
|
)}</mwc-list
|
||||||
>
|
>
|
||||||
`}
|
`}
|
||||||
|
|
||||||
@@ -204,72 +203,74 @@ 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 {
|
||||||
.center-item {
|
return css`
|
||||||
display: flex;
|
.center-item {
|
||||||
justify-content: space-around;
|
display: flex;
|
||||||
}
|
justify-content: space-around;
|
||||||
|
}
|
||||||
|
|
||||||
.action-item {
|
.action-item {
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
justify-content: space-between;
|
justify-content: space-between;
|
||||||
}
|
}
|
||||||
|
|
||||||
.question {
|
.question {
|
||||||
position: relative;
|
position: relative;
|
||||||
padding: 8px 16px;
|
padding: 8px 16px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.question:before {
|
.question:before {
|
||||||
border-radius: 4px;
|
border-radius: 4px;
|
||||||
position: absolute;
|
position: absolute;
|
||||||
top: 0;
|
top: 0;
|
||||||
right: 0;
|
right: 0;
|
||||||
bottom: 0;
|
bottom: 0;
|
||||||
left: 0;
|
left: 0;
|
||||||
pointer-events: none;
|
pointer-events: none;
|
||||||
content: "";
|
content: "";
|
||||||
background-color: var(--primary-color);
|
background-color: var(--primary-color);
|
||||||
opacity: 0.12;
|
opacity: 0.12;
|
||||||
will-change: opacity;
|
will-change: opacity;
|
||||||
}
|
}
|
||||||
|
|
||||||
.connection,
|
.connection,
|
||||||
.connection a {
|
.connection a {
|
||||||
color: var(--secondary-text-color);
|
color: var(--secondary-text-color);
|
||||||
}
|
}
|
||||||
|
|
||||||
mwc-button ha-svg-icon {
|
mwc-button ha-svg-icon {
|
||||||
margin-right: 8px;
|
margin-right: 8px;
|
||||||
margin-inline-end: 8px;
|
margin-inline-end: 8px;
|
||||||
margin-inline-start: initial;
|
margin-inline-start: initial;
|
||||||
height: 18px;
|
height: 18px;
|
||||||
}
|
}
|
||||||
|
|
||||||
ha-list-item ha-icon,
|
ha-list-item ha-icon,
|
||||||
ha-list-item ha-svg-icon {
|
ha-list-item ha-svg-icon {
|
||||||
padding: 12px;
|
padding: 12px;
|
||||||
color: var(--secondary-text-color);
|
color: var(--secondary-text-color);
|
||||||
}
|
}
|
||||||
|
|
||||||
:host([hide-icons]) ha-icon {
|
:host([hide-icons]) ha-icon {
|
||||||
display: none;
|
display: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
.spacer {
|
.spacer {
|
||||||
flex: 1;
|
flex: 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
.card-content a {
|
.card-content a {
|
||||||
color: var(--primary-color);
|
color: var(--primary-color);
|
||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -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,39 +288,41 @@ 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 {
|
||||||
.card-content a {
|
return css`
|
||||||
color: var(--primary-color);
|
.card-content a {
|
||||||
}
|
color: var(--primary-color);
|
||||||
.card-actions a {
|
}
|
||||||
text-decoration: none;
|
.card-actions a {
|
||||||
}
|
text-decoration: none;
|
||||||
.error {
|
}
|
||||||
color: red;
|
.error {
|
||||||
font-weight: bold;
|
color: red;
|
||||||
}
|
font-weight: bold;
|
||||||
|
}
|
||||||
|
|
||||||
.error a {
|
.error a {
|
||||||
color: darkred;
|
color: darkred;
|
||||||
}
|
}
|
||||||
|
|
||||||
mwc-button ha-svg-icon {
|
mwc-button ha-svg-icon {
|
||||||
margin-left: 8px;
|
margin-left: 8px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.spacer {
|
.spacer {
|
||||||
flex: 1;
|
flex: 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
ha-textfield {
|
ha-textfield {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -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,94 +63,96 @@ class HcLayout extends LitElement {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
:host {
|
return css`
|
||||||
display: flex;
|
|
||||||
min-height: 100%;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
flex-direction: column;
|
|
||||||
}
|
|
||||||
|
|
||||||
ha-card {
|
|
||||||
display: flex;
|
|
||||||
width: 100%;
|
|
||||||
max-width: 500px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.layout {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
}
|
|
||||||
|
|
||||||
.card-header {
|
|
||||||
color: var(--ha-card-header-color, var(--primary-text-color));
|
|
||||||
font-family: var(--ha-card-header-font-family, inherit);
|
|
||||||
font-size: var(--ha-card-header-font-size, 24px);
|
|
||||||
letter-spacing: -0.012em;
|
|
||||||
line-height: 32px;
|
|
||||||
padding: 24px 16px 16px;
|
|
||||||
display: block;
|
|
||||||
margin: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero {
|
|
||||||
border-radius: 4px 4px 0 0;
|
|
||||||
}
|
|
||||||
.subtitle {
|
|
||||||
font-size: 14px;
|
|
||||||
color: var(--secondary-text-color);
|
|
||||||
line-height: initial;
|
|
||||||
}
|
|
||||||
.subtitle a {
|
|
||||||
color: var(--secondary-text-color);
|
|
||||||
}
|
|
||||||
|
|
||||||
:host ::slotted(.card-content:not(:first-child)),
|
|
||||||
slot:not(:first-child)::slotted(.card-content) {
|
|
||||||
padding-top: 0px;
|
|
||||||
margin-top: -8px;
|
|
||||||
}
|
|
||||||
|
|
||||||
:host ::slotted(.section-header) {
|
|
||||||
font-weight: 500;
|
|
||||||
padding: 4px 16px;
|
|
||||||
text-transform: uppercase;
|
|
||||||
}
|
|
||||||
|
|
||||||
:host ::slotted(.card-content) {
|
|
||||||
padding: 16px;
|
|
||||||
flex: 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
:host ::slotted(.card-actions) {
|
|
||||||
border-top: 1px solid #e8e8e8;
|
|
||||||
padding: 5px 16px;
|
|
||||||
display: flex;
|
|
||||||
}
|
|
||||||
|
|
||||||
img {
|
|
||||||
width: 100%;
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer {
|
|
||||||
text-align: center;
|
|
||||||
font-size: 12px;
|
|
||||||
padding: 8px 0 24px;
|
|
||||||
color: var(--secondary-text-color);
|
|
||||||
}
|
|
||||||
.footer a {
|
|
||||||
color: var(--secondary-text-color);
|
|
||||||
}
|
|
||||||
|
|
||||||
@media all and (max-width: 500px) {
|
|
||||||
:host {
|
:host {
|
||||||
justify-content: flex-start;
|
display: flex;
|
||||||
min-height: 90%;
|
min-height: 100%;
|
||||||
margin-bottom: 30px;
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
flex-direction: column;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
`;
|
ha-card {
|
||||||
|
display: flex;
|
||||||
|
width: 100%;
|
||||||
|
max-width: 500px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.layout {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
}
|
||||||
|
|
||||||
|
.card-header {
|
||||||
|
color: var(--ha-card-header-color, var(--primary-text-color));
|
||||||
|
font-family: var(--ha-card-header-font-family, inherit);
|
||||||
|
font-size: var(--ha-card-header-font-size, 24px);
|
||||||
|
letter-spacing: -0.012em;
|
||||||
|
line-height: 32px;
|
||||||
|
padding: 24px 16px 16px;
|
||||||
|
display: block;
|
||||||
|
margin: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.hero {
|
||||||
|
border-radius: 4px 4px 0 0;
|
||||||
|
}
|
||||||
|
.subtitle {
|
||||||
|
font-size: 14px;
|
||||||
|
color: var(--secondary-text-color);
|
||||||
|
line-height: initial;
|
||||||
|
}
|
||||||
|
.subtitle a {
|
||||||
|
color: var(--secondary-text-color);
|
||||||
|
}
|
||||||
|
|
||||||
|
:host ::slotted(.card-content:not(:first-child)),
|
||||||
|
slot:not(:first-child)::slotted(.card-content) {
|
||||||
|
padding-top: 0px;
|
||||||
|
margin-top: -8px;
|
||||||
|
}
|
||||||
|
|
||||||
|
:host ::slotted(.section-header) {
|
||||||
|
font-weight: 500;
|
||||||
|
padding: 4px 16px;
|
||||||
|
text-transform: uppercase;
|
||||||
|
}
|
||||||
|
|
||||||
|
:host ::slotted(.card-content) {
|
||||||
|
padding: 16px;
|
||||||
|
flex: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
:host ::slotted(.card-actions) {
|
||||||
|
border-top: 1px solid #e8e8e8;
|
||||||
|
padding: 5px 16px;
|
||||||
|
display: flex;
|
||||||
|
}
|
||||||
|
|
||||||
|
img {
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.footer {
|
||||||
|
text-align: center;
|
||||||
|
font-size: 12px;
|
||||||
|
padding: 8px 0 24px;
|
||||||
|
color: var(--secondary-text-color);
|
||||||
|
}
|
||||||
|
.footer a {
|
||||||
|
color: var(--secondary-text-color);
|
||||||
|
}
|
||||||
|
|
||||||
|
@media all and (max-width: 500px) {
|
||||||
|
:host {
|
||||||
|
justify-content: flex-start;
|
||||||
|
min-height: 90%;
|
||||||
|
margin-bottom: 30px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -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,29 +24,31 @@ class HcLaunchScreen extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
:host {
|
return css`
|
||||||
display: block;
|
:host {
|
||||||
height: 100vh;
|
display: block;
|
||||||
background-color: #f2f4f9;
|
height: 100vh;
|
||||||
font-size: 24px;
|
background-color: #f2f4f9;
|
||||||
}
|
font-size: 24px;
|
||||||
.container {
|
}
|
||||||
display: flex;
|
.container {
|
||||||
flex-direction: column;
|
display: flex;
|
||||||
text-align: center;
|
flex-direction: column;
|
||||||
align-items: center;
|
text-align: center;
|
||||||
height: 100%;
|
align-items: center;
|
||||||
justify-content: space-evenly;
|
height: 100%;
|
||||||
}
|
justify-content: space-evenly;
|
||||||
img {
|
}
|
||||||
max-width: 80%;
|
img {
|
||||||
object-fit: cover;
|
max-width: 80%;
|
||||||
}
|
object-fit: cover;
|
||||||
.status {
|
}
|
||||||
color: #1d2126;
|
.status {
|
||||||
}
|
color: #1d2126;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -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,18 +118,20 @@ class HcLovelace extends LitElement {
|
|||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles(): CSSResultGroup {
|
||||||
hui-view-container {
|
return css`
|
||||||
display: flex;
|
hui-view-container {
|
||||||
position: relative;
|
display: flex;
|
||||||
min-height: 100vh;
|
position: relative;
|
||||||
box-sizing: border-box;
|
min-height: 100vh;
|
||||||
}
|
box-sizing: border-box;
|
||||||
hui-view-container > * {
|
}
|
||||||
flex: 1 1 100%;
|
hui-view {
|
||||||
max-width: 100%;
|
flex: 1 1 100%;
|
||||||
}
|
max-width: 100%;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface CastViewChanged {
|
export interface CastViewChanged {
|
||||||
|
|||||||
@@ -109,7 +109,7 @@ export class HcMain extends HassElement {
|
|||||||
protected firstUpdated(changedProps) {
|
protected firstUpdated(changedProps) {
|
||||||
super.firstUpdated(changedProps);
|
super.firstUpdated(changedProps);
|
||||||
import("./hc-lovelace");
|
import("./hc-lovelace");
|
||||||
import("../../../../src/resources/append-ha-style");
|
import("../../../../src/resources/ha-style");
|
||||||
|
|
||||||
window.addEventListener("location-changed", () => {
|
window.addEventListener("location-changed", () => {
|
||||||
const panelPath = `/${this._urlPath || "lovelace"}/`;
|
const panelPath = `/${this._urlPath || "lovelace"}/`;
|
||||||
@@ -309,7 +309,7 @@ export class HcMain extends HassElement {
|
|||||||
"../../../../src/panels/lovelace/strategies/get-strategy"
|
"../../../../src/panels/lovelace/strategies/get-strategy"
|
||||||
);
|
);
|
||||||
const config = await generateLovelaceDashboardStrategy(
|
const config = await generateLovelaceDashboardStrategy(
|
||||||
rawConfig,
|
rawConfig.strategy,
|
||||||
this.hass!
|
this.hass!
|
||||||
);
|
);
|
||||||
this._handleNewLovelaceConfig(config);
|
this._handleNewLovelaceConfig(config);
|
||||||
@@ -351,7 +351,10 @@ export class HcMain extends HassElement {
|
|||||||
"../../../../src/panels/lovelace/strategies/get-strategy"
|
"../../../../src/panels/lovelace/strategies/get-strategy"
|
||||||
);
|
);
|
||||||
this._handleNewLovelaceConfig(
|
this._handleNewLovelaceConfig(
|
||||||
await generateLovelaceDashboardStrategy(DEFAULT_CONFIG, this.hass!)
|
await generateLovelaceDashboardStrategy(
|
||||||
|
DEFAULT_CONFIG.strategy,
|
||||||
|
this.hass!
|
||||||
|
)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -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,28 +1,37 @@
|
|||||||
export const demoThemeJimpower = () => ({
|
export const demoThemeJimpower = () => ({
|
||||||
"text-primary-color": "var(--primary-text-color)",
|
"text-primary-color": "var(--primary-text-color)",
|
||||||
|
"paper-item-icon-color": "var(--primary-text-color)",
|
||||||
"primary-color": "#5294E2",
|
"primary-color": "#5294E2",
|
||||||
"label-badge-red": "var(--accent-color)",
|
"label-badge-red": "var(--accent-color)",
|
||||||
|
"paper-tabs-selection-bar-color": "green",
|
||||||
"light-primary-color": "var(--accent-color)",
|
"light-primary-color": "var(--accent-color)",
|
||||||
"primary-background-color": "#383C45",
|
"primary-background-color": "#383C45",
|
||||||
"primary-text-color": "#FFFFFF",
|
"primary-text-color": "#FFFFFF",
|
||||||
|
"paper-item-selected_-_background-color": "#434954",
|
||||||
"secondary-background-color": "#383C45",
|
"secondary-background-color": "#383C45",
|
||||||
"disabled-text-color": "#7F848E",
|
"disabled-text-color": "#7F848E",
|
||||||
|
"paper-item-icon_-_color": "green",
|
||||||
"paper-grey-200": "#414A59",
|
"paper-grey-200": "#414A59",
|
||||||
"label-badge-background-color": "#2E333A",
|
"label-badge-background-color": "#2E333A",
|
||||||
"sidebar-icon-color": "var(--state-icon-color)",
|
"paper-card-header-color": "var(--accent-color)",
|
||||||
|
"sidebar-icon-color": "var(--paper-item-icon-color)",
|
||||||
|
"paper-listbox-background-color": "#2E333A",
|
||||||
"table-row-background-color": "#353840",
|
"table-row-background-color": "#353840",
|
||||||
"paper-grey-50": "var(--primary-text-color)",
|
"paper-grey-50": "var(--primary-text-color)",
|
||||||
"switch-checked-color": "var(--accent-color)",
|
"switch-checked-color": "var(--accent-color)",
|
||||||
|
"paper-dialog-background-color": "#434954",
|
||||||
"secondary-text-color": "#5294E2",
|
"secondary-text-color": "#5294E2",
|
||||||
"error-color": "#E45E65",
|
"error-color": "#E45E65",
|
||||||
"divider-color": "rgba(0, 0, 0, .12)",
|
"divider-color": "rgba(0, 0, 0, .12)",
|
||||||
"success-color": "#39E949",
|
"success-color": "#39E949",
|
||||||
"switch-unchecked-button-color": "var(--disabled-text-color)",
|
"switch-unchecked-button-color": "var(--disabled-text-color)",
|
||||||
"label-badge-border-color": "green",
|
"label-badge-border-color": "green",
|
||||||
|
"paper-listbox-color": "var(--primary-color)",
|
||||||
"card-background-color": "#434954",
|
"card-background-color": "#434954",
|
||||||
"label-badge-text-color": "var(--primary-text-color)",
|
"label-badge-text-color": "var(--primary-text-color)",
|
||||||
"switch-unchecked-track-color": "var(--disabled-text-color)",
|
"switch-unchecked-track-color": "var(--disabled-text-color)",
|
||||||
"dark-primary-color": "var(--accent-color)",
|
"dark-primary-color": "var(--accent-color)",
|
||||||
|
"paper-item-icon-active-color": "#F9C536",
|
||||||
"accent-color": "#E45E65",
|
"accent-color": "#E45E65",
|
||||||
"table-row-alternative-background-color": "#3E424B",
|
"table-row-alternative-background-color": "#3E424B",
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,29 +1,38 @@
|
|||||||
// https://community.home-assistant.io/t/slate-a-new-dark-theme/86410
|
// https://community.home-assistant.io/t/slate-a-new-dark-theme/86410
|
||||||
export const demoThemeKernehed = () => ({
|
export const demoThemeKernehed = () => ({
|
||||||
"text-primary-color": "var(--primary-text-color)",
|
"text-primary-color": "var(--primary-text-color)",
|
||||||
|
"paper-item-icon-color": "var(--primary-text-color)",
|
||||||
"primary-color": "#2980b9",
|
"primary-color": "#2980b9",
|
||||||
"label-badge-red": "var(--accent-color)",
|
"label-badge-red": "var(--accent-color)",
|
||||||
|
"paper-tabs-selection-bar-color": "green",
|
||||||
"primary-text-color": "#FFFFFF",
|
"primary-text-color": "#FFFFFF",
|
||||||
"light-primary-color": "var(--accent-color)",
|
"light-primary-color": "var(--accent-color)",
|
||||||
"primary-background-color": "#222222",
|
"primary-background-color": "#222222",
|
||||||
"sidebar-icon-color": "#777777",
|
"sidebar-icon-color": "#777777",
|
||||||
|
"paper-item-selected_-_background-color": "#292929",
|
||||||
"secondary-background-color": "#222222",
|
"secondary-background-color": "#222222",
|
||||||
"disabled-text-color": "#777777",
|
"disabled-text-color": "#777777",
|
||||||
|
"paper-item-icon_-_color": "green",
|
||||||
"paper-grey-200": "#222222",
|
"paper-grey-200": "#222222",
|
||||||
"label-badge-background-color": "#222222",
|
"label-badge-background-color": "#222222",
|
||||||
|
"paper-card-header-color": "var(--accent-color)",
|
||||||
|
"paper-listbox-background-color": "#141414",
|
||||||
"table-row-background-color": "#292929",
|
"table-row-background-color": "#292929",
|
||||||
"paper-grey-50": "var(--primary-text-color)",
|
"paper-grey-50": "var(--primary-text-color)",
|
||||||
"switch-checked-color": "var(--accent-color)",
|
"switch-checked-color": "var(--accent-color)",
|
||||||
|
"paper-dialog-background-color": "#292929",
|
||||||
"secondary-text-color": "#b58e31",
|
"secondary-text-color": "#b58e31",
|
||||||
"error-color": "#b58e31",
|
"error-color": "#b58e31",
|
||||||
"divider-color": "rgba(0, 0, 0, .12)",
|
"divider-color": "rgba(0, 0, 0, .12)",
|
||||||
"success-color": "#2980b9",
|
"success-color": "#2980b9",
|
||||||
"switch-unchecked-button-color": "var(--disabled-text-color)",
|
"switch-unchecked-button-color": "var(--disabled-text-color)",
|
||||||
"label-badge-border-color": "green",
|
"label-badge-border-color": "green",
|
||||||
|
"paper-listbox-color": "#777777",
|
||||||
"card-background-color": "#292929",
|
"card-background-color": "#292929",
|
||||||
"label-badge-text-color": "var(--primary-text-color)",
|
"label-badge-text-color": "var(--primary-text-color)",
|
||||||
"switch-unchecked-track-color": "var(--disabled-text-color)",
|
"switch-unchecked-track-color": "var(--disabled-text-color)",
|
||||||
"dark-primary-color": "var(--accent-color)",
|
"dark-primary-color": "var(--accent-color)",
|
||||||
|
"paper-item-icon-active-color": "#b58e31",
|
||||||
"accent-color": "#2980b9",
|
"accent-color": "#2980b9",
|
||||||
"table-row-alternative-background-color": "#292929",
|
"table-row-alternative-background-color": "#292929",
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,18 +1,26 @@
|
|||||||
export const demoThemeTeachingbirds = () => ({
|
export const demoThemeTeachingbirds = () => ({
|
||||||
|
"paper-card-header-color": "var(--paper-item-icon-color)",
|
||||||
|
"paper-listbox-background-color": "#202020",
|
||||||
"paper-grey-50": "var(--primary-text-color)",
|
"paper-grey-50": "var(--primary-text-color)",
|
||||||
|
"paper-item-icon-color": "#d3d3d3",
|
||||||
"divider-color": "rgba(255, 255, 255, 0.12)",
|
"divider-color": "rgba(255, 255, 255, 0.12)",
|
||||||
"primary-color": "#389638",
|
"primary-color": "#389638",
|
||||||
"light-primary-color": "#6f956f",
|
"light-primary-color": "#6f956f",
|
||||||
"label-badge-red": "var(--primary-color)",
|
"label-badge-red": "var(--primary-color)",
|
||||||
|
"paper-listbox-color": "#FFFFFF",
|
||||||
|
"paper-toggle-button-checked-bar-color": "var(--light-primary-color)",
|
||||||
"switch-unchecked-track-color": "var(--primary-text-color)",
|
"switch-unchecked-track-color": "var(--primary-text-color)",
|
||||||
"card-background-color": "#4e4e4e",
|
"card-background-color": "#4e4e4e",
|
||||||
"label-badge-text-color": "var(--text-primary-color)",
|
"label-badge-text-color": "var(--text-primary-color)",
|
||||||
"primary-background-color": "#303030",
|
"primary-background-color": "#303030",
|
||||||
"sidebar-icon-color": "#d3d3d3",
|
"sidebar-icon-color": "var(--paper-item-icon-color)",
|
||||||
"secondary-background-color": "#2b2b2b",
|
"secondary-background-color": "#2b2b2b",
|
||||||
|
"paper-item-icon-active-color": "#d8bf50",
|
||||||
"switch-checked-color": "var(--primary-color)",
|
"switch-checked-color": "var(--primary-color)",
|
||||||
"secondary-text-color": "#389638",
|
"secondary-text-color": "#389638",
|
||||||
"disabled-text-color": "#545454",
|
"disabled-text-color": "#545454",
|
||||||
|
"paper-item-icon_-_color": "var(--primary-text-color)",
|
||||||
"paper-grey-200": "#191919",
|
"paper-grey-200": "#191919",
|
||||||
|
"primary-text-color": "#cfcfcf",
|
||||||
"label-badge-background-color": "var(--secondary-background-color)",
|
"label-badge-background-color": "var(--secondary-background-color)",
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -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,35 +67,37 @@ 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 {
|
||||||
:host {
|
return css`
|
||||||
display: flex;
|
:host {
|
||||||
align-items: center;
|
display: flex;
|
||||||
}
|
align-items: center;
|
||||||
ha-svg-icon {
|
}
|
||||||
padding: 8px;
|
ha-svg-icon {
|
||||||
color: var(--state-icon-color);
|
padding: 8px;
|
||||||
}
|
color: var(--paper-item-icon-color);
|
||||||
.flex {
|
}
|
||||||
flex: 1;
|
.flex {
|
||||||
overflow: hidden;
|
flex: 1;
|
||||||
margin-left: 16px;
|
overflow: hidden;
|
||||||
display: flex;
|
margin-left: 16px;
|
||||||
justify-content: space-between;
|
display: flex;
|
||||||
align-items: center;
|
justify-content: space-between;
|
||||||
}
|
align-items: center;
|
||||||
.name {
|
}
|
||||||
white-space: nowrap;
|
.name {
|
||||||
overflow: hidden;
|
white-space: nowrap;
|
||||||
text-overflow: ellipsis;
|
overflow: hidden;
|
||||||
}
|
text-overflow: ellipsis;
|
||||||
google-cast-launcher {
|
}
|
||||||
cursor: pointer;
|
google-cast-launcher {
|
||||||
display: inline-block;
|
cursor: pointer;
|
||||||
height: 24px;
|
display: inline-block;
|
||||||
width: 24px;
|
height: 24px;
|
||||||
}
|
width: 24px;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import { until } from "lit/directives/until";
|
|||||||
import { fireEvent } from "../../../src/common/dom/fire_event";
|
import { fireEvent } from "../../../src/common/dom/fire_event";
|
||||||
import "../../../src/components/ha-card";
|
import "../../../src/components/ha-card";
|
||||||
import "../../../src/components/ha-button";
|
import "../../../src/components/ha-button";
|
||||||
import "../../../src/components/ha-spinner";
|
import "../../../src/components/ha-circular-progress";
|
||||||
import type { LovelaceCardConfig } from "../../../src/data/lovelace/config/card";
|
import type { LovelaceCardConfig } from "../../../src/data/lovelace/config/card";
|
||||||
import type { MockHomeAssistant } from "../../../src/fake_data/provide_hass";
|
import type { MockHomeAssistant } from "../../../src/fake_data/provide_hass";
|
||||||
import type {
|
import type {
|
||||||
@@ -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() {
|
||||||
@@ -44,7 +43,9 @@ export class HADemoCard extends LitElement implements LovelaceCard {
|
|||||||
<div class="picker">
|
<div class="picker">
|
||||||
<div class="label">
|
<div class="label">
|
||||||
${this._switching
|
${this._switching
|
||||||
? html`<ha-spinner></ha-spinner>`
|
? html`
|
||||||
|
<ha-circular-progress indeterminate></ha-circular-progress>
|
||||||
|
`
|
||||||
: until(
|
: until(
|
||||||
selectedDemoConfig.then(
|
selectedDemoConfig.then(
|
||||||
(conf) => html`
|
(conf) => html`
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import "./util/is_frontpage";
|
import "./util/is_frontpage";
|
||||||
import "./ha-demo";
|
import "./ha-demo";
|
||||||
|
|
||||||
import("../../src/resources/append-ha-style");
|
import("../../src/resources/ha-style");
|
||||||
|
|||||||
@@ -1,3 +1,5 @@
|
|||||||
|
// Compat needs to be first import
|
||||||
|
import "../../src/resources/compatibility";
|
||||||
import { customElement } from "lit/decorators";
|
import { customElement } from "lit/decorators";
|
||||||
import { isNavigationClick } from "../../src/common/dom/is-navigation-click";
|
import { isNavigationClick } from "../../src/common/dom/is-navigation-click";
|
||||||
import { navigate } from "../../src/common/navigate";
|
import { navigate } from "../../src/common/navigate";
|
||||||
@@ -63,7 +65,6 @@ export class HaDemo extends HomeAssistantAppEl {
|
|||||||
mockEntityRegistry(hass, [
|
mockEntityRegistry(hass, [
|
||||||
{
|
{
|
||||||
config_entry_id: "co2signal",
|
config_entry_id: "co2signal",
|
||||||
config_subentry_id: null,
|
|
||||||
device_id: "co2signal",
|
device_id: "co2signal",
|
||||||
area_id: null,
|
area_id: null,
|
||||||
disabled_by: null,
|
disabled_by: null,
|
||||||
@@ -84,7 +85,6 @@ export class HaDemo extends HomeAssistantAppEl {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
config_entry_id: "co2signal",
|
config_entry_id: "co2signal",
|
||||||
config_subentry_id: null,
|
|
||||||
device_id: "co2signal",
|
device_id: "co2signal",
|
||||||
area_id: null,
|
area_id: null,
|
||||||
disabled_by: null,
|
disabled_by: null,
|
||||||
|
|||||||
@@ -1,10 +1,9 @@
|
|||||||
import type { validateConfig } from "../../../src/data/config";
|
|
||||||
import type { MockHomeAssistant } from "../../../src/fake_data/provide_hass";
|
import type { MockHomeAssistant } from "../../../src/fake_data/provide_hass";
|
||||||
|
|
||||||
export const mockConfig = (hass: MockHomeAssistant) => {
|
export const mockConfig = (hass: MockHomeAssistant) => {
|
||||||
hass.mockWS<typeof validateConfig>("validate_config", () => ({
|
hass.mockWS("validate_config", () => ({
|
||||||
actions: { valid: true, error: null },
|
actions: { valid: true },
|
||||||
conditions: { valid: true, error: null },
|
conditions: { valid: true },
|
||||||
triggers: { valid: true, error: null },
|
triggers: { valid: true },
|
||||||
}));
|
}));
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,26 +1,19 @@
|
|||||||
import type { getConfigEntries } from "../../../src/data/config_entries";
|
|
||||||
import type { MockHomeAssistant } from "../../../src/fake_data/provide_hass";
|
import type { MockHomeAssistant } from "../../../src/fake_data/provide_hass";
|
||||||
|
|
||||||
export const mockConfigEntries = (hass: MockHomeAssistant) => {
|
export const mockConfigEntries = (hass: MockHomeAssistant) => {
|
||||||
hass.mockWS<typeof getConfigEntries>("config_entries/get", () => [
|
hass.mockWS("config_entries/get", () => ({
|
||||||
{
|
entry_id: "co2signal",
|
||||||
entry_id: "mock-entry-co2signal",
|
domain: "co2signal",
|
||||||
domain: "co2signal",
|
title: "Electricity Maps",
|
||||||
title: "Electricity Maps",
|
source: "user",
|
||||||
source: "user",
|
state: "loaded",
|
||||||
state: "loaded",
|
supports_options: false,
|
||||||
supports_options: false,
|
supports_remove_device: false,
|
||||||
supports_remove_device: false,
|
supports_unload: true,
|
||||||
supports_unload: true,
|
supports_reconfigure: true,
|
||||||
supports_reconfigure: true,
|
pref_disable_new_entities: false,
|
||||||
supported_subentry_types: {},
|
pref_disable_polling: false,
|
||||||
pref_disable_new_entities: false,
|
disabled_by: null,
|
||||||
pref_disable_polling: false,
|
reason: null,
|
||||||
disabled_by: null,
|
}));
|
||||||
reason: null,
|
|
||||||
num_subentries: 0,
|
|
||||||
error_reason_translation_key: null,
|
|
||||||
error_reason_translation_placeholders: null,
|
|
||||||
},
|
|
||||||
]);
|
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -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 () => {};
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -2,36 +2,25 @@ import type { TodoItem } from "../../../src/data/todo";
|
|||||||
import { TodoItemStatus } from "../../../src/data/todo";
|
import { TodoItemStatus } from "../../../src/data/todo";
|
||||||
import type { MockHomeAssistant } from "../../../src/fake_data/provide_hass";
|
import type { MockHomeAssistant } from "../../../src/fake_data/provide_hass";
|
||||||
|
|
||||||
const items = {
|
|
||||||
items: [
|
|
||||||
{
|
|
||||||
uid: "12",
|
|
||||||
summary: "Milk",
|
|
||||||
status: TodoItemStatus.NeedsAction,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
uid: "13",
|
|
||||||
summary: "Eggs",
|
|
||||||
status: TodoItemStatus.NeedsAction,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
uid: "14",
|
|
||||||
summary: "Oranges",
|
|
||||||
status: TodoItemStatus.Completed,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
uid: "15",
|
|
||||||
summary: "Beer",
|
|
||||||
},
|
|
||||||
] as TodoItem[],
|
|
||||||
};
|
|
||||||
|
|
||||||
export const mockTodo = (hass: MockHomeAssistant) => {
|
export const mockTodo = (hass: MockHomeAssistant) => {
|
||||||
hass.mockWS("todo/item/list", () => items);
|
hass.mockWS("todo/item/list", () => ({
|
||||||
hass.mockWS("todo/item/move", () => undefined);
|
items: [
|
||||||
hass.mockWS("todo/item/subscribe", (_msg, _hass, onChange) => {
|
{
|
||||||
onChange!(items);
|
uid: "12",
|
||||||
// eslint-disable-next-line @typescript-eslint/no-empty-function
|
summary: "Milk",
|
||||||
return () => {};
|
status: TodoItemStatus.NeedsAction,
|
||||||
});
|
},
|
||||||
|
{
|
||||||
|
uid: "13",
|
||||||
|
summary: "Eggs",
|
||||||
|
status: TodoItemStatus.NeedsAction,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
uid: "14",
|
||||||
|
summary: "Oranges",
|
||||||
|
status: TodoItemStatus.Completed,
|
||||||
|
},
|
||||||
|
] as TodoItem[],
|
||||||
|
}));
|
||||||
|
hass.mockWS("todo/item/subscribe", (_msg, _hass) => () => {});
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,16 +1,11 @@
|
|||||||
// @ts-check
|
|
||||||
|
|
||||||
/* eslint-disable import/no-extraneous-dependencies */
|
/* eslint-disable import/no-extraneous-dependencies */
|
||||||
import unusedImports from "eslint-plugin-unused-imports";
|
import unusedImports from "eslint-plugin-unused-imports";
|
||||||
import globals from "globals";
|
import globals from "globals";
|
||||||
|
import tsParser from "@typescript-eslint/parser";
|
||||||
import path from "node:path";
|
import path from "node:path";
|
||||||
import { fileURLToPath } from "node:url";
|
import { fileURLToPath } from "node:url";
|
||||||
import js from "@eslint/js";
|
import js from "@eslint/js";
|
||||||
import { FlatCompat } from "@eslint/eslintrc";
|
import { FlatCompat } from "@eslint/eslintrc";
|
||||||
import tseslint from "typescript-eslint";
|
|
||||||
import eslintConfigPrettier from "eslint-config-prettier";
|
|
||||||
import { configs as litConfigs } from "eslint-plugin-lit";
|
|
||||||
import { configs as wcConfigs } from "eslint-plugin-wc";
|
|
||||||
|
|
||||||
const _filename = fileURLToPath(import.meta.url);
|
const _filename = fileURLToPath(import.meta.url);
|
||||||
const _dirname = path.dirname(_filename);
|
const _dirname = path.dirname(_filename);
|
||||||
@@ -20,14 +15,16 @@ const compat = new FlatCompat({
|
|||||||
allConfig: js.configs.all,
|
allConfig: js.configs.all,
|
||||||
});
|
});
|
||||||
|
|
||||||
export default tseslint.config(
|
export default [
|
||||||
...compat.extends("airbnb-base", "plugin:lit-a11y/recommended"),
|
...compat.extends(
|
||||||
eslintConfigPrettier,
|
"airbnb-base",
|
||||||
litConfigs["flat/all"],
|
"airbnb-typescript/base",
|
||||||
tseslint.configs.recommended,
|
"plugin:@typescript-eslint/recommended",
|
||||||
tseslint.configs.strict,
|
"plugin:wc/recommended",
|
||||||
tseslint.configs.stylistic,
|
"plugin:lit/all",
|
||||||
wcConfigs["flat/recommended"],
|
"plugin:lit-a11y/recommended",
|
||||||
|
"prettier"
|
||||||
|
),
|
||||||
{
|
{
|
||||||
plugins: {
|
plugins: {
|
||||||
"unused-imports": unusedImports,
|
"unused-imports": unusedImports,
|
||||||
@@ -42,9 +39,10 @@ export default tseslint.config(
|
|||||||
__VERSION__: false,
|
__VERSION__: false,
|
||||||
__STATIC_PATH__: false,
|
__STATIC_PATH__: false,
|
||||||
__SUPERVISOR__: false,
|
__SUPERVISOR__: false,
|
||||||
|
Polymer: true,
|
||||||
},
|
},
|
||||||
|
|
||||||
parser: tseslint.parser,
|
parser: tsParser,
|
||||||
ecmaVersion: 2020,
|
ecmaVersion: 2020,
|
||||||
sourceType: "module",
|
sourceType: "module",
|
||||||
|
|
||||||
@@ -52,6 +50,8 @@ export default tseslint.config(
|
|||||||
ecmaFeatures: {
|
ecmaFeatures: {
|
||||||
modules: true,
|
modules: true,
|
||||||
},
|
},
|
||||||
|
|
||||||
|
project: "./tsconfig.json",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|
||||||
@@ -148,15 +148,15 @@ export default tseslint.config(
|
|||||||
},
|
},
|
||||||
],
|
],
|
||||||
|
|
||||||
"@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,
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
@@ -174,16 +174,6 @@ export default tseslint.config(
|
|||||||
"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",
|
|
||||||
},
|
},
|
||||||
}
|
},
|
||||||
);
|
];
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
// @ts-check
|
|
||||||
|
|
||||||
import tseslint from "typescript-eslint";
|
|
||||||
import rootConfig from "../eslint.config.mjs";
|
import rootConfig from "../eslint.config.mjs";
|
||||||
|
|
||||||
export default tseslint.config(...rootConfig, {
|
export default [
|
||||||
rules: {
|
...rootConfig,
|
||||||
"no-console": "off",
|
{
|
||||||
|
rules: {
|
||||||
|
"no-console": "off",
|
||||||
|
},
|
||||||
},
|
},
|
||||||
});
|
];
|
||||||
|
|||||||
@@ -1,10 +0,0 @@
|
|||||||
<svg width="94" height="64" viewBox="0 0 94 64" fill="none" xmlns="http://www.w3.org/2000/svg">
|
|
||||||
<rect width="94" height="64" rx="8" fill="white"/>
|
|
||||||
<rect x="0.5" y="0.5" width="93" height="63" rx="7.5" stroke="black" stroke-opacity="0.12"/>
|
|
||||||
<path d="M8 14C8 10.6863 10.6863 8 14 8H33C36.3137 8 39 10.6863 39 14C39 17.3137 36.3137 20 33 20H14C10.6863 20 8 17.3137 8 14Z" fill="black" fill-opacity="0.32"/>
|
|
||||||
<path d="M8 27C8 25.3431 9.34315 24 11 24H31C32.6569 24 34 25.3431 34 27V29C34 30.6569 32.6569 32 31 32H11C9.34315 32 8 30.6569 8 29V27Z" fill="black" fill-opacity="0.12"/>
|
|
||||||
<path d="M38 27C38 25.3431 39.3431 24 41 24H83C84.6569 24 86 25.3431 86 27V29C86 30.6569 84.6569 32 83 32H41C39.3431 32 38 30.6569 38 29V27Z" fill="black" fill-opacity="0.12"/>
|
|
||||||
<path d="M8 39C8 37.3431 9.34315 36 11 36H53C54.6569 36 56 37.3431 56 39V41C56 42.6569 54.6569 44 53 44H11C9.34315 44 8 42.6569 8 41V39Z" fill="black" fill-opacity="0.12"/>
|
|
||||||
<path d="M60 39C60 37.3431 61.3431 36 63 36H83C84.6569 36 86 37.3431 86 39V41C86 42.6569 84.6569 44 83 44H63C61.3431 44 60 42.6569 60 41V39Z" fill="black" fill-opacity="0.12"/>
|
|
||||||
<path d="M8 51C8 49.3431 9.34315 48 11 48H31C32.6569 48 34 49.3431 34 51V53C34 54.6569 32.6569 56 31 56H11C9.34315 56 8 54.6569 8 53V51Z" fill="black" fill-opacity="0.12"/>
|
|
||||||
</svg>
|
|
||||||
|
Before Width: | Height: | Size: 1.3 KiB |
@@ -1,7 +0,0 @@
|
|||||||
<svg width="94" height="48" viewBox="0 0 94 48" fill="none" xmlns="http://www.w3.org/2000/svg">
|
|
||||||
<path d="M0 11C0 9.34315 1.34315 8 3 8H23C24.6569 8 26 9.34315 26 11V13C26 14.6569 24.6569 16 23 16H3C1.34315 16 0 14.6569 0 13V11Z" fill="black" fill-opacity="0.12"/>
|
|
||||||
<path d="M30 11C30 9.34315 31.3431 8 33 8H91C92.6569 8 94 9.34315 94 11V13C94 14.6569 92.6569 16 91 16H33C31.3431 16 30 14.6569 30 13V11Z" fill="black" fill-opacity="0.12"/>
|
|
||||||
<path d="M0 23C0 21.3431 1.34315 20 3 20H61C62.6569 20 64 21.3431 64 23V25C64 26.6569 62.6569 28 61 28H3C1.34315 28 0 26.6569 0 25V23Z" fill="black" fill-opacity="0.12"/>
|
|
||||||
<path d="M68 23C68 21.3431 69.3431 20 71 20H91C92.6569 20 94 21.3431 94 23V25C94 26.6569 92.6569 28 91 28H71C69.3431 28 68 26.6569 68 25V23Z" fill="black" fill-opacity="0.12"/>
|
|
||||||
<path d="M0 35C0 33.3431 1.34315 32 3 32H23C24.6569 32 26 33.3431 26 35V37C26 38.6569 24.6569 40 23 40H3C1.34315 40 0 38.6569 0 37V35Z" fill="black" fill-opacity="0.12"/>
|
|
||||||
</svg>
|
|
||||||
|
Before Width: | Height: | Size: 964 B |
@@ -1,5 +1,5 @@
|
|||||||
import "./ha-gallery";
|
import "./ha-gallery";
|
||||||
|
|
||||||
import("../../src/resources/append-ha-style");
|
import("../../src/resources/ha-style");
|
||||||
|
|
||||||
document.body.appendChild(document.createElement("ha-gallery"));
|
document.body.appendChild(document.createElement("ha-gallery"));
|
||||||
|
|||||||
@@ -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,24 +177,26 @@ 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() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
.action {
|
}
|
||||||
padding: 16px;
|
.action {
|
||||||
display: flex;
|
padding: 16px;
|
||||||
align-items: center;
|
display: flex;
|
||||||
justify-content: space-between;
|
align-items: center;
|
||||||
}
|
justify-content: space-between;
|
||||||
span {
|
}
|
||||||
margin-right: 16px;
|
span {
|
||||||
}
|
margin-right: 16px;
|
||||||
ha-yaml-editor {
|
}
|
||||||
width: 50%;
|
ha-yaml-editor {
|
||||||
}
|
width: 50%;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -98,24 +98,26 @@ 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() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
.condition {
|
}
|
||||||
padding: 16px;
|
.condition {
|
||||||
display: flex;
|
padding: 16px;
|
||||||
align-items: center;
|
display: flex;
|
||||||
justify-content: space-between;
|
align-items: center;
|
||||||
}
|
justify-content: space-between;
|
||||||
span {
|
}
|
||||||
margin-right: 16px;
|
span {
|
||||||
}
|
margin-right: 16px;
|
||||||
ha-yaml-editor {
|
}
|
||||||
width: 50%;
|
ha-yaml-editor {
|
||||||
}
|
width: 50%;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -121,24 +121,26 @@ 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() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
.trigger {
|
}
|
||||||
padding: 16px;
|
.trigger {
|
||||||
display: flex;
|
padding: 16px;
|
||||||
align-items: center;
|
display: flex;
|
||||||
justify-content: space-between;
|
align-items: center;
|
||||||
}
|
justify-content: space-between;
|
||||||
span {
|
}
|
||||||
margin-right: 16px;
|
span {
|
||||||
}
|
margin-right: 16px;
|
||||||
ha-yaml-editor {
|
}
|
||||||
width: 50%;
|
ha-yaml-editor {
|
||||||
}
|
width: 50%;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -1,30 +1,29 @@
|
|||||||
import type { TemplateResult } from "lit";
|
import type { TemplateResult } from "lit";
|
||||||
import { LitElement, css, html } from "lit";
|
import { LitElement, html, css } from "lit";
|
||||||
import { customElement, state } from "lit/decorators";
|
import { customElement, state } from "lit/decorators";
|
||||||
import "../../../../src/components/ha-formfield";
|
|
||||||
import { provideHass } from "../../../../src/fake_data/provide_hass";
|
import { provideHass } from "../../../../src/fake_data/provide_hass";
|
||||||
import type { HomeAssistant } from "../../../../src/types";
|
import type { HomeAssistant } from "../../../../src/types";
|
||||||
import "../../components/demo-black-white-row";
|
import "../../components/demo-black-white-row";
|
||||||
import { mockAreaRegistry } from "../../../../demo/src/stubs/area_registry";
|
|
||||||
import { mockDeviceRegistry } from "../../../../demo/src/stubs/device_registry";
|
|
||||||
import { mockEntityRegistry } from "../../../../demo/src/stubs/entity_registry";
|
import { mockEntityRegistry } from "../../../../demo/src/stubs/entity_registry";
|
||||||
|
import { mockDeviceRegistry } from "../../../../demo/src/stubs/device_registry";
|
||||||
|
import { mockAreaRegistry } from "../../../../demo/src/stubs/area_registry";
|
||||||
import { mockHassioSupervisor } from "../../../../demo/src/stubs/hassio_supervisor";
|
import { mockHassioSupervisor } from "../../../../demo/src/stubs/hassio_supervisor";
|
||||||
import type { Action } from "../../../../src/data/script";
|
|
||||||
import "../../../../src/panels/config/automation/action/ha-automation-action";
|
import "../../../../src/panels/config/automation/action/ha-automation-action";
|
||||||
import { HaChooseAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-choose";
|
import { HaChooseAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-choose";
|
||||||
import { HaConditionAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-condition";
|
|
||||||
import { HaDelayAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-delay";
|
import { HaDelayAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-delay";
|
||||||
import { HaDeviceAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-device_id";
|
import { HaDeviceAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-device_id";
|
||||||
import { HaEventAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-event";
|
import { HaEventAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-event";
|
||||||
import { HaIfAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-if";
|
|
||||||
import { HaParallelAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-parallel";
|
|
||||||
import { HaPlayMediaAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-play_media";
|
|
||||||
import { HaRepeatAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-repeat";
|
import { HaRepeatAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-repeat";
|
||||||
import { HaSequenceAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-sequence";
|
|
||||||
import { HaServiceAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-service";
|
import { HaServiceAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-service";
|
||||||
import { HaStopAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-stop";
|
|
||||||
import { HaWaitForTriggerAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-wait_for_trigger";
|
import { HaWaitForTriggerAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-wait_for_trigger";
|
||||||
import { HaWaitAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-wait_template";
|
import { HaWaitAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-wait_template";
|
||||||
|
import type { Action } from "../../../../src/data/script";
|
||||||
|
import { HaConditionAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-condition";
|
||||||
|
import { HaSequenceAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-sequence";
|
||||||
|
import { HaParallelAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-parallel";
|
||||||
|
import { HaIfAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-if";
|
||||||
|
import { HaStopAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-stop";
|
||||||
|
import { HaPlayMediaAction } from "../../../../src/panels/config/automation/action/types/ha-automation-action-play_media";
|
||||||
|
|
||||||
const SCHEMAS: { name: string; actions: Action[] }[] = [
|
const SCHEMAS: { name: string; actions: Action[] }[] = [
|
||||||
{ name: "Event", actions: [HaEventAction.defaultConfig] },
|
{ name: "Event", actions: [HaEventAction.defaultConfig] },
|
||||||
|
|||||||
@@ -1,27 +1,26 @@
|
|||||||
import type { TemplateResult } from "lit";
|
import type { TemplateResult } from "lit";
|
||||||
import { LitElement, css, html } from "lit";
|
import { LitElement, html, css } from "lit";
|
||||||
import { customElement, state } from "lit/decorators";
|
import { customElement, state } from "lit/decorators";
|
||||||
import { mockAreaRegistry } from "../../../../demo/src/stubs/area_registry";
|
|
||||||
import { mockDeviceRegistry } from "../../../../demo/src/stubs/device_registry";
|
|
||||||
import { mockEntityRegistry } from "../../../../demo/src/stubs/entity_registry";
|
|
||||||
import { mockHassioSupervisor } from "../../../../demo/src/stubs/hassio_supervisor";
|
|
||||||
import "../../../../src/components/ha-formfield";
|
|
||||||
import type { ConditionWithShorthand } from "../../../../src/data/automation";
|
|
||||||
import { provideHass } from "../../../../src/fake_data/provide_hass";
|
import { provideHass } from "../../../../src/fake_data/provide_hass";
|
||||||
|
import type { HomeAssistant } from "../../../../src/types";
|
||||||
|
import "../../components/demo-black-white-row";
|
||||||
|
import { mockEntityRegistry } from "../../../../demo/src/stubs/entity_registry";
|
||||||
|
import { mockDeviceRegistry } from "../../../../demo/src/stubs/device_registry";
|
||||||
|
import { mockAreaRegistry } from "../../../../demo/src/stubs/area_registry";
|
||||||
|
import { mockHassioSupervisor } from "../../../../demo/src/stubs/hassio_supervisor";
|
||||||
|
import type { ConditionWithShorthand } from "../../../../src/data/automation";
|
||||||
import "../../../../src/panels/config/automation/condition/ha-automation-condition";
|
import "../../../../src/panels/config/automation/condition/ha-automation-condition";
|
||||||
import { HaAndCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-and";
|
|
||||||
import { HaDeviceCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-device";
|
import { HaDeviceCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-device";
|
||||||
import { HaNotCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-not";
|
|
||||||
import HaNumericStateCondition from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-numeric_state";
|
import HaNumericStateCondition from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-numeric_state";
|
||||||
import { HaOrCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-or";
|
|
||||||
import { HaStateCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-state";
|
import { HaStateCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-state";
|
||||||
import { HaSunCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-sun";
|
import { HaSunCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-sun";
|
||||||
import { HaTemplateCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-template";
|
import { HaTemplateCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-template";
|
||||||
import { HaTimeCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-time";
|
import { HaTimeCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-time";
|
||||||
import { HaTriggerCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-trigger";
|
import { HaTriggerCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-trigger";
|
||||||
import { HaZoneCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-zone";
|
import { HaZoneCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-zone";
|
||||||
import type { HomeAssistant } from "../../../../src/types";
|
import { HaAndCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-and";
|
||||||
import "../../components/demo-black-white-row";
|
import { HaOrCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-or";
|
||||||
|
import { HaNotCondition } from "../../../../src/panels/config/automation/condition/types/ha-automation-condition-not";
|
||||||
|
|
||||||
const SCHEMAS: { name: string; conditions: ConditionWithShorthand[] }[] = [
|
const SCHEMAS: { name: string; conditions: ConditionWithShorthand[] }[] = [
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -1,36 +1,35 @@
|
|||||||
import type { TemplateResult } from "lit";
|
import type { TemplateResult } from "lit";
|
||||||
import { LitElement, css, html } from "lit";
|
import { LitElement, html, css } from "lit";
|
||||||
import { customElement, state } from "lit/decorators";
|
import { customElement, state } from "lit/decorators";
|
||||||
import { mockAreaRegistry } from "../../../../demo/src/stubs/area_registry";
|
|
||||||
import { mockAuth } from "../../../../demo/src/stubs/auth";
|
|
||||||
import { mockConfig } from "../../../../demo/src/stubs/config";
|
|
||||||
import { mockDeviceRegistry } from "../../../../demo/src/stubs/device_registry";
|
|
||||||
import { mockEntityRegistry } from "../../../../demo/src/stubs/entity_registry";
|
|
||||||
import { mockHassioSupervisor } from "../../../../demo/src/stubs/hassio_supervisor";
|
|
||||||
import { mockTags } from "../../../../demo/src/stubs/tags";
|
|
||||||
import "../../../../src/components/ha-formfield";
|
|
||||||
import type { Trigger } from "../../../../src/data/automation";
|
|
||||||
import { provideHass } from "../../../../src/fake_data/provide_hass";
|
import { provideHass } from "../../../../src/fake_data/provide_hass";
|
||||||
import "../../../../src/panels/config/automation/trigger/ha-automation-trigger";
|
import type { HomeAssistant } from "../../../../src/types";
|
||||||
import { HaConversationTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-conversation";
|
import "../../components/demo-black-white-row";
|
||||||
import { HaDeviceTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-device";
|
import { mockEntityRegistry } from "../../../../demo/src/stubs/entity_registry";
|
||||||
import { HaEventTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-event";
|
import { mockDeviceRegistry } from "../../../../demo/src/stubs/device_registry";
|
||||||
|
import { mockAreaRegistry } from "../../../../demo/src/stubs/area_registry";
|
||||||
|
import { mockHassioSupervisor } from "../../../../demo/src/stubs/hassio_supervisor";
|
||||||
|
import { mockConfig } from "../../../../demo/src/stubs/config";
|
||||||
|
import { mockTags } from "../../../../demo/src/stubs/tags";
|
||||||
|
import { mockAuth } from "../../../../demo/src/stubs/auth";
|
||||||
|
import type { Trigger } from "../../../../src/data/automation";
|
||||||
import { HaGeolocationTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-geo_location";
|
import { HaGeolocationTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-geo_location";
|
||||||
|
import { HaEventTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-event";
|
||||||
import { HaHassTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-homeassistant";
|
import { HaHassTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-homeassistant";
|
||||||
import { HaTriggerList } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-list";
|
|
||||||
import { HaMQTTTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-mqtt";
|
|
||||||
import { HaNumericStateTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-numeric_state";
|
import { HaNumericStateTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-numeric_state";
|
||||||
import { HaPersistentNotificationTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-persistent_notification";
|
|
||||||
import { HaStateTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-state";
|
|
||||||
import { HaSunTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-sun";
|
import { HaSunTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-sun";
|
||||||
import { HaTagTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-tag";
|
import { HaTagTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-tag";
|
||||||
import { HaTemplateTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-template";
|
import { HaTemplateTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-template";
|
||||||
import { HaTimeTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-time";
|
import { HaTimeTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-time";
|
||||||
import { HaTimePatternTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-time_pattern";
|
import { HaTimePatternTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-time_pattern";
|
||||||
import { HaWebhookTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-webhook";
|
import { HaWebhookTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-webhook";
|
||||||
|
import { HaPersistentNotificationTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-persistent_notification";
|
||||||
import { HaZoneTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-zone";
|
import { HaZoneTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-zone";
|
||||||
import type { HomeAssistant } from "../../../../src/types";
|
import { HaDeviceTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-device";
|
||||||
import "../../components/demo-black-white-row";
|
import { HaStateTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-state";
|
||||||
|
import { HaMQTTTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-mqtt";
|
||||||
|
import "../../../../src/panels/config/automation/trigger/ha-automation-trigger";
|
||||||
|
import { HaConversationTrigger } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-conversation";
|
||||||
|
import { HaTriggerList } from "../../../../src/panels/config/automation/trigger/types/ha-automation-trigger-list";
|
||||||
|
|
||||||
const SCHEMAS: { name: string; triggers: Trigger[] }[] = [
|
const SCHEMAS: { name: string; triggers: Trigger[] }[] = [
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -58,20 +58,22 @@ export class DemoAutomationTraceTimeline extends LitElement {
|
|||||||
hass.updateTranslations("config", "en");
|
hass.updateTranslations("config", "en");
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px;
|
max-width: 600px;
|
||||||
}
|
margin: 24px;
|
||||||
.card-content {
|
}
|
||||||
display: flex;
|
.card-content {
|
||||||
}
|
display: flex;
|
||||||
button {
|
}
|
||||||
position: absolute;
|
button {
|
||||||
top: 0;
|
position: absolute;
|
||||||
right: 0;
|
top: 0;
|
||||||
}
|
right: 0;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -68,26 +68,28 @@ 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() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px;
|
max-width: 600px;
|
||||||
}
|
margin: 24px;
|
||||||
.card-content {
|
}
|
||||||
display: flex;
|
.card-content {
|
||||||
}
|
display: flex;
|
||||||
.card-content > * {
|
}
|
||||||
margin-right: 16px;
|
.card-content > * {
|
||||||
}
|
margin-right: 16px;
|
||||||
.card-content > *:last-child {
|
}
|
||||||
margin-right: 0;
|
.card-content > *:last-child {
|
||||||
}
|
margin-right: 0;
|
||||||
button {
|
}
|
||||||
position: absolute;
|
button {
|
||||||
top: 0;
|
position: absolute;
|
||||||
right: 0;
|
top: 0;
|
||||||
}
|
right: 0;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -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,44 +177,46 @@ export class DemoHaAlert extends LitElement {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
:host {
|
return css`
|
||||||
display: flex;
|
:host {
|
||||||
flex-direction: row;
|
display: flex;
|
||||||
justify-content: space-between;
|
flex-direction: row;
|
||||||
}
|
justify-content: space-between;
|
||||||
.dark,
|
}
|
||||||
.light {
|
.dark,
|
||||||
display: block;
|
.light {
|
||||||
background-color: var(--primary-background-color);
|
display: block;
|
||||||
padding: 0 50px;
|
background-color: var(--primary-background-color);
|
||||||
}
|
padding: 0 50px;
|
||||||
ha-card {
|
}
|
||||||
margin: 24px auto;
|
ha-card {
|
||||||
}
|
margin: 24px auto;
|
||||||
ha-alert {
|
}
|
||||||
display: block;
|
ha-alert {
|
||||||
margin: 24px 0;
|
display: block;
|
||||||
}
|
margin: 24px 0;
|
||||||
.condition {
|
}
|
||||||
padding: 16px;
|
.condition {
|
||||||
display: flex;
|
padding: 16px;
|
||||||
align-items: center;
|
display: flex;
|
||||||
justify-content: space-between;
|
align-items: center;
|
||||||
}
|
justify-content: space-between;
|
||||||
.image {
|
}
|
||||||
display: inline-flex;
|
.image {
|
||||||
height: 100%;
|
display: inline-flex;
|
||||||
align-items: center;
|
height: 100%;
|
||||||
}
|
align-items: center;
|
||||||
img {
|
}
|
||||||
max-height: 24px;
|
img {
|
||||||
width: 24px;
|
max-height: 24px;
|
||||||
}
|
width: 24px;
|
||||||
mwc-button {
|
}
|
||||||
--mdc-theme-primary: var(--primary-text-color);
|
mwc-button {
|
||||||
}
|
--mdc-theme-primary: var(--primary-text-color);
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -1,65 +0,0 @@
|
|||||||
---
|
|
||||||
title: Badge
|
|
||||||
subtitle: Lovelace dashboard badge
|
|
||||||
---
|
|
||||||
|
|
||||||
<style>
|
|
||||||
.wrapper {
|
|
||||||
display: flex;
|
|
||||||
gap: 24px;
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
|
|
||||||
# Badge `<ha-badge>`
|
|
||||||
|
|
||||||
The badge component is a small component that displays a number or status information. It is used in the lovelace dashboard on the top.
|
|
||||||
|
|
||||||
## Implementation
|
|
||||||
|
|
||||||
### Example Usage
|
|
||||||
|
|
||||||
<div class="wrapper">
|
|
||||||
<ha-badge>
|
|
||||||
simple badge
|
|
||||||
</ha-badge>
|
|
||||||
|
|
||||||
<ha-badge label="Info">
|
|
||||||
With a label
|
|
||||||
</ha-badge>
|
|
||||||
|
|
||||||
<ha-badge type="button">
|
|
||||||
Type button
|
|
||||||
</ha-badge>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
```html
|
|
||||||
<ha-badge> simple badge </ha-badge>
|
|
||||||
|
|
||||||
<ha-badge label="Info"> With a label </ha-badge>
|
|
||||||
|
|
||||||
<ha-badge type="button"> Type button </ha-badge>
|
|
||||||
```
|
|
||||||
|
|
||||||
### API
|
|
||||||
|
|
||||||
**Slots**
|
|
||||||
|
|
||||||
- default slot is the content of the badge
|
|
||||||
- no default
|
|
||||||
- `icon` set the icon of the badge
|
|
||||||
- no default
|
|
||||||
|
|
||||||
**Properties/Attributes**
|
|
||||||
|
|
||||||
| Name | Type | Default | Description |
|
|
||||||
| -------- | ----------------------- | ----------- | ------------------------------------------------------------ |
|
|
||||||
| type | `"badge"` or `"button"` | `"badge"` | If it's button it shows a ripple effect |
|
|
||||||
| label | string | `undefined` | Text label for the badge, only visible if `iconOnly = false` |
|
|
||||||
| iconOnly | boolean | `false` | Only show label |
|
|
||||||
|
|
||||||
**CSS Custom Properties**
|
|
||||||
|
|
||||||
- `--ha-badge-size` (default `36px`)
|
|
||||||
- `--ha-badge-border-radius` (default `calc(var(--ha-badge-size, 36px) / 2)`)
|
|
||||||
- `--ha-badge-font-size` (default `var(--ha-font-size-s)`)
|
|
||||||
- `--ha-badge-icon-size` (default `18px`)
|
|
||||||
@@ -1,129 +0,0 @@
|
|||||||
import { mdiButtonCursor, mdiHome } from "@mdi/js";
|
|
||||||
import type { TemplateResult } from "lit";
|
|
||||||
import { css, html, LitElement } from "lit";
|
|
||||||
import { customElement } from "lit/decorators";
|
|
||||||
import { applyThemesOnElement } from "../../../../src/common/dom/apply_themes_on_element";
|
|
||||||
import "../../../../src/components/ha-badge";
|
|
||||||
import "../../../../src/components/ha-card";
|
|
||||||
import "../../../../src/components/ha-svg-icon";
|
|
||||||
import { mdiHomeAssistant } from "../../../../src/resources/home-assistant-logo-svg";
|
|
||||||
|
|
||||||
const badges: {
|
|
||||||
type?: "badge" | "button";
|
|
||||||
label?: string;
|
|
||||||
iconOnly?: boolean;
|
|
||||||
slot?: TemplateResult;
|
|
||||||
iconSlot?: TemplateResult;
|
|
||||||
}[] = [
|
|
||||||
{
|
|
||||||
slot: html`<span>Badge</span>`,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
type: "badge",
|
|
||||||
label: "Badge",
|
|
||||||
iconSlot: html`<ha-svg-icon slot="icon" .path=${mdiHome}></ha-svg-icon>`,
|
|
||||||
slot: html`<span>Badge</span>`,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
type: "button",
|
|
||||||
label: "Button",
|
|
||||||
iconSlot: html`<ha-svg-icon
|
|
||||||
slot="icon"
|
|
||||||
.path=${mdiButtonCursor}
|
|
||||||
></ha-svg-icon>`,
|
|
||||||
slot: html`<span>Button</span>`,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
type: "button",
|
|
||||||
label: "Label only",
|
|
||||||
iconSlot: html`<ha-svg-icon
|
|
||||||
slot="icon"
|
|
||||||
.path=${mdiButtonCursor}
|
|
||||||
></ha-svg-icon>`,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
type: "button",
|
|
||||||
label: "Label",
|
|
||||||
slot: html`<span>Button no label</span>`,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: "Icon only",
|
|
||||||
iconOnly: true,
|
|
||||||
iconSlot: html`<ha-svg-icon
|
|
||||||
slot="icon"
|
|
||||||
.path=${mdiHomeAssistant}
|
|
||||||
></ha-svg-icon>`,
|
|
||||||
},
|
|
||||||
];
|
|
||||||
|
|
||||||
@customElement("demo-components-ha-badge")
|
|
||||||
export class DemoHaBadge extends LitElement {
|
|
||||||
protected render(): TemplateResult {
|
|
||||||
return html`
|
|
||||||
${["light", "dark"].map(
|
|
||||||
(mode) => html`
|
|
||||||
<div class=${mode}>
|
|
||||||
<ha-card header="ha-badge ${mode} demo">
|
|
||||||
<div class="card-content">
|
|
||||||
${badges.map(
|
|
||||||
(badge) => html`
|
|
||||||
<ha-badge
|
|
||||||
.type=${badge.type || undefined}
|
|
||||||
.label=${badge.label}
|
|
||||||
.iconOnly=${badge.iconOnly || false}
|
|
||||||
>
|
|
||||||
${badge.iconSlot} ${badge.slot}
|
|
||||||
</ha-badge>
|
|
||||||
`
|
|
||||||
)}
|
|
||||||
</div>
|
|
||||||
</ha-card>
|
|
||||||
</div>
|
|
||||||
`
|
|
||||||
)}
|
|
||||||
`;
|
|
||||||
}
|
|
||||||
|
|
||||||
firstUpdated(changedProps) {
|
|
||||||
super.firstUpdated(changedProps);
|
|
||||||
applyThemesOnElement(
|
|
||||||
this.shadowRoot!.querySelector(".dark"),
|
|
||||||
{
|
|
||||||
default_theme: "default",
|
|
||||||
default_dark_theme: "default",
|
|
||||||
themes: {},
|
|
||||||
darkMode: true,
|
|
||||||
theme: "default",
|
|
||||||
},
|
|
||||||
undefined,
|
|
||||||
undefined,
|
|
||||||
true
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
static styles = css`
|
|
||||||
:host {
|
|
||||||
display: flex;
|
|
||||||
justify-content: center;
|
|
||||||
}
|
|
||||||
.dark,
|
|
||||||
.light {
|
|
||||||
display: block;
|
|
||||||
background-color: var(--primary-background-color);
|
|
||||||
padding: 0 50px;
|
|
||||||
}
|
|
||||||
ha-card {
|
|
||||||
margin: 24px auto;
|
|
||||||
}
|
|
||||||
.card-content {
|
|
||||||
display: flex;
|
|
||||||
gap: 24px;
|
|
||||||
}
|
|
||||||
`;
|
|
||||||
}
|
|
||||||
|
|
||||||
declare global {
|
|
||||||
interface HTMLElementTagNameMap {
|
|
||||||
"demo-components-ha-badge": DemoHaBadge;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -63,18 +63,20 @@ export class DemoHaBar extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
.warning {
|
}
|
||||||
--ha-bar-primary-color: var(--warning-color);
|
.warning {
|
||||||
}
|
--ha-bar-primary-color: var(--warning-color);
|
||||||
.error {
|
}
|
||||||
--ha-bar-primary-color: var(--error-color);
|
.error {
|
||||||
}
|
--ha-bar-primary-color: var(--error-color);
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -103,17 +103,19 @@ export class DemoHaChips extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
.card-content {
|
}
|
||||||
display: flex;
|
.card-content {
|
||||||
flex-direction: column;
|
display: flex;
|
||||||
align-items: flex-start;
|
flex-direction: column;
|
||||||
}
|
align-items: flex-start;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
---
|
---
|
||||||
title: Spinner
|
title: Circular Progress
|
||||||
subtitle: Can be used to indicate an ongoing task.
|
subtitle: Can be used to indicate an ongoing task.
|
||||||
---
|
---
|
||||||
65
gallery/src/pages/components/ha-circular-progress.ts
Normal file
65
gallery/src/pages/components/ha-circular-progress.ts
Normal file
@@ -0,0 +1,65 @@
|
|||||||
|
import type { TemplateResult } from "lit";
|
||||||
|
import { html, css, LitElement } from "lit";
|
||||||
|
import { customElement, property } from "lit/decorators";
|
||||||
|
import "../../../../src/components/ha-bar";
|
||||||
|
import "../../../../src/components/ha-card";
|
||||||
|
import "../../../../src/components/ha-circular-progress";
|
||||||
|
import "@material/web/progress/circular-progress";
|
||||||
|
import type { HomeAssistant } from "../../../../src/types";
|
||||||
|
|
||||||
|
@customElement("demo-components-ha-circular-progress")
|
||||||
|
export class DemoHaCircularProgress extends LitElement {
|
||||||
|
@property({ attribute: false }) hass!: HomeAssistant;
|
||||||
|
|
||||||
|
protected render(): TemplateResult {
|
||||||
|
return html`<ha-card header="Basic circular progress">
|
||||||
|
<div class="card-content">
|
||||||
|
<ha-circular-progress indeterminate></ha-circular-progress></div
|
||||||
|
></ha-card>
|
||||||
|
<ha-card header="Different circular progress sizes">
|
||||||
|
<div class="card-content">
|
||||||
|
<ha-circular-progress
|
||||||
|
indeterminate
|
||||||
|
size="tiny"
|
||||||
|
></ha-circular-progress>
|
||||||
|
<ha-circular-progress
|
||||||
|
indeterminate
|
||||||
|
size="small"
|
||||||
|
></ha-circular-progress>
|
||||||
|
<ha-circular-progress
|
||||||
|
indeterminate
|
||||||
|
size="medium"
|
||||||
|
></ha-circular-progress>
|
||||||
|
<ha-circular-progress
|
||||||
|
indeterminate
|
||||||
|
size="large"
|
||||||
|
></ha-circular-progress></div
|
||||||
|
></ha-card>
|
||||||
|
<ha-card header="Circular progress with an aria-label">
|
||||||
|
<div class="card-content">
|
||||||
|
<ha-circular-progress
|
||||||
|
indeterminate
|
||||||
|
aria-label="Doing something..."
|
||||||
|
></ha-circular-progress>
|
||||||
|
<ha-circular-progress
|
||||||
|
indeterminate
|
||||||
|
.ariaLabel=${"Doing something..."}
|
||||||
|
></ha-circular-progress></div
|
||||||
|
></ha-card>`;
|
||||||
|
}
|
||||||
|
|
||||||
|
static get styles() {
|
||||||
|
return css`
|
||||||
|
ha-card {
|
||||||
|
max-width: 600px;
|
||||||
|
margin: 24px auto;
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
declare global {
|
||||||
|
interface HTMLElementTagNameMap {
|
||||||
|
"demo-components-ha-circular-progress": DemoHaCircularProgress;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -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,51 +137,53 @@ export class DemoHaBarButton extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
pre {
|
}
|
||||||
margin-top: 0;
|
pre {
|
||||||
margin-bottom: 8px;
|
margin-top: 0;
|
||||||
}
|
margin-bottom: 8px;
|
||||||
p {
|
}
|
||||||
margin: 0;
|
p {
|
||||||
}
|
margin: 0;
|
||||||
label {
|
}
|
||||||
font-weight: 600;
|
label {
|
||||||
}
|
font-weight: 600;
|
||||||
.custom {
|
}
|
||||||
--control-button-icon-color: var(--primary-color);
|
.custom {
|
||||||
--control-button-background-color: var(--primary-color);
|
--control-button-icon-color: var(--primary-color);
|
||||||
--control-button-background-opacity: 0.2;
|
--control-button-background-color: var(--primary-color);
|
||||||
--control-button-border-radius: 18px;
|
--control-button-background-opacity: 0.2;
|
||||||
height: 100px;
|
--control-button-border-radius: 18px;
|
||||||
width: 100px;
|
height: 100px;
|
||||||
}
|
width: 100px;
|
||||||
.custom-group {
|
}
|
||||||
--control-button-group-thickness: 100px;
|
.custom-group {
|
||||||
--control-button-group-border-radius: 36px;
|
--control-button-group-thickness: 100px;
|
||||||
--control-button-group-spacing: 20px;
|
--control-button-group-border-radius: 36px;
|
||||||
}
|
--control-button-group-spacing: 20px;
|
||||||
.custom-group ha-control-button {
|
}
|
||||||
--control-button-border-radius: 18px;
|
.custom-group ha-control-button {
|
||||||
--mdc-icon-size: 32px;
|
--control-button-border-radius: 18px;
|
||||||
}
|
--mdc-icon-size: 32px;
|
||||||
.vertical-buttons {
|
}
|
||||||
height: 300px;
|
.vertical-buttons {
|
||||||
display: flex;
|
height: 300px;
|
||||||
flex-direction: row;
|
display: flex;
|
||||||
justify-content: space-between;
|
flex-direction: row;
|
||||||
}
|
justify-content: space-between;
|
||||||
p.title {
|
}
|
||||||
margin-bottom: 12px;
|
p.title {
|
||||||
}
|
margin-bottom: 12px;
|
||||||
.vertical-switches > *:not(:last-child) {
|
}
|
||||||
margin-right: 4px;
|
.vertical-switches > *:not(:last-child) {
|
||||||
}
|
margin-right: 4px;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -133,37 +133,39 @@ export class DemoHaCircularSlider extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
pre {
|
}
|
||||||
margin-top: 0;
|
pre {
|
||||||
margin-bottom: 8px;
|
margin-top: 0;
|
||||||
}
|
margin-bottom: 8px;
|
||||||
p {
|
}
|
||||||
margin: 0;
|
p {
|
||||||
}
|
margin: 0;
|
||||||
p.title {
|
}
|
||||||
margin-bottom: 12px;
|
p.title {
|
||||||
}
|
margin-bottom: 12px;
|
||||||
ha-control-circular-slider {
|
}
|
||||||
--control-circular-slider-color: #ff9800;
|
ha-control-circular-slider {
|
||||||
}
|
--control-circular-slider-color: #ff9800;
|
||||||
ha-control-circular-slider[inverted] {
|
}
|
||||||
--control-circular-slider-color: #2196f3;
|
ha-control-circular-slider[inverted] {
|
||||||
}
|
--control-circular-slider-color: #2196f3;
|
||||||
ha-control-circular-slider[dual] {
|
}
|
||||||
--control-circular-slider-high-color: #2196f3;
|
ha-control-circular-slider[dual] {
|
||||||
--control-circular-slider-low-color: #ff9800;
|
--control-circular-slider-high-color: #2196f3;
|
||||||
}
|
--control-circular-slider-low-color: #ff9800;
|
||||||
.field {
|
}
|
||||||
display: flex;
|
.field {
|
||||||
flex-direction: row;
|
display: flex;
|
||||||
align-items: center;
|
flex-direction: row;
|
||||||
}
|
align-items: center;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -73,30 +73,32 @@ export class DemoHarControlNumberButtons extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
pre {
|
}
|
||||||
margin-top: 0;
|
pre {
|
||||||
margin-bottom: 8px;
|
margin-top: 0;
|
||||||
}
|
margin-bottom: 8px;
|
||||||
p {
|
}
|
||||||
margin: 0;
|
p {
|
||||||
}
|
margin: 0;
|
||||||
label {
|
}
|
||||||
font-weight: 600;
|
label {
|
||||||
}
|
font-weight: 600;
|
||||||
.custom {
|
}
|
||||||
color: #2196f3;
|
.custom {
|
||||||
--control-number-buttons-color: #2196f3;
|
color: #2196f3;
|
||||||
--control-number-buttons-background-color: #2196f3;
|
--control-number-buttons-color: #2196f3;
|
||||||
--control-number-buttons-background-opacity: 0.1;
|
--control-number-buttons-background-color: #2196f3;
|
||||||
--control-number-buttons-thickness: 100px;
|
--control-number-buttons-background-opacity: 0.1;
|
||||||
--control-number-buttons-border-radius: 36px;
|
--control-number-buttons-thickness: 100px;
|
||||||
}
|
--control-number-buttons-border-radius: 36px;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -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,30 +112,32 @@ export class DemoHaControlSelectMenu extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
pre {
|
}
|
||||||
margin-top: 0;
|
pre {
|
||||||
margin-bottom: 8px;
|
margin-top: 0;
|
||||||
}
|
margin-bottom: 8px;
|
||||||
p {
|
}
|
||||||
margin: 0;
|
p {
|
||||||
}
|
margin: 0;
|
||||||
label {
|
}
|
||||||
font-weight: 600;
|
label {
|
||||||
}
|
font-weight: 600;
|
||||||
.custom {
|
}
|
||||||
--control-button-icon-color: var(--primary-color);
|
.custom {
|
||||||
--control-button-background-color: var(--primary-color);
|
--control-button-icon-color: var(--primary-color);
|
||||||
--control-button-background-opacity: 0.2;
|
--control-button-background-color: var(--primary-color);
|
||||||
--control-button-border-radius: 18px;
|
--control-button-background-opacity: 0.2;
|
||||||
height: 100px;
|
--control-button-border-radius: 18px;
|
||||||
width: 100px;
|
height: 100px;
|
||||||
}
|
width: 100px;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -168,40 +168,42 @@ export class DemoHaControlSelect extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
pre {
|
}
|
||||||
margin-top: 0;
|
pre {
|
||||||
margin-bottom: 8px;
|
margin-top: 0;
|
||||||
}
|
margin-bottom: 8px;
|
||||||
p {
|
}
|
||||||
margin: 0;
|
p {
|
||||||
}
|
margin: 0;
|
||||||
label {
|
}
|
||||||
font-weight: 600;
|
label {
|
||||||
}
|
font-weight: 600;
|
||||||
.custom {
|
}
|
||||||
--mdc-icon-size: 24px;
|
.custom {
|
||||||
--control-select-color: var(--state-fan-active-color);
|
--mdc-icon-size: 24px;
|
||||||
--control-select-thickness: 130px;
|
--control-select-color: var(--state-fan-active-color);
|
||||||
--control-select-border-radius: 36px;
|
--control-select-thickness: 130px;
|
||||||
}
|
--control-select-border-radius: 36px;
|
||||||
.vertical-selects {
|
}
|
||||||
height: 300px;
|
.vertical-selects {
|
||||||
display: flex;
|
height: 300px;
|
||||||
flex-direction: row;
|
display: flex;
|
||||||
justify-content: space-between;
|
flex-direction: row;
|
||||||
}
|
justify-content: space-between;
|
||||||
p.title {
|
}
|
||||||
margin-bottom: 12px;
|
p.title {
|
||||||
}
|
margin-bottom: 12px;
|
||||||
.vertical-selects > *:not(:last-child) {
|
}
|
||||||
margin-right: 4px;
|
.vertical-selects > *:not(:last-child) {
|
||||||
}
|
margin-right: 4px;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -131,41 +131,43 @@ export class DemoHaBarSlider extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
pre {
|
}
|
||||||
margin-top: 0;
|
pre {
|
||||||
margin-bottom: 8px;
|
margin-top: 0;
|
||||||
}
|
margin-bottom: 8px;
|
||||||
p {
|
}
|
||||||
margin: 0;
|
p {
|
||||||
}
|
margin: 0;
|
||||||
label {
|
}
|
||||||
font-weight: 600;
|
label {
|
||||||
}
|
font-weight: 600;
|
||||||
.custom {
|
}
|
||||||
--control-slider-color: #ffcf4c;
|
.custom {
|
||||||
--control-slider-background: #ffcf4c;
|
--control-slider-color: #ffcf4c;
|
||||||
--control-slider-background-opacity: 0.2;
|
--control-slider-background: #ffcf4c;
|
||||||
--control-slider-thickness: 130px;
|
--control-slider-background-opacity: 0.2;
|
||||||
--control-slider-border-radius: 36px;
|
--control-slider-thickness: 130px;
|
||||||
}
|
--control-slider-border-radius: 36px;
|
||||||
.vertical-sliders {
|
}
|
||||||
height: 300px;
|
.vertical-sliders {
|
||||||
display: flex;
|
height: 300px;
|
||||||
flex-direction: row;
|
display: flex;
|
||||||
justify-content: space-between;
|
flex-direction: row;
|
||||||
}
|
justify-content: space-between;
|
||||||
p.title {
|
}
|
||||||
margin-bottom: 12px;
|
p.title {
|
||||||
}
|
margin-bottom: 12px;
|
||||||
.vertical-sliders > *:not(:last-child) {
|
}
|
||||||
margin-right: 4px;
|
.vertical-sliders > *:not(:last-child) {
|
||||||
}
|
margin-right: 4px;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -99,42 +99,44 @@ export class DemoHaControlSwitch extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
pre {
|
}
|
||||||
margin-top: 0;
|
pre {
|
||||||
margin-bottom: 8px;
|
margin-top: 0;
|
||||||
}
|
margin-bottom: 8px;
|
||||||
p {
|
}
|
||||||
margin: 0;
|
p {
|
||||||
}
|
margin: 0;
|
||||||
label {
|
}
|
||||||
font-weight: 600;
|
label {
|
||||||
}
|
font-weight: 600;
|
||||||
.custom {
|
}
|
||||||
--control-switch-on-color: var(--green-color);
|
.custom {
|
||||||
--control-switch-off-color: var(--red-color);
|
--control-switch-on-color: var(--green-color);
|
||||||
--control-switch-thickness: 130px;
|
--control-switch-off-color: var(--red-color);
|
||||||
--control-switch-border-radius: 36px;
|
--control-switch-thickness: 130px;
|
||||||
--control-switch-padding: 6px;
|
--control-switch-border-radius: 36px;
|
||||||
--mdc-icon-size: 24px;
|
--control-switch-padding: 6px;
|
||||||
}
|
--mdc-icon-size: 24px;
|
||||||
.vertical-switches {
|
}
|
||||||
height: 300px;
|
.vertical-switches {
|
||||||
display: flex;
|
height: 300px;
|
||||||
flex-direction: row;
|
display: flex;
|
||||||
justify-content: space-between;
|
flex-direction: row;
|
||||||
}
|
justify-content: space-between;
|
||||||
p.title {
|
}
|
||||||
margin-bottom: 12px;
|
p.title {
|
||||||
}
|
margin-bottom: 12px;
|
||||||
.vertical-switches > *:not(:last-child) {
|
}
|
||||||
margin-right: 4px;
|
.vertical-switches > *:not(:last-child) {
|
||||||
}
|
margin-right: 4px;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import { mdiLightbulbOn, mdiPacMan } from "@mdi/js";
|
import { mdiPacMan } from "@mdi/js";
|
||||||
import type { TemplateResult } from "lit";
|
import type { TemplateResult } from "lit";
|
||||||
import { css, html, LitElement } from "lit";
|
import { css, html, LitElement } from "lit";
|
||||||
import { customElement } from "lit/decorators";
|
import { customElement } from "lit/decorators";
|
||||||
@@ -125,23 +125,6 @@ const SAMPLES: {
|
|||||||
`;
|
`;
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
|
||||||
template(slot, leftChevron) {
|
|
||||||
return html`
|
|
||||||
<ha-expansion-panel
|
|
||||||
slot=${slot}
|
|
||||||
.leftChevron=${leftChevron}
|
|
||||||
header="Attr Header with actions"
|
|
||||||
>
|
|
||||||
<ha-svg-icon
|
|
||||||
slot="leading-icon"
|
|
||||||
.path=${mdiLightbulbOn}
|
|
||||||
></ha-svg-icon>
|
|
||||||
${SHORT_TEXT}
|
|
||||||
</ha-expansion-panel>
|
|
||||||
`;
|
|
||||||
},
|
|
||||||
},
|
|
||||||
];
|
];
|
||||||
|
|
||||||
@customElement("demo-components-ha-expansion-panel")
|
@customElement("demo-components-ha-expansion-panel")
|
||||||
@@ -160,11 +143,13 @@ export class DemoHaExpansionPanel extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-expansion-panel {
|
return css`
|
||||||
margin: -16px;
|
ha-expansion-panel {
|
||||||
}
|
margin: -16px;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -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,12 +61,14 @@ export class DemoHaFaded extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -48,7 +48,6 @@ const DEVICES: DeviceRegistryEntry[] = [
|
|||||||
area_id: "bedroom",
|
area_id: "bedroom",
|
||||||
configuration_url: null,
|
configuration_url: null,
|
||||||
config_entries: ["config_entry_1"],
|
config_entries: ["config_entry_1"],
|
||||||
config_entries_subentries: {},
|
|
||||||
connections: [],
|
connections: [],
|
||||||
disabled_by: null,
|
disabled_by: null,
|
||||||
entry_type: null,
|
entry_type: null,
|
||||||
@@ -72,7 +71,6 @@ const DEVICES: DeviceRegistryEntry[] = [
|
|||||||
area_id: "backyard",
|
area_id: "backyard",
|
||||||
configuration_url: null,
|
configuration_url: null,
|
||||||
config_entries: ["config_entry_2"],
|
config_entries: ["config_entry_2"],
|
||||||
config_entries_subentries: {},
|
|
||||||
connections: [],
|
connections: [],
|
||||||
disabled_by: null,
|
disabled_by: null,
|
||||||
entry_type: null,
|
entry_type: null,
|
||||||
@@ -96,7 +94,6 @@ const DEVICES: DeviceRegistryEntry[] = [
|
|||||||
area_id: null,
|
area_id: null,
|
||||||
configuration_url: null,
|
configuration_url: null,
|
||||||
config_entries: ["config_entry_3"],
|
config_entries: ["config_entry_3"],
|
||||||
config_entries_subentries: {},
|
|
||||||
connections: [],
|
connections: [],
|
||||||
disabled_by: null,
|
disabled_by: null,
|
||||||
entry_type: null,
|
entry_type: null,
|
||||||
@@ -127,8 +124,6 @@ const AREAS: AreaRegistryEntry[] = [
|
|||||||
picture: null,
|
picture: null,
|
||||||
aliases: [],
|
aliases: [],
|
||||||
labels: [],
|
labels: [],
|
||||||
temperature_entity_id: null,
|
|
||||||
humidity_entity_id: null,
|
|
||||||
created_at: 0,
|
created_at: 0,
|
||||||
modified_at: 0,
|
modified_at: 0,
|
||||||
},
|
},
|
||||||
@@ -140,8 +135,6 @@ const AREAS: AreaRegistryEntry[] = [
|
|||||||
picture: null,
|
picture: null,
|
||||||
aliases: [],
|
aliases: [],
|
||||||
labels: [],
|
labels: [],
|
||||||
temperature_entity_id: null,
|
|
||||||
humidity_entity_id: null,
|
|
||||||
created_at: 0,
|
created_at: 0,
|
||||||
modified_at: 0,
|
modified_at: 0,
|
||||||
},
|
},
|
||||||
@@ -153,8 +146,6 @@ const AREAS: AreaRegistryEntry[] = [
|
|||||||
picture: null,
|
picture: null,
|
||||||
aliases: [],
|
aliases: [],
|
||||||
labels: [],
|
labels: [],
|
||||||
temperature_entity_id: null,
|
|
||||||
humidity_entity_id: null,
|
|
||||||
created_at: 0,
|
created_at: 0,
|
||||||
modified_at: 0,
|
modified_at: 0,
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -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,25 +91,27 @@ export class DemoHaHsColorPicker extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
.card-content {
|
}
|
||||||
display: flex;
|
.card-content {
|
||||||
align-items: center;
|
display: flex;
|
||||||
flex-direction: column;
|
align-items: center;
|
||||||
}
|
flex-direction: column;
|
||||||
ha-hs-color-picker {
|
}
|
||||||
width: 400px;
|
ha-hs-color-picker {
|
||||||
}
|
width: 400px;
|
||||||
.value {
|
}
|
||||||
font-size: 22px;
|
.value {
|
||||||
font-weight: bold;
|
font-size: 22px;
|
||||||
margin: 0 0 12px 0;
|
font-weight: bold;
|
||||||
}
|
margin: 0 0 12px 0;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -95,23 +95,25 @@ export class DemoHaLabelBadge extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
ha-card {
|
return css`
|
||||||
max-width: 600px;
|
ha-card {
|
||||||
margin: 24px auto;
|
max-width: 600px;
|
||||||
}
|
margin: 24px auto;
|
||||||
pre {
|
}
|
||||||
margin-left: 16px;
|
pre {
|
||||||
background-color: var(--markdown-code-background-color);
|
margin-left: 16px;
|
||||||
padding: 8px;
|
background-color: var(--markdown-code-background-color);
|
||||||
}
|
padding: 8px;
|
||||||
.badge {
|
}
|
||||||
display: flex;
|
.badge {
|
||||||
flex-direction: row;
|
display: flex;
|
||||||
margin-bottom: 16px;
|
flex-direction: row;
|
||||||
align-items: center;
|
margin-bottom: 16px;
|
||||||
}
|
align-items: center;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
@@ -1,3 +0,0 @@
|
|||||||
---
|
|
||||||
title: Select box
|
|
||||||
---
|
|
||||||
@@ -1,152 +0,0 @@
|
|||||||
import type { TemplateResult } from "lit";
|
|
||||||
import { css, html, LitElement } from "lit";
|
|
||||||
import { customElement, state } from "lit/decorators";
|
|
||||||
import { repeat } from "lit/directives/repeat";
|
|
||||||
import "../../../../src/components/ha-card";
|
|
||||||
import "../../../../src/components/ha-select-box";
|
|
||||||
import type { SelectBoxOption } from "../../../../src/components/ha-select-box";
|
|
||||||
|
|
||||||
const basicOptions: SelectBoxOption[] = [
|
|
||||||
{
|
|
||||||
value: "text-only",
|
|
||||||
label: "Text only",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
value: "card",
|
|
||||||
label: "Card",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
value: "disabled",
|
|
||||||
label: "Disabled option",
|
|
||||||
disabled: true,
|
|
||||||
},
|
|
||||||
];
|
|
||||||
|
|
||||||
const fullOptions: SelectBoxOption[] = [
|
|
||||||
{
|
|
||||||
value: "text-only",
|
|
||||||
label: "Text only",
|
|
||||||
description: "Only text, no border and background",
|
|
||||||
image: "/images/select_box/text_only.svg",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
value: "card",
|
|
||||||
label: "Card",
|
|
||||||
description: "With border and background",
|
|
||||||
image: "/images/select_box/card.svg",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
value: "disabled",
|
|
||||||
label: "Disabled",
|
|
||||||
description: "Option that can not be selected",
|
|
||||||
disabled: true,
|
|
||||||
},
|
|
||||||
];
|
|
||||||
|
|
||||||
const selects: {
|
|
||||||
id: string;
|
|
||||||
label: string;
|
|
||||||
class?: string;
|
|
||||||
options: SelectBoxOption[];
|
|
||||||
disabled?: boolean;
|
|
||||||
}[] = [
|
|
||||||
{
|
|
||||||
id: "basic",
|
|
||||||
label: "Basic",
|
|
||||||
options: basicOptions,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: "full",
|
|
||||||
label: "With description and image",
|
|
||||||
options: fullOptions,
|
|
||||||
},
|
|
||||||
];
|
|
||||||
|
|
||||||
@customElement("demo-components-ha-select-box")
|
|
||||||
export class DemoHaSelectBox extends LitElement {
|
|
||||||
@state() private value?: string = "off";
|
|
||||||
|
|
||||||
handleValueChanged(e: CustomEvent) {
|
|
||||||
this.value = e.detail.value as string;
|
|
||||||
}
|
|
||||||
|
|
||||||
protected render(): TemplateResult {
|
|
||||||
return html`
|
|
||||||
${repeat(selects, (select) => {
|
|
||||||
const { id, label, options } = select;
|
|
||||||
return html`
|
|
||||||
<ha-card>
|
|
||||||
<div class="card-content">
|
|
||||||
<label id=${id}>${label}</label>
|
|
||||||
<ha-select-box
|
|
||||||
.value=${this.value}
|
|
||||||
.options=${options}
|
|
||||||
@value-changed=${this.handleValueChanged}
|
|
||||||
>
|
|
||||||
</ha-select-box>
|
|
||||||
</div>
|
|
||||||
</ha-card>
|
|
||||||
`;
|
|
||||||
})}
|
|
||||||
<ha-card>
|
|
||||||
<div class="card-content">
|
|
||||||
<p class="title"><b>Column layout</b></p>
|
|
||||||
<div class="vertical-selects">
|
|
||||||
${repeat(selects, (select) => {
|
|
||||||
const { options } = select;
|
|
||||||
return html`
|
|
||||||
<ha-select-box
|
|
||||||
.value=${this.value}
|
|
||||||
.options=${options}
|
|
||||||
.maxColumns=${1}
|
|
||||||
@value-changed=${this.handleValueChanged}
|
|
||||||
>
|
|
||||||
</ha-select-box>
|
|
||||||
`;
|
|
||||||
})}
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</ha-card>
|
|
||||||
`;
|
|
||||||
}
|
|
||||||
|
|
||||||
static styles = css`
|
|
||||||
ha-card {
|
|
||||||
max-width: 600px;
|
|
||||||
margin: 24px auto;
|
|
||||||
}
|
|
||||||
pre {
|
|
||||||
margin-top: 0;
|
|
||||||
margin-bottom: 8px;
|
|
||||||
}
|
|
||||||
p {
|
|
||||||
margin: 0;
|
|
||||||
}
|
|
||||||
label {
|
|
||||||
font-weight: 600;
|
|
||||||
margin-bottom: 8px;
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
.custom {
|
|
||||||
--mdc-icon-size: 24px;
|
|
||||||
--control-select-color: var(--state-fan-active-color);
|
|
||||||
--control-select-thickness: 130px;
|
|
||||||
--control-select-border-radius: 36px;
|
|
||||||
}
|
|
||||||
|
|
||||||
p.title {
|
|
||||||
margin-bottom: 12px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.vertical-selects ha-select-box {
|
|
||||||
display: block;
|
|
||||||
margin-bottom: 24px;
|
|
||||||
}
|
|
||||||
`;
|
|
||||||
}
|
|
||||||
|
|
||||||
declare global {
|
|
||||||
interface HTMLElementTagNameMap {
|
|
||||||
"demo-components-ha-select-box": DemoHaSelectBox;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -6,23 +6,22 @@ import { mockAreaRegistry } from "../../../../demo/src/stubs/area_registry";
|
|||||||
import { mockConfigEntries } from "../../../../demo/src/stubs/config_entries";
|
import { mockConfigEntries } from "../../../../demo/src/stubs/config_entries";
|
||||||
import { mockDeviceRegistry } from "../../../../demo/src/stubs/device_registry";
|
import { mockDeviceRegistry } from "../../../../demo/src/stubs/device_registry";
|
||||||
import { mockEntityRegistry } from "../../../../demo/src/stubs/entity_registry";
|
import { mockEntityRegistry } from "../../../../demo/src/stubs/entity_registry";
|
||||||
import { mockFloorRegistry } from "../../../../demo/src/stubs/floor_registry";
|
|
||||||
import { mockHassioSupervisor } from "../../../../demo/src/stubs/hassio_supervisor";
|
import { mockHassioSupervisor } from "../../../../demo/src/stubs/hassio_supervisor";
|
||||||
import { mockLabelRegistry } from "../../../../demo/src/stubs/label_registry";
|
|
||||||
import "../../../../src/components/ha-formfield";
|
|
||||||
import "../../../../src/components/ha-selector/ha-selector";
|
import "../../../../src/components/ha-selector/ha-selector";
|
||||||
import "../../../../src/components/ha-settings-row";
|
import "../../../../src/components/ha-settings-row";
|
||||||
import type { AreaRegistryEntry } from "../../../../src/data/area_registry";
|
import type { AreaRegistryEntry } from "../../../../src/data/area_registry";
|
||||||
import type { BlueprintInput } from "../../../../src/data/blueprint";
|
import type { BlueprintInput } from "../../../../src/data/blueprint";
|
||||||
import type { DeviceRegistryEntry } from "../../../../src/data/device_registry";
|
|
||||||
import type { FloorRegistryEntry } from "../../../../src/data/floor_registry";
|
|
||||||
import type { LabelRegistryEntry } from "../../../../src/data/label_registry";
|
|
||||||
import { showDialog } from "../../../../src/dialogs/make-dialog-manager";
|
import { showDialog } from "../../../../src/dialogs/make-dialog-manager";
|
||||||
import { getEntity } from "../../../../src/fake_data/entity";
|
import { getEntity } from "../../../../src/fake_data/entity";
|
||||||
import { provideHass } from "../../../../src/fake_data/provide_hass";
|
import { provideHass } from "../../../../src/fake_data/provide_hass";
|
||||||
import type { ProvideHassElement } from "../../../../src/mixins/provide-hass-lit-mixin";
|
import type { ProvideHassElement } from "../../../../src/mixins/provide-hass-lit-mixin";
|
||||||
import type { HomeAssistant } from "../../../../src/types";
|
import type { HomeAssistant } from "../../../../src/types";
|
||||||
import "../../components/demo-black-white-row";
|
import "../../components/demo-black-white-row";
|
||||||
|
import type { FloorRegistryEntry } from "../../../../src/data/floor_registry";
|
||||||
|
import type { LabelRegistryEntry } from "../../../../src/data/label_registry";
|
||||||
|
import { mockFloorRegistry } from "../../../../demo/src/stubs/floor_registry";
|
||||||
|
import { mockLabelRegistry } from "../../../../demo/src/stubs/label_registry";
|
||||||
|
import type { DeviceRegistryEntry } from "../../../../src/data/device_registry";
|
||||||
|
|
||||||
const ENTITIES = [
|
const ENTITIES = [
|
||||||
getEntity("alarm_control_panel", "alarm", "disarmed", {
|
getEntity("alarm_control_panel", "alarm", "disarmed", {
|
||||||
@@ -48,7 +47,6 @@ const DEVICES: DeviceRegistryEntry[] = [
|
|||||||
area_id: "bedroom",
|
area_id: "bedroom",
|
||||||
configuration_url: null,
|
configuration_url: null,
|
||||||
config_entries: ["config_entry_1"],
|
config_entries: ["config_entry_1"],
|
||||||
config_entries_subentries: {},
|
|
||||||
connections: [],
|
connections: [],
|
||||||
disabled_by: null,
|
disabled_by: null,
|
||||||
entry_type: null,
|
entry_type: null,
|
||||||
@@ -72,7 +70,6 @@ const DEVICES: DeviceRegistryEntry[] = [
|
|||||||
area_id: "backyard",
|
area_id: "backyard",
|
||||||
configuration_url: null,
|
configuration_url: null,
|
||||||
config_entries: ["config_entry_2"],
|
config_entries: ["config_entry_2"],
|
||||||
config_entries_subentries: {},
|
|
||||||
connections: [],
|
connections: [],
|
||||||
disabled_by: null,
|
disabled_by: null,
|
||||||
entry_type: null,
|
entry_type: null,
|
||||||
@@ -96,7 +93,6 @@ const DEVICES: DeviceRegistryEntry[] = [
|
|||||||
area_id: null,
|
area_id: null,
|
||||||
configuration_url: null,
|
configuration_url: null,
|
||||||
config_entries: ["config_entry_3"],
|
config_entries: ["config_entry_3"],
|
||||||
config_entries_subentries: {},
|
|
||||||
connections: [],
|
connections: [],
|
||||||
disabled_by: null,
|
disabled_by: null,
|
||||||
entry_type: null,
|
entry_type: null,
|
||||||
@@ -127,8 +123,6 @@ const AREAS: AreaRegistryEntry[] = [
|
|||||||
picture: null,
|
picture: null,
|
||||||
aliases: [],
|
aliases: [],
|
||||||
labels: [],
|
labels: [],
|
||||||
temperature_entity_id: null,
|
|
||||||
humidity_entity_id: null,
|
|
||||||
created_at: 0,
|
created_at: 0,
|
||||||
modified_at: 0,
|
modified_at: 0,
|
||||||
},
|
},
|
||||||
@@ -140,8 +134,6 @@ const AREAS: AreaRegistryEntry[] = [
|
|||||||
picture: null,
|
picture: null,
|
||||||
aliases: [],
|
aliases: [],
|
||||||
labels: [],
|
labels: [],
|
||||||
temperature_entity_id: null,
|
|
||||||
humidity_entity_id: null,
|
|
||||||
created_at: 0,
|
created_at: 0,
|
||||||
modified_at: 0,
|
modified_at: 0,
|
||||||
},
|
},
|
||||||
@@ -153,8 +145,6 @@ const AREAS: AreaRegistryEntry[] = [
|
|||||||
picture: null,
|
picture: null,
|
||||||
aliases: [],
|
aliases: [],
|
||||||
labels: [],
|
labels: [],
|
||||||
temperature_entity_id: null,
|
|
||||||
humidity_entity_id: null,
|
|
||||||
created_at: 0,
|
created_at: 0,
|
||||||
modified_at: 0,
|
modified_at: 0,
|
||||||
},
|
},
|
||||||
@@ -644,6 +634,9 @@ class DemoHaSelector extends LitElement implements ProvideHassElement {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static styles = css`
|
||||||
|
ha-settings-row {
|
||||||
|
--paper-item-body-two-line-min-height: 0;
|
||||||
|
}
|
||||||
.options {
|
.options {
|
||||||
max-width: 800px;
|
max-width: 800px;
|
||||||
margin: 16px auto;
|
margin: 16px auto;
|
||||||
|
|||||||
@@ -1,44 +0,0 @@
|
|||||||
import type { TemplateResult } from "lit";
|
|
||||||
import { html, css, LitElement } from "lit";
|
|
||||||
import { customElement, property } from "lit/decorators";
|
|
||||||
import "../../../../src/components/ha-bar";
|
|
||||||
import "../../../../src/components/ha-card";
|
|
||||||
import "../../../../src/components/ha-spinner";
|
|
||||||
import type { HomeAssistant } from "../../../../src/types";
|
|
||||||
|
|
||||||
@customElement("demo-components-ha-spinner")
|
|
||||||
export class DemoHaSpinner extends LitElement {
|
|
||||||
@property({ attribute: false }) hass!: HomeAssistant;
|
|
||||||
|
|
||||||
protected render(): TemplateResult {
|
|
||||||
return html`<ha-card header="Basic spinner">
|
|
||||||
<div class="card-content">
|
|
||||||
<ha-spinner></ha-spinner></div
|
|
||||||
></ha-card>
|
|
||||||
<ha-card header="Different spinner sizes">
|
|
||||||
<div class="card-content">
|
|
||||||
<ha-spinner size="tiny"></ha-spinner>
|
|
||||||
<ha-spinner size="small"></ha-spinner>
|
|
||||||
<ha-spinner size="medium"></ha-spinner>
|
|
||||||
<ha-spinner size="large"></ha-spinner></div
|
|
||||||
></ha-card>
|
|
||||||
<ha-card header="Spinner with an aria-label">
|
|
||||||
<div class="card-content">
|
|
||||||
<ha-spinner aria-label="Doing something..."></ha-spinner>
|
|
||||||
<ha-spinner .ariaLabel=${"Doing something..."}></ha-spinner></div
|
|
||||||
></ha-card>`;
|
|
||||||
}
|
|
||||||
|
|
||||||
static styles = css`
|
|
||||||
ha-card {
|
|
||||||
max-width: 600px;
|
|
||||||
margin: 24px auto;
|
|
||||||
}
|
|
||||||
`;
|
|
||||||
}
|
|
||||||
|
|
||||||
declare global {
|
|
||||||
interface HTMLElementTagNameMap {
|
|
||||||
"demo-components-ha-spinner": DemoHaSpinner;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -48,25 +48,27 @@ export class DemoHaTip extends LitElement {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
static styles = css`
|
static get styles() {
|
||||||
:host {
|
return css`
|
||||||
display: flex;
|
:host {
|
||||||
flex-direction: row;
|
display: flex;
|
||||||
justify-content: space-between;
|
flex-direction: row;
|
||||||
}
|
justify-content: space-between;
|
||||||
.dark,
|
}
|
||||||
.light {
|
.dark,
|
||||||
display: block;
|
.light {
|
||||||
background-color: var(--primary-background-color);
|
display: block;
|
||||||
padding: 0 50px;
|
background-color: var(--primary-background-color);
|
||||||
}
|
padding: 0 50px;
|
||||||
ha-tip {
|
}
|
||||||
margin-bottom: 14px;
|
ha-tip {
|
||||||
}
|
margin-bottom: 14px;
|
||||||
ha-card {
|
}
|
||||||
margin: 24px auto;
|
ha-card {
|
||||||
}
|
margin: 24px auto;
|
||||||
`;
|
}
|
||||||
|
`;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
declare global {
|
declare global {
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user