From cc64f873fd79cc0aac2dbe81116ea2a20a1ce695 Mon Sep 17 00:00:00 2001 From: KRKeegan Date: Tue, 30 Jul 2013 19:06:18 -0700 Subject: [PATCH 1/5] Insteon: Relocate local_onlevel, local_ramprate, and update_local_properties Moved to the more appropriate DimmableLight class --- lib/Insteon/BaseInsteon.pm | 57 -------------------------------------- lib/Insteon/Lighting.pm | 54 ++++++++++++++++++++++++++++++++++++ 2 files changed, 54 insertions(+), 57 deletions(-) diff --git a/lib/Insteon/BaseInsteon.pm b/lib/Insteon/BaseInsteon.pm index 545c0fc87..ff8e00599 100644 --- a/lib/Insteon/BaseInsteon.pm +++ b/lib/Insteon/BaseInsteon.pm @@ -1887,42 +1887,6 @@ sub states } -=item C - -Sets and returns the local onlevel for the device in MH only. Level is a -percentage from 0%-100% - -=cut - -sub local_onlevel -{ - my ($self, $p_onlevel) = @_; - if (defined $p_onlevel) - { - my ($onlevel) = $p_onlevel =~ /(\d+)%?/; - $$self{_onlevel} = $onlevel; - } - return $$self{_onlevel}; -} - -=item C - -Sets and returns the local ramp rate for the device in MH only. Rate is a time -between .1 and 540 seconds. Only 32 rate steps exist, to MH will pick a time -equal to of the closest below this time. - -=cut - -sub local_ramprate -{ - my ($self, $p_ramprate) = @_; - if (defined $p_ramprate) { - $$self{_ramprate} = &Insteon::DimmableLight::convert_ramp($p_ramprate); - } - return $$self{_ramprate}; - -} - =item C Reviews the cached version of all of the ALDBs and based on this review removes @@ -1959,27 +1923,6 @@ sub log_alllink_table $self->_aldb->log_alllink_table if $self->_aldb; } -=item C - -Pushes the values set in C and C to the device. -The device will only reread these values when it is power-cycled. This can be -done by pulling the air-gap for 4 seconds or unplugging the device. - -=cut - -sub update_local_properties -{ - my ($self) = @_; - if ($self->isa('Insteon::DimmableLight')) - { - $self->_aldb->update_local_properties() if $self->_aldb; - } - else - { - &::print_log("[Insteon::BaseDevice] update_local_properties may only be applied to dimmable devices!"); - } -} - =item C Can be used to set the button layout and light level on a keypadlinc. Flag diff --git a/lib/Insteon/Lighting.pm b/lib/Insteon/Lighting.pm index 92d69cf18..ca20c0322 100644 --- a/lib/Insteon/Lighting.pm +++ b/lib/Insteon/Lighting.pm @@ -218,6 +218,60 @@ sub new return $self; } +=item C + +Sets and returns the local onlevel for the device in MH only. Level is a +percentage from 0%-100%. + +This setting can be pushed to the device using C. + +=cut + +sub local_onlevel +{ + my ($self, $p_onlevel) = @_; + if (defined $p_onlevel) + { + my ($onlevel) = $p_onlevel =~ /(\d+)%?/; + $$self{_onlevel} = $onlevel; + } + return $$self{_onlevel}; +} + +=item C + +Sets and returns the local ramp rate for the device in MH only. Rate is a time +between .1 and 540 seconds. Only 32 rate steps exist, to MH will pick a time +equal to of the closest below this time. + +This setting can be pushed to the device using C. + +=cut + +sub local_ramprate +{ + my ($self, $p_ramprate) = @_; + if (defined $p_ramprate) { + $$self{_ramprate} = &Insteon::DimmableLight::convert_ramp($p_ramprate); + } + return $$self{_ramprate}; + +} + +=item C + +Pushes the values set in C and C to the device. +The device will only reread these values when it is power-cycled. This can be +done by pulling the air-gap for 4 seconds or unplugging the device. + +=cut + +sub update_local_properties +{ + my ($self) = @_; + $self->_aldb->update_local_properties() if $self->_aldb; +} + =item C Takes the p_level, and stores it as a numeric level in memory. If the p_level From d5b2e4c83152bb80f76822a070bf0274b4c9657f Mon Sep 17 00:00:00 2001 From: KRKeegan Date: Tue, 30 Jul 2013 19:13:27 -0700 Subject: [PATCH 2/5] Insteon: Supplement update_local_properties to handle I2 devices - Added necessary messages. - Relocated definition of extended_get_set to BaseObject as multiple objects use this - Added some better descriptions of the functions --- lib/Insteon/BaseInsteon.pm | 1 + lib/Insteon/Controller.pm | 3 +-- lib/Insteon/IOLinc.pm | 6 ------ lib/Insteon/Lighting.pm | 36 ++++++++++++++++++++++++++++++++++-- lib/Insteon/Security.pm | 6 ------ 5 files changed, 36 insertions(+), 16 deletions(-) diff --git a/lib/Insteon/BaseInsteon.pm b/lib/Insteon/BaseInsteon.pm index ff8e00599..5f5959a89 100644 --- a/lib/Insteon/BaseInsteon.pm +++ b/lib/Insteon/BaseInsteon.pm @@ -1156,6 +1156,7 @@ our %message_types = ( peek => 0x2b, peek_internal => 0x2c, poke_internal => 0x2d, + extended_set_get => 0x2e, read_write_aldb => 0x2f, ); diff --git a/lib/Insteon/Controller.pm b/lib/Insteon/Controller.pm index 573439dc9..20b081bcb 100644 --- a/lib/Insteon/Controller.pm +++ b/lib/Insteon/Controller.pm @@ -59,8 +59,7 @@ use Insteon::BaseInsteon; my %message_types = ( %Insteon::BaseDevice::message_types, bright => 0x15, - dim => 0x16, - extended_set_get => 0x2e + dim => 0x16 ); =item C diff --git a/lib/Insteon/IOLinc.pm b/lib/Insteon/IOLinc.pm index d5186fee7..3e0b44bff 100755 --- a/lib/Insteon/IOLinc.pm +++ b/lib/Insteon/IOLinc.pm @@ -122,11 +122,6 @@ my %operating_flags = ( 'momentary_c_off' => '15', ); -my %message_types = ( - %Insteon::BaseDevice::message_types, - extended_set_get => 0x2e -); - =item C Instantiates a new object. @@ -138,7 +133,6 @@ sub new my ($class, $p_deviceid, $p_interface) = @_; my $self = new Insteon::BaseDevice($p_deviceid, $p_interface); $$self{operating_flags} = \%operating_flags; - $$self{message_types} = \%message_types; bless $self, $class; $self->restore_data('momentary_time'); $$self{momentary_timer} = new Timer; diff --git a/lib/Insteon/Lighting.pm b/lib/Insteon/Lighting.pm index ca20c0322..a273ae971 100644 --- a/lib/Insteon/Lighting.pm +++ b/lib/Insteon/Lighting.pm @@ -225,6 +225,10 @@ percentage from 0%-100%. This setting can be pushed to the device using C. +Parameters: level [0-100] + +Returns: [0-100] + =cut sub local_onlevel @@ -246,6 +250,10 @@ equal to of the closest below this time. This setting can be pushed to the device using C. +Parameters: rate = ramp rate [.1s - 540s] see C for valid values + +Returns: hexadecimal representation of the ramprate. + =cut sub local_ramprate @@ -261,23 +269,47 @@ sub local_ramprate =item C Pushes the values set in C and C to the device. + +I1 Devices: + The device will only reread these values when it is power-cycled. This can be done by pulling the air-gap for 4 seconds or unplugging the device. +I2 & I2CS Devices + +The device will immediately read and update the values. + =cut sub update_local_properties { my ($self) = @_; - $self->_aldb->update_local_properties() if $self->_aldb; + if ($self->engine_version eq 'I1'){ + $self->_aldb->update_local_properties() if $self->_aldb; + } + else { + #Queue Ramp Rate First + my $extra = '000005' . $self->local_ramprate(); + $extra .= '0' x (30 - length $extra); + my $message = new Insteon::InsteonMessage('insteon_ext_send', $self, 'extended_set_get', $extra); + $self->_send_cmd($message); + + #Now queue on level + $extra = '000006' . ::Insteon::DimmableLight::convert_level($self->local_onlevel()); + $extra .= '0' x (30 - length $extra); + $message = new Insteon::InsteonMessage('insteon_ext_send', $self, 'extended_set_get', $extra); + $self->_send_cmd($message); + } } =item C -Takes the p_level, and stores it as a numeric level in memory. If the p_level +Stores and returns the objects current on_level as a percentage. If p_level is ON and the device has a defined local_onlevel, the local_onlevel is stored as the numeric level in memory. +Returns [0-100] + =cut sub level diff --git a/lib/Insteon/Security.pm b/lib/Insteon/Security.pm index 27f7d04f0..6f69695ff 100644 --- a/lib/Insteon/Security.pm +++ b/lib/Insteon/Security.pm @@ -110,11 +110,6 @@ use Insteon::BaseInsteon; @Insteon::MotionSensor::ISA = ('Insteon::DeviceController','Insteon::BaseDevice'); -my %message_types = ( - %Insteon::BaseDevice::message_types, - extended_set_get => 0x2e -); - =item C Instantiates a new object. @@ -126,7 +121,6 @@ sub new my ($class,$p_deviceid,$p_interface) = @_; my $self = new Insteon::BaseDevice($p_deviceid,$p_interface); - $$self{message_types} = \%message_types; if ($self->is_root){ $self->restore_data('query_timer', 'last_query_time'); $$self{queue_timer} = new Timer; From 02ee1f22a2e30b26581a2a2e9f3df7b5126eead5 Mon Sep 17 00:00:00 2001 From: KRKeegan Date: Tue, 30 Jul 2013 20:42:55 -0700 Subject: [PATCH 3/5] Insteon: Move update_flags, Condense KeypadLinc Classes, Add I2 Support to update_flags - Update flags belongs in the Keypadlinc class as it only works on these devices - Condensed the set routine from Keypadlinc and KeypadlincRelay into Keypadlinc - Added I2 support to update_flags - - In order to support the old version of update_flags, the manner in which the routine works is a little odd as users have to pass a hexadecimal flag to the routine. This could obviously be changed or supplemented in the future. --- lib/Insteon/BaseInsteon.pm | 30 ----------- lib/Insteon/Lighting.pm | 108 +++++++++++++++++++++---------------- 2 files changed, 61 insertions(+), 77 deletions(-) diff --git a/lib/Insteon/BaseInsteon.pm b/lib/Insteon/BaseInsteon.pm index 5f5959a89..33bf97d77 100644 --- a/lib/Insteon/BaseInsteon.pm +++ b/lib/Insteon/BaseInsteon.pm @@ -1924,36 +1924,6 @@ sub log_alllink_table $self->_aldb->log_alllink_table if $self->_aldb; } -=item C - -Can be used to set the button layout and light level on a keypadlinc. Flag -options include: - - '0a' - 8 button; backlighting dim - '06' - 8 button; backlighting off - '02' - 8 button; backlighting normal - - '08' - 6 button; backlighting dim - '04' - 6 button; backlighting off - '00' - 6 button; backlighting normal - -Note: This routine will likely be moved to L at some point. - -=cut - -sub update_flags -{ - my ($self, $flags) = @_; - if (!($self->isa('Insteon::KeyPadLinc') or $self->isa('Insteon::KeyPadLincRelay'))) - { - &::print_log("[Insteon::BaseDevice] Operating flags may only be revised on keypadlincs!"); - return; - } - return unless defined $flags; - - $self->_aldb->update_flags($flags) if $self->_aldb; -} - =item C Sets or gets the device object engine version. If setting the engine version, diff --git a/lib/Insteon/Lighting.pm b/lib/Insteon/Lighting.pm index a273ae971..0a91dea56 100644 --- a/lib/Insteon/Lighting.pm +++ b/lib/Insteon/Lighting.pm @@ -712,6 +712,21 @@ use Insteon::BaseInsteon; @Insteon::KeyPadLincRelay::ISA = ('Insteon::BaseLight','Insteon::DeviceController'); +my %operating_flags = ( + 'program_lock_on' => '00', + 'program_lock_off' => '01', + 'led_on_during_tx' => '02', + 'led_off_during_tx' => '03', + 'resume_dim_on' => '04', + 'resume_dim_off' => '05', + '8_key_mode' => '06', + '6_key_mode' => '07', + 'led_off' => '08', + 'led_enabled' => '09', + 'key_beep_enabled' => '0a', + 'key_beep_off' => '0b' +); + =item C Instantiates a new object. @@ -762,6 +777,7 @@ sub set } else { + $link_state = $p_state if $self->can('level'); return $self->Insteon::DeviceController::set($link_state, $p_setby, $p_respond); } @@ -769,6 +785,50 @@ sub set } +=item C + +Can be used to set the button layout and light level on a keypadlinc. Flag +options include: + + '0a' - 8 button; backlighting dim + '06' - 8 button; backlighting off + '02' - 8 button; backlighting normal + + '08' - 6 button; backlighting dim + '04' - 6 button; backlighting off + '00' - 6 button; backlighting normal + +=cut + +sub update_flags +{ + my ($self, $flags) = @_; + return unless defined $flags; + if ($self->engine_version ne 'I1') { + $self->_aldb->update_flags($flags) if $self->_aldb; + } + else { + if ($flags & 0x02) { + $self->set_operating_flags('8_key_mode'); + } + else { + $self->set_operating_flags('6_key_mode'); + } + if ($flags & 0x04) { + $self->set_operating_flags('led_off'); + } + else { + $self->set_operating_flags('led_enabled'); + } + if ($flags & 0x08) { + $self->set_operating_flags('resume_dim_on'); + } + else { + $self->set_operating_flags('resume_dim_off'); + } + } +} + =back =head2 AUTHOR @@ -822,7 +882,7 @@ package Insteon::KeyPadLinc; use strict; use Insteon::BaseInsteon; -@Insteon::KeyPadLinc::ISA = ('Insteon::DimmableLight','Insteon::DeviceController'); +@Insteon::KeyPadLinc::ISA = ('Insteon::KeyPadLincRelay', 'Insteon::DimmableLight','Insteon::DeviceController'); =item C @@ -833,57 +893,11 @@ Instantiates a new object. sub new { my ($class,$p_deviceid,$p_interface) = @_; - my $self = new Insteon::DimmableLight($p_deviceid,$p_interface); bless $self,$class; return $self; } -=item C - -Handles setting and receiving states from the device and specifically its -subordinate buttons. - -NOTE: This could be merged somehow with the set() function in -C - -=cut - -sub set -{ - my ($self, $p_state, $p_setby, $p_respond) = @_; - - if (!($self->is_root)) - { - my $rslt_code = $self->Insteon::BaseController::set($p_state, $p_setby, $p_respond); - return $rslt_code if $rslt_code; - - my $link_state = &Insteon::BaseObject::derive_link_state($p_state); - - if (ref $p_setby and $p_setby->isa('Insteon::BaseDevice')) - { - $self->Insteon::BaseObject::set($p_state, $p_setby, $p_respond); - } - elsif (ref $$self{surrogate} && ($$self{surrogate}->isa('Insteon::InterfaceController'))) - { - $$self{surrogate}->set($link_state, $p_setby, $p_respond) - unless ref $p_setby and $p_setby eq $self; - } - else - { - &::print_log("[Insteon::KeyPadLinc] You may not directly attempt to set a keypadlinc's button " - . "unless you have defined a reverse link with the \"surrogate\" keyword"); - } - } - else - { - return $self->Insteon::DeviceController::set($p_state, $p_setby, $p_respond); - } - - return 0; - -} - =back =head2 AUTHOR From a853372623d0b4f0bf2b58944001a0fcec2f4672 Mon Sep 17 00:00:00 2001 From: KRKeegan Date: Tue, 30 Jul 2013 21:23:21 -0700 Subject: [PATCH 4/5] Insteon: Fix Typos in Update_Flags Routine --- lib/Insteon/BaseInsteon.pm | 2 +- lib/Insteon/Lighting.pm | 17 +++++++++-------- 2 files changed, 10 insertions(+), 9 deletions(-) diff --git a/lib/Insteon/BaseInsteon.pm b/lib/Insteon/BaseInsteon.pm index 33bf97d77..5fc64a860 100644 --- a/lib/Insteon/BaseInsteon.pm +++ b/lib/Insteon/BaseInsteon.pm @@ -545,7 +545,7 @@ sub derive_message if (!(defined $p_extra)) { if ($command eq 'on') { - if ($self->isa('Insteon::BaseDevice') && defined $self->local_onlevel) { + if ($self->can('local_onlevel') && defined $self->local_onlevel) { $level = 2.55 * $self->local_onlevel; $command = 'on_fast'; } else { diff --git a/lib/Insteon/Lighting.pm b/lib/Insteon/Lighting.pm index 0a91dea56..7945ea105 100644 --- a/lib/Insteon/Lighting.pm +++ b/lib/Insteon/Lighting.pm @@ -712,7 +712,7 @@ use Insteon::BaseInsteon; @Insteon::KeyPadLincRelay::ISA = ('Insteon::BaseLight','Insteon::DeviceController'); -my %operating_flags = ( +our %operating_flags = ( 'program_lock_on' => '00', 'program_lock_off' => '01', 'led_on_during_tx' => '02', @@ -736,8 +736,8 @@ Instantiates a new object. sub new { my ($class,$p_deviceid,$p_interface) = @_; - my $self = new Insteon::BaseLight($p_deviceid,$p_interface); + $$self{operating_flags} = \%operating_flags; bless $self,$class; return $self; } @@ -809,22 +809,22 @@ sub update_flags } else { if ($flags & 0x02) { - $self->set_operating_flags('8_key_mode'); + $self->set_operating_flag('8_key_mode'); } else { - $self->set_operating_flags('6_key_mode'); + $self->set_operating_flag('6_key_mode'); } if ($flags & 0x04) { - $self->set_operating_flags('led_off'); + $self->set_operating_flag('led_off'); } else { - $self->set_operating_flags('led_enabled'); + $self->set_operating_flag('led_enabled'); } if ($flags & 0x08) { - $self->set_operating_flags('resume_dim_on'); + $self->set_operating_flag('resume_dim_on'); } else { - $self->set_operating_flags('resume_dim_off'); + $self->set_operating_flag('resume_dim_off'); } } } @@ -894,6 +894,7 @@ sub new { my ($class,$p_deviceid,$p_interface) = @_; my $self = new Insteon::DimmableLight($p_deviceid,$p_interface); + $$self{operating_flags} = \%Insteon::KeyPadLincRelay::operating_flags; bless $self,$class; return $self; } From 3abcc1474ce7ce4ed924362e0397ad6e243c736d Mon Sep 17 00:00:00 2001 From: KRKeegan Date: Tue, 30 Jul 2013 22:58:30 -0700 Subject: [PATCH 5/5] Insteon: Fix Typo in Update_Flags Logic --- lib/Insteon/Lighting.pm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/Insteon/Lighting.pm b/lib/Insteon/Lighting.pm index 7945ea105..bcf81794e 100644 --- a/lib/Insteon/Lighting.pm +++ b/lib/Insteon/Lighting.pm @@ -804,7 +804,7 @@ sub update_flags { my ($self, $flags) = @_; return unless defined $flags; - if ($self->engine_version ne 'I1') { + if ($self->engine_version eq 'I1') { $self->_aldb->update_flags($flags) if $self->_aldb; } else {