-
-
Notifications
You must be signed in to change notification settings - Fork 3.6k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[knx] postUpdate for contact-control sends to bus (#16263)
contact-control items need to send to the bus like a switch item, to trigger a state update in the external device. * Add a new profile for contact-control items * Add a profile factory and a profile advisor class * Handle postUpdate like a command and send message on KNX bus Fixes #16115. Signed-off-by: Holger Friedrich <mail@holger-friedrich.de>
- Loading branch information
1 parent
bed592c
commit d5fc695
Showing
4 changed files
with
217 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
100 changes: 100 additions & 0 deletions
100
...knx/src/main/java/org/openhab/binding/knx/internal/profiles/KNXContactControlProfile.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,100 @@ | ||
/** | ||
* Copyright (c) 2010-2024 Contributors to the openHAB project | ||
* | ||
* See the NOTICE file(s) distributed with this work for additional | ||
* information. | ||
* | ||
* This program and the accompanying materials are made available under the | ||
* terms of the Eclipse Public License 2.0 which is available at | ||
* http://www.eclipse.org/legal/epl-2.0 | ||
* | ||
* SPDX-License-Identifier: EPL-2.0 | ||
*/ | ||
package org.openhab.binding.knx.internal.profiles; | ||
|
||
import org.eclipse.jdt.annotation.NonNullByDefault; | ||
import org.eclipse.jdt.annotation.Nullable; | ||
import org.openhab.core.thing.ChannelUID; | ||
import org.openhab.core.thing.Thing; | ||
import org.openhab.core.thing.ThingRegistry; | ||
import org.openhab.core.thing.binding.ThingHandler; | ||
import org.openhab.core.thing.profiles.ProfileCallback; | ||
import org.openhab.core.thing.profiles.ProfileTypeUID; | ||
import org.openhab.core.thing.profiles.StateProfile; | ||
import org.openhab.core.types.Command; | ||
import org.openhab.core.types.State; | ||
import org.slf4j.Logger; | ||
import org.slf4j.LoggerFactory; | ||
|
||
/** | ||
* This is the implementation of a specialized profile for KNX contact-control-items. | ||
* | ||
* In contrast to the profile {@code FOLLOW} from {@link org.openhab.core.thing.profiles.SystemProfiles} | ||
* used for other *-control items, it sends to the bus also for contact items. | ||
* | ||
* @author Holger Friedrich - Initial contribution | ||
*/ | ||
@NonNullByDefault | ||
public class KNXContactControlProfile implements StateProfile { | ||
|
||
private final Logger logger = LoggerFactory.getLogger(KNXContactControlProfile.class); | ||
private final ProfileCallback callback; | ||
private final ThingRegistry thingRegistry; | ||
|
||
public KNXContactControlProfile(ProfileCallback callback, ThingRegistry thingRegistry) { | ||
this.callback = callback; | ||
this.thingRegistry = thingRegistry; | ||
} | ||
|
||
@Override | ||
public ProfileTypeUID getProfileTypeUID() { | ||
return KNXProfileFactory.UID_CONTACT_CONTROL; | ||
} | ||
|
||
@Override | ||
public void onStateUpdateFromItem(State state) { | ||
ChannelUID linkedChannelUID = callback.getItemChannelLink().getLinkedUID(); | ||
logger.trace("onStateUpdateFromItem({}) to {}", state.toString(), linkedChannelUID); | ||
|
||
if (!(state instanceof Command)) { | ||
logger.debug("The given state {} could not be transformed to a command", state); | ||
return; | ||
} | ||
Command command = (Command) state; | ||
|
||
// this does not have effect for contact items | ||
// callback.handleCommand(command); | ||
// workaround is to call handleCommand of the Thing directly | ||
@Nullable | ||
Thing linkedThing = thingRegistry.get(linkedChannelUID.getThingUID()); | ||
if (linkedThing != null) { | ||
@Nullable | ||
ThingHandler linkedThingHandler = linkedThing.getHandler(); | ||
if (linkedThingHandler != null) { | ||
linkedThingHandler.handleCommand(linkedChannelUID, command); | ||
} else { | ||
logger.warn("Failed to send to {}, no ThingHandler", linkedChannelUID); | ||
} | ||
} else { | ||
logger.warn("Failed to send to {}, no linked Thing", linkedChannelUID); | ||
} | ||
} | ||
|
||
@Override | ||
public void onCommandFromHandler(Command command) { | ||
logger.trace("onCommandFromHandler {}", command.toString()); | ||
callback.sendCommand(command); | ||
} | ||
|
||
@Override | ||
public void onCommandFromItem(Command command) { | ||
logger.trace("onCommandFromItem {}", command.toString()); | ||
// no-op | ||
} | ||
|
||
@Override | ||
public void onStateUpdateFromHandler(State state) { | ||
logger.trace("onStateUpdateFromHandler {}", state.toString()); | ||
// no-op | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
108 changes: 108 additions & 0 deletions
108
...inding.knx/src/main/java/org/openhab/binding/knx/internal/profiles/KNXProfileFactory.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,108 @@ | ||
/** | ||
* Copyright (c) 2010-2024 Contributors to the openHAB project | ||
* | ||
* See the NOTICE file(s) distributed with this work for additional | ||
* information. | ||
* | ||
* This program and the accompanying materials are made available under the | ||
* terms of the Eclipse Public License 2.0 which is available at | ||
* http://www.eclipse.org/legal/epl-2.0 | ||
* | ||
* SPDX-License-Identifier: EPL-2.0 | ||
*/ | ||
package org.openhab.binding.knx.internal.profiles; | ||
|
||
import java.util.Collection; | ||
import java.util.Locale; | ||
import java.util.stream.Collectors; | ||
import java.util.stream.Stream; | ||
|
||
import org.eclipse.jdt.annotation.NonNullByDefault; | ||
import org.eclipse.jdt.annotation.Nullable; | ||
import org.openhab.binding.knx.internal.KNXBindingConstants; | ||
import org.openhab.core.library.CoreItemFactory; | ||
import org.openhab.core.thing.Channel; | ||
import org.openhab.core.thing.ThingRegistry; | ||
import org.openhab.core.thing.profiles.Profile; | ||
import org.openhab.core.thing.profiles.ProfileAdvisor; | ||
import org.openhab.core.thing.profiles.ProfileCallback; | ||
import org.openhab.core.thing.profiles.ProfileContext; | ||
import org.openhab.core.thing.profiles.ProfileFactory; | ||
import org.openhab.core.thing.profiles.ProfileType; | ||
import org.openhab.core.thing.profiles.ProfileTypeBuilder; | ||
import org.openhab.core.thing.profiles.ProfileTypeProvider; | ||
import org.openhab.core.thing.profiles.ProfileTypeUID; | ||
import org.openhab.core.thing.profiles.StateProfileType; | ||
import org.openhab.core.thing.type.ChannelType; | ||
import org.openhab.core.thing.type.ChannelTypeUID; | ||
import org.osgi.service.component.annotations.Activate; | ||
import org.osgi.service.component.annotations.Component; | ||
import org.osgi.service.component.annotations.Reference; | ||
|
||
/** | ||
* This class defines and provides specialized KNX profiles. | ||
* | ||
* @author Holger Friedrich - Initial contribution | ||
* | ||
*/ | ||
@NonNullByDefault | ||
@Component | ||
public class KNXProfileFactory implements ProfileFactory, ProfileAdvisor, ProfileTypeProvider { | ||
|
||
static final ProfileTypeUID UID_CONTACT_CONTROL = new ProfileTypeUID(KNXBindingConstants.BINDING_ID, | ||
"contact-control"); | ||
|
||
private static final StateProfileType CONTACT_CONTROL_TYPE = ProfileTypeBuilder | ||
.newState(UID_CONTACT_CONTROL, "contact-control").withSupportedItemTypes(CoreItemFactory.CONTACT) | ||
.withSupportedChannelTypeUIDs(KNXBindingConstants.CHANNEL_CONTACT_CONTROL_UID).build(); | ||
|
||
private final ThingRegistry thingRegistry; | ||
|
||
@Activate | ||
public KNXProfileFactory(@Reference ThingRegistry thingRegistry) { | ||
this.thingRegistry = thingRegistry; | ||
} | ||
|
||
@Override | ||
public Collection<ProfileTypeUID> getSupportedProfileTypeUIDs() { | ||
return Stream.of(UID_CONTACT_CONTROL).collect(Collectors.toSet()); | ||
} | ||
|
||
@Override | ||
public Collection<ProfileType> getProfileTypes(@Nullable Locale locale) { | ||
return Stream.of(CONTACT_CONTROL_TYPE).collect(Collectors.toSet()); | ||
} | ||
|
||
@Override | ||
public @Nullable ProfileTypeUID getSuggestedProfileTypeUID(Channel channel, @Nullable String itemType) { | ||
return getSuggestedProfileTypeUID(channel.getChannelTypeUID(), itemType); | ||
} | ||
|
||
@Override | ||
public @Nullable ProfileTypeUID getSuggestedProfileTypeUID(ChannelType channelType, @Nullable String itemType) { | ||
return getSuggestedProfileTypeUID(channelType.getUID(), itemType); | ||
} | ||
|
||
private @Nullable ProfileTypeUID getSuggestedProfileTypeUID(@Nullable ChannelTypeUID channelTypeUID, | ||
@Nullable String itemType) { | ||
if (KNXBindingConstants.CHANNEL_CONTACT_CONTROL_UID.equals(channelTypeUID) && itemType != null) { | ||
switch (itemType) { | ||
case CoreItemFactory.CONTACT: | ||
return UID_CONTACT_CONTROL; | ||
default: | ||
return null; | ||
} | ||
} | ||
return null; | ||
} | ||
|
||
@Override | ||
public @Nullable Profile createProfile(ProfileTypeUID profileTypeUID, ProfileCallback callback, | ||
ProfileContext profileContext) { | ||
if (UID_CONTACT_CONTROL.equals(profileTypeUID)) { | ||
return new KNXContactControlProfile(callback, thingRegistry); | ||
} else { | ||
return null; | ||
} | ||
} | ||
} |