mirror of
https://github.com/home-assistant/frontend.git
synced 2025-07-13 04:16:34 +00:00
Add addon store
This commit is contained in:
parent
ce95af99fe
commit
110f152e23
70
panels/hassio/addon-store/hassio-addon-repository.html
Normal file
70
panels/hassio/addon-store/hassio-addon-repository.html
Normal file
@ -0,0 +1,70 @@
|
||||
<link rel="import" href="../../../bower_components/polymer/polymer.html">
|
||||
<link rel="import" href="../../../bower_components/paper-card/paper-card.html">
|
||||
<link rel="import" href="../../../bower_components/paper-item/paper-item.html">
|
||||
<link rel="import" href="../../../bower_components/paper-item/paper-item-body.html">
|
||||
|
||||
<dom-module id="hassio-addon-repository">
|
||||
<template>
|
||||
<style include="iron-flex ha-style">
|
||||
:host,
|
||||
paper-card {
|
||||
display: block;
|
||||
}
|
||||
|
||||
paper-item {
|
||||
cursor: pointer;
|
||||
}
|
||||
</style>
|
||||
<paper-card heading='[[repo.name]]'>
|
||||
<template is='dom-if' if='[[computeShowIntro(repo)]]'>
|
||||
<div class='card-content'>
|
||||
<template is='dom-if' if='[[repo.maintainer]]'>
|
||||
Maintained by [[repo.maintainer]].
|
||||
</template>
|
||||
<template is='dom-if' if='[[repo.url]]'>
|
||||
<a href='[[repo.url]]' target='_blank'>Visit repository website.</a>
|
||||
</template>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<template is='dom-repeat' items='[[addons]]' as='addon'>
|
||||
<paper-item>
|
||||
<paper-item-body two-line on-tap='addonTapped'>
|
||||
<div>[[addon.name]]</div>
|
||||
<div secondary>[[addon.description]]</div>
|
||||
</paper-item-body>
|
||||
[[computeInstallStatus(addon)]]
|
||||
</paper-item>
|
||||
</template>
|
||||
</paper-card>
|
||||
</template>
|
||||
</dom-module>
|
||||
|
||||
<script>
|
||||
Polymer({
|
||||
is: 'hassio-addon-repository',
|
||||
|
||||
properties: {
|
||||
repo: {
|
||||
type: Object,
|
||||
},
|
||||
|
||||
addons: {
|
||||
type: Array,
|
||||
}
|
||||
},
|
||||
|
||||
computeShowIntro: function (repo) {
|
||||
return repo.url || repo.maintainer;
|
||||
},
|
||||
|
||||
computeInstallStatus: function (addon) {
|
||||
return addon.installed || 'Not installed';
|
||||
},
|
||||
|
||||
addonTapped: function (ev) {
|
||||
this.fire('hassio-select-addon', { addon: this.addons[ev.model.index].slug });
|
||||
ev.target.blur();
|
||||
},
|
||||
});
|
||||
</script>
|
141
panels/hassio/addon-store/hassio-addon-store.html
Normal file
141
panels/hassio/addon-store/hassio-addon-store.html
Normal file
@ -0,0 +1,141 @@
|
||||
<link rel="import" href="../../../bower_components/polymer/polymer.html">
|
||||
<link rel="import" href="../../../bower_components/app-layout/app-header-layout/app-header-layout.html">
|
||||
<link rel="import" href="../../../bower_components/app-layout/app-header/app-header.html">
|
||||
<link rel="import" href="../../../bower_components/app-layout/app-toolbar/app-toolbar.html">
|
||||
<link rel="import" href="../../../bower_components/paper-icon-button/paper-icon-button.html">
|
||||
|
||||
<link rel="import" href="../../../src/components/ha-menu-button.html">
|
||||
|
||||
<link rel="import" href="./hassio-repositories-editor.html">
|
||||
<link rel="import" href="./hassio-addon-repository.html">
|
||||
|
||||
<dom-module id="hassio-addon-store">
|
||||
<template>
|
||||
<style include="iron-flex ha-style">
|
||||
paper-card {
|
||||
display: block;
|
||||
}
|
||||
.content {
|
||||
padding: 24px 0 32px;
|
||||
max-width: 600px;
|
||||
margin: 0 auto;
|
||||
}
|
||||
|
||||
hassio-addon-repository {
|
||||
margin-top: 24px;
|
||||
}
|
||||
</style>
|
||||
<app-header-layout has-scrolling-region>
|
||||
<app-header fixed>
|
||||
<app-toolbar>
|
||||
<paper-icon-button
|
||||
icon='mdi:arrow-left'
|
||||
on-tap='backTapped'
|
||||
></paper-icon-button>
|
||||
<div main-title>Hass.io Add-Ons</div>
|
||||
<paper-icon-button
|
||||
icon="mdi:refresh"
|
||||
on-tap="refreshTapped"
|
||||
></paper-icon-button>
|
||||
</app-toolbar>
|
||||
</app-header>
|
||||
|
||||
<div class='content'>
|
||||
<hassio-repositories-editor
|
||||
hass='[[hass]]'
|
||||
repos='[[supervisorInfo.addons_repositories]]'
|
||||
></hassio-repositories-editor>
|
||||
<template is='dom-repeat' items='[[repos]]' as='repo'>
|
||||
<hassio-addon-repository
|
||||
repo='[[repo]]'
|
||||
addons='[[computeAddOns(repo.slug)]]'
|
||||
></hassio-addon-repository>
|
||||
</template>
|
||||
</div>
|
||||
</app-header-layout>
|
||||
</template>
|
||||
</dom-module>
|
||||
|
||||
<script>
|
||||
Polymer({
|
||||
_coreRepos: [{
|
||||
slug: 'core',
|
||||
name: 'Built-in Add-Ons',
|
||||
url: 'https://home-assistant.io/addons',
|
||||
maintainer: 'Home Assistant authors',
|
||||
}],
|
||||
|
||||
is: 'hassio-addon-store',
|
||||
|
||||
properties: {
|
||||
hass: {
|
||||
type: Object,
|
||||
},
|
||||
|
||||
narrow: {
|
||||
type: Boolean,
|
||||
},
|
||||
|
||||
showMenu: {
|
||||
type: Boolean,
|
||||
value: false,
|
||||
},
|
||||
|
||||
addons: {
|
||||
type: Array,
|
||||
value: [],
|
||||
},
|
||||
|
||||
repos: {
|
||||
type: Array,
|
||||
value: []
|
||||
},
|
||||
|
||||
supervisorInfo: {
|
||||
type: Object,
|
||||
}
|
||||
},
|
||||
|
||||
listeners: {
|
||||
'hass-api-called': 'apiCalled',
|
||||
},
|
||||
|
||||
apiCalled: function (ev) {
|
||||
if (ev.detail.success) {
|
||||
this.loadData();
|
||||
}
|
||||
},
|
||||
|
||||
attached: function () {
|
||||
this.loadData();
|
||||
},
|
||||
|
||||
loadData: function () {
|
||||
this.hass.callApi('get', 'hassio/supervisor/addons')
|
||||
.then(function (info) {
|
||||
this.addons = info.data.addons;
|
||||
this.repos = this._coreRepos.concat(info.data.repositories);
|
||||
}.bind(this), function () {
|
||||
this.addons = [];
|
||||
this.repos = [];
|
||||
}.bind(this));
|
||||
},
|
||||
|
||||
computeAddOns: function (repo) {
|
||||
return this.addons.filter(function (addon) {
|
||||
return addon.repository === repo;
|
||||
});
|
||||
},
|
||||
|
||||
refreshTapped: function () {
|
||||
this.hass.callApi('post', 'hassio/supervisor/reload')
|
||||
.then(function () {
|
||||
this.loadData();
|
||||
}.bind(this));
|
||||
},
|
||||
|
||||
backTapped: function () {
|
||||
this.fire('hassio-select-addon', { addon: null });
|
||||
},
|
||||
});
|
||||
</script>
|
67
panels/hassio/addon-store/hassio-repositories-editor.html
Normal file
67
panels/hassio/addon-store/hassio-repositories-editor.html
Normal file
@ -0,0 +1,67 @@
|
||||
<link rel="import" href="../../../bower_components/polymer/polymer.html">
|
||||
<link rel="import" href="../../../bower_components/paper-card/paper-card.html">
|
||||
<link rel="import" href="../../../bower_components/iron-autogrow-textarea/iron-autogrow-textarea.html">
|
||||
|
||||
<link rel="import" href="../../../src/components/buttons/ha-call-api-button.html">
|
||||
|
||||
<dom-module id="hassio-repositories-editor">
|
||||
<template>
|
||||
<style include="ha-style">
|
||||
:host {
|
||||
display: block;
|
||||
}
|
||||
paper-card {
|
||||
display: block;
|
||||
}
|
||||
iron-autogrow-textarea {
|
||||
width: 100%;
|
||||
}
|
||||
</style>
|
||||
<paper-card heading='Add-On Repositories'>
|
||||
<div class="card-content">
|
||||
<p>Configure which add-on repositories to fetch data from. One repository per line.</p>
|
||||
<iron-autogrow-textarea value="{{options}}"></iron-autogrow-textarea>
|
||||
</div>
|
||||
<div class="card-actions">
|
||||
<ha-call-api-button
|
||||
hass='[[hass]]'
|
||||
data='[[computeOptionsData(options)]]'
|
||||
path="hassio/supervisor/options"
|
||||
>Save</ha-call-api-button>
|
||||
</div>
|
||||
</paper-card>
|
||||
</template>
|
||||
</dom-module>
|
||||
|
||||
<script>
|
||||
Polymer({
|
||||
is: 'hassio-repositories-editor',
|
||||
|
||||
properties: {
|
||||
hass: {
|
||||
type: Object,
|
||||
},
|
||||
|
||||
options: {
|
||||
type: String,
|
||||
value: '',
|
||||
},
|
||||
|
||||
repos: {
|
||||
type: Array,
|
||||
value: [],
|
||||
observer: 'reposChanged',
|
||||
},
|
||||
},
|
||||
|
||||
reposChanged: function (repos) {
|
||||
this.options = repos.join('\n');
|
||||
},
|
||||
|
||||
computeOptionsData: function (options) {
|
||||
return {
|
||||
addons_repositories: options.split('\n'),
|
||||
};
|
||||
},
|
||||
});
|
||||
</script>
|
@ -24,7 +24,7 @@
|
||||
</style>
|
||||
<paper-card heading='Info'>
|
||||
<div class="card-content">
|
||||
<div>[[addonInfo.description]]</div>
|
||||
<p>[[addonInfo.description]]</p>
|
||||
<table class='info'>
|
||||
<tr>
|
||||
<td>Installed</td>
|
||||
|
@ -17,17 +17,15 @@
|
||||
}
|
||||
</style>
|
||||
<paper-card heading="Installed Addons">
|
||||
<div class="card-content">
|
||||
<template is='dom-repeat' items='[[data]]' as='addon'>
|
||||
<paper-item>
|
||||
<paper-item-body two-line on-tap='addonTapped'>
|
||||
<div>[[addon.name]]</div>
|
||||
<div secondary>[[addon.description]]</div>
|
||||
</paper-item-body>
|
||||
[[computeInstallStatus(addon)]]
|
||||
</paper-item>
|
||||
</template>
|
||||
</div>
|
||||
<template is='dom-repeat' items='[[data]]' as='addon'>
|
||||
<paper-item>
|
||||
<paper-item-body two-line on-tap='addonTapped'>
|
||||
<div>[[addon.name]]</div>
|
||||
<div secondary>[[addon.description]]</div>
|
||||
</paper-item-body>
|
||||
[[addon.installed]]
|
||||
</paper-item>
|
||||
</template>
|
||||
</paper-card>
|
||||
</template>
|
||||
</dom-module>
|
||||
@ -56,10 +54,6 @@ Polymer({
|
||||
},
|
||||
},
|
||||
|
||||
computeInstallStatus(addon) {
|
||||
return addon.installed || 'Not installed';
|
||||
},
|
||||
|
||||
addonTapped: function (ev) {
|
||||
this.fire('hassio-select-addon', { addon: this.data[ev.model.index].slug });
|
||||
ev.target.blur();
|
||||
|
@ -3,6 +3,7 @@
|
||||
<link rel="import" href="../../../bower_components/app-layout/app-header/app-header.html">
|
||||
<link rel="import" href="../../../bower_components/app-layout/app-toolbar/app-toolbar.html">
|
||||
<link rel="import" href="../../../bower_components/iron-flex-layout/iron-flex-layout-classes.html">
|
||||
<link rel="import" href="../../../bower_components/paper-icon-button/paper-icon-button.html">
|
||||
|
||||
<link rel="import" href="../../../src/components/ha-menu-button.html">
|
||||
|
||||
@ -36,6 +37,10 @@
|
||||
<app-toolbar>
|
||||
<ha-menu-button narrow='[[narrow]]' show-menu='[[showMenu]]'></ha-menu-button>
|
||||
<div main-title>Hass.io</div>
|
||||
<paper-icon-button
|
||||
icon="mdi:shopping"
|
||||
on-tap="storeTapped"
|
||||
></paper-icon-button>
|
||||
</app-toolbar>
|
||||
</app-header>
|
||||
|
||||
@ -100,5 +105,9 @@ Polymer({
|
||||
value: {},
|
||||
},
|
||||
},
|
||||
|
||||
storeTapped: function () {
|
||||
this.fire('hassio-show-store');
|
||||
},
|
||||
});
|
||||
</script>
|
||||
|
@ -2,6 +2,7 @@
|
||||
|
||||
<link rel="import" href="./dashboard/hassio-dashboard.html">
|
||||
<link rel="import" href="./addon-view/hassio-addon-view.html">
|
||||
<link rel="import" href="./addon-store/hassio-addon-store.html">
|
||||
<link rel="import" href="./hassio-loading.html">
|
||||
<link rel="import" href="./hassio-data.html">
|
||||
|
||||
@ -20,34 +21,42 @@
|
||||
host='{{hostInfo}}'
|
||||
></hassio-data>
|
||||
|
||||
<template is='dom-if' if='[[!loaded]]'>
|
||||
<hassio-loading
|
||||
narrow='[[narrow]]'
|
||||
hass='[[hass]]'
|
||||
show-menu='[[showMenu]]'
|
||||
></hassio-loading>
|
||||
</template>
|
||||
<template is='dom-if' if='[[loaded]]' restamp>
|
||||
<template is='dom-if' if='[[addon]]'>
|
||||
<hassio-addon-view
|
||||
<template is='dom-if' if='[[dashboardSelected(currentPage)]]'>
|
||||
<template is='dom-if' if='[[!loaded]]'>
|
||||
<hassio-loading
|
||||
narrow='[[narrow]]'
|
||||
hass='[[hass]]'
|
||||
supervisor-info='[[supervisorInfo]]'
|
||||
host-info='[[hostInfo]]'
|
||||
addon='[[addon]]'
|
||||
></hassio-addon-view>
|
||||
show-menu='[[showMenu]]'
|
||||
></hassio-loading>
|
||||
</template>
|
||||
|
||||
<template is='dom-if' if='[[!addon]]'>
|
||||
<template is='dom-if' if='[[loaded]]'>
|
||||
<hassio-dashboard
|
||||
hass='[[hass]]'
|
||||
narrow='[[narrow]]'
|
||||
show-menu='[[showMenu]]'
|
||||
supervisor-info='{{supervisorInfo}}'
|
||||
host-info='{{hostInfo}}'
|
||||
supervisor-info='[[supervisorInfo]]'
|
||||
host-info='[[hostInfo]]'
|
||||
hass-info='[[hassInfo]]'
|
||||
></hassio-dashboard>
|
||||
</template>
|
||||
</template>
|
||||
|
||||
<template is='dom-if' if='[[addonViewSelected(currentPage)]]' restamp>
|
||||
<hassio-addon-view
|
||||
hass='[[hass]]'
|
||||
supervisor-info='[[supervisorInfo]]'
|
||||
host-info='[[hostInfo]]'
|
||||
addon='[[addon]]'
|
||||
></hassio-addon-view>
|
||||
</template>
|
||||
|
||||
<template is='dom-if' if='[[addonStoreSelected(currentPage)]]'>
|
||||
<hassio-addon-store
|
||||
id='addon-store'
|
||||
hass='[[hass]]'
|
||||
supervisor-info='[[supervisorInfo]]'
|
||||
></hassio-addon-store>
|
||||
</template>
|
||||
</template>
|
||||
</dom-module>
|
||||
|
||||
@ -97,16 +106,29 @@ Polymer({
|
||||
loaded: {
|
||||
type: Boolean,
|
||||
computed: 'computeIsLoaded(supervisorInfo, hostInfo, hassInfo, forceLoading)',
|
||||
}
|
||||
},
|
||||
|
||||
currentPage: {
|
||||
type: String,
|
||||
value: 'dashboard',
|
||||
},
|
||||
|
||||
lastPage: {
|
||||
type: String,
|
||||
value: 'dashboard',
|
||||
},
|
||||
},
|
||||
|
||||
listeners: {
|
||||
'hassio-select-addon': 'addonSelected',
|
||||
'hassio-show-store': 'showStore',
|
||||
'hass-api-called': 'apiCalled',
|
||||
},
|
||||
|
||||
apiCalled: function () {
|
||||
this.$.data.refresh();
|
||||
apiCalled: function (ev) {
|
||||
if (ev.detail.success) {
|
||||
this.$.data.refresh();
|
||||
}
|
||||
},
|
||||
|
||||
computeIsLoaded: function (supervisorInfo, hostInfo, hassInfo, forceLoading) {
|
||||
@ -117,11 +139,40 @@ Polymer({
|
||||
},
|
||||
|
||||
addonSelected: function (ev) {
|
||||
this.forceLoading = true;
|
||||
setTimeout(function () {
|
||||
this.addon = ev.detail.addon;
|
||||
this.forceLoading = false;
|
||||
}.bind(this), 0);
|
||||
var addon = ev.detail.addon;
|
||||
|
||||
if (this.currentPage === this.lastPage) {
|
||||
this.lastPage = 'dashboard';
|
||||
}
|
||||
|
||||
if (addon) {
|
||||
this.lastPage = this.currentPage;
|
||||
this.currentPage = 'addon-view';
|
||||
this.addon = addon;
|
||||
} else {
|
||||
this.currentPage = this.lastPage;
|
||||
// Give time to cleanup the addon-view panel or it crashes
|
||||
setTimeout(function () {
|
||||
this.addon = addon;
|
||||
}.bind(this), 0);
|
||||
}
|
||||
},
|
||||
|
||||
showStore: function () {
|
||||
this.currentPage = 'addon-store';
|
||||
},
|
||||
|
||||
dashboardSelected: function (currentPage) {
|
||||
return currentPage === 'dashboard';
|
||||
},
|
||||
|
||||
addonStoreSelected: function (currentPage) {
|
||||
return currentPage === 'addon-store';
|
||||
},
|
||||
|
||||
addonViewSelected: function (currentPage) {
|
||||
return currentPage === 'addon-view';
|
||||
},
|
||||
|
||||
});
|
||||
</script>
|
||||
|
Loading…
x
Reference in New Issue
Block a user