2
0
mirror of https://github.com/fhem/fhem-mirror.git synced 2025-03-03 23:06:37 +00:00
git-svn-id: https://svn.fhem.de/fhem/trunk@13056 2b470e98-0d58-463d-a4d8-8e2adae1ed80
This commit is contained in:
zap 2017-01-13 16:24:52 +00:00
parent f44b3f8128
commit e7ab37432d
4 changed files with 1203 additions and 711 deletions

File diff suppressed because it is too large Load Diff

View File

@ -4,13 +4,14 @@
# #
# $Id$ # $Id$
# #
# Version 3.6 # Version 3.7
# #
# (c) 2016 zap (zap01 <at> t-online <dot> de) # (c) 2016 zap (zap01 <at> t-online <dot> de)
# #
################################################################ ################################################################
# #
# define <name> HMCCUCHN <ccudev> [readonly] # define <name> HMCCUCHN <ccudev> [readonly] [defaults]
# [iodev=<iodevname>]
# #
# set <name> config <parameter>=<value> [...] # set <name> config <parameter>=<value> [...]
# set <name> control <value> # set <name> control <value>
@ -32,7 +33,7 @@
# get <name> update # get <name> update
# #
# attr <name> ccuackstate { 0 | 1 } # attr <name> ccuackstate { 0 | 1 }
# attr <name> ccuflags { nochn0, trace } # attr <name> ccuflags { altread, nochn0, trace }
# attr <name> ccuget { State | Value } # attr <name> ccuget { State | Value }
# attr <name> ccureadings { 0 | 1 } # attr <name> ccureadings { 0 | 1 }
# attr <name> ccureadingfilter <datapoint-expr> # attr <name> ccureadingfilter <datapoint-expr>
@ -41,6 +42,7 @@
# attr <name> ccuverify { 0 | 1 | 2 } # attr <name> ccuverify { 0 | 1 | 2 }
# attr <name> controldatapoint <datapoint> # attr <name> controldatapoint <datapoint>
# attr <name> disable { 0 | 1 } # attr <name> disable { 0 | 1 }
# attr <name> hmstatevals <subst-rule>[;...]
# attr <name> statedatapoint <datapoint> # attr <name> statedatapoint <datapoint>
# attr <name> statevals <text1>:<subtext1>[,...] # attr <name> statevals <text1>:<subtext1>[,...]
# attr <name> substexcl <reading-expr> # attr <name> substexcl <reading-expr>
@ -64,9 +66,9 @@ sub HMCCUCHN_Get ($@);
sub HMCCUCHN_Attr ($@); sub HMCCUCHN_Attr ($@);
sub HMCCUCHN_SetError ($$); sub HMCCUCHN_SetError ($$);
##################################### ##################################################
# Initialize module # Initialize module
##################################### ##################################################
sub HMCCUCHN_Initialize ($) sub HMCCUCHN_Initialize ($)
{ {
@ -76,64 +78,52 @@ sub HMCCUCHN_Initialize ($)
$hash->{SetFn} = "HMCCUCHN_Set"; $hash->{SetFn} = "HMCCUCHN_Set";
$hash->{GetFn} = "HMCCUCHN_Get"; $hash->{GetFn} = "HMCCUCHN_Get";
$hash->{AttrFn} = "HMCCUCHN_Attr"; $hash->{AttrFn} = "HMCCUCHN_Attr";
$hash->{parseParams} = 1;
$hash->{AttrList} = "IODev ccuackstate:0,1 ccuflags:multiple-strict,nochn0,trace ccureadingfilter ccureadingformat:name,namelc,address,addresslc,datapoint,datapointlc ccureadingname ccureadings:0,1 ccuscaleval ccuverify:0,1,2 ccuget:State,Value controldatapoint disable:0,1 statedatapoint statevals substitute:textField-long substexcl stripnumber ". $readingFnAttributes; $hash->{AttrList} = "IODev ccuackstate:0,1 ccuflags:multiple-strict,altread,nochn0,trace ccureadingfilter ccureadingformat:name,namelc,address,addresslc,datapoint,datapointlc ccureadingname ccureadings:0,1 ccuscaleval ccuverify:0,1,2 ccuget:State,Value controldatapoint disable:0,1 hmstatevals statedatapoint statevals substitute:textField-long substexcl stripnumber ". $readingFnAttributes;
} }
##################################### ##################################################
# Define device # Define device
##################################### ##################################################
sub HMCCUCHN_Define ($@) sub HMCCUCHN_Define ($@)
{ {
my ($hash, $def) = @_; my ($hash, $a, $h) = @_;
my $name = $hash->{NAME}; my $name = $hash->{NAME};
my @a = split("[ \t][ \t]*", $def);
my $usage = "Usage: define $name HMCCUCHN {device} ['readonly'] ['defaults']"; my $usage = "Usage: define $name HMCCUCHN {device} ['readonly'] ['defaults'] [iodev={iodevname}]";
return $usage if (@a < 3); return $usage if (@$a < 3);
my $devname = shift @a; my $devname = shift @$a;
my $devtype = shift @a; my $devtype = shift @$a;
my $devspec = shift @a; my $devspec = shift @$a;
return "Invalid or unknown CCU channel name or address" if (! HMCCU_IsValidDevice ($devspec)); my $hmccu_hash = undef;
if (HMCCU_IsChnAddr ($devspec, 1)) { # IO device can be set by command line parameter iodev
# CCU Channel address with interface if (exists ($h->{iodev})) {
$hash->{ccuif} = $1; $hmccu_hash = $defs{$h->{iodev}} if (exists ($defs{$h->{iodev}}));
$hash->{ccuaddr} = $2;
$hash->{ccuname} = HMCCU_GetChannelName ($hash->{ccuaddr}, '');
return "CCU device name not found for channel address $devspec" if ($hash->{ccuname} eq '');
}
elsif (HMCCU_IsChnAddr ($devspec, 0)) {
# CCU Channel address
$hash->{ccuaddr} = $devspec;
$hash->{ccuif} = HMCCU_GetDeviceInterface ($hash->{ccuaddr}, 'BidCos-RF');
$hash->{ccuname} = HMCCU_GetChannelName ($devspec, '');
return "CCU device name not found for channel address $devspec" if ($hash->{ccuname} eq '');
}
else {
# CCU Channel name
$hash->{ccuname} = $devspec;
my ($add, $chn) = HMCCU_GetAddress ($devspec, '', '');
return "Channel address not found for channel name $devspec" if ($add eq '' || $chn eq '');
$hash->{ccuaddr} = $add.':'.$chn;
$hash->{ccuif} = HMCCU_GetDeviceInterface ($hash->{ccuaddr}, 'BidCos-RF');
} }
$hmccu_hash = HMCCU_FindIODevice ($devspec) if (!defined ($hmccu_hash));
return "Cannot detect IO device" if (!defined ($hmccu_hash));
$hash->{ccutype} = HMCCU_GetDeviceType ($hash->{ccuaddr}, ''); return "Invalid or unknown CCU channel name or address"
if (! HMCCU_IsValidDevice ($hmccu_hash, $devspec));
my ($di, $da, $dn, $dt, $dc) = HMCCU_GetCCUDeviceParam ($hmccu_hash, $devspec);
return "Invalid or unknown CCU device name or address" if (!defined ($da));
$hash->{ccuif} = $di;
$hash->{ccuaddr} = $da;
$hash->{ccuname} = $dn;
$hash->{ccutype} = $dt;
$hash->{channels} = 1; $hash->{channels} = 1;
$hash->{statevals} = 'devstate'; $hash->{statevals} = 'devstate';
# my $arg = shift @a;
# if (defined ($arg) && $arg eq 'readonly') {
# $hash->{statevals} = $arg;
# }
# Parse optional command line parameters # Parse optional command line parameters
my $n = 0; my $n = 0;
my $arg = shift @a; my $arg = shift @$a;
while (defined ($arg)) { while (defined ($arg)) {
return $usage if ($n == 3); return $usage if ($n == 3);
if ($arg eq 'readonly') { if ($arg eq 'readonly') {
@ -146,11 +136,11 @@ sub HMCCUCHN_Define ($@)
return $usage; return $usage;
} }
$n++; $n++;
$arg = shift @a; $arg = shift @$a;
} }
# Inform HMCCU device about client device # Inform HMCCU device about client device
AssignIoPort ($hash); AssignIoPort ($hash, $hmccu_hash->{NAME});
readingsSingleUpdate ($hash, "state", "Initialized", 1); readingsSingleUpdate ($hash, "state", "Initialized", 1);
$hash->{ccudevstate} = 'Active'; $hash->{ccudevstate} = 'Active';
@ -198,16 +188,15 @@ sub HMCCUCHN_Attr ($@)
sub HMCCUCHN_Set ($@) sub HMCCUCHN_Set ($@)
{ {
my ($hash, @a) = @_; my ($hash, $a, $h) = @_;
my $name = shift @a; my $name = shift @$a;
my $opt = shift @a; my $opt = shift @$a;
my $rocmds = "clear config defaults:noArg"; my $rocmds = "clear config defaults:noArg";
return HMCCU_SetError ($hash, -3) if (!defined ($hash->{IODev})); return HMCCU_SetError ($hash, -3) if (!defined ($hash->{IODev}));
return undef return undef if ($hash->{statevals} eq 'readonly' && $opt ne '?' &&
if ($hash->{statevals} eq 'readonly' && $opt ne '?' && $opt ne 'clear' && $opt ne 'config' && $opt !~ /^(clear|config|defaults)$/);
$opt ne 'defaults');
my $disable = AttrVal ($name, "disable", 0); my $disable = AttrVal ($name, "disable", 0);
return undef if ($disable == 1); return undef if ($disable == 1);
@ -228,8 +217,8 @@ sub HMCCUCHN_Set ($@)
my $rc; my $rc;
if ($opt eq 'datapoint') { if ($opt eq 'datapoint') {
my $objname = shift @a; my $objname = shift @$a;
my $objvalue = shift @a; my $objvalue = shift @$a;
return HMCCU_SetError ($hash, "Usage: set $name datapoint {datapoint} {value}") return HMCCU_SetError ($hash, "Usage: set $name datapoint {datapoint} {value}")
if (!defined ($objname) || !defined ($objvalue)); if (!defined ($objname) || !defined ($objvalue));
@ -249,7 +238,7 @@ sub HMCCUCHN_Set ($@)
elsif ($opt eq 'control') { elsif ($opt eq 'control') {
return HMCCU_SetError ($hash, -14) if ($cd eq ''); return HMCCU_SetError ($hash, -14) if ($cd eq '');
return HMCCU_SetError ($hash, -8) if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $cc, $cd, 2)); return HMCCU_SetError ($hash, -8) if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $cc, $cd, 2));
my $objvalue = shift @a; my $objvalue = shift @$a;
return HMCCU_SetError ($hash, "Usage: set $name control {value}") if (!defined ($objvalue)); return HMCCU_SetError ($hash, "Usage: set $name control {value}") if (!defined ($objvalue));
$objvalue =~ s/\\_/%20/g; $objvalue =~ s/\\_/%20/g;
@ -264,7 +253,7 @@ sub HMCCUCHN_Set ($@)
} }
elsif ($opt =~ /^($hash->{statevals})$/) { elsif ($opt =~ /^($hash->{statevals})$/) {
my $cmd = $1; my $cmd = $1;
my $objvalue = ($cmd ne 'devstate') ? $cmd : shift @a; my $objvalue = ($cmd ne 'devstate') ? $cmd : shift @$a;
return HMCCU_SetError ($hash, -13) if ($sd eq ''); return HMCCU_SetError ($hash, -13) if ($sd eq '');
return HMCCU_SetError ($hash, -8) return HMCCU_SetError ($hash, -8)
@ -324,12 +313,12 @@ sub HMCCUCHN_Set ($@)
if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $ccuaddr, "LEVEL", 2)); if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $ccuaddr, "LEVEL", 2));
my $objname = ''; my $objname = '';
my $objvalue = shift @a; my $objvalue = shift @$a;
return HMCCU_SetError ($hash, "Usage: set $name pct {value} [{ontime} [{ramptime}]]") return HMCCU_SetError ($hash, "Usage: set $name pct {value} [{ontime} [{ramptime}]]")
if (!defined ($objvalue)); if (!defined ($objvalue));
my $timespec = shift @a; my $timespec = shift @$a;
my $ramptime = shift @a; my $ramptime = shift @$a;
# Set on time # Set on time
if (defined ($timespec)) { if (defined ($timespec)) {
@ -379,7 +368,7 @@ sub HMCCUCHN_Set ($@)
return HMCCU_SetError ($hash, "Can't find ON_TIME datapoint for device type") return HMCCU_SetError ($hash, "Can't find ON_TIME datapoint for device type")
if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $ccuaddr, "ON_TIME", 2)); if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $ccuaddr, "ON_TIME", 2));
my $timespec = shift @a; my $timespec = shift @$a;
return HMCCU_SetError ($hash, "Usage: set $name $opt {ontime-spec}") return HMCCU_SetError ($hash, "Usage: set $name $opt {ontime-spec}")
if (!defined ($timespec)); if (!defined ($timespec));
@ -409,7 +398,7 @@ sub HMCCUCHN_Set ($@)
return undef; return undef;
} }
elsif ($opt eq 'clear') { elsif ($opt eq 'clear') {
my $rnexp = shift @a; my $rnexp = shift @$a;
$rnexp = '.*' if (!defined ($rnexp)); $rnexp = '.*' if (!defined ($rnexp));
my @readlist = keys %{$hash->{READINGS}}; my @readlist = keys %{$hash->{READINGS}};
foreach my $rd (@readlist) { foreach my $rd (@readlist) {
@ -417,9 +406,10 @@ sub HMCCUCHN_Set ($@)
} }
} }
elsif ($opt eq 'config') { elsif ($opt eq 'config') {
return HMCCU_SetError ($hash, "Usage: set $name config {parameter}={value} [...]") if (@a < 1);; return HMCCU_SetError ($hash, "Usage: set $name config {parameter}={value} [...]")
if (scalar (keys %{$h}) < 1);
my $rc = HMCCU_RPCSetConfig ($hash, $ccuaddr, \@a); my $rc = HMCCU_RPCSetConfig ($hash, $ccuaddr, $h);
return HMCCU_SetError ($hash, $rc) if ($rc < 0); return HMCCU_SetError ($hash, $rc) if ($rc < 0);
HMCCU_SetState ($hash, "OK"); HMCCU_SetState ($hash, "OK");
return undef; return undef;
@ -459,9 +449,9 @@ sub HMCCUCHN_Set ($@)
sub HMCCUCHN_Get ($@) sub HMCCUCHN_Get ($@)
{ {
my ($hash, @a) = @_; my ($hash, $a, $h) = @_;
my $name = shift @a; my $name = shift @$a;
my $opt = shift @a; my $opt = shift @$a;
return HMCCU_SetError ($hash, -3) if (!defined ($hash->{IODev})); return HMCCU_SetError ($hash, -3) if (!defined ($hash->{IODev}));
@ -494,7 +484,7 @@ sub HMCCUCHN_Get ($@)
return $ccureadings ? undef : $result; return $ccureadings ? undef : $result;
} }
elsif ($opt eq 'datapoint') { elsif ($opt eq 'datapoint') {
my $objname = shift @a; my $objname = shift @$a;
return HMCCU_SetError ($hash, "Usage: get $name datapoint {datapoint}") return HMCCU_SetError ($hash, "Usage: get $name datapoint {datapoint}")
if (!defined ($objname)); if (!defined ($objname));
@ -507,7 +497,7 @@ sub HMCCUCHN_Get ($@)
return $ccureadings ? undef : $result; return $ccureadings ? undef : $result;
} }
elsif ($opt eq 'update') { elsif ($opt eq 'update') {
my $ccuget = shift @a; my $ccuget = shift @$a;
$ccuget = 'Attr' if (!defined ($ccuget)); $ccuget = 'Attr' if (!defined ($ccuget));
if ($ccuget !~ /^(Attr|State|Value)$/) { if ($ccuget !~ /^(Attr|State|Value)$/) {
return HMCCU_SetError ($hash, "Usage: get $name update [{'State'|'Value'}]"); return HMCCU_SetError ($hash, "Usage: get $name update [{'State'|'Value'}]");
@ -518,7 +508,7 @@ sub HMCCUCHN_Get ($@)
} }
elsif ($opt eq 'config') { elsif ($opt eq 'config') {
my $ccuobj = $ccuaddr; my $ccuobj = $ccuaddr;
my $par = shift @a; my $par = shift @$a;
$par = '.*' if (!defined ($par)); $par = '.*' if (!defined ($par));
my ($rc, $res) = HMCCU_RPCGetConfig ($hash, $ccuobj, "getParamset", $par); my ($rc, $res) = HMCCU_RPCGetConfig ($hash, $ccuobj, "getParamset", $par);
@ -527,7 +517,7 @@ sub HMCCUCHN_Get ($@)
} }
elsif ($opt eq 'configlist') { elsif ($opt eq 'configlist') {
my $ccuobj = $ccuaddr; my $ccuobj = $ccuaddr;
my $par = shift @a; my $par = shift @$a;
$par = '.*' if (!defined ($par)); $par = '.*' if (!defined ($par));
my ($rc, $res) = HMCCU_RPCGetConfig ($hash, $ccuobj, "listParamset", $par); my ($rc, $res) = HMCCU_RPCGetConfig ($hash, $ccuobj, "listParamset", $par);
@ -607,7 +597,7 @@ sub HMCCUCHN_SetError ($$)
<b>Define</b><br/><br/> <b>Define</b><br/><br/>
<ul> <ul>
<code>define &lt;name&gt; HMCCUCHN {&lt;channel-name&gt; | &lt;channel-address&gt;} <code>define &lt;name&gt; HMCCUCHN {&lt;channel-name&gt; | &lt;channel-address&gt;}
[readonly] [defaults]</code> [readonly] [defaults] [iodev=&lt;iodev-name&gt;]</code>
<br/><br/> <br/><br/>
If option 'readonly' is specified no set command will be available. With option 'defaults' If option 'readonly' is specified no set command will be available. With option 'defaults'
some default attributes depending on CCU device type will be set. Default attributes are only some default attributes depending on CCU device type will be set. Default attributes are only
@ -756,8 +746,9 @@ sub HMCCUCHN_SetError ($$)
If set to 1 state will be set to result of command (i.e. 'OK'). Otherwise state is only If set to 1 state will be set to result of command (i.e. 'OK'). Otherwise state is only
updated if value of state datapoint has changed. updated if value of state datapoint has changed.
</li><br/> </li><br/>
<li><b>ccuflags {nochn0, trace}</b><br/> <li><b>ccuflags {altread, nochn0, trace}</b><br/>
Control behaviour of device:<br/> Control behaviour of device:<br/>
altread: Create additional CUL_HM style readings.<br/>
nochn0: Prevent update of status channel 0 datapoints / readings.<br/> nochn0: Prevent update of status channel 0 datapoints / readings.<br/>
trace: Write log file information for operations related to this device. trace: Write log file information for operations related to this device.
</li><br/> </li><br/>
@ -773,6 +764,9 @@ sub HMCCUCHN_SetError ($$)
Only datapoints matching specified expression are stored as readings.<br/> Only datapoints matching specified expression are stored as readings.<br/>
Syntax for <i>filter-rule</i> is: [&lt;channel-name&gt;!]&lt;RegExp&gt;<br/> Syntax for <i>filter-rule</i> is: [&lt;channel-name&gt;!]&lt;RegExp&gt;<br/>
If <i>channel-name</i> is specified the following rule applies only to this channel. If <i>channel-name</i> is specified the following rule applies only to this channel.
If ccuflag 'nohmstate' is not set in I/O device datapoints UNREACH, LOWBAT, LOW_BAT,
ERROR.* and FAULT.* are always stored as readings and must not be specified in this
attribute.
</li><br/> </li><br/>
<li><b>ccureadingformat {address[lc] | name[lc] | datapoint[lc]}</b><br/> <li><b>ccureadingformat {address[lc] | name[lc] | datapoint[lc]}</b><br/>
Set format of reading names. Default is 'name'. If set to 'address' format of reading names Set format of reading names. Default is 'name'. If set to 'address' format of reading names
@ -780,8 +774,25 @@ sub HMCCUCHN_SetError ($$)
channel-name.datapoint. If set to 'datapoint' format is channel-number.datapoint. With channel-name.datapoint. If set to 'datapoint' format is channel-number.datapoint. With
suffix 'lc' reading names are converted to lowercase. suffix 'lc' reading names are converted to lowercase.
</li><br/> </li><br/>
<li><b>ccureadingname &lt;old-readingname-expr&gt;:&lt;new-readingname&gt;[,...]</b><br/> <li><b>ccureadingname &lt;old-readingname-expr&gt;:[+]&lt;new-readingname&gt;[,...]</b><br/>
Set alternative reading names. Set alternative or additional reading names or group readings. Only part of old reading
name matching <i>old-readingname-exptr</i> is substituted by <i>new-readingname</i>.
If <i>new-readingname</i> is preceded by '+' an additional reading is created. If
<i>old-readingname-expr</i> matches more than one reading the values of these readings
are stored in one reading. This makes sense only in some cases, i.e. if a device has
several pressed_short datapoints and a reading should contain a value if any button
is pressed.<br/><br/>
Examples:<br/>
<code>
# Rename readings 0.LOWBAT and 0.LOW_BAT as battery<br/>
attr mydev ccureadingname 0.(LOWBAT|LOW_BAT):battery<br/>
# Add reading battery as a copy of readings LOWBAT and LOW_BAT.<br/>
# Rename reading 4.SET_TEMPERATURE as desired-temp<br/>
attr mydev ccureadingname 0.(LOWBAT|LOW_BAT):+battery,1.SET_TEMPERATURE:desired-temp<br/>
# Store values of readings n.PRESS_SHORT in new reading pressed.<br/>
# Value of pressed is 1/true if any button is pressed<br/>
attr mydev ccureadingname [1-4].PRESSED_SHORT:+pressed
</code>
</li><br/> </li><br/>
<li><b>ccuscaleval &lt;datapoint&gt;:&lt;factor&gt;[,...]</b><br/> <li><b>ccuscaleval &lt;datapoint&gt;:&lt;factor&gt;[,...]</b><br/>
<b>ccuscaleval &lt;[!]datapoint&gt;:&lt;min&gt;:&lt;max&gt;:&lt;minn&gt;:&lt;maxn&gt;[,...] <b>ccuscaleval &lt;[!]datapoint&gt;:&lt;min&gt;:&lt;max&gt;:&lt;minn&gt;:&lt;maxn&gt;[,...]
@ -815,6 +826,13 @@ sub HMCCUCHN_SetError ($$)
</li><br/> </li><br/>
<li><b>disable {<u>0</u> | 1}</b><br/> <li><b>disable {<u>0</u> | 1}</b><br/>
Disable client device. Disable client device.
</li><br/>
<li><b>hmstatevals &lt;subst-rule&gt;[;...]</b><br/>
Define substitution rules for datapoint values stored in reading 'hmstate'. Parameter
<i>subst-rule</i> is equal to attribute 'substitute'. Default substitution rule is
LOWBAT,LOW_BAT!1:battery_low;UNREACH!1:unreachable. The substitution rule must
contain only error conditions because 'hmstate' contains only error conditions or
the 'state' value.
</li><br/> </li><br/>
<li><b>statedatapoint &lt;datapoint&gt;</b><br/> <li><b>statedatapoint &lt;datapoint&gt;</b><br/>
Set state datapoint used by some commands like 'set devstate'. Set state datapoint used by some commands like 'set devstate'.

View File

@ -4,14 +4,14 @@
# #
# $Id$ # $Id$
# #
# Version 3.6 # Version 3.7
# #
# (c) 2016 zap (zap01 <at> t-online <dot> de) # (c) 2016 zap (zap01 <at> t-online <dot> de)
# #
##################################################################### #####################################################################
# #
# define <name> HMCCUDEV {<ccudev>|virtual} [<statechannel>] [readonly] [defaults] # define <name> HMCCUDEV {<ccudev>|virtual} [<statechannel>] [readonly] [defaults]
# [{group={<device>|<channel>}[,...]|groupexp=<regexp>}] # [{group={<device>|<channel>}[,...]|groupexp=<regexp>}] [iodev=<iodevname>]
# #
# set <name> clear [<regexp>] # set <name> clear [<regexp>]
# set <name> config [<channel-number>] <parameter>=<value> [...] # set <name> config [<channel-number>] <parameter>=<value> [...]
@ -34,7 +34,7 @@
# get <name> update # get <name> update
# #
# attr <name> ccuackstate { 0 | 1 } # attr <name> ccuackstate { 0 | 1 }
# attr <name> ccuflags { nochn0, trace } # attr <name> ccuflags { altread, nochn0, trace }
# attr <name> ccuget { State | Value } # attr <name> ccuget { State | Value }
# attr <name> ccureadings { 0 | 1 } # attr <name> ccureadings { 0 | 1 }
# attr <name> ccureadingformat { address[lc] | name[lc] | datapoint[lc] } # attr <name> ccureadingformat { address[lc] | name[lc] | datapoint[lc] }
@ -44,11 +44,12 @@
# attr <name> ccuverify { 0 | 1 | 2} # attr <name> ccuverify { 0 | 1 | 2}
# attr <name> controldatapoint <channel-number>.<datapoint> # attr <name> controldatapoint <channel-number>.<datapoint>
# attr <name> disable { 0 | 1 } # attr <name> disable { 0 | 1 }
# attr <name> hmstatevals <subst-rule>[;...]
# attr <name> statechannel <channel> # attr <name> statechannel <channel>
# attr <name> statedatapoint [<channel-number>.]<datapoint> # attr <name> statedatapoint [<channel-number>.]<datapoint>
# attr <name> statevals <text1>:<subtext1>[,...] # attr <name> statevals <text1>:<subtext1>[,...]
# attr <name> substexcl <reading-expr> # attr <name> substexcl <reading-expr>
# attr <name> substitute <regexp1>:<subtext1>[,...] # attr <name> substitute <subst-rule>[;...]
# #
##################################################################### #####################################################################
# Requires module 88_HMCCU # Requires module 88_HMCCU
@ -80,8 +81,9 @@ sub HMCCUDEV_Initialize ($)
$hash->{SetFn} = "HMCCUDEV_Set"; $hash->{SetFn} = "HMCCUDEV_Set";
$hash->{GetFn} = "HMCCUDEV_Get"; $hash->{GetFn} = "HMCCUDEV_Get";
$hash->{AttrFn} = "HMCCUDEV_Attr"; $hash->{AttrFn} = "HMCCUDEV_Attr";
$hash->{parseParams} = 1;
$hash->{AttrList} = "IODev ccuackstate:0,1 ccuflags:multiple-strict,nochn0,trace ccureadingfilter:textField-long ccureadingformat:name,namelc,address,addresslc,datapoint,datapointlc ccureadingname ccureadings:0,1 ccuget:State,Value ccuscaleval ccuverify:0,1,2 disable:0,1 statevals substexcl substitute:textField-long statechannel statedatapoint controldatapoint stripnumber ". $readingFnAttributes; $hash->{AttrList} = "IODev ccuackstate:0,1 ccuflags:multiple-strict,altread,nochn0,trace ccureadingfilter:textField-long ccureadingformat:name,namelc,address,addresslc,datapoint,datapointlc ccureadingname ccureadings:0,1 ccuget:State,Value ccuscaleval ccuverify:0,1,2 disable:0,1 hmstatevals statevals substexcl substitute:textField-long statechannel statedatapoint controldatapoint stripnumber ". $readingFnAttributes;
} }
##################################### #####################################
@ -90,110 +92,96 @@ sub HMCCUDEV_Initialize ($)
sub HMCCUDEV_Define ($@) sub HMCCUDEV_Define ($@)
{ {
my ($hash, $def) = @_; my ($hash, $a, $h) = @_;
my $name = $hash->{NAME}; my $name = $hash->{NAME};
my @a = split("[ \t][ \t]*", $def);
my $usage = "Usage: define $name HMCCUDEV {device|'virtual'} [state-channel] " .
"['readonly'] ['defaults'] [iodev={iodev-name}] [{groupexp=regexp|group={device|channel}[,...]]";
return $usage if (@$a < 3);
my $usage = "Usage: define $name HMCCUDEV {device|'virtual'} [state-channel] ['readonly'] ['defaults'] [{groupexp=regexp|group={device|channel}[,...]]"; my $devname = shift @$a;
return $usage if (@a < 3); my $devtype = shift @$a;
my $devspec = shift @$a;
my $devname = shift @a; my $gdcount = 0;
my $devtype = shift @a;
my $devspec = shift @a;
my $hmccu_hash = undef; my $hmccu_hash = undef;
if ($devspec ne 'virtual') {
return "Invalid or unknown CCU device name or address" if (!HMCCU_IsValidDevice ($devspec));
}
# IO device can be set by command line parameter iodev
if (exists ($h->{iodev})) {
$hmccu_hash = $defs{$h->{iodev}} if (exists ($defs{$h->{iodev}}));
}
if ($devspec eq 'virtual') { if ($devspec eq 'virtual') {
# Virtual device FHEM only # Virtual device FHEM only
$hmccu_hash = HMCCU_GetHash (0);
return "Cannot detect IO device" if (!defined ($hmccu_hash));
my $no = 0; my $no = 0;
foreach my $d (sort keys %defs) { foreach my $d (sort keys %defs) {
my $ch = $defs{$d}; my $ch = $defs{$d};
$hmccu_hash = $ch if ($ch->{TYPE} eq 'HMCCU' && !defined ($hmccu_hash)); next if (!exists ($ch->{TYPE}));
next if ($ch->{TYPE} ne 'HMCCUDEV'); next if ($ch->{TYPE} ne 'HMCCUDEV');
next if ($d eq $name); next if ($d eq $name);
next if ($ch->{ccuif} ne 'VirtualDevices' || $ch->{ccuname} ne 'none'); next if ($ch->{ccuif} ne 'VirtualDevices' || $ch->{ccuname} ne 'none');
$no++; $no++;
} }
return "No IO device found" if (!defined ($hmccu_hash));
$hash->{ccuif} = "VirtualDevices"; $hash->{ccuif} = "VirtualDevices";
$hash->{ccuaddr} = sprintf ("VIR%07d", $no+1); $hash->{ccuaddr} = sprintf ("VIR%07d", $no+1);
$hash->{ccuname} = "none"; $hash->{ccuname} = "none";
}
elsif (HMCCU_IsDevAddr ($devspec, 1)) {
# CCU Device address with interface
my ($i, $add) = split ('\.', $devspec);
$hash->{ccuif} = $i;
$hash->{ccuaddr} = $add;
$hash->{ccuname} = HMCCU_GetDeviceName ($add, '');
}
elsif (HMCCU_IsDevAddr ($devspec, 0)) {
# CCU Device address without interface
$hash->{ccuaddr} = $devspec;
$hash->{ccuname} = HMCCU_GetDeviceName ($devspec, '');
$hash->{ccuif} = HMCCU_GetDeviceInterface ($hash->{ccuaddr}, 'BidCos-RF');
}
else {
# CCU Device or channel name
$hash->{ccuname} = $devspec;
my ($add, $chn) = HMCCU_GetAddress ($devspec, '', '');
return "Channel name not allowed" if ($chn ne '');
$hash->{ccuaddr} = $add;
$hash->{ccuif} = HMCCU_GetDeviceInterface ($hash->{ccuaddr}, 'BidCos-RF');
}
return "CCU device address not found for $devspec" if ($hash->{ccuaddr} eq '');
return "CCU device name not found for $devspec" if ($hash->{ccuname} eq '');
$hash->{ccutype} = HMCCU_GetDeviceType ($hash->{ccuaddr}, '');
$hash->{channels} = HMCCU_GetDeviceChannels ($hash->{ccuaddr});
if ($hash->{ccuif} eq "VirtualDevices" && $hash->{ccuname} eq 'none') {
$hash->{statevals} = 'readonly'; $hash->{statevals} = 'readonly';
} }
else { else {
$hmccu_hash = HMCCU_FindIODevice ($devspec) if (!defined ($hmccu_hash));
return "Cannot detect IO device" if (!defined ($hmccu_hash));
my ($di, $da, $dn, $dt, $dc) = HMCCU_GetCCUDeviceParam ($hmccu_hash, $devspec);
return "Invalid or unknown CCU device name or address: $devspec" if (!defined ($da));
$hash->{ccuif} = $di;
$hash->{ccuaddr} = $da;
$hash->{ccuname} = $dn;
$hash->{ccutype} = $dt;
$hash->{channels} = $dc;
$hash->{statevals} = 'devstate'; $hash->{statevals} = 'devstate';
} }
# Parse optional command line parameters # Parse optional command line parameters
my $arg = shift @a; foreach my $arg (@$a) {
while (defined ($arg)) {
if ($arg eq 'readonly') { if ($arg eq 'readonly') {
$hash->{statevals} = $arg; $hash->{statevals} = $arg;
} }
elsif ($arg eq 'defaults') { elsif ($arg eq 'defaults') {
HMCCU_SetDefaults ($hash); HMCCU_SetDefaults ($hash);
} }
elsif ($arg =~ /^groupexp=/ && $hash->{ccuif} eq "VirtualDevices") { elsif ($arg =~ /^[0-9]+$/) {
my ($g, $gdev) = split ("=", $arg); $attr{$name}{statechannel} = $arg;
return $usage if (!defined ($gdev));
my @devlist;
my $cnt = HMCCU_GetMatchingDevices ($hmccu_hash, $gdev, 'dev', \@devlist);
return "No matching CCU devices found" if ($cnt == 0);
$hash->{ccugroup} = shift @devlist;
foreach my $gd (@devlist) {
$hash->{ccugroup} .= ",".$gd;
}
} }
elsif ($arg =~ /^group=/ && $hash->{ccuif} eq "VirtualDevices") { else {
my ($g, $gdev) = split ("=", $arg); return $usage;
return $usage if (!defined ($gdev)); }
my @gdevlist = split (",", $gdev); }
# Parse group options
if ($hash->{ccuif} eq "VirtualDevices") {
if (exists ($h->{groupexp}) && $hash->{ccuif} eq "VirtualDevices") {
my @devlist;
$gdcount = HMCCU_GetMatchingDevices ($hmccu_hash, $h->{groupexp}, 'dev', \@devlist);
return "No matching CCU devices found" if ($gdcount == 0);
$hash->{ccugroup} = join (',', @devlist);
}
elsif (exists ($h->{group}) && $hash->{ccuif} eq "VirtualDevices") {
my @gdevlist = split (",", $h->{group});
$hash->{ccugroup} = '' if (@gdevlist > 0); $hash->{ccugroup} = '' if (@gdevlist > 0);
foreach my $gd (@gdevlist) { foreach my $gd (@gdevlist) {
my ($gda, $gdc, $gdo) = ('', '', '', ''); my ($gda, $gdc, $gdo) = ('', '', '', '');
return "Invalid device or channel $gd" return "Invalid device or channel $gd" if (!HMCCU_IsValidDevice ($hmccu_hash, $gd));
if (!HMCCU_IsValidDevice ($gd));
if (HMCCU_IsDevAddr ($gd, 0) || HMCCU_IsChnAddr ($gd, 1)) { if (HMCCU_IsDevAddr ($gd, 0) || HMCCU_IsChnAddr ($gd, 1)) {
$gdo = $gd; $gdo = $gd;
} }
else { else {
($gda, $gdc) = HMCCU_GetAddress ($gd, '', ''); ($gda, $gdc) = HMCCU_GetAddress ($hmccu_hash, $gd, '', '');
$gdo = $gda; $gdo = $gda;
$gdo .= ':'.$gdc if ($gdc ne ''); $gdo .= ':'.$gdc if ($gdc ne '');
} }
@ -204,22 +192,15 @@ sub HMCCUDEV_Define ($@)
else { else {
$hash->{ccugroup} = $gdo; $hash->{ccugroup} = $gdo;
} }
$gdcount++;
} }
} }
elsif ($arg =~ /^[0-9]+$/) {
$attr{$name}{statechannel} = $arg; return "No devices in group" if ($hash->{ccuif} eq "VirtualDevices" && $gdcount == 0);
}
else {
return $usage;
}
$arg = shift @a;
} }
return "No devices in group" if ($hash->{ccuif} eq "VirtualDevices" && ( AssignIoPort ($hash, $hmccu_hash->{NAME});
!exists ($hash->{ccugroup}) || $hash->{ccugroup} eq ''));
# Inform HMCCU device about client device
AssignIoPort ($hash);
readingsSingleUpdate ($hash, "state", "Initialized", 1); readingsSingleUpdate ($hash, "state", "Initialized", 1);
$hash->{ccudevstate} = 'Active'; $hash->{ccudevstate} = 'Active';
@ -267,27 +248,31 @@ sub HMCCUDEV_Attr ($@)
sub HMCCUDEV_Set ($@) sub HMCCUDEV_Set ($@)
{ {
my ($hash, @a) = @_; my ($hash, $a, $h) = @_;
my $name = shift @a; my $name = shift @$a;
my $opt = shift @a; my $opt = shift @$a;
# Valid commands for read only devices
my $rocmds = "clear config defaults:noArg"; my $rocmds = "clear config defaults:noArg";
return HMCCU_SetError ($hash, -3) if (!exists ($hash->{IODev})); # Get I/O device
return undef my $hmccu_hash = HMCCU_GetHash ($hash);
if ($hash->{statevals} eq 'readonly' && $opt ne '?' && $opt ne 'clear' && $opt ne 'config' && return HMCCU_SetError ($hash, -3) if (!defined ($hmccu_hash));
$opt ne 'defaults'); my $hmccu_name = $hmccu_hash->{NAME};
# Handle read only and disabled devices
return undef if ($hash->{statevals} eq 'readonly' && $opt ne '?'
&& $opt !~ /^(clear|config|defaults)$/);
my $disable = AttrVal ($name, "disable", 0); my $disable = AttrVal ($name, "disable", 0);
return undef if ($disable == 1); return undef if ($disable == 1);
my $hmccu_hash = $hash->{IODev}; # Check if CCU is busy
my $hmccu_name = $hash->{IODev}->{NAME};
if (HMCCU_IsRPCStateBlocking ($hmccu_hash)) { if (HMCCU_IsRPCStateBlocking ($hmccu_hash)) {
return undef if ($opt eq '?'); return undef if ($opt eq '?');
return "HMCCUDEV: CCU busy"; return "HMCCUDEV: CCU busy";
} }
# Get parameters of current device
my $ccutype = $hash->{ccutype}; my $ccutype = $hash->{ccutype};
my $ccuaddr = $hash->{ccuaddr}; my $ccuaddr = $hash->{ccuaddr};
my $ccuif = $hash->{ccuif}; my $ccuif = $hash->{ccuif};
@ -298,8 +283,8 @@ sub HMCCUDEV_Set ($@)
my $rc; my $rc;
if ($opt eq 'datapoint') { if ($opt eq 'datapoint') {
my $objname = shift @a; my $objname = shift @$a;
my $objvalue = shift @a; my $objvalue = shift @$a;
return HMCCU_SetError ($hash, "Usage: set $name datapoint [{channel-number}.]{datapoint} {value}") return HMCCU_SetError ($hash, "Usage: set $name datapoint [{channel-number}.]{datapoint} {value}")
if (!defined ($objname) || !defined ($objvalue)); if (!defined ($objname) || !defined ($objvalue));
@ -331,7 +316,7 @@ sub HMCCUDEV_Set ($@)
return HMCCU_SetError ($hash, -14) if ($cd eq ''); return HMCCU_SetError ($hash, -14) if ($cd eq '');
return HMCCU_SetError ($hash, -7) if ($cc >= $hash->{channels}); return HMCCU_SetError ($hash, -7) if ($cc >= $hash->{channels});
my $objvalue = shift @a; my $objvalue = shift @$a;
return HMCCU_SetError ($hash, "Usage: set $name control {value}") if (!defined ($objvalue)); return HMCCU_SetError ($hash, "Usage: set $name control {value}") if (!defined ($objvalue));
return HMCCU_SetError ($hash, -8) if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $cc, $cd, 2)); return HMCCU_SetError ($hash, -8) if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $cc, $cd, 2));
@ -347,7 +332,7 @@ sub HMCCUDEV_Set ($@)
} }
elsif ($opt =~ /^($hash->{statevals})$/) { elsif ($opt =~ /^($hash->{statevals})$/) {
my $cmd = $1; my $cmd = $1;
my $objvalue = ($cmd ne 'devstate') ? $cmd : shift @a; my $objvalue = ($cmd ne 'devstate') ? $cmd : shift @$a;
return HMCCU_SetError ($hash, -11) if ($sc eq ''); return HMCCU_SetError ($hash, -11) if ($sc eq '');
return HMCCU_SetError ($hash, -13) if ($sd eq ''); return HMCCU_SetError ($hash, -13) if ($sd eq '');
@ -409,12 +394,12 @@ sub HMCCUDEV_Set ($@)
if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $sc, "LEVEL", 2)); if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $sc, "LEVEL", 2));
my $objname = ''; my $objname = '';
my $objvalue = shift @a; my $objvalue = shift @$a;
return HMCCU_SetError ($hash, "Usage: set $name pct {value} [{ontime} [{ramptime}]]") return HMCCU_SetError ($hash, "Usage: set $name pct {value} [{ontime} [{ramptime}]]")
if (!defined ($objvalue)); if (!defined ($objvalue));
my $timespec = shift @a; my $timespec = shift @$a;
my $ramptime = shift @a; my $ramptime = shift @$a;
# Set on time # Set on time
if (defined ($timespec)) { if (defined ($timespec)) {
@ -458,7 +443,7 @@ sub HMCCUDEV_Set ($@)
return HMCCU_SetError ($hash, "Can't find ON_TIME datapoint for device type") return HMCCU_SetError ($hash, "Can't find ON_TIME datapoint for device type")
if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $sc, "ON_TIME", 2)); if (!HMCCU_IsValidDatapoint ($hash, $ccutype, $sc, "ON_TIME", 2));
my $timespec = shift @a; my $timespec = shift @$a;
return HMCCU_SetError ($hash, "Usage: set $name $opt {ontime-spec}") return HMCCU_SetError ($hash, "Usage: set $name $opt {ontime-spec}")
if (!defined ($timespec)); if (!defined ($timespec));
@ -482,7 +467,7 @@ sub HMCCUDEV_Set ($@)
return undef; return undef;
} }
elsif ($opt eq 'clear') { elsif ($opt eq 'clear') {
my $rnexp = shift @a; my $rnexp = shift @$a;
$rnexp = '.*' if (!defined ($rnexp)); $rnexp = '.*' if (!defined ($rnexp));
my @readlist = keys %{$hash->{READINGS}}; my @readlist = keys %{$hash->{READINGS}};
foreach my $rd (@readlist) { foreach my $rd (@readlist) {
@ -491,16 +476,16 @@ sub HMCCUDEV_Set ($@)
} }
elsif ($opt eq 'config') { elsif ($opt eq 'config') {
return HMCCU_SetError ($hash, "Usage: set $name config [{channel-number}] {parameter}={value} [...]") return HMCCU_SetError ($hash, "Usage: set $name config [{channel-number}] {parameter}={value} [...]")
if (@a < 1); if (scalar (keys %{$h}) < 1);
my $objname = $ccuaddr; my $objname = $ccuaddr;
# Channel number is optional because parameter can be related to device or channel # Channel number is optional because parameter can be related to device or channel
if ($a[0] =~ /^([0-9]{1,2})$/) { if (scalar (@$a) > 0) && $$a[0] =~ /^([0-9]{1,2})$/) {
return HMCCU_SetError ($hash, -7) if ($1 >= $hash->{channels}); return HMCCU_SetError ($hash, -7) if ($1 >= $hash->{channels});
$objname .= ':'.$1; $objname .= ':'.$1;
} }
my $rc = HMCCU_RPCSetConfig ($hash, $objname, \@a); my $rc = HMCCU_RPCSetConfig ($hash, $objname, $h);
return HMCCU_SetError ($hash, $rc) if ($rc < 0); return HMCCU_SetError ($hash, $rc) if ($rc < 0);
HMCCU_SetState ($hash, "OK"); HMCCU_SetState ($hash, "OK");
@ -544,21 +529,26 @@ sub HMCCUDEV_Set ($@)
sub HMCCUDEV_Get ($@) sub HMCCUDEV_Get ($@)
{ {
my ($hash, @a) = @_; my ($hash, $a, $h) = @_;
my $name = shift @a; my $name = shift @$a;
my $opt = shift @a; my $opt = shift @$a;
return HMCCU_SetError ($hash, -3) if (!defined ($hash->{IODev})); # Get I/O device
my $hmccu_hash = HMCCU_GetHash ($hash);
return HMCCU_SetError ($hash, -3) if (!defined ($hmccu_hash));
my $hmccu_name = $hmccu_hash->{NAME};
# Handle disabled devices
my $disable = AttrVal ($name, "disable", 0); my $disable = AttrVal ($name, "disable", 0);
return undef if ($disable == 1); return undef if ($disable == 1);
my $hmccu_hash = $hash->{IODev}; # Check if CCU is busy
if (HMCCU_IsRPCStateBlocking ($hmccu_hash)) { if (HMCCU_IsRPCStateBlocking ($hmccu_hash)) {
return undef if ($opt eq '?'); return undef if ($opt eq '?');
return "HMCCUDEV: CCU busy"; return "HMCCUDEV: CCU busy";
} }
# Get parameters of current device
my $ccutype = $hash->{ccutype}; my $ccutype = $hash->{ccutype};
my $ccuaddr = $hash->{ccuaddr}; my $ccuaddr = $hash->{ccuaddr};
my $ccuif = $hash->{ccuif}; my $ccuif = $hash->{ccuif};
@ -584,7 +574,7 @@ sub HMCCUDEV_Get ($@)
return $ccureadings ? undef : $result; return $ccureadings ? undef : $result;
} }
elsif ($opt eq 'datapoint') { elsif ($opt eq 'datapoint') {
my $objname = shift @a; my $objname = shift @$a;
return HMCCU_SetError ($hash, "Usage: get $name datapoint [{channel-number}.]{datapoint}") return HMCCU_SetError ($hash, "Usage: get $name datapoint [{channel-number}.]{datapoint}")
if (!defined ($objname)); if (!defined ($objname));
@ -609,7 +599,7 @@ sub HMCCUDEV_Get ($@)
return $ccureadings ? undef : $result; return $ccureadings ? undef : $result;
} }
elsif ($opt eq 'update') { elsif ($opt eq 'update') {
my $ccuget = shift @a; my $ccuget = shift @$a;
$ccuget = 'Attr' if (!defined ($ccuget)); $ccuget = 'Attr' if (!defined ($ccuget));
if ($ccuget !~ /^(Attr|State|Value)$/) { if ($ccuget !~ /^(Attr|State|Value)$/) {
return HMCCU_SetError ($hash, "Usage: get $name update [{'State'|'Value'}]"); return HMCCU_SetError ($hash, "Usage: get $name update [{'State'|'Value'}]");
@ -632,7 +622,7 @@ sub HMCCUDEV_Get ($@)
return undef; return undef;
} }
elsif ($opt eq 'deviceinfo') { elsif ($opt eq 'deviceinfo') {
my $ccuget = shift @a; my $ccuget = shift @$a;
$ccuget = 'Attr' if (!defined ($ccuget)); $ccuget = 'Attr' if (!defined ($ccuget));
if ($ccuget !~ /^(Attr|State|Value)$/) { if ($ccuget !~ /^(Attr|State|Value)$/) {
return HMCCU_SetError ($hash, "Usage: get $name deviceinfo [{'State'|'Value'}]"); return HMCCU_SetError ($hash, "Usage: get $name deviceinfo [{'State'|'Value'}]");
@ -644,12 +634,12 @@ sub HMCCUDEV_Get ($@)
elsif ($opt eq 'config') { elsif ($opt eq 'config') {
my $channel = undef; my $channel = undef;
my $ccuobj = $ccuaddr; my $ccuobj = $ccuaddr;
my $par = shift @a; my $par = shift @$a;
if (defined ($par)) { if (defined ($par)) {
if ($par =~ /^([0-9]{1,2})$/) { if ($par =~ /^([0-9]{1,2})$/) {
return HMCCU_SetError ($hash, -7) if ($1 >= $hash->{channels}); return HMCCU_SetError ($hash, -7) if ($1 >= $hash->{channels});
$ccuobj .= ':'.$1; $ccuobj .= ':'.$1;
$par = shift @a; $par = shift @$a;
} }
} }
$par = '.*' if (!defined ($par)); $par = '.*' if (!defined ($par));
@ -662,12 +652,12 @@ sub HMCCUDEV_Get ($@)
elsif ($opt eq 'configlist') { elsif ($opt eq 'configlist') {
my $channel = undef; my $channel = undef;
my $ccuobj = $ccuaddr; my $ccuobj = $ccuaddr;
my $par = shift @a; my $par = shift @$a;
if (defined ($par)) { if (defined ($par)) {
if ($par =~ /^([0-9]{1,2})$/) { if ($par =~ /^([0-9]{1,2})$/) {
return HMCCU_SetError ($hash, -7) if ($1 >= $hash->{channels}); return HMCCU_SetError ($hash, -7) if ($1 >= $hash->{channels});
$ccuobj .= ':'.$1; $ccuobj .= ':'.$1;
$par = shift @a; $par = shift @$a;
} }
} }
$par = '.*' if (!defined ($par)); $par = '.*' if (!defined ($par));
@ -680,7 +670,7 @@ sub HMCCUDEV_Get ($@)
elsif ($opt eq 'configdesc') { elsif ($opt eq 'configdesc') {
my $channel = undef; my $channel = undef;
my $ccuobj = $ccuaddr; my $ccuobj = $ccuaddr;
my $par = shift @a; my $par = shift @$a;
if (defined ($par)) { if (defined ($par)) {
if ($par =~ /^([0-9]{1,2})$/) { if ($par =~ /^([0-9]{1,2})$/) {
return HMCCU_SetError ($hash, -7) if ($1 >= $hash->{channels}); return HMCCU_SetError ($hash, -7) if ($1 >= $hash->{channels});
@ -735,7 +725,8 @@ sub HMCCUDEV_Get ($@)
<b>Define</b><br/><br/> <b>Define</b><br/><br/>
<ul> <ul>
<code>define &lt;name&gt; HMCCUDEV {&lt;device&gt; | 'virtual'} [&lt;statechannel&gt;] <code>define &lt;name&gt; HMCCUDEV {&lt;device&gt; | 'virtual'} [&lt;statechannel&gt;]
[readonly] [defaults] [{group={device|channel}[,...]|groupexp=regexp]</code> [readonly] [defaults] [{group={device|channel}[,...]|groupexp=regexp]
[iodev=&lt;iodev-name&gt;]</code>
<br/><br/> <br/><br/>
If option 'readonly' is specified no set command will be available. With option 'defaults' If option 'readonly' is specified no set command will be available. With option 'defaults'
some default attributes depending on CCU device type will be set. Default attributes are only some default attributes depending on CCU device type will be set. Default attributes are only
@ -896,7 +887,7 @@ sub HMCCUDEV_Get ($@)
<li><b>ccuackstate {<u>0</u> | 1}</b><br/> <li><b>ccuackstate {<u>0</u> | 1}</b><br/>
<a href="#HMCCUCHNattr">see HMCCUCHN</a> <a href="#HMCCUCHNattr">see HMCCUCHN</a>
</li><br/> </li><br/>
<li><b>ccuflags {nochn0, trace}</b><br/> <li><b>ccuflags {altread, nochn0, trace}</b><br/>
<a href="#HMCCUCHNattr">see HMCCUCHN</a> <a href="#HMCCUCHNattr">see HMCCUCHN</a>
</li><br/> </li><br/>
<li><b>ccuget {State | <u>Value</u>}</b><br/> <li><b>ccuget {State | <u>Value</u>}</b><br/>
@ -928,6 +919,9 @@ sub HMCCUDEV_Get ($@)
<li><b>disable {<u>0</u> | 1}</b><br/> <li><b>disable {<u>0</u> | 1}</b><br/>
<a href="#HMCCUCHNattr">see HMCCUCHN</a> <a href="#HMCCUCHNattr">see HMCCUCHN</a>
</li><br/> </li><br/>
<li><b>hmstatevals &lt;subst-rule&gt;[;...]</b><br/>
<a href="#HMCCUCHNattr">see HMCCUCHN</a>
</li><br/>
<li><b>statechannel &lt;channel-number&gt;</b><br/> <li><b>statechannel &lt;channel-number&gt;</b><br/>
Channel for setting device state by devstate command. Deprecated, use attribute Channel for setting device state by devstate command. Deprecated, use attribute
'statedatapoint' instead. 'statedatapoint' instead.

View File

@ -4,12 +4,18 @@
# #
# $Id$ # $Id$
# #
# Version 3.6 # Version 3.7
# #
# Configuration parameters for Homematic devices. # Configuration parameters for Homematic devices.
# #
# (c) 2016 zap (zap01 <at> t-online <dot> de) # (c) 2016 zap (zap01 <at> t-online <dot> de)
# #
# Datapoints LOWBAT, LOW_BAT, UNREACH, ERROR* and FAULT* must not be
# specified in ccureadingfilter. They are always stored as readings.
# Datapoints LOWBAT, LOW_BAT and UNREACH must not be specified in
# substitute because they are substituted by default. See attribute
# substdefaults in module HMCCU.
#
######################################################################### #########################################################################
package HMCCUConf; package HMCCUConf;
@ -20,6 +26,7 @@ use warnings;
use vars qw(%HMCCU_CHN_DEFAULTS); use vars qw(%HMCCU_CHN_DEFAULTS);
use vars qw(%HMCCU_DEV_DEFAULTS); use vars qw(%HMCCU_DEV_DEFAULTS);
#
# #
# Default attributes for Homematic devices of type HMCCUCHN # Default attributes for Homematic devices of type HMCCUCHN
# #
@ -27,86 +34,204 @@ use vars qw(%HMCCU_DEV_DEFAULTS);
"HM-Sec-SCo|HM-Sec-SC|HMIP-SWDO" => { "HM-Sec-SCo|HM-Sec-SC|HMIP-SWDO" => {
_description => "Tuer/Fensterkontakt optisch und magnetisch", _description => "Tuer/Fensterkontakt optisch und magnetisch",
_channels => "1", _channels => "1",
ccureadingfilter => "(^UNREACH|LOWBAT|LOW_BAT|STATE)", ccureadingfilter => "STATE",
hmstatevals => "ERROR,SABOTAGE!1:sabotage",
statedatapoint => "STATE", statedatapoint => "STATE",
substitute => "STATE!(0|false):closed,(1|true):open;UNREACH,LOWBAT,LOW_BAT!(0|false):no,(1|true):yes" substitute => "STATE!(0|false):closed,(1|true):open"
},
"HM-Sec-RHS|HM-Sec-RHS-2" => {
_description => "Fenster Drehgriffkontakt",
_channels => "1",
ccureadingfilter => "STATE",
hmstatevals => "ERROR!1:sabotage",
statedatapoint => "STATE",
substitute => "STATE!0:closed,1:tilted,2:open;ERROR!0:no,1:sabotage"
},
"HM-Sec-Key|HM-Sec-Key-S|HM-Sec-Key-O|HM-Sec-Key-Generic" => {
_description => "Funk-Tuerschlossantrieb KeyMatic",
_channels => "1",
ccureadingfilter => "(STATE|INHIBIT)",
eventMap => "/datapoint OPEN true:open/",
hmstatevals => "ERROR!1:clutch_failure,2:motor_aborted",
statedatapoint => "STATE",
statevals => "lock:false,unlock:true",
substitute => "STATE!(0|false):locked,(1|true):unlocked,2:open;INHIBIT!(0|false):no,(1|true):yes;STATE_UNCERTAIN!(1|true):manual;DIRECTION!0:none,1:up,2:down,3:undefined;ERROR!0:no,1:clutch_failure,2:motor_aborted"
}, },
"HM-LC-Sw1-Pl-2|HMIP-PS" => { "HM-LC-Sw1-Pl-2|HMIP-PS" => {
_description => "Steckdose", _description => "Steckdose",
_channels => "1,3", _channels => "1,3",
ccureadingfilter => "(STATE|^UNREACH)", ccureadingfilter => "STATE",
controldatapoint => "STATE", controldatapoint => "STATE",
statedatapoint => "STATE", statedatapoint => "STATE",
statevals => "on:true,off:false", statevals => "on:true,off:false",
substitute => "STATE!(1|true):on,(0|false):off;UNREACH!(true|1):yes,(false|0):no", substitute => "STATE!(1|true):on,(0|false):off",
webCmd => "control", webCmd => "control",
widgetOverride => "control:uzsuToggle,off,on" widgetOverride => "control:uzsuToggle,off,on"
}, },
"HM-LC-Dim1T-Pl-3" => { "HM-LC-Dim1L-Pl|HM-LC-Dim1L-Pl-2|HM-LC-Dim1L-CV|HM-LC-Dim2L-CV|HM-LC-Dim2L-SM|HM-LC-Dim1L-Pl-3|HM-LC-Dim1L-CV-2" => {
_description => "Steckdose mit Dimmer", _description => "Funk-Anschnitt-Dimmaktor",
_channels => "1", _channels => "1",
ccureadingfilter => "(^LEVEL\$|ERROR|^UNREACH)", ccureadingfilter => "(^LEVEL$|DIRECTION)",
ccuscaleval => "LEVEL:0:1:0:100", ccuscaleval => "LEVEL:0:1:0:100",
cmdIcon => "on:general_an off:general_aus", cmdIcon => "on:general_an off:general_aus",
controldatapoint => "LEVEL", controldatapoint => "LEVEL",
hmstatevals => "ERROR!1:load_failure",
statedatapoint => "LEVEL", statedatapoint => "LEVEL",
statevals => "on:100,off:0", statevals => "on:100,off:0",
stripnumber => 1, stripnumber => 1,
substexcl => "control", substexcl => "control",
substitute => "ERROR_OVERHEAT,ERROR_OVERLOAD,ERROR_REDUCED,UNREACH!(0|false):no,(1|true):yes;LEVEL!#0-0:off,#1-100:on", substitute => "ERROR!0:no,1:load_failure:yes;LEVEL!#0-0:off,#1-100:on",
webCmd => "control:on:off", webCmd => "control:on:off",
widgetOverride => "control:slider,0,10,100" widgetOverride => "control:slider,0,10,100"
},
"HM-LC-Dim1PWM-CV|HM-LC-Dim1PWM-CV-2" => {
_description => "Funk-PWM-Dimmaktor",
_channels => "1",
ccureadingfilter => "(^LEVEL$|DIRECTION)",
ccuscaleval => "LEVEL:0:1:0:100",
cmdIcon => "on:general_an off:general_aus",
controldatapoint => "LEVEL",
hmstatevals => "ERROR_REDUCED!1:error_reduced;ERROR_OVERHEAT!1:error_overheat",
statedatapoint => "LEVEL",
statevals => "on:100,off:0",
stripnumber => 1,
substexcl => "control",
substitute => "ERROR_REDUCED,ERROR_OVERHEAT!(0|false):no,(1|true):yes;LEVEL!#0-0:off,#1-100:on;DIRECTION!0:none,1:up,2:down,3:undefined",
webCmd => "control:on:off",
widgetOverride => "control:slider,0,10,100"
}, "HM-LC-Dim1T-Pl|HM-LC-Dim1T-CV|HM-LC-Dim1T-FM|HM-LC-Dim1T-CV-2|HM-LC-Dim2T-SM|HM-LC-Dim2T-SM-2|HM-LC-Dim1T-DR|HM-LC-Dim1T-FM-LF|HM-LC-Dim1T-FM-2|HM-LC-Dim1T-Pl-3|HM-LC-Dim1TPBU-FM|HM-LC-Dim1TPBU-FM-2" => {
_description => "Funk-Abschnitt-Dimmaktor",
_channels => "1",
ccureadingfilter => "(^LEVEL\$|DIRECTION)",
ccuscaleval => "LEVEL:0:1:0:100",
cmdIcon => "on:general_an off:general_aus",
controldatapoint => "LEVEL",
hmstatevals => "ERROR_REDUCED!1:error_reduced;ERROR_OVERHEAT!1:error_overheat;ERROR_OVERLOAD!1:error_overload",
statedatapoint => "LEVEL",
statevals => "on:100,off:0",
stripnumber => 1,
substexcl => "control",
substitute => "ERROR_OVERHEAT,ERROR_OVERLOAD,ERROR_REDUCED!(0|false):no,(1|true):yes;LEVEL!#0-0:off,#1-100:on;DIRECTION!0:none,1:up,2:down,3:undefined",
webCmd => "control:on:off",
widgetOverride => "control:slider,0,10,100"
},
"HM-PB-2-FM" => {
_description => "Funk-Wandtaster 2-fach",
_channels => "1,2",
ccureadingfilter => "PRESS",
statedatapoint => "PRESS_SHORT",
statevals => "press:true",
substitute => "PRESS_SHORT,PRESS_LONG,PRESS_CONT!(1|true):pressed,(0|false):released;PRESS_LONG_RELEASE!(0|false):no,(1|true):yes"
}, },
"HM-LC-Sw1PBU-FM" => { "HM-LC-Sw1PBU-FM" => {
_description => "Unterputz Schaltaktor für Markenschalter", _description => "Unterputz Schaltaktor für Markenschalter",
_channels => "1", _channels => "1",
ccureadingfilter => "(STATE|^UNREACH)", ccureadingfilter => "STATE",
controldatapoint => "STATE", controldatapoint => "STATE",
statedatapoint => "STATE", statedatapoint => "STATE",
statevals => "on:true,off:false", statevals => "on:true,off:false",
substitute => "STATE!(true|1):on,(false|0):off;UNREACH!(true|1):yes,(false|0):no", substitute => "STATE!(true|1):on,(false|0):off",
webCmd => "control", webCmd => "control",
widgetOverride => "control:uzsuToggle,off,on" widgetOverride => "control:uzsuToggle,off,on"
}, },
"HM-SCI-3-FM" => { "HM-SCI-3-FM" => {
_description => "3 Kanal Schliesserkontakt", _description => "3 Kanal Schliesserkontakt",
_channels => "1,2,3", _channels => "1,2,3",
ccureadingfilter => "(STATE|LOWBAT|^UNREACH)", ccureadingfilter => "STATE",
statedatapoint => "STATE", statedatapoint => "STATE",
statevals => "on:true,off:false", statevals => "on:true,off:false",
substitute => "STATE!(1|true):on,(0|false):off;LOWBAT,UNREACH!(1|true):yes,(0|false):no" substitute => "STATE!(1|true):on,(0|false):off"
}, },
"HM-LC-Sw1-Pl|HM-LC-Sw1-Pl-2|HM-LC-Sw1-SM|HM-LC-Sw1-FM|HM-LC-Sw1-PB-FM" => { "HM-LC-Sw1-Pl|HM-LC-Sw1-Pl-2|HM-LC-Sw1-SM|HM-LC-Sw1-FM|HM-LC-Sw1-PB-FM" => {
_description => "1 Kanal Funk-Schaltaktor", _description => "1 Kanal Funk-Schaltaktor",
_channels => "1", _channels => "1",
ccureadingfilter => "(STATE|LOWBAT|^UNREACH)", ccureadingfilter => "STATE",
statedatapoint => "STATE", statedatapoint => "STATE",
statevals => "on:true,off:false", statevals => "on:true,off:false",
substitute => "STATE!(1|true):on,(0|false):off;LOWBAT,UNREACH!(1|true):yes,(0|false):no" substitute => "STATE!(1|true):on,(0|false):off"
}, },
"HM-LC-Sw2-SM|HM-LC-Sw2-FM|HM-LC-Sw2-PB-FM|HM-LC-Sw2-DR" => { "HM-LC-Sw2-SM|HM-LC-Sw2-FM|HM-LC-Sw2-PB-FM|HM-LC-Sw2-DR" => {
_description => "2 Kanal Funk-Schaltaktor", _description => "2 Kanal Funk-Schaltaktor",
_channels => "1,2", _channels => "1,2",
ccureadingfilter => "(STATE|LOWBAT|^UNREACH)", ccureadingfilter => "STATE",
statedatapoint => "STATE", statedatapoint => "STATE",
statevals => "on:true,off:false", statevals => "on:true,off:false",
substitute => "STATE!(1|true):on,(0|false):off;LOWBAT,UNREACH!(1|true):yes,(0|false):no" substitute => "STATE!(1|true):on,(0|false):off"
}, },
"HM-LC-Sw4-DR|HM-LC-Sw4-WM|HM-LC-Sw4-PCB|HM-LC-Sw4-SM" => { "HM-LC-Sw4-DR|HM-LC-Sw4-WM|HM-LC-Sw4-PCB|HM-LC-Sw4-SM" => {
_description => "4 Kanal Funk-Schaltaktor", _description => "4 Kanal Funk-Schaltaktor",
_channels => "1,2,3,4", _channels => "1,2,3,4",
ccureadingfilter => "(STATE|LOWBAT|^UNREACH)", ccureadingfilter => "STATE",
statedatapoint => "STATE", statedatapoint => "STATE",
statevals => "on:true,off:false", statevals => "on:true,off:false",
substitute => "STATE!(1|true):on,(0|false):off;LOWBAT,UNREACH!(1|true):yes,(0|false):no" substitute => "STATE!(1|true):on,(0|false):off"
},
"HM-WDS40-TH-I|HM-WDS10-TH-O|HM-WDS20-TH-O|IS-WDS-TH-OD-S-R3|ASH550I|ASH550" => {
_description => "Temperatur/Luftfeuchte Sensor",
_channels => "1",
ccureadingfilter => "(^HUMIDITY|^TEMPERATURE)",
statedatapoint => "TEMPERATURE",
stripnumber => 1
},
"HM-Sec-MD|HM-Sec-MDIR|HM-Sec-MDIR-2|HM-Sec-MDIR-3" => {
_description => "Bewegungsmelder",
_channels => "1",
ccureadingfilter => "(BRIGHTNESS|MOTION)",
hmstatevals => "ERROR!1:sabotage",
statedatapoint => "MOTION",
substitute => "MOTION!(0|false):no,(1|true):yes;ERROR!0:no,1:sabotage"
}, },
"HM-Sen-LI-O" => { "HM-Sen-LI-O" => {
_description => "Lichtsensor", _description => "Lichtsensor",
_channels => "1", _channels => "1",
ccureadingfilter => "(LUX|LOWBAT|UNREACH)", ccureadingfilter => "LUX",
statedatapoint => "LUX", statedatapoint => "LUX",
stripnumber => 1, stripnumber => 1
substitute => "LOWBAT,UNREACH!(0|false):no,(1|true):yes" },
"HM-CC-SCD" => {
_description => "CO2 Sensor",
_channels => "1",
statedatapoint => "STATE",
substitute => "STATE!0:normal,1:added,2:strong"
},
"HM-Sec-SD-2" => {
_description => "Funk-Rauchmelder",
_channels => "1",
ccureadingfilter => "STATE",
hmstatevals => "ERROR_ALARM_TEST!1:alarm_test_failed;ERROR_SMOKE_CHAMBER!1:degraded_smoke_chamber",
statedatapoint => "STATE",
substitute => "ERROR_ALARM_TEST!0:no,1:failed;ERROR_SMOKE_CHAMBER!0:no,1:degraded"
},
"HM-Sec-SFA-SM" => {
_description => "Alarmsirene",
_channels => "1",
ccureadingfilter => "STATE",
hmstatevals => "ERROR_POWER!1:power_failure;ERROR_SABOTAGE!1:sabotage;ERROR_BATTERY!1:battery_defect",
statedatapoint => "STATE",
substitute => "STATE!(0|false):off,(1|true):alarm;ERROR_POWER!0:no,1:failure;ERROR_SABOTAGE!0:no,1:sabotage;ERROR_BATTERY!0:no,1:defect"
},
"WS550|WS888|WS550Tech|WS550LCB|WS550LCW|HM-WDC7000" => {
_description => "Wetterstation",
_channels => "10",
ccureadingfilter => "(TEMPERATURE|HUMIDITY|AIR_PRESSURE)",
statedatapoint => "TEMPERATURE",
stripnumber => 1
},
"HM-Sec-WDS|HM-Sec-WDS-2" => {
_description => "Funk-Wassermelder",
_channels => "1",
ccureadingfilter => "STATE",
statedatapoint => "STATE",
substitute => "STATE!0:dry,1:wet,2:water"
},
"HM-OU-LED16|HM-OU-X" => {
_description => "Statusanzeige 16 Kanal LED",
_channels => "1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16",
ccureadingfilter => "PRESS_SHORT|LED_STATUS",
eventMap => "/datapoint LED_SLEEP_MODE 0:sleep-off/datapoint LED_SLEEP_MODE 1:sleep-on/",
statedatapoint => "LED_STATUS",
statevals => "off:0,red:1,green:2,orange:3",
substitute => "LED_STATUS!0:off,1:red:2:green:3:orange"
} }
); );
@ -114,171 +239,305 @@ use vars qw(%HMCCU_DEV_DEFAULTS);
# Default attributes for Homematic devices of type HMCCUDEV # Default attributes for Homematic devices of type HMCCUDEV
# #
%HMCCU_DEV_DEFAULTS = ( %HMCCU_DEV_DEFAULTS = (
"HM-Sec-SCo|HM-Sec-SC" => { "HM-Sec-SCo|HM-Sec-SC|HMIP-SWDO" => {
_description => "Tuer/Fensterkontakt optisch und magnetisch", _description => "Tuer/Fensterkontakt optisch und magnetisch",
ccureadingfilter => "(^UNREACH|LOWBAT|LOW_BAT|STATE)", ccureadingfilter => "(SABOTAGE|STATE)",
hmstatevals => "ERROR,SABOTAGE!1:sabotage",
statedatapoint => "1.STATE", statedatapoint => "1.STATE",
substitute => "STATE!(0|false):closed,(1|true):open;UNREACH,LOWBAT,LOW_BAT!(0|false):no,(1|true):yes" substitute => "STATE!(0|false):closed,(1|true):open"
},
"HM-Sec-RHS|HM-Sec-RHS-2" => {
_description => "Fenster Drehgriffkontakt",
ccureadingfilter => "STATE",
hmstatevals => "ERROR!1:sabotage",
statedatapoint => "1.STATE",
substitute => "STATE!0:closed,1:tilted,2:open;ERROR!0:no,1:sabotage"
},
"HM-Sec-Key|HM-Sec-Key-S|HM-Sec-Key-O|HM-Sec-Key-Generic" => {
_description => "Funk-Tuerschlossantrieb KeyMatic",
ccureadingfilter => "(STATE|INHIBIT)",
eventMap => "/datapoint 1.OPEN true:open/",
hmstatevals => "ERROR!1:clutch_failure,2:motor_aborted",
statedatapoint => "1.STATE",
statevals => "lock:false,unlock:true",
substitute => "STATE!(0|false):locked,(1|true):unlocked,2:open;INHIBIT!(0|false):no,(1|true):yes;STATE_UNCERTAIN!(1|true):manual;DIRECTION!0:none,1:up,2:down,3:undefined;ERROR!0:no,1:clutch_failure,2:motor_aborted"
},
"HM-Sec-Win|HM-Sec-Win-Generic" => {
_description => "WinMatic",
ccureadingfilter => "(STATE_UNCERTAIN|INHIBIT|LEVEL|STATUS)",
ccuscaleval => "LEVEL:0:1:0:100,SPEED:0.1:0:100",
eventMap => "/datapoint 1.STOP true:stop/",
statedatapoint => "1.LEVEL",
statevals => "open:100,close:0",
stripnumber => 1,
substitute => "LEVEL!-0.005:locked,#0-0:closed,#100-100:open;INHIBIT!(0|false):no,(1|true):yes;ERROR!0:no,1:motor_turn,2:motor_tilt;STATUS!0:trickle_charge,1:charge,2:discharge,3:unknown"
}, },
"HM-LC-Sw1-Pl-2" => { "HM-LC-Sw1-Pl-2" => {
_description => "Steckdose", _description => "Steckdose",
ccureadingfilter => "(STATE|^UNREACH)", ccureadingfilter => "STATE",
controldatapoint => "1.STATE", controldatapoint => "1.STATE",
statedatapoint => "1.STATE", statedatapoint => "1.STATE",
statevals => "on:true,off:false", statevals => "on:true,off:false",
substitute => "STATE!(1|true):on,(0|false):off;UNREACH!(true|1):yes,(false|0):no", substitute => "STATE!(1|true):on,(0|false):off",
webCmd => "control", webCmd => "control",
widgetOverride => "control:uzsuToggle,off,on" widgetOverride => "control:uzsuToggle,off,on"
}, },
"HMIP-PS" => { "HMIP-PS" => {
_description => "Steckdose IP", _description => "Steckdose IP",
ccureadingfilter => "(STATE|^UNREACH)", ccureadingfilter => "STATE",
controldatapoint => "3.STATE", controldatapoint => "3.STATE",
statedatapoint => "3.STATE", statedatapoint => "3.STATE",
statevals => "on:1,off:0", statevals => "on:1,off:0",
substitute => "STATE!(1|true):on,(0|false):off;UNREACH!(true|1):yes,(false|0):no", substitute => "STATE!(1|true):on,(0|false):off",
webCmd => "control", webCmd => "control",
widgetOverride => "control:uzsuToggle,off,on" widgetOverride => "control:uzsuToggle,off,on"
}, },
"HM-ES-PMSw1-Pl" => { "HM-ES-PMSw1-Pl|HM-ES-PMSw1-Pl-DN-R1|HM-ES-PMSw1-Pl-DN-R2|HM-ES-PMSw1-Pl-DN-R3|HM-ES-PMSw1-Pl-DN-R4|HM-ES-PMSw1-Pl-DN-R5" => {
_description => "Steckdose mit Energiemessung", _description => "Steckdose mit Energiemessung",
ccureadingfilter => "(STATE|^UNREACH|CURRENT|ENERGY_COUNTER|POWER)", ccureadingfilter => "(STATE|CURRENT|ENERGY_COUNTER|POWER)",
controldatapoint => "1.STATE", controldatapoint => "1.STATE",
statedatapoint => "1.STATE", statedatapoint => "1.STATE",
statevals => "on:1,off:0", statevals => "on:1,off:0",
stripnumber => 1, stripnumber => 1,
substitute => "STATE!(1|true):on,(0|false):off;UNREACH!(true|1):yes,(false|0):no", substitute => "STATE!(1|true):on,(0|false):off",
webCmd => "control", webCmd => "control",
widgetOverride => "control:uzsuToggle,off,on" widgetOverride => "control:uzsuToggle,off,on"
}, },
"HMIP-PSM" => { "HMIP-PSM" => {
_description => "Steckdose mit Energiemessung IP", _description => "Steckdose mit Energiemessung IP",
ccureadingfilter => "(STATE|^UNREACH|CURRENT|ENERGY_COUNTER|POWER)", ccureadingfilter => "(STATE|CURRENT|ENERGY_COUNTER|POWER)",
controldatapoint => "3.STATE", controldatapoint => "3.STATE",
statedatapoin => "3.STATE", statedatapoin => "3.STATE",
statevals => "on:true,off:false", statevals => "on:true,off:false",
stripnumber => 1, stripnumber => 1,
substitute => "STATE!(true|1):on,(false|0):off;UNREACH!(true|1):yes,(false|0):no", substitute => "STATE!(true|1):on,(false|0):off",
webCmd => "control", webCmd => "control",
widgetOverride => "control:uzsuToggle,off,on" widgetOverride => "control:uzsuToggle,off,on"
}, }, "HM-LC-Dim1L-Pl|HM-LC-Dim1L-Pl-2|HM-LC-Dim1L-CV|HM-LC-Dim2L-CV|HM-LC-Dim2L-SM|HM-LC-Dim1L-Pl-3|HM-LC-Dim1L-CV-2" => {
"HM-LC-Dim1T-Pl-3" => { _description => "Funk-Anschnitt-Dimmaktor",
_description => "Steckdose mit Dimmer", ccureadingfilter => "(^LEVEL$|DIRECTION)",
ccureadingfilter => "(^LEVEL\$|ERROR|^UNREACH)",
ccuscaleval => "LEVEL:0:1:0:100", ccuscaleval => "LEVEL:0:1:0:100",
cmdIcon => "on:general_an off:general_aus", cmdIcon => "on:general_an off:general_aus",
controldatapoint => "1.LEVEL", controldatapoint => "1.LEVEL",
hmstatevals => "ERROR!1:load_failure",
statedatapoint => "1.LEVEL", statedatapoint => "1.LEVEL",
statevals => "on:100,off:0", statevals => "on:100,off:0",
stripnumber => 1, stripnumber => 1,
substexcl => "control", substexcl => "control",
substitute => "ERROR_OVERHEAT,ERROR_OVERLOAD,ERROR_REDUCED,UNREACH!(0|false):no,(1|true):yes;LEVEL!#0-0:off,#1-100:on", substitute => "ERROR!0:no,1:load_failure;LEVEL!#0-0:off,#1-100:on",
webCmd => "control:on:off", webCmd => "control:on:off",
widgetOverride => "control:slider,0,10,100" widgetOverride => "control:slider,0,10,100"
}, },
"HM-LC-Dim1PWM-CV|HM-LC-Dim1PWM-CV-2" => {
_description => "Funk-PWM-Dimmaktor",
ccureadingfilter => "(^LEVEL$|DIRECTION)",
ccuscaleval => "LEVEL:0:1:0:100",
cmdIcon => "on:general_an off:general_aus",
controldatapoint => "1.LEVEL",
hmstatevals => "ERROR_REDUCED!1:error_reduced;ERROR_OVERHEAT!1:error_overheat",
statedatapoint => "1.LEVEL",
statevals => "on:100,off:0",
stripnumber => 1,
substexcl => "control",
substitute => "ERROR_REDUCED,ERROR_OVERHEAT!(0|false):no,(1|true):yes;LEVEL!#0-0:off,#1-100:on;DIRECTION!0:none,1:up,2:down,3:undefined",
webCmd => "control:on:off",
widgetOverride => "control:slider,0,10,100"
}, "HM-LC-Dim1T-Pl|HM-LC-Dim1T-CV|HM-LC-Dim1T-FM|HM-LC-Dim1T-CV-2|HM-LC-Dim2T-SM|HM-LC-Dim2T-SM-2|HM-LC-Dim1T-DR|HM-LC-Dim1T-FM-LF|HM-LC-Dim1T-FM-2|HM-LC-Dim1T-Pl-3|HM-LC-Dim1TPBU-FM|HM-LC-Dim1TPBU-FM-2" => {
_description => "Funk-Abschnitt-Dimmaktor",
ccureadingfilter => "(^LEVEL\$|DIRECTION)",
ccuscaleval => "LEVEL:0:1:0:100",
cmdIcon => "on:general_an off:general_aus",
controldatapoint => "1.LEVEL",
hmstatevals => "ERROR_REDUCED!1:error_reduced;ERROR_OVERHEAT!1:error_overheat;ERROR_OVERLOAD!1:error_overload",
statedatapoint => "1.LEVEL",
statevals => "on:100,off:0",
stripnumber => 1,
substexcl => "control",
substitute => "ERROR_OVERHEAT,ERROR_OVERLOAD,ERROR_REDUCED!(0|false):no,(1|true):yes;LEVEL!#0-0:off,#1-100:on;DIRECTION!0:none,1:up,2:down,3:undefined",
webCmd => "control:on:off",
widgetOverride => "control:slider,0,10,100"
},
"HM-PB-2-FM" => {
_description => "Funk-Wandtaster 2-fach",
ccureadingfilter => "PRESS",
substitute => "PRESS_SHORT,PRESS_LONG,PRESS_CONT!(1|true):pressed,(0|false):released;PRESS_LONG_RELEASE!(0|false):no,(1|true):yes"
},
"HM-LC-Sw1PBU-FM" => { "HM-LC-Sw1PBU-FM" => {
_description => "Unterputz Schaltaktor für Markenschalter", _description => "Unterputz Schaltaktor für Markenschalter",
ccureadingfilter => "(STATE|^UNREACH)", ccureadingfilter => "STATE",
controldatapoint => "1.STATE", controldatapoint => "1.STATE",
statedatapoint => "1.STATE", statedatapoint => "1.STATE",
statevals => "on:true,off:false", statevals => "on:true,off:false",
substitute => "STATE!(true|1):on,(false|0):off;UNREACH!(true|1):yes,(false|0):no", substitute => "STATE!(true|1):on,(false|0):off",
webCmd => "control", webCmd => "control",
widgetOverride => "control:uzsuToggle,off,on" widgetOverride => "control:uzsuToggle,off,on"
}, },
"HM-LC-SW4-BA-PCB|HM-SCI-3-FM" => { "HM-LC-SW4-BA-PCB|HM-SCI-3-FM" => {
_description => "4 Kanal Funk Schaltaktor für Batteriebetrieb, 3 Kanal Schließerkontakt", _description => "4 Kanal Funk Schaltaktor für Batteriebetrieb, 3 Kanal Schließerkontakt",
ccureadingfilter => "(STATE|LOWBAT|^UNREACH)", ccureadingfilter => "STATE",
statevals => "on:true,off:false", statevals => "on:true,off:false",
substitute => "STATE!(1|true):on,(0|false):off;LOWBAT,UNREACH!(1|true):yes,(0|false):no" substitute => "STATE!(1|true):on,(0|false):off"
}, },
"HM-LC-Bl1PBU-FM|HM-LC-Bl1-FM" => { "HM-LC-Bl1PBU-FM|HM-LC-Bl1-FM|HM-LC-Bl1-SM|HM-LC-BlX|HM-LC-Bl1-SM-2|HM-LC-Bl1-FM-2" => {
_description => "Rolladenaktor Markenschalter, Rolladenaktor unterputz", _description => "Jalousieaktor",
ccureadingfilter => "(LEVEL|^UNREACH)", ccureadingfilter => "(LEVEL|INHIBIT|DIRECTION)",
ccuscaleval => "LEVEL:0:1:0:100", ccuscaleval => "LEVEL:0:1:0:100",
cmdIcon => "up:fts_shutter_up stop:fts_shutter_manual down:fts_shutter_down", cmdIcon => "up:fts_shutter_up stop:fts_shutter_manual down:fts_shutter_down",
controldatapoint => "1.LEVEL", controldatapoint => "1.LEVEL",
eventMap => "/datapoint 1.STOP 1:stop/datapoint 1.LEVEL 0:down/datapoint 1.LEVEL 100:up/", eventMap => "/datapoint 1.STOP 1:stop/datapoint 1.LEVEL 0:down/datapoint 1.LEVEL 100:up/datapoint 1.STOP true:stop/",
statedatapoint => "1.LEVEL", statedatapoint => "1.LEVEL",
stripnumber => 1, stripnumber => 1,
substexcl => "control", substexcl => "control",
substitute => "UNREACH!(false|0):no,(true|1):yes;LEVEL!#0-0:closed,#100-100:open", substitute => "LEVEL!#0-0:closed,#100-100:open;DIRECTION!0:none,1:up,2:down,3:undefined",
webCmd => "control:up:stop:down", webCmd => "control:up:stop:down",
widgetOverride => "control:slider,0,10,100" widgetOverride => "control:slider,0,10,100"
}, },
"HM-TC-IT-WM-W-EU" => { "HM-TC-IT-WM-W-EU" => {
_description => "Wandthermostat", _description => "Wandthermostat",
ccureadingfilter => "(^UNREACH|^HUMIDITY|^TEMPERATURE|^SET_TEMPERATURE|^LOWBAT\$|^WINDOW_OPEN)", ccureadingfilter => "(^HUMIDITY|^TEMPERATURE|^SET_TEMPERATURE|^WINDOW_OPEN)",
cmdIcon => "Auto:sani_heating_automatic Manu:sani_heating_manual Boost:sani_heating_boost on:general_an off:general_aus", cmdIcon => "Auto:sani_heating_automatic Manu:sani_heating_manual Boost:sani_heating_boost on:general_an off:general_aus",
controldatapoint => "2.SET_TEMPERATURE", controldatapoint => "2.SET_TEMPERATURE",
eventMap => "/datapoint 2.MANU_MODE 20.0:Manu/datapoint 2.AUTO_MODE 1:Auto/datapoint 2.BOOST_MODE 1:Boost/datapoint 2.MANU_MODE 4.5:off/datapoint 2.MANU_MODE 30.5:on/", eventMap => "/datapoint 2.MANU_MODE 20.0:Manu/datapoint 2.AUTO_MODE 1:Auto/datapoint 2.BOOST_MODE 1:Boost/datapoint 2.MANU_MODE 4.5:off/datapoint 2.MANU_MODE 30.5:on/",
statedatapoint => "2.SET_TEMPERATURE", statedatapoint => "2.SET_TEMPERATURE",
stripnumber => 1, stripnumber => 1,
substexcl => "control", substexcl => "control",
substitute => "LOWBAT,UNREACH!(0|false):no,(1|true):yes;CONTROL_MODE!0:AUTO,1:MANU,2:PARTY,3:BOOST;WINDOW_OPEN_REPORTING!(true|1):open,(false|0):closed;SET_TEMPERATURE!#0-3.5:off,#30.5-40:on", substitute => "CONTROL_MODE!0:AUTO,1:MANU,2:PARTY,3:BOOST;WINDOW_OPEN_REPORTING!(true|1):open,(false|0):closed;SET_TEMPERATURE!#0-3.5:off,#30.5-40:on",
webCmd => "control:Auto:Manu:Boost:on:off", webCmd => "control:Auto:Manu:Boost:on:off",
widgetOverride => "control:slider,4.5,0.5,30.5,1" widgetOverride => "control:slider,4.5,0.5,30.5,1"
}, },
"HM-CC-RT-DN" => { "HM-CC-RT-DN" => {
_description => "Heizkoerperthermostat", _description => "Heizkoerperthermostat",
ccureadingfilter => "(^UNREACH|LOWBAT|TEMPERATURE|VALVE_STATE|CONTROL)", ccureadingfilter => "(TEMPERATURE|VALVE_STATE|CONTROL)",
cmdIcon => "Auto:sani_heating_automatic Manu:sani_heating_manual Boost:sani_heating_boost on:general_an off:general_aus", cmdIcon => "Auto:sani_heating_automatic Manu:sani_heating_manual Boost:sani_heating_boost on:general_an off:general_aus",
controldatapoint => "4.SET_TEMPERATURE", controldatapoint => "4.SET_TEMPERATURE",
eventMap => "/datapoint 4.MANU_MODE 20.0:Manu/datapoint 4.AUTO_MODE 1:Auto/datapoint 4.BOOST_MODE 1:Boost/datapoint 4.MANU_MODE 4.5:off/datapoint 4.MANU_MODE 30.5:on/", eventMap => "/datapoint 4.MANU_MODE 20.0:Manu/datapoint 4.AUTO_MODE 1:Auto/datapoint 4.BOOST_MODE 1:Boost/datapoint 4.MANU_MODE 4.5:off/datapoint 4.MANU_MODE 30.5:on/",
hmstatevals => "FAULT_REPORTING!1:valve_tight,2:range_too_large,3:range_too_small,4:communication_error,5:other_error,6:battery_low,7:valve_error_pos",
statedatapoint => "4.SET_TEMPERATURE", statedatapoint => "4.SET_TEMPERATURE",
stripnumber => 1, stripnumber => 1,
substexcl => "control", substexcl => "control",
substitute => "UNREACH,LOWBAT!(0|false):no,(1|true):yes;CONTROL_MODE!0:AUTO,1:MANU,2:PARTY,3:BOOST;SET_TEMPERATURE!#0-3.5:off,#30.5-40:on", substitute => "CONTROL_MODE!0:AUTO,1:MANU,2:PARTY,3:BOOST;SET_TEMPERATURE!#0-4.5:off,#30.5-40:on;FAULT_REPORTING!0:no,1:valve_tight,2:range_too_large,3:range_too_small,4:communication_error,5:other_error,6:battery_low,7:valve:error_pos",
webCmd => "control:Auto:Manu:Boost:on:off", webCmd => "control:Auto:Manu:Boost:on:off",
widgetOverride => "control:slider,3.5,0.5,30.5,1" widgetOverride => "control:slider,4.5,0.5,30.5,1"
}, },
"HM-WDS40-TH-I" => { "HMIP-eTRV" => {
_description => "Temperatur/Luftfeuchte Sensor", _description => "Heizkoerperthermostat HM-IP",
ccureadingfilter => "(^UNREACH|^HUMIDITY|^TEMPERATURE|^LOWBAT\$)", ccureadingname => "1.LEVEL:valve_position",
statedatapoint => "1.TEMPERATURE", ccuscaleval => "LEVEL:0:1:0:100",
controldatapoint => "1.SET_POINT_TEMPERATURE",
eventMap => "/datapoint 1.BOOST_MODE true:Boost/datapoint 1.CONTROL_MODE 0:Auto/datapoint 1.CONTROL_MODE 1:Manual/datapoint 1.CONTROL_MODE 2:Holiday/datapoint 1.SET_POINT_TEMPERATURE 4.5:off/datapoint 1.SET_POINT_TEMPERATURE 30.5:on/",
statedatapoint => "1.SET_POINT_TEMPERATURE",
stripnumber => 1, stripnumber => 1,
substitute => "UNREACH,LOWBAT!(0|false):no,(1|true):yes" substexcl => "control",
substitute => "SET_POINT_TEMPERATURE!#0-4.5:off,#30.5-40:on;WINDOW_STATE!(0|false):closed,(1|true):open",
webCmd => "control:Boost:Auto:Manual:Holiday:on:off",
widgetOverride => "control:slider,4.5,0.5,30.5,1"
},
"HMIP-WTH|HMIP-WTH-2" => {
_description => "Wandthermostat HM-IP",
controldatapoint => "1.SET_POINT_TEMPERATURE",
eventMap => "/datapoint 1.BOOST_MODE true:Boost/datapoint 1.CONTROL_MODE 0:Auto/datapoint 1.CONTROL_MODE 1:Manual/datapoint 1.CONTROL_MODE 2:Holiday/datapoint 1.SET_POINT_TEMPERATURE 4.5:off/datapoint 1.SET_POINT_TEMPERATURE 30.5:on/",
statedatapoint => "1.SET_POINT_TEMPERATURE",
stripnumber => 1,
substexcl => "control",
substitute => "SET_POINT_TEMPERATURE!#0-4.5:off,#30.5-40:on;WINDOW_STATE!(0|false):closed,(1|true):open",
webCmd => "control:Boost:Auto:Manual:Holiday:on:off",
widgetOverride => "control:slider,4.5,0.5,30.5,1"
},
"HM-WDS40-TH-I|HM-WDS10-TH-O|HM-WDS20-TH-O|IS-WDS-TH-OD-S-R3|ASH550I|ASH550" => {
_description => "Temperatur/Luftfeuchte Sensor",
ccureadingfilter => "(^HUMIDITY|^TEMPERATURE)",
statedatapoint => "1.TEMPERATURE",
stripnumber => 1
}, },
"HM-ES-TX-WM" => { "HM-ES-TX-WM" => {
_description => "Stromzaehler Sensor", _description => "Energiezaehler Sensor",
ccureadingfilter => "(^UNREACH|LOWBAT|^ENERGY_COUNTER|^POWER)", ccureadingfilter => "(ENERGY_COUNTER|POWER)"
substitute => "UNREACH,LOWBAT!(true|1):yes,(false|0):no"
}, },
"HM-CC-VG-1" => { "HM-CC-VG-1" => {
_description => "Heizungsgruppe", _description => "Heizungsgruppe",
ccureadingfilter => "(^SET_TEMPERATURE|^TEMPERATURE|^HUMIDITY|LOWBAT\$|^VALVE|^CONTROL|^WINDOW_OPEN)", ccureadingfilter => "(^SET_TEMPERATURE|^TEMPERATURE|^HUMIDITY|^VALVE|^CONTROL|^WINDOW_OPEN)",
cmdIcon => "Auto:sani_heating_automatic Manu:sani_heating_manual Boost:sani_heating_boost on:general_an off:general_aus", cmdIcon => "Auto:sani_heating_automatic Manu:sani_heating_manual Boost:sani_heating_boost on:general_an off:general_aus",
controldatapoint => "1.SET_TEMPERATURE", controldatapoint => "1.SET_TEMPERATURE",
eventMap => "/datapoint 1.MANU_MODE 20.0:Manu/datapoint 1.AUTO_MODE 1:Auto/datapoint 1.BOOST_MODE 1:Boost/datapoint 1.MANU_MODE 4.5:off/datapoint 1.MANU_MODE 30.5:on/", eventMap => "/datapoint 1.MANU_MODE 20.0:Manu/datapoint 1.AUTO_MODE 1:Auto/datapoint 1.BOOST_MODE 1:Boost/datapoint 1.MANU_MODE 4.5:off/datapoint 1.MANU_MODE 30.5:on/",
statedatapoint => "1.SET_TEMPERATURE", statedatapoint => "1.SET_TEMPERATURE",
stripnumber => 1, stripnumber => 1,
substexcl => "control", substexcl => "control",
substitute => "LOWBAT!(0|false):no,(1|true):yes;CONTROL_MODE!0:AUTO,1:MANU,2:PARTY,3:BOOST;WINDOW_OPEN_REPORTING!(true|1):open,(false|0):closed;SET_TEMPERATURE!#0-4.5:off,#30.5-40:on", substitute => "CONTROL_MODE!0:AUTO,1:MANU,2:PARTY,3:BOOST;WINDOW_OPEN_REPORTING!(true|1):open,(false|0):closed;SET_TEMPERATURE!#0-4.5:off,#30.5-40:on",
webCmd => "control:Auto:Manu:Boost:on:off", webCmd => "control:Auto:Manu:Boost:on:off",
widgetOverride => "control:slider,3.5,0.5,30.5,1" widgetOverride => "control:slider,3.5,0.5,30.5,1"
}, },
"HM-Sec-MD|HM-Sec-MDIR|HM-Sec-MDIR-2|HM-Sec-MDIR-3" => { "HM-Sec-MD|HM-Sec-MDIR|HM-Sec-MDIR-2|HM-Sec-MDIR-3" => {
_description => "Bewegungsmelder", _description => "Bewegungsmelder",
ccureadingfilter => "(^UNREACH|LOWBAT|BRIGHTNESS|MOTION)", ccureadingfilter => "(BRIGHTNESS|MOTION)",
hmstatevals => "ERROR!1:sabotage",
statedatapoint => "1.MOTION", statedatapoint => "1.MOTION",
substitute => "LOWBAT,UNREACH,MOTION!(0|false):no,(1|true):yes" substitute => "MOTION!(0|false):no,(1|true):yes;ERROR!0:no,1:sabotage"
}, },
"HM-Sen-LI-O" => { "HM-Sen-LI-O" => {
_description => "Lichtsensor", _description => "Lichtsensor",
ccureadingfilter => "(^UNREACH|LUX|LOWBAT)", ccureadingfilter => "LUX",
statedatapoint => "1.LUX", statedatapoint => "1.LUX",
stripnumber => 1, stripnumber => 1
substitute => "LOWBAT,UNREACH!(0|false):no,(1|true):yes" },
"HM-CC-SCD" => {
_description => "CO2 Sensor",
ccureadingfilter => "STATE",
statedatapoint => "1.STATE",
substitute => "STATE!0:normal,1:added,2:strong"
},
"HM-Sec-SD-2" => {
_description => "Funk-Rauchmelder",
ccureadingfilter => "STATE",
hmstatevals => "ERROR_ALARM_TEST!1:alarm_test_failed;ERROR_SMOKE_CHAMBER!1:degraded_smoke_chamber",
statedatapoint => "1.STATE",
substitute => "ERROR_ALARM_TEST!0:no,1:failed;ERROR_SMOKE_CHAMBER!0:no,1:degraded"
},
"HM-Sec-SFA-SM" => {
_description => "Alarmsirene",
ccureadingfilter => "STATE",
hmstatevals => "ERROR_POWER!1:power_failure;ERROR_SABOTAGE!1:sabotage;ERROR_BATTERY!1:battery_defect",
statedatapoint => "1.STATE",
substitute => "STATE!(0|false):off,(1|true):alarm;ERROR_POWER!0:no,1:failure;ERROR_SABOTAGE!0:no,1:sabotage;ERROR_BATTERY!0:no,1:defect"
},
"HM-Sec-Sir-WM" => {
_description => "Funk-Innensirene",
ccureadingfilter => "STATE",
ccureadingname => "1.STATE:STATE_SENSOR1,2.STATE:STATE_SENSOR2,3.STATE:STATE_PANIC",
eventMap => "/datapoint 3.STATE true:panic/",
hmstatevals => "ERROR_SABOTAGE!1:sabotage",
statedatapoint => "4.ARMSTATE",
statevals => "disarmed:0,extsens-armed:1,allsens-armed:2,alarm-blocked:3",
substitute => "ERROR_SABOTAGE!(0|false):no,(1|true):yes;ARMSTATE!0:disarmed,1:extsens_armed,2:allsens_armed,3:alarm_blocked"
},
"WS550|WS888|WS550Tech|WS550LCB|WS550LCW|HM-WDC7000" => {
_description => "Wetterstation",
ccureadingfilter => "(TEMPERATURE|HUMIDITY|AIR_PRESSURE)",
statedatapoint => "10.TEMPERATURE",
stripnumber => 1
},
"HM-Sec-WDS|HM-Sec-WDS-2" => {
_description => "Funk-Wassermelder",
ccureadingfilter => "STATE",
statedatapoint => "1.STATE",
substitute => "STATE!0:dry,1:wet,2:water"
},
"HM-OU-CF-Pl|HM-OU-CFM-Pl|HM-OU-CFM-TW" => {
_description => "Funk-Gong mit Signalleuchte mit/ohne Batterie und Speicher",
ccureadingfilter => "STATE",
eventMap => "/datapoint 1.STATE 1:led-on/datapoint 1.STATE 0:led-off/datapoint 2.STATE 1:sound-on/datapoint 2.STATE 0:sound-off",
statedatapoint => "1.STATE",
statevals => "on:true,off:false",
substitute => "STATE!(0|false):ledOff,(1|true):ledOn;2.STATE!(0|false):soundOff,(1|true):soundOn"
}, },
"HM-PB-4Dis-WM" => { "HM-PB-4Dis-WM" => {
_description => "Funk-Display Wandtaster", _description => "Funk-Display Wandtaster",
ccureadingfilter => "(^UNREACH|LOWBAT|PRESS_SHORT|PRESS_LONG)", ccureadingfilter => "(PRESS_SHORT|PRESS_LONG)",
substitute => "PRESS_SHORT,PRESS_LONG!(1|true):pressed;UNREACH,LOWBAT!(1|true):yes,(0|false):no" substitute => "PRESS_SHORT,PRESS_LONG!(1|true):pressed"
}, },
"HM-Dis-EP-WM55" => { "HM-Dis-EP-WM55|HM-Dis-WM55" => {
_description => "E-Paper Display", _description => "E-Paper Display, Display Statusanzeige",
ccureadingfilter => "(^UNREACH|LOWBAT|PRESS_SHORT|PRESS_LONG)", ccureadingfilter => "PRESS",
substitute => "PRESS_LONG,PRESS_SHORT!(1|true):pressed;UNREACH,LOWBAT!(1|true):yes,(0|false):no" substitute => "PRESS_LONG,PRESS_SHORT,PRESS_CONT!(1|true):pressed,(0|false):notPressed;PRESS_LONG_RELEASE!(1|true):release"
} }
); );