Search in sources :

Example 1 with PacketFieldSpec

use of de.resol.vbus.Specification.PacketFieldSpec in project openhab-addons by openhab.

the class ResolThingHandler method packetReceived.

@Override
protected void packetReceived(Specification spec, Language lang, Packet packet) {
    PacketFieldValue[] pfvs = spec.getPacketFieldValuesForHeaders(new Packet[] { packet });
    for (PacketFieldValue pfv : pfvs) {
        logger.trace("Id: {}, Name: {}, Raw: {}, Text: {}", pfv.getPacketFieldId(), pfv.getName(lang), pfv.getRawValueDouble(), pfv.formatTextValue(null, Locale.getDefault()));
        // use English name as channel
        String channelId = pfv.getName();
        channelId = channelId.replace(" [", "-");
        channelId = channelId.replace("]", "");
        channelId = channelId.replace("(", "-");
        channelId = channelId.replace(")", "");
        channelId = channelId.replace(" #", "-");
        channelId = channelId.replaceAll("[^A-Za-z0-9_-]+", "_");
        channelId = channelId.toLowerCase(Locale.ENGLISH);
        ChannelTypeUID channelTypeUID;
        if (pfv.getPacketFieldSpec().getUnit().getUnitId() >= 0) {
            channelTypeUID = new ChannelTypeUID(ResolBindingConstants.BINDING_ID, pfv.getPacketFieldSpec().getUnit().getUnitCodeText());
        } else if (pfv.getPacketFieldSpec().getType() == SpecificationFile.Type.DateTime) {
            channelTypeUID = new ChannelTypeUID(ResolBindingConstants.BINDING_ID, "datetime");
        } else if (pfv.getPacketFieldSpec().getType() == SpecificationFile.Type.WeekTime) {
            channelTypeUID = new ChannelTypeUID(ResolBindingConstants.BINDING_ID, "weektime");
        } else if (pfv.getPacketFieldSpec().getType() == SpecificationFile.Type.Time) {
            channelTypeUID = new ChannelTypeUID(ResolBindingConstants.BINDING_ID, "time");
        } else {
            /* used for enums and the numeric types without unit */
            channelTypeUID = new ChannelTypeUID(ResolBindingConstants.BINDING_ID, "None");
        }
        String acceptedItemType;
        Thing thing = getThing();
        switch(pfv.getPacketFieldSpec().getType()) {
            case WeekTime:
            case DateTime:
                acceptedItemType = "DateTime";
                break;
            case Number:
                acceptedItemType = ResolChannelTypeProvider.itemTypeForUnit(pfv.getPacketFieldSpec().getUnit());
                break;
            case Time:
            default:
                acceptedItemType = "String";
                break;
        }
        Channel a = thing.getChannel(channelId);
        if (a == null) {
            /* channel doesn't exit, let's create it */
            ThingBuilder thingBuilder = editThing();
            ChannelUID channelUID = new ChannelUID(thing.getUID(), channelId);
            if (pfv.getEnumVariant() != null) {
                /* create a state option channel */
                List<StateOption> options = new ArrayList<>();
                PacketFieldSpec ff = pfv.getPacketFieldSpec();
                Enum e = ff.getEnum();
                for (long l : e.getValues()) {
                    EnumVariant v = e.getEnumVariantForValue(l);
                    options.add(new StateOption(Long.toString(l), v.getText(lang)));
                }
                stateDescriptionProvider.setStateOptions(channelUID, options);
                Channel channel = ChannelBuilder.create(channelUID, "Number").withType(channelTypeUID).withLabel(pfv.getName(lang)).build();
                thingBuilder.withChannel(channel).withLabel(thing.getLabel());
                updateThing(thingBuilder.build());
            } else if ("DateTime".equals(acceptedItemType)) {
                /* a date channel */
                Channel channel = ChannelBuilder.create(channelUID, acceptedItemType).withType(channelTypeUID).withLabel(pfv.getName(lang)).build();
                thingBuilder.withChannel(channel).withLabel(thing.getLabel());
                updateThing(thingBuilder.build());
            } else if ("String".equals(acceptedItemType)) {
                /* a string channel */
                Channel channel = ChannelBuilder.create(channelUID, "String").withType(channelTypeUID).withLabel(pfv.getName(lang)).build();
                thingBuilder.withChannel(channel).withLabel(thing.getLabel());
                updateThing(thingBuilder.build());
            } else if (pfv.getRawValueDouble() != null) {
                /* a number channel */
                Channel channel = ChannelBuilder.create(channelUID, acceptedItemType).withType(channelTypeUID).withLabel(pfv.getName(lang)).build();
                thingBuilder.withChannel(channel).withLabel(thing.getLabel());
                updateThing(thingBuilder.build());
            } else {
                /* a string channel */
                Channel channel = ChannelBuilder.create(channelUID, "String").withType(channelTypeUID).withLabel(pfv.getName(lang)).build();
                thingBuilder.withChannel(channel).withLabel(thing.getLabel());
                updateThing(thingBuilder.build());
            }
            logger.debug("Creating channel: {}", channelUID);
        }
        if (pfv.getEnumVariant() != null) {
            /* update the enum / State channel */
            this.updateState(channelId, new StringType(Long.toString(pfv.getRawValueLong())));
        } else {
            switch(pfv.getPacketFieldSpec().getType()) {
                case Number:
                    Double dd = pfv.getRawValueDouble();
                    if (dd != null) {
                        if (!isSpecialValue(dd)) {
                            /* only set the value if no error occurred */
                            String str = pfv.formatText();
                            if (str.endsWith("RH")) {
                                /* unit %RH for relative humidity is not known in openHAB UoM, so we remove it */
                                str = str.substring(0, str.length() - 2);
                            }
                            if (str.endsWith("Ω")) {
                                QuantityType<?> q = new QuantityType<>(dd, Units.OHM);
                                this.updateState(channelId, q);
                            } else {
                                try {
                                    QuantityType<?> q = new QuantityType<>(str);
                                    this.updateState(channelId, q);
                                } catch (IllegalArgumentException e) {
                                    logger.debug("unit of '{}' unknown in openHAB", str);
                                    QuantityType<?> q = new QuantityType<>(dd.toString());
                                    this.updateState(channelId, q);
                                }
                            }
                        }
                    }
                    /*
                         * else {
                         * field not available in this packet, e. g. old firmware version not (yet) transmitting it
                         * }
                         */
                    break;
                case Time:
                    synchronized (TIME_FORMAT) {
                        this.updateState(channelId, new StringType(TIME_FORMAT.format(pfv.getRawValueDate())));
                    }
                    break;
                case WeekTime:
                    synchronized (WEEK_FORMAT) {
                        DateTimeType d = new DateTimeType(WEEK_FORMAT.format(pfv.getRawValueDate()));
                        this.updateState(channelId, d);
                    }
                    break;
                case DateTime:
                    synchronized (DATE_FORMAT) {
                        DateTimeType d = new DateTimeType(DATE_FORMAT.format(pfv.getRawValueDate()));
                        this.updateState(channelId, d);
                    }
                    break;
                default:
                    Bridge b = getBridge();
                    if (b != null) {
                        ResolBridgeHandler handler = (ResolBridgeHandler) b.getHandler();
                        String value;
                        if (handler != null) {
                            value = pfv.formatTextValue(pfv.getPacketFieldSpec().getUnit(), handler.getLocale());
                        } else {
                            value = pfv.formatTextValue(pfv.getPacketFieldSpec().getUnit(), Locale.getDefault());
                        }
                        try {
                            QuantityType<?> q = new QuantityType<>(value);
                            this.updateState(channelId, q);
                        } catch (IllegalArgumentException e) {
                            this.updateState(channelId, new StringType(value));
                            logger.debug("unit of '{}' unknown in openHAB, using string", value);
                        }
                    }
            }
        }
    }
}
Also used : Enum(de.resol.vbus.SpecificationFile.Enum) ThingBuilder(org.openhab.core.thing.binding.builder.ThingBuilder) StringType(org.openhab.core.library.types.StringType) Channel(org.openhab.core.thing.Channel) ArrayList(java.util.ArrayList) EnumVariant(de.resol.vbus.SpecificationFile.EnumVariant) StateOption(org.openhab.core.types.StateOption) PacketFieldSpec(de.resol.vbus.Specification.PacketFieldSpec) DateTimeType(org.openhab.core.library.types.DateTimeType) ChannelTypeUID(org.openhab.core.thing.type.ChannelTypeUID) QuantityType(org.openhab.core.library.types.QuantityType) ChannelUID(org.openhab.core.thing.ChannelUID) PacketFieldValue(de.resol.vbus.Specification.PacketFieldValue) Thing(org.openhab.core.thing.Thing) Bridge(org.openhab.core.thing.Bridge)

Aggregations

PacketFieldSpec (de.resol.vbus.Specification.PacketFieldSpec)1 PacketFieldValue (de.resol.vbus.Specification.PacketFieldValue)1 Enum (de.resol.vbus.SpecificationFile.Enum)1 EnumVariant (de.resol.vbus.SpecificationFile.EnumVariant)1 ArrayList (java.util.ArrayList)1 DateTimeType (org.openhab.core.library.types.DateTimeType)1 QuantityType (org.openhab.core.library.types.QuantityType)1 StringType (org.openhab.core.library.types.StringType)1 Bridge (org.openhab.core.thing.Bridge)1 Channel (org.openhab.core.thing.Channel)1 ChannelUID (org.openhab.core.thing.ChannelUID)1 Thing (org.openhab.core.thing.Thing)1 ThingBuilder (org.openhab.core.thing.binding.builder.ThingBuilder)1 ChannelTypeUID (org.openhab.core.thing.type.ChannelTypeUID)1 StateOption (org.openhab.core.types.StateOption)1