Compare commits

..

No commits in common. "main" and "v2.2.1" have entirely different histories.
main ... v2.2.1

View file

@ -21,13 +21,6 @@ class AirQualityCard extends HTMLElement {
{ name: 'pm25_entity', selector: { entity: { domain: 'sensor' } } },
]
},
{
type: 'grid',
schema: [
{ name: 'hcho_entity', selector: { entity: { domain: 'sensor' } } },
{ name: 'tvoc_entity', selector: { entity: { domain: 'sensor' } } },
]
},
{
type: 'grid',
schema: [
@ -54,8 +47,6 @@ class AirQualityCard extends HTMLElement {
humidity_entity: 'Humidity Sensor (optional)',
temperature_entity: 'Temperature Sensor (optional)',
air_quality_entity: 'Air Quality Index (optional)',
hcho_entity: 'Formaldehyde (HCHO; CH2O) Sensor (optional)',
tvoc_entity: 'Volatile Organic Compounds (tVOC) Sensor (optional)',
recommendation_entity: 'Recommendation Sensor (optional)',
hours_to_show: 'Graph History',
temperature_unit: 'Temperature Unit'
@ -121,8 +112,6 @@ class AirQualityCard extends HTMLElement {
let size = 3; // Base size for header and recommendation
if (this._config.co2_entity) size += 1;
if (this._config.pm25_entity) size += 1;
if (this._config.hcho_entity) size += 1;
if (this._config.tvoc_entity) size += 1;
if (this._config.humidity_entity) size += 1;
if (this._config.temperature_entity) size += 1;
return size;
@ -146,14 +135,6 @@ class AirQualityCard extends HTMLElement {
promises.push(this._fetchHistory(this._config.pm25_entity, startTime, endTime));
keys.push('pm25');
}
if (this._config.hcho_entity) {
promises.push(this._fetchHistory(this._config.hcho_entity, startTime, endTime));
keys.push('hcho');
}
if (this._config.tvoc_entity) {
promises.push(this._fetchHistory(this._config.tvoc_entity, startTime, endTime));
keys.push('voc');
}
if (this._config.humidity_entity) {
promises.push(this._fetchHistory(this._config.humidity_entity, startTime, endTime));
keys.push('humidity');
@ -218,22 +199,6 @@ class AirQualityCard extends HTMLElement {
return '#f44336';
}
_getHCHOColor(value) {
if (value < 20) return '#4caf50';
if (value < 50) return '#8bc34a';
if (value < 100) return '#ffc107';
if (value < 200) return '#ff9800';
return '#f44336';
}
_getTVOCColor(value) {
if (value < 100) return '#4caf50';
if (value < 300) return '#8bc34a';
if (value < 500) return '#ffc107';
if (value < 1000) return '#ff9800';
return '#f44336';
}
_getHumidityColor(value) {
if (value < 30) return '#ff9800';
if (value < 40) return '#8bc34a';
@ -337,8 +302,6 @@ class AirQualityCard extends HTMLElement {
_initialRender() {
const showCO2 = !!this._config.co2_entity;
const showPM25 = !!this._config.pm25_entity;
const showHCHO = !!this._config.hcho_entity;
const showTVOC = !!this._config.tvoc_entity;
const showHumidity = !!this._config.humidity_entity;
const showTemp = !!this._config.temperature_entity;
@ -601,45 +564,6 @@ class AirQualityCard extends HTMLElement {
<div class="graph-time-axis" id="pm25-time-axis"></div>
</div>
` : ''}
${showHCHO ? `
<div class="graph-container" id="hcho-graph-container" data-entity="${this._config.hcho_entity}">
<div class="graph-header">
<span class="graph-label">HCHO / CH₂O</span>
<span class="graph-value" id="hcho-value">-- <span class="unit">ppm</span><span class="status" id="hcho-status"></span></span>
</div>
<div class="graph-wrapper">
<div class="graph" id="hcho-graph">
<svg id="hcho-svg" viewBox="0 0 300 50" preserveAspectRatio="none"></svg>
</div>
<div class="graph-cursor" id="hcho-cursor"></div>
<div class="graph-tooltip" id="hcho-tooltip">
<div class="graph-tooltip-value"></div>
<div class="graph-tooltip-time"></div>
</div>
</div>
<div class="graph-time-axis" id="hcho-time-axis"></div>
</div>
` : ''}
${showTVOC ? `
<div class="graph-container" id="tvoc-graph-container" data-entity="${this._config.tvoc_entity}">
<div class="graph-header">
<span class="graph-label">tVOC</span>
<span class="graph-value" id="tvoc-value">-- <span class="unit">μg/</span><span class="status" id="tvoc-status"></span></span>
</div>
<div class="graph-wrapper">
<div class="graph" id="tvoc-graph">
<svg id="tvoc-svg" viewBox="0 0 300 50" preserveAspectRatio="none"></svg>
</div>
<div class="graph-cursor" id="tvoc-cursor"></div>
<div class="graph-tooltip" id="tvoc-tooltip">
<div class="graph-tooltip-value"></div>
<div class="graph-tooltip-time"></div>
</div>
</div>
<div class="graph-time-axis" id="tvoc-time-axis"></div>
</div>
` : ''}
${showHumidity ? `
<div class="graph-container" id="humidity-graph-container" data-entity="${this._config.humidity_entity}">
@ -691,8 +615,6 @@ class AirQualityCard extends HTMLElement {
const co2 = this._config.co2_entity ? this._getNumericState(this._config.co2_entity) : null;
const pm25 = this._config.pm25_entity ? this._getNumericState(this._config.pm25_entity) : null;
const hcho = this._config.hcho_entity ? this._getNumericState(this._config.hcho_entity) : null;
const tvoc = this._config.tvoc_entity ? this._getNumericState(this._config.tvoc_entity) : null;
const humidity = this._config.humidity_entity ? this._getNumericState(this._config.humidity_entity) : null;
const temp = this._config.temperature_entity ? this._getNumericState(this._config.temperature_entity) : null;
const recommendation = this._getRecommendation();
@ -778,34 +700,6 @@ class AirQualityCard extends HTMLElement {
}
}
// Update HCHO
if (hcho !== null) {
const hchoColor = this._getHCHOColor(hcho);
const hchoValueEl = this.shadowRoot.getElementById('hcho-value');
if (hchoValueEl) {
hchoValueEl.innerHTML = `${hcho.toFixed(1)} <span class="unit">ppb</span><span class="status" id="hcho-status"></span>`;
const statusEl = hchoValueEl.querySelector('.status');
statusEl.textContent = hcho < 20 ? 'Excellent' : hcho < 50 ? 'Good' : hcho < 100 ? 'Moderate' : hcho < 200 ? 'Elevated' : 'Poor';
statusEl.style.background = hchoColor + '22';
statusEl.style.color = hchoColor;
hchoValueEl.style.color = hchoColor;
}
}
// Update tVOC
if (tvoc !== null) {
const tvocColor = this._getTVOCColor(tvoc);
const tvocValueEl = this.shadowRoot.getElementById('tvoc-value');
if (tvocValueEl) {
tvocValueEl.innerHTML = `${tvoc.toFixed(1)} <span class="unit">ppb</span><span class="status" id="tvoc-status"></span>`;
const statusEl = tvocValueEl.querySelector('.status');
statusEl.textContent = tvoc < 100 ? 'Excellent' : tvoc < 300 ? 'Good' : tvoc < 500 ? 'Moderate' : tvoc < 1000 ? 'Elevated' : 'Poor';
statusEl.style.background = tvocColor + '22';
statusEl.style.color = tvocColor;
tvocValueEl.style.color = tvocColor;
}
}
// Update Humidity
if (humidity !== null) {
const humidityColor = this._getHumidityColor(humidity);
@ -862,12 +756,6 @@ class AirQualityCard extends HTMLElement {
if (this._config.pm25_entity && this._history.pm25.length) {
this._renderGraph('pm25', this._history.pm25, this._getPM25Color.bind(this), 0, 60, 'μg/m³');
}
if (this._config.hcho_entity && this._history.hcho.length) {
this._renderGraph('hcho', this._history.hcho, this._getHCHOColor.bind(this), 0, 60, 'ppb');
}
if (this._config.tvoc_entity && this._history.tvoc.length) {
this._renderGraph('tvoc', this._history.tvoc, this._getTVOCColor.bind(this), 0, 60, 'ppb');
}
if (this._config.humidity_entity && this._history.humidity.length) {
this._renderGraph('humidity', this._history.humidity, this._getHumidityColor.bind(this), 0, 100, '%');
}
@ -1126,8 +1014,6 @@ if (LitElement && !customElements.get('air-quality-card-editor')) {
name: 'Card Name',
co2_entity: 'CO₂ Sensor',
pm25_entity: 'PM2.5 Sensor',
hcho_entity: 'HCHO Sensor (optional)',
tvoc_entity: 'tVOC Sensor (optional)',
humidity_entity: 'Humidity Sensor (optional)',
temperature_entity: 'Temperature Sensor (optional)',
air_quality_entity: 'Air Quality Index (optional)',
@ -1143,8 +1029,6 @@ if (LitElement && !customElements.get('air-quality-card-editor')) {
{ name: 'name', selector: { text: {} } },
{ name: 'co2_entity', selector: { entity: { domain: 'sensor' } } },
{ name: 'pm25_entity', selector: { entity: { domain: 'sensor' } } },
{ name: 'hcho_entity', selector: { entity: { domain: 'sensor' } } },
{ name: 'tvoc_entity', selector: { entity: { domain: 'sensor' } } },
{ name: 'humidity_entity', selector: { entity: { domain: 'sensor' } } },
{ name: 'temperature_entity', selector: { entity: { domain: 'sensor' } } },
{ name: 'air_quality_entity', selector: { entity: { domain: 'sensor' } } },