Note that sending an ON command will switch the dimmer to the value stored when last turning the dimmer off, or 100% depending on the configuration in the Niko Home Control Controller.
This can be changed with the Niko Home Control programming software.
-For thing type `blind` the supported channel is `rollershutter`. UpDown, StopMove and Percent command types are supported.
+For thing type `blind` the supported channel is `rollershutter`.
+UpDown, StopMove and Percent command types are supported.
-For thing type `thermostat` the supported channels are `measured`, `mode`, `setpoint`, `overruletime` and `demand`.
+For thing type `thermostat` the supported channels are `measured`, `heatingmode`, `mode`, `setpoint`, `overruletime`, `heatingdemand` and `demand`.
`measured` gives the current temperature in QuantityType<Temperature>, allowing for different temperature units.
This channel is read only.
-`mode` can be set and shows the current thermostat mode.
-Allowed values are 0 (day), 1 (night), 2 (eco), 3 (off), 4 (cool), 5 (prog 1), 6 (prog 2), 7 (prog 3).
-If mode is set, the `setpoint` temperature will return to its standard value from the mode.
-`setpoint` can be set and shows the current thermostat setpoint value in QuantityType<Temperature>.
+`heatingmode` can be set and shows the current thermostat mode.
+Allowed values are Day, Night, Eco, Off, Cool, Prog1, Prog2, Prog3.
+As an alternative to `heatingmode` and for backward compatibility, the advanced channel `mode` is provided.
+This channel has the same meaning, but with numeric values (0=Day, 1=Night, 2=Eco, 3=Off, 4=Cool, 5=Prog1, 6=Prog2, 7=Prog3) instead of string values.
+If `heatingmode` or `mode` is set, the `setpoint` temperature will return to the standard value for the mode as defined in Niko Home Control.
+`setpoint` shows the current thermostat setpoint value in QuantityType<Temperature>.
When updating `setpoint`, it will overrule the temperature setpoint defined by the thermostat mode for `overruletime` duration.
-`overruletime` is used to set the total duration to apply the setpoint temperature set in the setpoint channel before the thermostat returns to the setting in its mode.
-`demand` is a number indicating of the system is actively heating/cooling.
+`overruletime` is used to set the total duration to apply the setpoint temperature set in the setpoint channel before the thermostat returns to the setting from its mode.
+`heatingdemand` is a string indicating if the system is actively heating/cooling.
+This channel will have value Heating, Cooling or None.
+As an alternative to `heatingdemand`, the advanced channel `demand` is provided.
The value will be 1 for heating, -1 for cooling and 0 if not heating or cooling.
+`heatingdemand` and `demand` are read only channels.
Note that cooling in NHC I is set by the binding, and will incorrectly show cooling demand when the system does not have cooling capabilities.
In NHC II, `measured` and `setpoint` temperatures will always report in 0.5°C increments due to a Niko Home Control II API restriction.
Switch LivingRoom {channel="nikohomecontrol:onOff:nhc1:2:switch"} # Switch for onOff type action
Dimmer TVRoom {channel="nikohomecontrol:dimmer:nhc1:3:brightness"} # Changing brightness dimmer type action
Rollershutter Kitchen {channel="nikohomecontrol:blind:nhc1:4:rollershutter"} # Controlling rollershutter or blind type action
-Number:Temperature CurTemperature "[%.1f °F]" {channel="nikohomecontrol:thermostat:nhc1:5:measured"} # Getting measured temperature from thermostat in °F, read only
-Number ThermostatMode {channel="nikohomecontrol:thermostat:nhc1:5:mode"} # Get and set thermostat mode
-Number:Temperature SetTemperature "[%.1f °C]" {channel="nikohomecontrol:thermostat:nhc1:5:setpoint"} # Get and set target temperature in °C
-Number OverruleDuration {channel="nikohomecontrol:thermostat:nhc1:5:overruletime"} # Get and set the overrule time
-Number ThermostatDemand {channel="nikohomecontrol:thermostat:nhc1:5:demand"} # Get the current heating/cooling demand
-Number:Power CurPower "[%.0f W]" {channel="nikohomecontrol:energyMeter:nhc2:6:power"} # Get current power consumption
+Number:Temperature CurTemperature "[%.1f °F]" {channel="nikohomecontrol:thermostat:nhc1:5:measured"} # Getting measured temperature from thermostat in °F, read only
+String ThermostatMode {channel="nikohomecontrol:thermostat:nhc1:5:heatingmode"} # Get and set thermostat mode
+Number:Temperature SetTemperature "[%.1f °C]" {channel="nikohomecontrol:thermostat:nhc1:5:setpoint"} # Get and set target temperature in °C
+Number OverruleDuration {channel="nikohomecontrol:thermostat:nhc1:5:overruletime"} # Get and set the overrule time
+String ThermostatDemand {channel="nikohomecontrol:thermostat:nhc1:5:heatingdemand"} # Get the current heating/cooling demand
+Number:Power CurPower "[%.0f W]" {channel="nikohomecontrol:energyMeter:nhc2:6:power"} # Get current power consumption
```
.sitemap:
Switch item=TVRoom # allows switching dimmer item off or on (with controller defined behavior)
Rollershutter item=Kitchen
Text item=CurTemperature
-Selection item=ThermostatMode mappings=[0="day", 1="night", 2="eco", 3="off", 4="cool", 5="prog 1", 6="prog 2", 7="prog 3"]
+Selection item=ThermostatMode mappings=[Day="day", Night="night", Eco="eco", Off="off", Prog1="Away"]
Setpoint item=SetTemperature minValue=0 maxValue=30
Slider item=OverruleDuration minValue=0 maxValue=120
Text item=Power
public static final String CHANNEL_OVERRULETIME = "overruletime";
public static final String CHANNEL_MODE = "mode";
public static final String CHANNEL_DEMAND = "demand";
+ public static final String CHANNEL_HEATING_MODE = "heatingmode";
+ public static final String CHANNEL_HEATING_DEMAND = "heatingdemand";
public static final String CHANNEL_POWER = "power";
import org.openhab.binding.nikohomecontrol.internal.handler.NikoHomeControlBridgeHandler2;
import org.openhab.binding.nikohomecontrol.internal.handler.NikoHomeControlEnergyMeterHandler;
import org.openhab.binding.nikohomecontrol.internal.handler.NikoHomeControlThermostatHandler;
+import org.openhab.core.i18n.TimeZoneProvider;
import org.openhab.core.net.NetworkAddressService;
import org.openhab.core.thing.Bridge;
import org.openhab.core.thing.Thing;
import org.openhab.core.thing.binding.BaseThingHandlerFactory;
import org.openhab.core.thing.binding.ThingHandler;
import org.openhab.core.thing.binding.ThingHandlerFactory;
+import org.osgi.service.component.annotations.Activate;
import org.osgi.service.component.annotations.Component;
import org.osgi.service.component.annotations.Reference;
@Component(service = ThingHandlerFactory.class, configurationPid = "binding.nikohomecontrol")
public class NikoHomeControlHandlerFactory extends BaseThingHandlerFactory {
- private @NonNullByDefault({}) NetworkAddressService networkAddressService;
+ private final NetworkAddressService networkAddressService;
+ private final TimeZoneProvider timeZoneProvider;
+
+ @Activate
+ public NikoHomeControlHandlerFactory(final @Reference NetworkAddressService networkAddressService,
+ final @Reference TimeZoneProvider timeZoneProvider) {
+ super();
+ this.networkAddressService = networkAddressService;
+ this.timeZoneProvider = timeZoneProvider;
+ }
@Override
public boolean supportsThingType(ThingTypeUID thingTypeUID) {
protected @Nullable ThingHandler createHandler(Thing thing) {
if (BRIDGE_THING_TYPES_UIDS.contains(thing.getThingTypeUID())) {
if (BRIDGEII_THING_TYPE.equals(thing.getThingTypeUID())) {
- return new NikoHomeControlBridgeHandler2((Bridge) thing, networkAddressService);
+ return new NikoHomeControlBridgeHandler2((Bridge) thing, networkAddressService, timeZoneProvider);
} else {
- return new NikoHomeControlBridgeHandler1((Bridge) thing);
+ return new NikoHomeControlBridgeHandler1((Bridge) thing, timeZoneProvider);
}
} else if (THING_TYPE_THERMOSTAT.equals(thing.getThingTypeUID())) {
return new NikoHomeControlThermostatHandler(thing);
return null;
}
-
- @Reference
- protected void setNetworkAddressService(NetworkAddressService networkAddressService) {
- this.networkAddressService = networkAddressService;
- }
-
- protected void unsetNetworkAddressService(NetworkAddressService networkAddressService) {
- this.networkAddressService = null;
- }
}
import java.net.InetAddress;
import java.net.UnknownHostException;
+import java.time.ZoneId;
import java.util.Collection;
import java.util.Map;
import java.util.Map.Entry;
import org.openhab.binding.nikohomecontrol.internal.protocol.NhcControllerEvent;
import org.openhab.binding.nikohomecontrol.internal.protocol.NikoHomeControlCommunication;
import org.openhab.core.config.core.Configuration;
+import org.openhab.core.i18n.TimeZoneProvider;
import org.openhab.core.thing.Bridge;
import org.openhab.core.thing.ChannelUID;
import org.openhab.core.thing.ThingStatus;
private volatile @Nullable ScheduledFuture<?> refreshTimer;
- public NikoHomeControlBridgeHandler(Bridge nikoHomeControlBridge) {
+ protected final TimeZoneProvider timeZoneProvider;
+
+ public NikoHomeControlBridgeHandler(Bridge nikoHomeControlBridge, TimeZoneProvider timeZoneProvider) {
super(nikoHomeControlBridge);
+ this.timeZoneProvider = timeZoneProvider;
}
@Override
return getConfig().as(NikoHomeControlBridgeConfig.class).port;
}
+ @Override
+ public ZoneId getTimeZone() {
+ return timeZoneProvider.getTimeZone();
+ }
+
@Override
public Collection<Class<? extends ThingHandlerService>> getServices() {
return Set.of(NikoHomeControlDiscoveryService.class);
import org.eclipse.jdt.annotation.NonNullByDefault;
import org.openhab.binding.nikohomecontrol.internal.protocol.nhc1.NikoHomeControlCommunication1;
+import org.openhab.core.i18n.TimeZoneProvider;
import org.openhab.core.thing.Bridge;
import org.openhab.core.thing.ThingStatus;
import org.openhab.core.thing.ThingStatusDetail;
private final Logger logger = LoggerFactory.getLogger(NikoHomeControlBridgeHandler1.class);
- public NikoHomeControlBridgeHandler1(Bridge nikoHomeControlBridge) {
- super(nikoHomeControlBridge);
+ public NikoHomeControlBridgeHandler1(Bridge nikoHomeControlBridge, TimeZoneProvider timeZoneProvider) {
+ super(nikoHomeControlBridge, timeZoneProvider);
}
@Override
import org.eclipse.jdt.annotation.NonNullByDefault;
import org.eclipse.jdt.annotation.Nullable;
import org.openhab.binding.nikohomecontrol.internal.protocol.nhc2.NikoHomeControlCommunication2;
+import org.openhab.core.i18n.TimeZoneProvider;
import org.openhab.core.net.NetworkAddressService;
import org.openhab.core.thing.Bridge;
import org.openhab.core.thing.ThingStatus;
NetworkAddressService networkAddressService;
- public NikoHomeControlBridgeHandler2(Bridge nikoHomeControlBridge, NetworkAddressService networkAddressService) {
- super(nikoHomeControlBridge);
+ public NikoHomeControlBridgeHandler2(Bridge nikoHomeControlBridge, NetworkAddressService networkAddressService,
+ TimeZoneProvider timeZoneProvider) {
+ super(nikoHomeControlBridge, timeZoneProvider);
this.networkAddressService = networkAddressService;
}
package org.openhab.binding.nikohomecontrol.internal.handler;
import static org.openhab.binding.nikohomecontrol.internal.NikoHomeControlBindingConstants.*;
+import static org.openhab.binding.nikohomecontrol.internal.protocol.NikoHomeControlConstants.*;
import static org.openhab.core.library.unit.SIUnits.CELSIUS;
import static org.openhab.core.types.RefreshType.REFRESH;
+import java.math.BigDecimal;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.ScheduledFuture;
import java.util.concurrent.TimeUnit;
-import javax.measure.quantity.Temperature;
-
import org.eclipse.jdt.annotation.NonNullByDefault;
import org.eclipse.jdt.annotation.Nullable;
import org.openhab.binding.nikohomecontrol.internal.protocol.NhcThermostat;
import org.openhab.binding.nikohomecontrol.internal.protocol.nhc2.NhcThermostat2;
import org.openhab.core.library.types.DecimalType;
import org.openhab.core.library.types.QuantityType;
+import org.openhab.core.library.types.StringType;
import org.openhab.core.thing.Bridge;
import org.openhab.core.thing.ChannelUID;
import org.openhab.core.thing.Thing;
switch (channelUID.getId()) {
case CHANNEL_MEASURED:
case CHANNEL_DEMAND:
+ case CHANNEL_HEATING_DEMAND:
updateStatus(ThingStatus.ONLINE);
break;
-
case CHANNEL_MODE:
if (command instanceof DecimalType) {
nhcThermostat.executeMode(((DecimalType) command).intValue());
}
updateStatus(ThingStatus.ONLINE);
break;
-
+ case CHANNEL_HEATING_MODE:
+ if (command instanceof StringType) {
+ nhcThermostat.executeMode(command.toString());
+ }
+ updateStatus(ThingStatus.ONLINE);
+ break;
case CHANNEL_SETPOINT:
- QuantityType<Temperature> setpoint = null;
- if (command instanceof QuantityType) {
- setpoint = ((QuantityType<Temperature>) command).toUnit(CELSIUS);
- // Always set the new setpoint temperature as an overrule
- // If no overrule time is given yet, set the overrule time to the configuration parameter
- int time = nhcThermostat.getOverruletime();
- if (time <= 0) {
- time = overruleTime;
- }
+ // Always set the new setpoint temperature as an overrule
+ // If no overrule time is given yet, set the overrule time to the configuration parameter
+ int time = nhcThermostat.getOverruletime();
+ if (time <= 0) {
+ time = overruleTime;
+ }
+ if (command instanceof QuantityType<?>) {
+ QuantityType<?> setpoint = ((QuantityType<?>) command).toUnit(CELSIUS);
if (setpoint != null) {
nhcThermostat.executeOverrule(Math.round(setpoint.floatValue() * 10), time);
}
+ } else if (command instanceof DecimalType) {
+ BigDecimal setpoint = ((DecimalType) command).toBigDecimal();
+ nhcThermostat.executeOverrule(Math.round(setpoint.floatValue() * 10), time);
}
updateStatus(ThingStatus.ONLINE);
break;
-
case CHANNEL_OVERRULETIME:
if (command instanceof DecimalType) {
int overruletime = ((DecimalType) command).intValue();
return;
}
- updateState(CHANNEL_MEASURED, new QuantityType<>(nhcThermostat.getMeasured() / 10.0, CELSIUS));
+ updateState(CHANNEL_MEASURED, new QuantityType<>(measured / 10.0, CELSIUS));
int overruletime = nhcThermostat.getRemainingOverruletime();
updateState(CHANNEL_OVERRULETIME, new DecimalType(overruletime));
}
updateState(CHANNEL_MODE, new DecimalType(mode));
+ updateState(CHANNEL_HEATING_MODE, new StringType(THERMOSTATMODES[mode]));
updateState(CHANNEL_DEMAND, new DecimalType(demand));
+ updateState(CHANNEL_HEATING_DEMAND, new StringType(THERMOSTATDEMAND[Math.abs(demand) <= 1 ? (demand + 1) : 0]));
updateStatus(ThingStatus.ONLINE);
}
private void scheduleRefreshOverruletime(NhcThermostat nhcThermostat) {
cancelRefreshTimer();
- if (nhcThermostat.getRemainingOverruletime() <= 0) {
+ if (nhcThermostat.getRemainingOverruletime() == 0) {
return;
}
refreshTimer = scheduler.scheduleWithFixedDelay(() -> {
int remainingTime = nhcThermostat.getRemainingOverruletime();
updateState(CHANNEL_OVERRULETIME, new DecimalType(remainingTime));
- if (remainingTime <= 0) {
+ if (remainingTime == 0) {
cancelRefreshTimer();
}
}, 1, 1, TimeUnit.MINUTES);
package org.openhab.binding.nikohomecontrol.internal.protocol;
import java.net.InetAddress;
+import java.time.ZoneId;
import org.eclipse.jdt.annotation.NonNullByDefault;
import org.eclipse.jdt.annotation.Nullable;
return "";
}
+ /**
+ * Get the time zone ID of the Niko Home Control system.
+ *
+ * @return the zone ID
+ */
+ public ZoneId getTimeZone();
+
/**
* Called to indicate the connection with the Niko Home Control Controller is offline.
*
/**
* The {@link NhcEnergyMeter} class represents the energyMeters metering Niko Home Control communication object. It
- * contains all
- * fields representing a Niko Home Control energyMeters meter and has methods to receive energyMeters usage information.
- * A specific
- * implementation is {@link NhcEnergyMeter2}.
+ * contains all fields representing a Niko Home Control energyMeters meter and has methods to receive energyMeters usage
+ * information. A specific implementation is {@link NhcEnergyMeter2}.
*
* @author Mark Herwege - Initial Contribution
*/
*/
package org.openhab.binding.nikohomecontrol.internal.protocol;
+import static org.openhab.binding.nikohomecontrol.internal.protocol.NikoHomeControlConstants.THERMOSTATMODES;
+
import java.time.LocalDateTime;
+import java.time.ZonedDateTime;
import java.time.temporal.ChronoUnit;
+import java.util.Arrays;
import org.eclipse.jdt.annotation.NonNullByDefault;
import org.eclipse.jdt.annotation.Nullable;
protected volatile int ecosave;
protected volatile int demand;
- private @Nullable LocalDateTime overruleStart;
+ private @Nullable volatile ZonedDateTime overruleStart;
private @Nullable NhcThermostatEvent eventHandler;
updateChannels();
}
- /**
- * Update overrule values of the thermostat without touching the thermostat definition (id, name and location) and
- * without changing the ThingHandler callback.
- *
- * @param overrule the overrule temperature in 0.1°C multiples
- * @param overruletime in minutes
- */
- public void updateState(int overrule, int overruletime) {
- setOverrule(overrule);
- setOverruletime(overruletime);
-
- updateChannels();
- }
-
- /**
- * Update overrule values of the thermostat without touching the thermostat definition (id, name and location) and
- * without changing the ThingHandler callback.
- *
- * @param overrule the overrule temperature in 0.1°C multiples
- * @param overruletime in minutes
- */
- public void updateState(int mode) {
- setMode(mode);
-
- updateChannels();
- }
-
/**
* Method called when thermostat is removed from the Niko Home Control Controller.
*/
private void setOverrule(int overrule) {
this.overrule = overrule;
+ if (overrule <= 0) {
+ stopOverrule();
+ }
}
/**
* @param overruletime the overruletime in minutes
*/
private void setOverruletime(int overruletime) {
- if (overruletime <= 0) {
- stopOverrule();
- } else if (overruletime != this.overruletime) {
- startOverrule();
+ if (overruletime != this.overruletime) {
+ if (overruletime <= 0) {
+ stopOverrule();
+ } else {
+ startOverrule();
+ }
+ this.overruletime = overruletime;
}
- this.overruletime = overruletime;
}
/**
}
/**
- * @return the heating/cooling demand: 0 if no demand, >0 if heating, <0 if cooling
+ * @return the heating/cooling demand: 0 if no demand, 1 if heating, -1 if cooling
*/
public int getDemand() {
return demand;
*/
public abstract void executeMode(int mode);
+ /**
+ * Sends thermostat mode to Niko Home Control.
+ *
+ * @param mode allowed values are Day, Night, Eco, Off, Cool, Prog1, Prog2, Prog3
+ */
+ public void executeMode(String mode) {
+ int intMode = Arrays.asList(THERMOSTATMODES).indexOf(mode);
+ if (intMode < 0) { // if not recognized, default to Day
+ intMode = 0;
+ logger.debug("Thermostat mode {} not recognized, default to Day mode", mode);
+ }
+ executeMode(intMode);
+ };
+
/**
* Sends thermostat setpoint to Niko Home Control. This method is implemented in {@link NhcThermostat1} and
* {@link NhcThermostat2}.
public abstract void executeOverrule(int overrule, int overruletime);
/**
- * @return remaining overrule time in minutes
+ * @return remaining overrule time in minutes, 0 or positive
*/
public int getRemainingOverruletime() {
- if (overruleStart == null) {
- return 0;
- } else {
+ int remainingTime = 0;
+ if (overruleStart != null) {
// overruletime time max 23h59min, therefore can safely cast to int
- return overruletime - (int) ChronoUnit.MINUTES.between(overruleStart, LocalDateTime.now());
+ remainingTime = Math.max(0, overruletime - (int) ChronoUnit.MINUTES.between(overruleStart,
+ LocalDateTime.now().atZone(nhcComm.getTimeZone())));
}
+ logger.trace("Getting remaining overrule time, remaining: {}", remainingTime);
+ return remainingTime;
}
/**
* Start a new overrule, this method is used to be able to calculate the remaining overrule time
*/
private void startOverrule() {
- overruleStart = LocalDateTime.now();
+ overruleStart = LocalDateTime.now().atZone(nhcComm.getTimeZone());
}
/**
*/
private void stopOverrule() {
overruleStart = null;
+ overruletime = 0;
+ overrule = 0;
}
}
*/
package org.openhab.binding.nikohomecontrol.internal.protocol;
+import java.time.ZoneId;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ScheduledExecutorService;
// restart attempts
private volatile int delay = 0;
private volatile int attempt = 0;
- protected @Nullable ScheduledFuture<?> scheduledRestart = null;
+ protected volatile @Nullable ScheduledFuture<?> scheduledRestart = null;
protected NikoHomeControlCommunication(NhcControllerEvent handler, ScheduledExecutorService scheduler) {
this.handler = handler;
*/
public abstract boolean communicationActive();
+ /**
+ * Return the timezone for the system.
+ *
+ * @return zoneId
+ */
+ public ZoneId getTimeZone() {
+ return handler.getTimeZone();
+ }
+
/**
* Return all actions in the Niko Home Control Controller.
*
// NhcII thermostat modes
public static final String[] THERMOSTATMODES = { "Day", "Night", "Eco", "Off", "Cool", "Prog1", "Prog2", "Prog3" };
+ public static final String[] THERMOSTATDEMAND = { "Cooling", "None", "Heating" };
}
int measured = ambientTemperatureProperty.orElse(thermostat.getMeasured());
int setpoint = setpointTemperatureProperty.orElse(thermostat.getSetpoint());
- int overrule = thermostat.getOverrule();
- int overruletime = thermostat.getRemainingOverruletime();
- if (overruleActiveProperty.orElse(false)) {
- overrule = overruleSetpointProperty.orElse(0);
- overruletime = overruleTimeProperty.orElse(0);
+ int overrule = 0;
+ int overruletime = 0;
+ if (overruleActiveProperty.orElse(true)) {
+ overrule = overruleSetpointProperty.orElse(thermostat.getOverrule());
+ overruletime = overruleTimeProperty.orElse(thermostat.getRemainingOverruletime());
}
int ecosave = thermostat.getEcosave();
energyMeter.setPower(power);
} catch (NumberFormatException e) {
energyMeter.setPower(null);
- logger.trace("received empty energy meter {} power reading", energyMeter.getId());
+ logger.trace("wrong format in energy meter {} power reading", energyMeter.getId());
}
}
channelModeLabel = Mode
channelModeDescription = Thermostat mode
-channelModeOption0 = day
-channelModeOption1 = night
-channelModeOption2 = eco
-channelModeOption3 = off
-channelModeOption4 = cool
-channelModeOption5 = prog 1
-channelModeOption6 = prog 2
-channelModeOption7 = prog 3
+channelModeOption0 = Day
+channelModeOption1 = Night
+channelModeOption2 = Eco
+channelModeOption3 = Off
+channelModeOption4 = Cool
+channelModeOption5 = Program 1
+channelModeOption6 = Program 2
+channelModeOption7 = Program 3
+
+channelDemandLabel = Demand
+channelDemandDescription = Heating/cooling demand
+channelDemand-1 = Cooling
+channelDemand0 = None
+channelDemand1 = Heating
channelPowerLabel = Power
channelPowerDescription = Momentary power consumption/production (positive is consumption)
<bridge-type-ref id="bridge"/>
<bridge-type-ref id="bridge2"/>
</supported-bridge-type-refs>
- <label>@text/ThermostatLabel</label>
- <description>@text/ThermostatDescription</description>
+ <label>@text/thermostatLabel</label>
+ <description>@text/thermostatDescription</description>
<channels>
<channel id="measured" typeId="measured"/>
+ <channel id="heatingmode" typeId="heatingmode"/>
<channel id="mode" typeId="mode"/>
<channel id="setpoint" typeId="setpoint"/>
<channel id="overruletime" typeId="overruletime"/>
+ <channel id="heatingdemand" typeId="heatingdemand"/>
+ <channel id="demand" typeId="demand"/>
</channels>
<config-description>
<parameter name="thermostatId" type="text" required="true">
<category>Number</category>
<state min="0" max="1440" step="5"/>
</channel-type>
- <channel-type id="mode">
+ <channel-type id="heatingmode">
+ <item-type>String</item-type>
+ <label>@text/channelModeLabel</label>
+ <description>@text/channelModeDescription</description>
+ <state>
+ <options>
+ <option value="Day">@text/channelModeOption0</option>
+ <option value="Night">@text/channelModeOption1</option>
+ <option value="Eco">@text/channelModeOption2</option>
+ <option value="Off">@text/channelModeOption3</option>
+ <option value="Cool">@text/channelModeOption4</option>
+ <option value="Prog1">@text/channelModeOption5</option>
+ <option value="Prog2">@text/channelModeOption6</option>
+ <option value="Prog3">@text/channelModeOption7</option>
+ </options>
+ </state>
+ </channel-type>
+ <channel-type id="mode" advanced="true">
<item-type>Number</item-type>
<label>@text/channelModeLabel</label>
<description>@text/channelModeDescription</description>
- <category>Number</category>
<state>
<options>
<option value="0">@text/channelModeOption0</option>
</options>
</state>
</channel-type>
+ <channel-type id="heatingdemand">
+ <item-type>String</item-type>
+ <label>@text/channelDemandLabel</label>
+ <description>@text/channelDemandDescription</description>
+ <state readOnly="true">
+ <options>
+ <option value="Cooling">@text/channelDemand-1</option>
+ <option value="None">@text/channelDemand0</option>
+ <option value="Heating">@text/channelDemand1</option>
+ </options>
+ </state>
+ </channel-type>
+ <channel-type id="demand" advanced="true">
+ <item-type>Number</item-type>
+ <label>@text/channelDemandLabel</label>
+ <description>@text/channelDemandDescription</description>
+ <state readOnly="true">
+ <options>
+ <option value="-1">@text/channelDemand-1</option>
+ <option value="0">@text/channelDemand0</option>
+ <option value="1">@text/channelDemand1</option>
+ </options>
+ </state>
+ </channel-type>
+
<channel-type id="power">
<item-type>Number:Power</item-type>
<label>@text/channelPowerLabel</label>