NEWS
Script zur Einbindung/Steuerung von motion+camera am Raspi
-
Hallo ihr lieben!
Wie ich auf http://forum.iobroker.net/viewtopic.php … 140#p35043 schon erwähnt habe bin ich dabei meine node-red-Lösung auf ioBroker umzustellen.
Eine der Aufgaben war meine Raspi-Cam (ginge auch mit anderen cams) mit motion zu betreiben und als Bewegungsmeldung mit Filmaufnahme zu betreiben.
Als Vorbedingung muss motion mit
sudo apt-get install motion installiert werden
Wer die Raspi-Cam verwendet miss diese natürlich im raspi-config freischalten.
Falls ihr ein neueres Jessie frisch installiert schaut auch ob das Modul "bcm2835-v4l2" in"/etc/modules" eingetragen ist, falls dies nicht der Fall ist bitte eine Zeile mit dem Text "bcm2835-v4l2" (ohne Appostrophe) mit````
sudo nano /etc/modulesNun musst ihr mit```` sudo nano /etc/motion/motion.conf ````motion kopnfigurieren. Wichtig ist dass ihr den Streamport setzt (stream_port 8181), bei mir 8181 weil ja der ioBrokerAdmin die 8081 besetzt. Noch wichtiger ist den Webcontrol port zu setzen (webcontrol_port 8180), damit kann ioBroker de Detection ein und Ausschalten was sinnvoll ist wenn kein Alarm ausgelöst werden soll, z.B. Am Tag wenn wir dauernd reinlaufen würden. Dadurch wird auch der CPU-Bedarf heruntergesetzt da nicht jedes Frame nach Bewegung untersucht wird. Im script muss dann die Adresse des Raspi und die Instanz von Motion (Ihr könnt ja auch USB oder Webcams zusätzlich betreiben und mehrere Instanzen überwachen). Bei mir ist das die Zeile```` var motionControlHost = "localhost:8180/0/";
Übrigens, wenn ihr /etc/motion/motion.conf ändert motion mit````
sudo service motion restartIhr könnt Änderungen an der Konfiguretion auch über die webcontrol-Adress vornehmen, dies habe ich im Script benutzt um ioBroker zu informieren wenn Bewegungen entstehen und was diel letzten aufgezeichneten Dateien waren. Hier das ganze Script.
// =============================================================================
// Motion - Interface to Raspi Motion detection daemon
// =============================================================================
//
// Version: 0.1.0
// Datum: 20.9.2016
// Autor: fsjoke// benötigt mind. die Version 2.x des Javascript-Adapters
// verwendete globale Funktionen (müssen als globale Funktion vorhanden sein)
// -----------------------------------------------------------------------------// logs() // für individuelle Loglevel innerhalb des Scripts
// printSubs() // liestet die Subscritions im Script auf// =============================================================================
// Einstellungen Scriptverhalten
// =============================================================================var loglevel = "debug2"; // logs() - Loglevel des Scriptes (debug2, debug1, debug, info, warn, error) // benötigt den loglevel info beim Javascript Adapter
var dpPfad = "Motion" + "."; // In welchem Pfad sollen die Datenpunkte angelegt werden. String mit "." am Ende.
var instanz = "javascript." + instance + ".";
var idPfad = instanz+dpPfad;
var idDE = idPfad + 'DetectionEnabled';// =============================================================================
// Required Packages or definitions
// =============================================================================
var request = require('request');var motionControlHost = "localhost:8180/0/"; // /0/ gibt die Instanz an, wenn nur eine Cam dann 0
var motionConfig = true; // automatically configure motion when start! Muß nur einmal gemacht werden wenn Namen oder instanzen geändert werden!logs('--== ' + name + ' ==-- gestartet. Instanz: "' + instanz + '", Loglevel: ' + loglevel,"info","darkgreen");
logs('Vars, Loglevel und Scriptname gesetzt','debug1');// -----------------------------------------------------------------------------
// Funktionen Funktionen
// -----------------------------------------------------------------------------function motionControl(cmd, cbk) {
var url = "http://" + motionControlHost + cmd;
request(url, cb(function (error, response, body) {
if (!error && response.statusCode == 200) {
if (cbk) {
var r = body.trim().split('\n');
if (r.length === 1)
r = r[0];
cbk(r);
}
} else logs("could not send command '"+ cmd + "' to motion, url was:" + url);
}));
}// =============================================================================
// Datenpunkte anlegen
// =============================================================================
function dpAnlegen() {// einfach angelegte Datenpunkte // ----------------------------- //createState(dbPfad + 'datenpunktName',"Test"); // ausführlich beschriebene Datenpunkte // ------------------------------------ createState(dpPfad + 'DetectionEnabled', true, { // Datenpunktname ohne Leerzeichen und Sonderzeichen, wie er in den Objekten angelegt wird name: 'MotionDetectionEnabled', // Lesbarer Name des Datenpunkts desc: 'Starte oder stoppe Bewegungserkennung', // Beschreibung des Datenpunkts type: 'boolean', // Bescreibung des Typ, wie: number, string, boolean unit: '', // Einheit, wenn benötigt role: "state.enabled", write: true, }); createState(dpPfad + 'Detected', false, { // Datenpunktname ohne Leerzeichen und Sonderzeichen, wie er in den Objekten angelegt wird name: 'MotionDetected', // Lesbarer Name des Datenpunkts desc: 'Eine Bewegung wurde erkannt', // Beschreibung des Datenpunkts type: 'boolean', // Bescreibung des Typ, wie: number, string, boolean unit: '', // Einheit, wenn benötigt role: "sensor", }); createState(dpPfad + 'VideoFile', "leer", { // Datenpunktname ohne Leerzeichen und Sonderzeichen, wie er in den Objekten angelegt wird name: 'FilenameVideoBewegung', // Lesbarer Name des Datenpunkts desc: 'Erzeugte Videodatei der Bewegungserkennung', // Beschreibung des Datenpunkts type: 'string', // Bescreibung des Typ, wie: number, string, boolean unit: '', // Einheit, wenn benötigt role: "info", }); createState(dpPfad + 'PictureFile', "leer", { // Datenpunktname ohne Leerzeichen und Sonderzeichen, wie er in den Objekten angelegt wird name: 'FilenamePictureBewegung', // Lesbarer Name des Datenpunkts desc: 'Erzeugte Bilddatei der Bewegungserkennung', // Beschreibung des Datenpunkts type: 'string', // Bescreibung des Typ, wie: number, string, boolean unit: '', // Einheit, wenn benötigt role: "info", }); if (motionConfig) { motionControl('config/set?webcontrol_html_output=off',logo); motionControl('config/set?on_event_start=iobroker state set '+ idPfad + 'Detected true true &',logo); motionControl('config/set?on_event_end=iobroker state set '+ idPfad + 'Detected false true &',logo); motionControl('config/set?on_picture_save=iobroker state set '+ idPfad + escape('PictureFile "%f" true &'),logo); motionControl('config/set?on_movie_end=iobroker state set '+ idPfad + escape('VideoFile "%f" true &'),logo); motionControl('config/write',logo); } else {// Diese Information kann weggelassen werden wenn motion mit den Zeilen darunter ko logs("Please make sure you ener the following lines in '/etc/motion/motion.conf':"); logs(" on_event_start iobroker state set "+ idPfad + "Detected true true &"); logs(" on_event_end iobroker state set "+ idPfad + "Detected false true &"); logs(" on_picture_save iobroker state set "+ idPfad + 'PictureFile "%f" true &'); logs(" on_movie_end iobroker state set "+ idPfad + 'VideoFile "%f" true &'); } logs("dpAnlegen() - Datenpunkte angelegt (createState) in " + instanz + dpPfad,'debug1');
}
// =============================================================================
// Autokorrekturen Autokorrekturen
// =============================================================================// -----------------------------------------------------------------------------
// Schedule Schedule
// -----------------------------------------------------------------------------
function onAnlegen() {/*
// wird um 00:00 ausgeführt
schedule({hour: 0, minute: 0}, function (){
// was soll passieren
});
*/// -----------------------------------------------------------------------------
// ON ON
// -----------------------------------------------------------------------------logs("register '"+ idDE+"' with 'ne'"); on({id: idDE ,change:'ne'}, function (obj) { // was soll bei Datenpunktänderung passieren var nst = obj.state.val; logs("DetectionEnabled set to " + nst); motionControl("detection/" + (nst ? "start" : "pause"),logo); });
printSubs(name,loglevel); // globale Funktion. listet die Subscription im Script im Log auf.
}// =============================================================================
// main - Hauptprogramm (wird beim Scriptstart ausgeführt) main
// =============================================================================
function main() {// Hauptprogramm nach Timeout (z.B. damit neu angelegte Datenpunkte vorhanden sind) // Im Hauptprogramm weiter: motionControl("detection/status",logo); var stDE = getState(dpPfad+"DetectionEnabled").val; logs("Current detection state is "+stDE); motionControl("detection/" + (stDE ? "start" : "pause"),logo);
}
dpAnlegen(); // erst die notwendigen Datenpunkte anlegen
setTimeout(onAnlegen, 500); // dann die Subscriptions setzen
setTimeout(main, 1000); // dann das Hauptprogramm startenEs erzeugt 4 states, einer (DetectionEnabled) um die Bewegungserkennung ein oder auszuschalten, über "Detected" wird erkannt ob eine Bewegung stattfindet und mit PictuteFile und VideoFile werden die Dateinamen der erzeugten Bilder/Videos angegeben (ich lass nur ein Bild pro Bewegungssequenz erzeugen). Was ihr damit macht ist euch überlassen, ich beobachte PictureFile und schicke es mir per email aufs Handy…. aber das ist Teil des Alarm-scripts :) Ja, ich habe mir auch ein vis-frame gemacht das auf :8181 zugreift und wo ich das momentane Bild life anschauen kann (egal ob Bewegungserkennung an ist). p.s.: Habe vergessen zu erwähnen dass ich logs() verändert und erweitert habe um Objekte leichter als JSON zu loggen. ändert einfach alle logo/logj/logol- Aufrufe in normal logs-Versionen. Viel Spaß Frank
-
Hallo fsjoke,
könntest Du noch etwas genauer auf die Scriptanpassung eingehen.
Habe die Cam auf raspizero am laufen und möchte das Bild der letzten erkannten Bewegung mit Telegram verschicken.
Bin noch Anfänger und bekomme Dein Script nicht angepasst. Die VIS Frame der Cam läuft (xxx:8181)