2 * Copyright (c) 2010-2022 Contributors to the openHAB project
4 * See the NOTICE file(s) distributed with this work for additional
7 * This program and the accompanying materials are made available under the
8 * terms of the Eclipse Public License 2.0 which is available at
9 * http://www.eclipse.org/legal/epl-2.0
11 * SPDX-License-Identifier: EPL-2.0
13 package org.openhab.binding.lgwebos.internal;
15 import java.util.concurrent.ScheduledExecutorService;
16 import java.util.concurrent.TimeUnit;
18 import org.eclipse.jdt.annotation.NonNullByDefault;
19 import org.openhab.binding.lgwebos.internal.handler.LGWebOSHandler;
20 import org.openhab.binding.lgwebos.internal.handler.LGWebOSTVSocket.State;
21 import org.openhab.binding.lgwebos.internal.handler.core.CommandConfirmation;
22 import org.openhab.core.library.types.OnOffType;
23 import org.openhab.core.types.Command;
24 import org.openhab.core.types.RefreshType;
25 import org.slf4j.Logger;
26 import org.slf4j.LoggerFactory;
29 * Handles Power Control Command.
30 * Note: Connect SDK only supports powering OFF for most devices.
32 * @author Sebastian Prehn - Initial contribution
35 public class PowerControlPower extends BaseChannelHandler<CommandConfirmation> {
36 private static final int WOL_PACKET_RETRY_COUNT = 10;
37 private static final int WOL_PACKET_RETRY_DELAY_MILLIS = 100;
39 private final Logger logger = LoggerFactory.getLogger(PowerControlPower.class);
40 private final ConfigProvider configProvider;
41 private final ScheduledExecutorService scheduler;
43 public PowerControlPower(ConfigProvider configProvider, ScheduledExecutorService scheduler) {
44 this.configProvider = configProvider;
45 this.scheduler = scheduler;
49 public void onReceiveCommand(String channelId, LGWebOSHandler handler, Command command) {
50 final State state = handler.getSocket().getState();
51 if (RefreshType.REFRESH == command) {
52 handler.postUpdate(channelId, state == State.REGISTERED ? OnOffType.ON : OnOffType.OFF);
53 } else if (OnOffType.ON == command) {
57 logger.debug("Received ON - TV is currently connecting.");
58 handler.postUpdate(channelId, OnOffType.OFF);
61 logger.debug("Received ON - TV is already on.");
63 case DISCONNECTING: // WOL will not stop the shutdown process, but we must not update the state to ON
65 String macAddress = configProvider.getMacAddress();
66 if (macAddress.isEmpty()) {
67 logger.debug("Received ON - Turning TV on via API is not supported by LG WebOS TVs. "
68 + "You may succeed using wake on lan (WOL). "
69 + "Please set the macAddress config value in Thing configuration to enable this.");
70 handler.postUpdate(channelId, OnOffType.OFF);
72 for (int i = 0; i < WOL_PACKET_RETRY_COUNT; i++) {
73 scheduler.schedule(() -> {
75 WakeOnLanUtility.sendWOLPacket(macAddress);
76 } catch (IllegalArgumentException e) {
77 logger.debug("Failed to send WOL packet: {}", e.getMessage());
79 }, i * WOL_PACKET_RETRY_DELAY_MILLIS, TimeUnit.MILLISECONDS);
84 } else if (OnOffType.OFF == command) {
88 // in both states no message will sent to TV, thus the operation won't have an effect
89 logger.debug("Received OFF - TV is currently connecting.");
92 handler.getSocket().powerOff(getDefaultResponseListener());
96 logger.debug("Received OFF - TV is already off.");
100 logger.info("Only accept OnOffType, RefreshType. Type was {}.", command.getClass());
105 public void onDeviceReady(String channelId, LGWebOSHandler handler) {
106 handler.postUpdate(channelId, OnOffType.ON);
110 public void onDeviceRemoved(String channelId, LGWebOSHandler handler) {
111 handler.postUpdate(channelId, OnOffType.OFF);
114 public interface ConfigProvider {
115 String getMacAddress();