Hauptmenü

Perl für Anfänger

Begonnen von 87insane, 04 Mai 2019, 12:17:07

Vorheriges Thema - Nächstes Thema

CoolTux

Zitat von: MCh76 am 16 Mai 2019, 08:28:26
super initiative. verzweifele auch regelmäßig an bestimmten punkten.

Dann darfst Du hier einen Punkt einbringen. Wir versuchen gemeinsam eine Lösung zu finden und wenn alles steht bringst Du Deine Lösung ins Wiki.
Ich denke es bedarf mehr Praxislösungen.

Wobei ich sagen muß das Beta-User sein Anliegen und seine Lösung schon ein Recht hohes Niveau.
Ich würde versuchen die Grundstruktur einer einer 99_myUtils auf zu zeigen und der Rest ist dann wieder Perl pur.
Du musst nicht wissen wie es geht! Du musst nur wissen wo es steht, wie es geht.
Support me to buy new test hardware for development: https://www.paypal.com/paypalme/MOldenburg
My FHEM Git: https://git.cooltux.net/FHEM/
Das TuxNet Wiki:
https://www.cooltux.net

CoolTux

Als Beispiel mal ganz einfach.

Ich möchte gerne eine myUtils für zukünftige komplexe Lichtsteuerung haben. Was genau ist unwichtig, aber da es komplex wird ist es immer gut sowas in eine myUtils aus zu lagern.
Also gehe ich daher und öffne die vorhandene
myUtilsTemplate.pm
erstes Bild

Diese speichere ich unter einen neuen Namen ab.
99_myUtils_Lichtsteuerung.pm
99 Weil nur Module mit 99 automatisch geladen werden. Immer und noch vor dem Start irgendwelcher anderer Module.

Jede Moduldatei bekommt eine Initialize Funktion. Diese heißt wie der Dateiname. Also für unsere Lichtsteuerung
99_myUtils_Lichtsteuerung.pm
myUtils_Lichtsteuerung_Initialize($$)

Das 99 kann man sich sparen.

Und das ist schon das ganze Geheimnis einer 99_myUtils. Ab hier kann man nun eigene Funktionen einbauen. ACHTUNG!!! Da die eigenen Funktionen in der main Routine laufen, also im Kontext des Hauptprogrammes müßen ein eindeutige Namen für die Funktionen verwendet werden. Es darf sie also nicht noch einmal geben sonst wird eine Überschrieben.


Grüße
Du musst nicht wissen wie es geht! Du musst nur wissen wo es steht, wie es geht.
Support me to buy new test hardware for development: https://www.paypal.com/paypalme/MOldenburg
My FHEM Git: https://git.cooltux.net/FHEM/
Das TuxNet Wiki:
https://www.cooltux.net

CoolTux

Und so kann dann eine Lichtsteuerung aussehen

##############################################
# $Id: myUtilsTemplate.pm 7570 2015-01-14 18:31:44Z rudolfkoenig $
#
# Save this file as 99_myUtils.pm, and create your own functions in the new
# file. They are then available in every Perl expression.

package main;

use strict;
use warnings;
use POSIX;



sub myUtils_LightControl_Initialize($$) {

  my ($hash) = @_;

}

###### Wohnungslicht ################
sub autoLightFn() {
    # Hilfsvariablen
    my $adv = adv();
    my ($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) = localtime(gettimeofday());
   
    ## Berechnung des Durchscnittlichen Helligkeitswertes und setzen des lux Wertes unter twilight
    # my $lux = (ReadingsVal('PflanzenSensor3','lux',1000) + ReadingsVal('PflanzenSensor2','lux',1000)) / 2;
    my $lux = ReadingsVal('brightnessWohnzimmer','lux',1000);
    readingsSingleUpdate($defs{'twilightStahnsdorf'},'lux',$lux,1);
   
    my $twilightWeather = ReadingsVal( 'twilightStahnsdorf', 'twilight_weather', 100 );
    my $twilight = ReadingsVal( 'twilightStahnsdorf', 'state', 6 );
    my $light = ReadingsVal( 'twilightStahnsdorf', 'light', 6 );
    my $presenceEltern = ReadingsVal('Eltern','state','absent');
    my $stateTv = Value('dummyLgTV');
    my $autoTwilightDummy = Value( 'LED_StreifenSelectTwilightDummy' );
    my $lichtWinter = Value('dummyLichtWinter');
    my $wheinachtsbaumAuto = Value('dummyWeihnachtsbaumAutoOFF');

    ########################
    ## Abends Licht an
    if ( $hour > 20 and $twilightWeather < 45 and $lux < 30 and ($stateTv eq 'on' or
     $presenceEltern eq 'home') ) {
    if ( $autoTwilightDummy eq 'on' ) {
            if ( $adv and $wheinachtsbaumAuto eq 'active' ) {     ## Abfrage Adventszeit aus 99_myUtils_Helper
                CommandSet(undef,'lightScenenLicht_Media scene Twilight_10_WohnzimmerFlurWeihnacht');
                CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on');
            }
            else {
                CommandSet(undef,'lightScenenLicht_Media scene Twilight_10_WohnzimmerFlur');
                CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on') if ( $lichtWinter eq 'active' );
            }
    }
        else {
            if ( $adv and $wheinachtsbaumAuto eq 'active' ) {     ## Abfrage Adventszeit aus 99_myUtils_Helper
                CommandSet(undef,'lightScenenLicht_Media scene Twilight_10_WohnzimmerWeihnacht');
                CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on');
            }
            else {
                CommandSet(undef,'lightScenenLicht_Media scene Twilight_10_Wohnzimmer');
                CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on') if ( $lichtWinter eq 'active' );
            }
    }
    }
    elsif ( $hour > 19 and $twilightWeather < 60 and $lux < 30 and ($stateTv eq 'on' or
     $presenceEltern eq 'home') ) {
    if ( $autoTwilightDummy eq 'on' ) {
            if (  $adv and $wheinachtsbaumAuto eq 'active' ) {     ## Abfrage Adventszeit aus 99_myUtils_Helper
                CommandSet(undef,'lightScenenLicht_Media scene Twilight_8_WohnzimmerFlurWeihnacht');
                CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on');
            }
            else {
                CommandSet(undef,'lightScenenLicht_Media scene Twilight_8_WohnzimmerFlur');
                CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on') if ( $lichtWinter eq 'active' );
            }
    }
        else {
            if ( $adv and $wheinachtsbaumAuto eq 'active' ) {     ## Abfrage Adventszeit aus 99_myUtils_Helper
                CommandSet(undef,'lightScenenLicht_Media scene Twilight_8_WohnzimmerWeihnacht');
                CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on');
            }
            else {
                CommandSet(undef,'lightScenenLicht_Media scene Twilight_8_Wohnzimmer');
                CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on') if ( $lichtWinter eq 'active' );
            }
    }
    }
    elsif ( (($twilightWeather < 75 and $twilightWeather > 24 and $twilight > 6
          and $twilight < 11 ) or ($twilightWeather < 65 and $twilight >= 5
          and $twilight < 11))
        and ($stateTv eq 'on' or $presenceEltern eq 'home') and $lux < 30 ) {

        if ( $autoTwilightDummy eq 'on' ) {
                if ( $adv and $wheinachtsbaumAuto eq 'active' ) {     ## Abfrage Adventszeit aus 99_myUtils_Helper
                    CommandSet(undef,'lightScenenLicht_Media scene Twilight_7_WohnzimmerFlurWeihnacht');
                    CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on');
                }
                else {
                    CommandSet(undef,'lightScenenLicht_Media scene Twilight_7_WohnzimmerFlur');
                    CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on') if ( $lichtWinter eq 'active' );
                }
        }
            else {
                if ( $adv and $wheinachtsbaumAuto eq 'active' ) {     ## Abfrage Adventszeit aus 99_myUtils_Helper
                    CommandSet(undef,'lightScenenLicht_Media scene Twilight_7_WohnzimmerWeihnacht');
                    CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on');
                } else {
                    CommandSet(undef,'lightScenenLicht_Media scene Twilight_7_Wohnzimmer');
                    CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on') if ( $lichtWinter eq 'active' );
                }
        }
           
            CommandSet(undef,'LichtDimmerStevenDeckenLampe_Sw:FILTER=state=off pct 50')
              if ( Value('rr_Steven') eq 'home'
                and Value('rg_Anna') ne 'asleep'
                and ReadingsVal('brightnessStevensZimmer','lux',50) < 15
                and ReadingsVal('brightnessStevensZimmer','dark',50) == 1
                and Value('presenceStevensZimmer') eq 'motion'
                and Value('autoLichtsteuerungSteven') eq 'on' );
    }
    elsif ( $twilightWeather < 85 and $twilightWeather > 24 and $twilight > 6
     and $twilight < 8 and ReadingsVal('brightnessFlur','lux',50) < 10 ) {
    fhem('set LED_StreifenFlurDecke bri 254; set LED_StreifenFlurDecke hue 44444 : sat 90') if ( $autoTwilightDummy eq 'on' );
    }
    elsif ( $twilightWeather < 85 and $twilight == 6
     and ReadingsVal( 'twilightStahnsdorf', 'nextEvent', 'ss_weather' ) eq 'ss_weather' and ReadingsVal('brightnessFlur','lux',50) < 10 ) {
    fhem('set LED_StreifenFlurDecke bri 254; set LED_StreifenFlurDecke hue 44444 : sat 90') if ( $autoTwilightDummy eq 'on' );
    }
    ### Wenn die Eltern nicht zu Hause sind aber die Kinder
    elsif ( $twilightWeather < 55 and $twilight > 9
     and $presenceEltern ne 'home' and ReadingsVal('Kinder','state','absent') eq 'home' and $lux < 10 ) {
    fhem('set LED_StreifenFlurDecke bri 254; set LED_StreifenFlurDecke hue 44444 : sat 90') if ( $autoTwilightDummy eq 'on' and $hour < 20 );
        fhem('set LED_StreifenFlurDecke bri 100; set LED_StreifenFlurDecke hue 47104 : sat 254') if ( $autoTwilightDummy eq 'on' and $hour > 19 );
        CommandSet(undef,'Weihnachtsbeleuchtung=on:FILTER=state=off on') if ( $adv or $lichtWinter eq 'active' );     ## Abfrage Adventszeit aus 99_myUtils_Helper
        CommandSet(undef,'LichtDimmerStevenDeckenLampe_Sw:FILTER=state=off pct 50')
          if ( Value('rr_Steven') eq 'home'
            and Value('rg_Anna') ne 'asleep'
            and $lux < 10
            and Value('presenceStevensZimmer') eq 'motion'
            and Value('autoLichtsteuerungSteven') eq 'on' );
    }
    ########################
    ## Abends Licht aus

    elsif ( $twilightWeather < 66 and $twilight > 5
     and $stateTv eq 'off' and Value('structureLichtIsabelsZimmer') eq 'on' and $presenceEltern ne 'home' ) {
    CommandSet(undef,'structureLichtWohnzimmer [FILTER=STATE!=off] off') if ( $autoTwilightDummy eq 'on' );
    }
    ########################
    ## Morgens Licht aus

    elsif ( $twilight > 4 and $twilightWeather > 30 and $lux > 50 and $lux < 50 ) {
    fhem('set (structureLichtWohnzimmer|NetzschalterKinZimIsabelHintenLinks):FILTER=STATE=on off; set Weihnachtsbeleuchtung=on:FILTER=state=on off');
        CommandSet(undef,'group=Licht.Weihnachtsbaum:FILTER=state=on off') if ( $wheinachtsbaumAuto eq 'active' ) ;
    }
    elsif( $twilight == 5 and $twilightWeather > 30 and $lux > 50 ) {
    fhem('set (structureLichtWohnzimmer|NetzschalterKinZimIsabelHintenLinks):FILTER=STATE=on off; set Weihnachtsbeleuchtung=on:FILTER=state=on off');
        CommandSet(undef,'group=Licht.Weihnachtsbaum:FILTER=state=on off') if ( $wheinachtsbaumAuto eq 'active' ) ;
       
        CommandSet(undef,'LED_StreifenFlurDecke:FILTER=onoff=1 off') if ( $autoTwilightDummy eq 'on' and $lux > 50);
        CommandSet(undef,'LichtDimmerStevenDeckenLampe_Sw:FILTER=state!=off off')
          if ( Value('rr_Steven') eq 'home'
            and Value('rg_Anna') ne 'asleep'
            and $lux > 25
            and Value('autoLichtsteuerungSteven') eq 'on' );
    }
    elsif ( ReadingsVal( "twilightStahnsdorf", "state", "100" ) == 6 and $twilightWeather > 30 and $lux > 50 or ($lux > 70 and $lux < 200 and $light > 3) ) {
        fhem('set (structureLichtWohnzimmer|structureLichtBadezimmer|NetzschalterKinZimIsabelHintenLinks):FILTER=STATE=on off; set Weihnachtsbeleuchtung=on:FILTER=state=on off');
        CommandSet(undef,'group=Licht.Weihnachtsbaum:FILTER=state=on off') if ( $wheinachtsbaumAuto eq 'active' );
       
        if ( ReadingsVal( 'twilightStahnsdorf', 'elevation', 15 ) < 15 and $twilightWeather > 75 and $lux > 100 ) {
            CommandSet(undef,'LED_StreifenFlurDecke:FILTER=onoff=1 off') if ( $autoTwilightDummy eq 'on' );
        }
       
        elsif ( ReadingsVal( 'twilightStahnsdorf', 'elevation', '15' ) > 15 and $lux > 100 ) {
            CommandSet(undef,'LED_StreifenFlurDecke:FILTER=onoff=1 off') if ( $autoTwilightDummy eq 'on' );
        }
       
        CommandSet(undef,'LED_StreifenFlurDecke:FILTER=onoff=1 off') if ( $autoTwilightDummy eq 'on' and $lux > 150 );
        CommandSet(undef,'LichtDimmerStevenDeckenLampe_Sw:FILTER=state!=off off')
          if ( Value('rr_Steven') eq 'home'
            and Value('rg_Anna') ne 'asleep'
            and ReadingsVal('brightnessStevensZimmer','lux',50) > 30
            and Value('autoLichtsteuerungSteven') eq 'on' );
    }
}

################################
##### Kaminfeuer ###############
sub startFireEffect(@) {
    my @bulbs=@_;
    foreach (@bulbs) {
        my $bulb=$_;
        my $hue = int((rand()*3460)+5460);
        my $sat = int(rand(64)+170);
        my $bri = int(rand(60)+16);
        my $delay = (rand()+0.1);
        my $transitiontime = int($delay * 10);
        fhem("set $bulb hue $hue: sat $sat : bri $bri : transitiontime $transitiontime : noUpdate");
        InternalTimer(gettimeofday()+$delay, 'startFireEffect', $bulb, 0);
    }
}

sub stopFireEffect(@) {
    my @bulbs=@_;
    foreach (@bulbs) {
        my $bulb=$_;
        RemoveInternalTimer($bulb);
        fhem("set $bulb off");
    }
}

sub startFireWorkEffect(@) {
   my @bulbs=@_;
   foreach (@bulbs) {
     my $bulb=$_;
     my $hue = int((rand(65534))+1);
     my $bri = int(rand(224)+30);
     my $transitiontime = int((rand(30))+1);
     my $delay = int(($transitiontime / 10)+1);
fhem("set $bulb hue $hue : bri $bri : transitiontime 1 immediateUpdate:noUpdate");
fhem("set $bulb rgb 000000 : transitiontime $transitiontime");
InternalTimer(gettimeofday()+$delay, 'startFireWorkEffect', $bulb, 0);
  }
}

sub stopFireWorkEffect(@) {
   my @bulbs=@_;
   foreach (@bulbs) {
     my $bulb=$_;
     RemoveInternalTimer($bulb);
##    fhem("set $bulb off");
   }
}

##############################################
### Sonnenaufgang / WakeUp Light
sub wakeuplight($@) {

    my ($ramptime,@lamps) = @_;
    my @sonne = ('0B0300','0B0300','0B0300','0C0300','0C0300','0C0300','0D0300','0D0300','0E0300','0E0300','0E0300','0F0300','0F0300','100300','100300','100300','110300','110300','110300','120300','120300',
                    '130300','130300','130300','140300','140300','150300','150300','150300','160300','160300','160300','170300','170300','180300','180401','180401','190401','190401','1A0401','1A0401','1A0401',
                    '1B0401','1B0401','1B0401','1C0401','1C0401','1D0401','1D0401','1D0401','1E0401','1E0401','1F0401','1F0401','1F0401','200401','200401','210401','210401','210401','220401','220401','220401',
                    '230401','230401','240401','240401','240401','250401','250502','260502','260502','260502','270502','270502','270502','280502','280502','290502','290502','290502','2A0502','2A0502','2B0502',
                    '2B0502','2B0502','2C0502','2C0502','2C0502','2D0502','2D0502','2E0502','2E0502','2E0502','2F0502','2F0502','300502','300502','300502','310502','310502','310502','320502','320603','330603',
                    '330603','330603','340603','340603','350603','350603','350603','360603','360603','370603','370603','370603','380603','380603','380603','390603','390603','3A0603','3A0603','3A0603','3B0603',
                    '3B0603','3C0603','3C0603','3C0603','3D0603','3D0603','3D0603','3E0603','3E0603','3F0603','3F0603','3F0704','400704','400704','410704','410704','410704','420704','420704','420704','430704',
                    '430704','440704','440704','440704','450704','450704','460704','460704','460704','470704','470704','470704','480704','480704','490704','490704','490704','4A0704','4A0704','4B0704','4B0704',
                    '4B0704','4C0704','4C0704','4D0805','4E0905','4F0A05','500B05','510C05','520D06','530E06','540F06','551006','561106','571207','581307','591407','5A1507','5B1607','5C1708','5D1908','5E1A08',
                    '5F1B08','601C09','611D09','621E09','631F09','642009','65210A','66220A','67230A','68240A','69250A','6A260B','6B270B','6C290B','6D2A0B','6E2B0B','6F2C0C','702D0C','712E0C','722F0C','73300D',
                    '74310D','75320D','76330D','77340D','79350E','7A360E','7B370E','7C380E','7D3A0E','7E3B0F','7F3C0F','803D0F','813E0F','823F10','834010','844110','854210','864310','874411','884511','894611',
                    '8A4711','8B4811','8C4A12','8D4B12','8E4C12','8F4D12','904E12','914F13','925013','935113','945213','955314','965414','975514','985614','995714','9A5815','9B5915','9C5B15','9D5C15','9E5D15',
                    '9F5E16','A05F16','A16016','A26116','A46217','A56317','A66417','A76517','A86617','A96718','AA6818','AB6918','AC6B18','AD6C18','AE6D19','AF6E19','B06F19','B17019','B27119','B3721A','B4731A',
                    'B5741A','B6751A','B7761B','B8771B','B9781B','BA791B','BB7A1B','BC7C1C','BD7D1C','BE7E1C','BF7F1C','C0801C','C1811D','C2821D','C3831D','C4841D','C5851D','C6861E','C7871E','C8881E','C9891E',
                    'CA8A1F','CB8C1F','CC8D1F','CD8E1F','CE8F1F','D09020','D19120','D29220','D39320','D49420','D59521','D69621','D79721','D89821','D99922','DA9A22','DB9B22','DC9D22','DD9E22','DE9F23','DFA023',
                    'E0A123','E1A223','E2A323','E3A424','E4A524','E5A624','E6A724','E7A824','E8A925','E9AA25','EAAB25','EBAD25','ECAE26','EDAF26','EEB026','EFB126','F0B226','F1B327','F2B427','F3B527','F4B627',
                    'F5B727','F6B828','F7B928','F8BA28','F9BB28','FBBD29','FBBD29','FBBD2A','FBBD2B','FBBD2B','FBBE2C','FBBE2D','FBBE2E','FBBE2E','FBBF2F','FBBF30','FBBF31','FBBF31','FBBF32','FBC033','FBC034',
                    'FBC034','FBC035','FBC136','FBC137','FBC137','FBC138','FBC239','FBC23A','FBC23A','FBC23B','FBC23C','FBC33D','FBC33D','FBC33E','FBC33F','FBC43F','FBC440','FBC441','FBC442','FBC542','FBC543',
                    'FBC544','FBC545','FBC545','FBC646','FBC647','FBC648','FBC648','FBC749','FBC74A','FBC74B','FBC74B','FBC84C','FBC84D','FBC84E','FBC84E','FBC84F','FBC950','FBC951','FBC951','FBC952','FBCA53',
                    'FBCA53','FBCA54','FBCA55','FBCA56','FBCB56','FBCB57','FBCB58','FBCB59','FBCC59','FBCC5A','FBCC5B','FBCC5C','FBCD5C','FBCD5D','FBCD5E','FBCD5F','FBCD5F','FBCE60','FBCE61','FBCE62','FBCE62',
                    'FBCF63','FBCF64','FBCF65','FBCF65','FBD066','FBD067','FCD068','FCD068','FCD069','FCD16A','FCD16A','FCD16B','FCD16C','FCD26D','FCD26D','FCD26E','FCD26F','FCD370','FCD370','FCD371','FCD372',
                    'FCD373','FCD473','FCD474','FCD475','FCD476','FCD576','FCD577','FCD578','FCD579','FCD679','FCD67A','FCD67B','FCD67C','FCD67C','FCD77D','FCD77E','FCD77E','FCD77F','FCD880','FCD881','FCD881',
                    'FCD882','FCD883','FCD984','FCD984','FCD985','FCD986','FCDA87','FCDA87','FCDA88','FCDA89','FCDB8A','FCDB8A','FCDB8B','FCDB8C','FCDB8D','FCDC8D','FCDC8E','FCDC8F','FCDC90','FCDD90','FCDD91',
                    'FCDD92','FCDD92','FCDE93','FCDE94','FCDE95','FCDE95','FCDE96','FCDF97','FCDF98','FCDF98','FCDF99','FCE09A','FCE09B','FCE09B','FCE09C','FCE19D','FCE19E','FCE19E','FCE19F','FCE1A0','FCE2A1',
                    'FCE2A1','FCE2A2','FCE2A3','FCE3A4','FCE3A4','FCE3A5','FCE3A6','FDE4A7'
                );

    my $sleepPerStep = $ramptime/@sonne;
    my $cmd = "";
    my $cancel = "";
    my $i = 1;
    my $lamp = "";

    foreach my $rgb (@sonne) {
        foreach $lamp (@lamps) {
            $cmd .= "set $lamp rgb $rgb;"; 
        }
       
        $cmd .= "sleep $sleepPerStep slwul_$i;";
        $cancel .= "cancel slwul_$i quiet;;";
   
        $i++;
    }

    foreach $lamp (@lamps) {
        $cancel .= "set $lamp off;;"; 
    }
   
    # mglw. bereits laufendes WUL beenden
    fhem('cancel_wul');
   
    # alias cancel_wul neu anlegen
    fhem("defmod cancel_wul cmdalias cancel_wul AS $cancel");
   
    # WUL starten
    fhem("$cmd if $cmd ne ''");
}

sub motionSensorControl($) {
    ## Hilfsvariablen
    my ($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) = localtime(gettimeofday());
   
    my $dev = shift;
    my $room = AttrVal($dev,'room','none');
    my $doswitch = 0;
    my $lux = ReadingsVal('brightness'.$room,'lux',100);
    my $daylight = ReadingsVal('brightness'.$room,'daylight',1);
    my $dark = ReadingsVal('brightness'.$room,'dark',0);
    my $resGotoSleep = ReadingsVal('AnniKraussStr','residentsGotosleep',0);
    my $resState = ReadingsVal('AnniKraussStr','state','home');
    my $stripeCmd;
    my $onForTimer = 300;
   
    if ( $room eq 'Badezimmer' ) {
        $doswitch = 1
        if (
          (isInTime('04:00-07:00')
            and $lux < 30
            and $daylight == 0)
          or
          (isInTime('18:00-24:00')
            and $resGotoSleep > 0
            and $lux < 15
            and $dark == 1)
        );
       
        $onForTimer = 900;
    }

    CommandSet(undef,'(LichtSchalter|LichtDimmer).*DeckenLampe_Sw:FILTER=room='.$room.' on-for-timer '.$onForTimer)
    if ( $doswitch );
}




1;
Du musst nicht wissen wie es geht! Du musst nur wissen wo es steht, wie es geht.
Support me to buy new test hardware for development: https://www.paypal.com/paypalme/MOldenburg
My FHEM Git: https://git.cooltux.net/FHEM/
Das TuxNet Wiki:
https://www.cooltux.net

Beta-User

Zitat von: CoolTux am 16 Mai 2019, 08:42:13
Dann darfst Du hier einen Punkt einbringen. Wir versuchen gemeinsam eine Lösung zu finden und wenn alles steht bringst Du Deine Lösung ins Wiki.
Auch wenn ich hier nicht der TE bin, würde ich vorschlagen, nicht alle möglichen Punkte hier einzubringen, sondern ggf. dazu dann einen eigenen Thread aufzumachen und von hier zu verlinken. So bleiben wir bei einem Thema, alles andere birgt das hohe Risiko, dass es schnell sehr unübersichtlich.

ZitatIch denke es bedarf mehr Praxislösungen.
Da stimme ich dir in Teilen zu; es ist aber auch schon einiges vorhanden (das ggf. mal überarbeitet werden sollte). Eine Sammlung - einschließlich einer (noch?) nicht bebilderten Anleitung, wie man "myUtils" anlegt, ist auch im Wiki zu finden: https://wiki.fhem.de/wiki/99_myUtils_anlegen bzw. das habe ich die Tage mal zusammengetragen. Wer da was brauchbares hat: her damit.

ZitatWobei ich sagen muß das Beta-User sein Anliegen und seine Lösung schon ein Recht hohes Niveau.
Ich würde versuchen die Grundstruktur einer einer 99_myUtils auf zu zeigen und der Rest ist dann wieder Perl pur.
Das "Grunddingens" (=Anliegen?) ist m.E. eher basic, und zu den Erweiterungen hatte ich ja geschrieben, dass das - jeweils für sich - kleine bzw. größere Herausforderungen (für Anfänger) sind.




Meine Idee war, das hier im Thread Schritt für Schritt zu entwickeln, um zu zeigen, wie man Infos zwischen der "puren" Perl-Ebene und der "FHEM"-Ebene austauschen kann. Danach kann man entscheiden, ob es als "Vorzeigebeispiel" (gestrafft) ins Wiki soll.

Um wieder zu diesem Ansatz zurückzukommen:

Zitat von: Beta-User am 14 Mai 2019, 13:04:16
Ich hatte eigentlich eher daran gedacht, die Funktion mit einem weitere Parameter für die Zeit aufzurufen.
Da das evtl. etwas abstrakt ist, lautet also die in diesem "Schritt-für-Schritt zu lösende erste Teilaufgabe konkreter, die DEF des notify so zu ändern:
Pumpe_Zisterne:.on {mySwitchOffAfter($NAME,"01:05")}
Mag jetzt jemand (von den Anfängern!) den entsprechend geänderten myUtils-Code erstellen und posten? Das muß noch nicht als optionaler Aufruf ausgelegt sein; das machen wir in Schritt 1b). Das sollte ohne weiteres mit Hilfe der o.g. Wiki-Seite zu lösen sein ;) .)
Server: HP-elitedesk@Debian 12, aktuelles FHEM@ConfigDB | CUL_HM (VCCU) | MQTT2: ZigBee2mqtt, MiLight@ESP-GW, BT@OpenMQTTGw | ZWave | SIGNALduino | MapleCUN | RHASSPY
svn: u.a Weekday-&RandomTimer, Twilight,  div. attrTemplate-files, MySensors

87insane

Bin da offen... Kann ich zusätzliche Personen zum Admin machen in einem Thread, hier?
Würde am WE hier mal aufräumen und es ordentlich gestalten....

Beta-User

M.E. braucht man noch nicht aufzuräumen, sooo unübersichtlich ist es doch (noch) nicht, oder?

Für eine "Wiki-Fassung" sollte es dann kein Problem sein, Auszüge rausnehmen, wer dann die "full Story" will, kann das dann ja nachlesen und findet ggf. auch die "Seitenzweige", wenn jemand ein anderes/weiteres/Teil-Problem aufmacht, und es dann hier verlinkt.



Zum Stichwort "Seitenzweige":
Evtl. würde es Sinn machen, wenn CoolTux sein Beispiel im Anfängerbereich oder unter Codeschnipsel veröffentlicht, dann kann man da dann konkrete Fragen dazu stellen. Ich würde bei dieser komplexen Geschichte aber anregen, ggf. "vorneweg" einen "Einrichtungsabschnitt" reinzumachen. Dort könnte man dann die Parametrierung zentral machen (also z.B. wie der Helligkeitssensor heißt usw.), damit der eigentliche Code für "Nachahmer" ggf. leichter angepaßt werden kann.
Server: HP-elitedesk@Debian 12, aktuelles FHEM@ConfigDB | CUL_HM (VCCU) | MQTT2: ZigBee2mqtt, MiLight@ESP-GW, BT@OpenMQTTGw | ZWave | SIGNALduino | MapleCUN | RHASSPY
svn: u.a Weekday-&RandomTimer, Twilight,  div. attrTemplate-files, MySensors

Beta-User

#21
Zitat von: Beta-User am 16 Mai 2019, 09:40:02
Um wieder zu diesem Ansatz zurückzukommen:
Da das evtl. etwas abstrakt ist, lautet also die in diesem "Schritt-für-Schritt zu lösende erste Teilaufgabe konkreter, die DEF des notify so zu ändern:
Pumpe_Zisterne:.on {mySwitchOffAfter($NAME,"01:05")}
Mag jetzt jemand (von den Anfängern!) den entsprechend geänderten myUtils-Code erstellen und posten? Das muß noch nicht als optionaler Aufruf ausgelegt sein; das machen wir in Schritt 1b). Das sollte ohne weiteres mit Hilfe der o.g. Wiki-Seite zu lösen sein ;) .)
Hmmm, das scheint zu einfach gewesen zu sein, oder warum traut sich keiner?

Hier also der nächste Schritt (Übergabe der Parameter in dem Fall nicht mit shift, sondern in einer anderen weit verbreiteten Form):

##############################################
# $Id: 99_myUtilsGeneralUse.pm 2019-05-17 Beta-User $
#
# forum: https://forum.fhem.de/index.php/topic,100206.msg939873.html#msg939873
#

package main;

use strict;
use warnings;
use POSIX;

sub
myUtilsGeneralUse_Initialize($$)
{
  my ($hash) = @_;
}

# Enter you functions below _this_ line.

sub
mySwitchOffAfter($$) {
  my ($ondevice,$duration) = @_;
  #Alternative writing (will modify @_):
  #my $ondevice = shift(@_);
  #my $duration = shift(@_);

  #gleichbedeutend mit 'fhem "defmod my_switchoff_$ondevice at +$duration set $ondevice off"'
  CommandDefMod(undef,"my_switchoff_$ondevice at +$duration set $ondevice off");
}

1;

Damit hätten wir den ersten Punkt auf der Liste erledigt:
Zitat von: Beta-User am 14 Mai 2019, 10:59:01
An unsere Einsteiger in das Thema: Wenn jemand Interesse an meinem Beispielchen hat, kann er gerne mal versuchen, das dahingehend zu erweitern, dass
- auch die Zeitdauer mitgegeben werden kann;
- die Zeitdauer _optional_ ist, wird keine angegeben, soll ein default-Wert gelten;
- kein at erstellt wird, sondern ein InternalTimer (damit kein Raum angelegt wird);
- ein SetExtensions-on anders behandelt wird (soll Vorrang haben, Pumpe bleibt als an, z.B. weil die Bewässerung durch einen Automatismus gesteuert wird, der länger aktiv ist).
Das nächste wäre also, die Zeitdauer optional zu machen, also: kann angegeben werden, muß aber nicht. Wird sie nicht angegeben, soll nach einer Stunde und einer Sekunde abgeschaltet werden.

Ausblick:
- Den smiley für die nächste Teilaufgabe kann man sich bis irgendwann Montag verdienen, dann gibt's ggf. einen Lösungsvorschlag von meiner Seite (beachten: Nach der allgemeinen Philosophie bei Perl sind immer mehrere Lösungswege möglich und zulässig...)

- Zu Schritt 3 würde ich noch eine Zwischenstufe einbauen wollen: FHEM-sleep (im Unterschied zu Perl-sleep).

Schönes WE allseits!
Server: HP-elitedesk@Debian 12, aktuelles FHEM@ConfigDB | CUL_HM (VCCU) | MQTT2: ZigBee2mqtt, MiLight@ESP-GW, BT@OpenMQTTGw | ZWave | SIGNALduino | MapleCUN | RHASSPY
svn: u.a Weekday-&RandomTimer, Twilight,  div. attrTemplate-files, MySensors

87insane

Naja... Leute wie ich brauchen dafür länger. Zum einen arbeite ich und zum anderen ist das bei mir mit x Tests verbunden bis ich das hin bekomme. Denk mal an das erste Template von mir. Das waren fast drei Wochen, an denen ich jeden Abend versucht und geweint habe bis es dann fertig war ;)

Beta-User

Zitat von: 87insane am 17 Mai 2019, 11:27:48
Naja... Leute wie ich brauchen dafür länger. Zum einen arbeite ich und zum anderen ist das bei mir mit x Tests verbunden bis ich das hin bekomme. Denk mal an das erste Template von mir. Das waren fast drei Wochen, an denen ich jeden Abend versucht und geweint habe bis es dann fertig war ;)
Du bist der TE ;) .

Du darfst daher auch bestimmen, wann es frühestens von meiner Seite aufgelöst werden soll... (Aber andere dürfen gerne früher, oder?)
Server: HP-elitedesk@Debian 12, aktuelles FHEM@ConfigDB | CUL_HM (VCCU) | MQTT2: ZigBee2mqtt, MiLight@ESP-GW, BT@OpenMQTTGw | ZWave | SIGNALduino | MapleCUN | RHASSPY
svn: u.a Weekday-&RandomTimer, Twilight,  div. attrTemplate-files, MySensors

87insane

War bisher eher am warten, wer alles mitmacht und wie man hier sogar zusammen arbeiten könnte. Aber leider gibt es bisher nur viele Mitleser aber wenig Tester. Bitte löse dann noch nicht weiter auf. Ich brauche ewig und wenn ich einer der Wenigen bin, die das aktiv versuchen, dann gib mir Zeit :)
Nebenbei laufen ja auch noch andere Projekte.

Wenn natürlich jemand was postet und du siehst das es nur eine Kleinigkeit ist, die falsch ist, dann kannst du auf deine Art gerne Hinweise geben. Bin aber schon dankbar für dein Beispiel und ich glaube auch CoolTux hat was geschrieben. Danke!

Prof. Dr. Peter Henning

Hmmm.

Das "Lernen von Perl" und das "Lösen von Perl-Problemen" sind zwei ganz unterschiedliche Dinge.

Ersteres lässt sich mit ein paar Seiten Text und grundlegenden Programmierkenntnissen schnell erledigen. Dafür stelle ich gerne das Perl-Kapitel aus dem "Handbuch Programmiersprachen" (erschienen 2006, ich bin einer der Herausgeber) hier kostenlos zur Verfügung (stammt auch direkt von mir).

Ersteres lässt sich nicht gut erledigen, wenn keinerlei Programmierkenntnisse vorhanden sind. Dafür ist Perl, vorsichtig gesagt, nicht gut geeignet.


Und das zweite, nämlich das Lösen von Perl-Problemen, lässt sich eben nicht generalisieren und mit einer größeren Gruppe gleichzeitig behandeln.

LG

pah

87insane

Das ist doch mal ne nette Geschichte! Danke!

Naja, wenn man schon bei der Syntax Probleme hat, dann sind die Grundkenntnisse natürlich wichtig. Ich selber bin sogar in der IT aber eben Admin. Programmieren muss man da meist nur ein paar Zeilen und das ist auch kein richtiges programmieren. So wie es alleine bei einem devStateIcon in FHEM ist, ist das für mich teilweise oder eher meistens echt komisch.

Hinzu dachte ich bzw. denke ich das ggf. ein paar Personen auch Interesse haben mal in live mit ein paar anderen drüber zu sprechen oder zu üben. Die ganze Theorie lese ich immer wieder aber da versteh ich nicht immer alles und da hilft es ungemein, jemanden zu kennen der es mit anderen Worten nochmal neu formuliert.

Ich würde mich freuen wenn du das mit dem Buch machst. Mega! DANKE!

Beta-User

Zitat von: Prof. Dr. Peter Henning am 17 Mai 2019, 12:20:25
Das "Lernen von Perl" und das "Lösen von Perl-Problemen" sind zwei ganz unterschiedliche Dinge.

Ersteres lässt sich mit ein paar Seiten Text und grundlegenden Programmierkenntnissen schnell erledigen. Dafür stelle ich gerne das Perl-Kapitel aus dem "Handbuch Programmiersprachen" (erschienen 2006, ich bin einer der Herausgeber) hier kostenlos zur Verfügung (stammt auch direkt von mir).
Ersteres lässt sich nicht gut erledigen, wenn keinerlei Programmierkenntnisse vorhanden sind. Dafür ist Perl, vorsichtig gesagt, nicht gut geeignet.
Dass es (fast) nicht geht, beides miteinander zu behandeln, ist klar, was ganz ähnliches hatte ich hier ja auch schon geschrieben:
Zitat von: Beta-User am 04 Mai 2019, 14:20:00
Aber grundsätzlich sollte man ein gewisses formal-logisches Denken bereits beherrschen und möglichst schon eine Vorstellung von Schleifen (-typen), Datentypen/Arrays usw. haben und seinen Programmablauf in Worten beschreiben können - daran fehlt es leider oft schon.
Es wäre sicher wünschenswert, wenn wir user erst darauf verweisen könnten, dass sie vorab eine andere Programmiersprache beherrschen sollten, aber in der Realität scheint es so zu sein, dass das entweder nicht vorhanden ist oder eben ziemlich verschüttet. Von daher werden die meisten sich dann eben zwangsläufig (wieder) mit Programmierung beschäftigen, wenn sie ein konkretes Problem (in FHEM) haben, und dann ist es gleich "das volle Programm", also Perl ;) .

Eine in der Muttersprache geschriebene theoretische Einführung werden die meisten daher dankend annehmen (mich eingeschlossen!). Wäre schön, wenn das (z.B.) an recht prominenter Stelle angepinnt werden könnte?

ZitatUnd das zweite, nämlich das Lösen von Perl-Problemen, lässt sich eben nicht generalisieren und mit einer größeren Gruppe gleichzeitig behandeln.
Das mag an sich stimmen, in meinem Beispiel geht es aber durchaus um ein, zwei typische "Probleme", nämlich den "Informationsaustausch" zwischen FHEM im allgemeinen und einem eigenen "PRogramm" sowie der Frage, wie man Dinge aus einem solchen eigenen Programm heraus "später" abprüfen kann und daraus dann wieder FHEM-Aktionen ableiten (oder eben nicht).

Da ich aber kein Didaktiker bin, mag der Vermittlungsansatz suboptimal sein, gerne nehme ich dazu Vorschläge an :) .
Server: HP-elitedesk@Debian 12, aktuelles FHEM@ConfigDB | CUL_HM (VCCU) | MQTT2: ZigBee2mqtt, MiLight@ESP-GW, BT@OpenMQTTGw | ZWave | SIGNALduino | MapleCUN | RHASSPY
svn: u.a Weekday-&RandomTimer, Twilight,  div. attrTemplate-files, MySensors

MCh76

Zitat von: CoolTux am 16 Mai 2019, 08:42:13
Dann darfst Du hier einen Punkt einbringen. Wir versuchen gemeinsam eine Lösung zu finden und wenn alles steht bringst Du Deine Lösung ins Wiki.
Ich denke es bedarf mehr Praxislösungen.

bei mir ist es aktuell kein konkretes eigenes programmiervorhaben sondern ich habe oft probleme durch coding das ich lese durchzusteigen, insbesondere
wenn ich mir fhem module anschaue und diese versuche zu verstehen.
oder aber auch einfach nur die frage warum bestimmtes coding so gemacht wird und nicht anders.

konkretes beispiel: in deinem beispiel zur lichtsteuerung arbeitest du in den funktionen mit Commandset().
welchen vorteil liefert das ggü. fhem("set ...") befehlen?

Beta-User

Zitat von: MCh76 am 17 Mai 2019, 14:08:48
konkretes beispiel: in deinem beispiel zur lichtsteuerung arbeitest du in den funktionen mit Commandset().
welchen vorteil liefert das ggü. fhem("set ...") befehlen?
Das "fhem ..." weist fhem.pl an, die Befehle auf eine bestimmte Art und Weise zu interpretieren (siehe Zeile 3785 dort). Das gibt es weiter an eine andere Funktion. Die macht dann wieder eine Analyse, und am Ende steht für "set"-Anweisungen?

Genau: CommandSet().

Man spart also den "Umweg".
Server: HP-elitedesk@Debian 12, aktuelles FHEM@ConfigDB | CUL_HM (VCCU) | MQTT2: ZigBee2mqtt, MiLight@ESP-GW, BT@OpenMQTTGw | ZWave | SIGNALduino | MapleCUN | RHASSPY
svn: u.a Weekday-&RandomTimer, Twilight,  div. attrTemplate-files, MySensors