Archiv für das Jahr: 2013

Doorbell – Teil 3: Platine

Letzter Teil, denn ich bin fertig :^)

2013-12-18 19.13.50

Da die Steckbrett-Lösung nicht so toll aussieht und bei der kleinsten Bewegung nichtmehr funktionierte, habe ich mir ein Humble-Pi bestellt.

Untitled

Super nette Platine … nicht teuer und praktisch. Sie passt direkt auf den Pi. Einziger Nachtteil ist, dass keine Aussparung für das Camera-Modul vorgesehen ist.

Untitled 2

Alles klar, los gehts mit Löten… da bin ich ein Profi, nicht. Aber hat mir viel Spaß gemacht und würde gerne mehr Löten :^)

Mein Spielzimmer Büro ist dafür auch gut ausgerüstet (Lötkolben & Lötroboter).

2013-12-18 18.11.04

Nach ca. einer Stunde sah die Platine dann so aus…

2013-12-18 20.16.49

Hier sei dazugesagt:

  • Blauer Draht zu GND wird nicht benötigt. Der Humble Pi schließt diesen bereits auf die Brücken (leider nirgends dokumentiert)
  • Die Verbindungen zu den Widerständen Rechts hätte ich nicht benötigt, man könnte direkt vom zweiten Pin abgreifen

Wie erwähnt hat leider das Kamera Flachband keinen Platz darum habe ich die Platine bisl eingeschnitten. Als Gehäuse habe ich ein Plexiglaskonstrukt gewählt. Hoffte dass hier von der Höhe alles reinpasst. Leider nicht. Klemmen und LEDs stehen bisl an, ist aber nicht schlimm (Deckel geht nicht mehr zu).

2013-12-19 19.56.44 2013-12-19 19.57.27

Nächstes Projekt ist schon in Planung… Zweiter Raspberry ist schon eingetroffen :^)

Projektübersicht

Von |2015-07-08T09:13:01+02:002013-12-22|Doorbell, Projekte, Raspberry Pi|

Internet du bist verrückt, Danke dafür…

Das Jahr neigt sich dem Ende und ich denke wieder vermehrt darüber nach, was gut und was schlecht in 2013 war.

Als Optimist bin ich zwar eher positiv der Zukunft gestellt, sehe aber die Vergangenheit immer sehr kritisch. Welche Schritte bzw. Handlungen waren gut, welche würde ich anders machen.

Das Jahr 2013 war für mich aber eine Steigerung in verschiedenen Bereichen, was ich mir auch immer für das kommende Jahr vornehme.

Mir ist auch Eines dieses Jahr immer wieder begegnet… Das persönliche Wohlbefinden hängt, zumindest bei mir, sehr stark am beruflichen Erfolg.

Anfang des Jahres habe ich eine neue Tätigkeit in der Firma übernommen und stellte mir selbst hohe Anforderungen, welche ich nach eigener Einschätzung, erfüllen konnte.

1387245578_sapin

Der Erfolg des CodeQuartetts ist sogar so groß dass es, wie schon angekündigt, einen neuen Druck in Version 2.0 geben wird. Dennoch hält sich der Aufwand wirklich gering und ich freue mich die Pakete jedes Mal zu verschicken.Zusätzlich lief dieses Jahr das Crowdfunding für CodeQuartett und ich hatte auf einmal privat auch noch „geschäftliches“ zu tun. Zu Beginn des Projektes bzw. bei der Anmeldung des Unternehmens, stellte ich mir die Frage ob es mich wohl beruflich einschränken würde bzw. mir Kraft rauben würde. Da der Aufwand meiner Meinung nach nicht zu groß sein wird, habe ich diesen Schritt gewagt.

Dies ist wohl auch Grund für den Titel. War eigentlich der Meinung ich könnte „Das Internet“ zumindest ein bisschen einschätzen, aber „Das Internet“ hat mich eines besseren belehrt. Dies natürlich im positiven Sinn. Ich hatte Bedenken bzgl. des Risikos für den finanziellen Einsatz, solch eines Projektes. Diese Angst hat mir aber das Crowdfunding genommen. Klar funktioniert diese Vorgehensweise nicht immer, dennoch hat es mir gezeigt, dass man sich etwas trauen sollte.

Überraschenderweise kann ich am Ende des Jahres sogar sagen, dass ich mehr Kraft denn je habe neue Projekte, egal ob beruflich oder privat, anzugehen. Grund ist, denke ich, die angesprochene Relation von persönlichem Wohlbefinden & beruflichen Erfolg.

Das hört sich alles sehr positiv an, was es auch größtenteils ist, dennoch sind andere „Sachen“, welche ich mir vorgenommen habe, auf der Strecke geblieben. Das liegt nach objektiver Einschätzung auch daran dass ich mir mehr vorgenommen habe, als machbar ist. Das mache ich aber bewusst um mich selbst zu fordern. An neuen Ideen scheitert es bei mir generell nicht, sondern an der Zeit bzw. der von mir gestellten Aufmerksamkeit an Projekten/Tätigkeiten.

Zurückblickend bin ich sehr stolz aber auch dankbar, den Personen gegenüber die mich unterstützen, privat wie auch beruflich.

Warum eigentlich der ganze sentimentale Text!?
Eigentlich nur, um Euch zu sagen… DANKE!

      ___           ___           ___           ___           ___     
     /\  \         /\  \         /\__\         /\__\         /\  \    
    /::\  \       /::\  \       /::|  |       /:/  /        /::\  \   
   /:/\:\  \     /:/\:\  \     /:|:|  |      /:/__/        /:/\:\  \  
  /:/  \:\__\   /::\~\:\  \   /:/|:|  |__   /::\__\____   /::\~\:\  \ 
 /:/__/ \:|__| /:/\:\ \:\__\ /:/ |:| /\__\ /:/\:::::\__\ /:/\:\ \:\__\
 \:\  \ /:/  / \/__\:\/:/  / \/__|:|/:/  / \/_|:|~~|~    \:\~\:\ \/__/
  \:\  /:/  /       \::/  /      |:/:/  /     |:|  |      \:\ \:\__\  
   \:\/:/  /        /:/  /       |::/  /      |:|  |       \:\ \/__/  
    \::/__/        /:/  /        /:/  /       |:|  |        \:\__\    
     ~~            \/__/         \/__/         \|__|         \/__/
Von |2013-12-16T21:10:26+01:002013-12-16|Allgemein|

CodeQuartett V2.0

Solch einen Erfolg mit dem CodeQuartett konnte ich mir in meinen kühnsten Träumen nicht vorstellen. Es macht mir eine riesige Freude die Päckchen in die Welt hinauszuschicken.

Und es gibt jetzt auch ein Update!

cover

Box: Ich habe mich von der Faltschachtel getrennt und es werden zukünftig Klarsichtetuis eingesetzt

Preis: Der Versand wurde billiger…

  • Deutschland: 2€
  • International: 4€

Karten: Die Spielkarten wurden ein bisschen angepasst. Beim Hello-World Programm waren die Schreibweisen des Strings unterschiedlich. Bei manchen hat sich dadurch die Zeichenlänge verringert.

Die aktuellen Daten liegen schon auf GitHub.

Gedruckt ist die neue Version ab Neujahr verfügbar.

Von |2013-12-06T16:19:48+01:002013-12-06|Projekte|

Doorbell – Teil 2: Störungen umgehen

Die Doorbell war nun eine Woche im Betatest und schnell stellte sich heraus da stimmt was nicht.

Wird ein Lichtschalter, welcher über ein Eltako-Relais geführt wird betätigt, klingelt sporadisch die Doorbell. Denke es gibt hier ein Problem mit der Abschirmung der Leitung zur Klingel. Leider kann ich diese nicht prüfen, da ich an die Abzweigdosen nicht herankomme.

Ich hab mal getestet ob es mit einer Pull-Up Schaltung besser funktioniert. Ja, es tritt nicht mehr so häufig auf. Aber Problem ist noch da.

OK, als nächstes einen Vorwiderstand von 2,2kOhm reingepackt.

Doorbell_Schaltplan

Problem fast nicht mehr reproduzierbar aber noch da. Also bisl einen Umweg und eine Einschaltverzögerung einprogrammiert. Ist keine saubere Lösung aber geht. Bessere wäre es galvanisch zu Trennen über z.B. einen Optokoppler.

if not (GPIO.input(11)):
  time.sleep(0.01)
  if not (GPIO.input(11)):

Gerade getestet mit 100ms. Das war zu viel, wenn man schnell auf den Knopf drückt läutet es nicht. dann hab ich es auf 10ms gestellt. Siehe da, Problem gelöst.

Projektübersicht

Von |2014-07-24T12:14:39+02:002013-12-05|Coding, Doorbell, Projekte, Raspberry Pi|

Doorbell – Teil 1: Schaltplan und Programm

War irgendwann klar dass ich mir einen Raspberry Pi hole, fand auch (natürlich erst nach dem Kauf) einen Anwendungsfall >>> unsere Türklingel.

Funktion JETZT:
Klingel ist an ISDN-Anlage (ohne sonstige Funktion) angeschlossen. Telefon klingelt wenn jemand an der Tür leutet.

Funktion SOLL:
Jemand klingelt, Audio wird abgespielt, Bild wird vom Besucher gemacht, Upload per SFTP auf Webserver, Pushmessage auf iPhone/iPad/Android

Die Schaltung ist überschaubar. Verwende einen Pullup / Pulldown Resistor (muss noch testen was besser funktioniert, da ich gemerkt habe dass statische Aufladung den Eingang setzt). Eine LED für die Anzeige dass das Python-Script läuft und eine LED für Aktivierung der Doorbell-Funktion.

Doorbell_Schaltplan

Hab es jetzt zum testen auf eine Steckplatine aufgebaut, funktioniert soweit. Werde es aber noch auf eine Platine löten, damit dass schön kompakt wird.

Zuerst wollte ich das ganze mit Mono programmieren, da ich Mono noch eine Chance geben wollte. Aber da es an einigen Ecken zu beginn schon zum knarzen begann, habe ich auf Python zurückgegriffen.

Finde Python keine schöne Sprache, aber mächtig. Naja, mein Anwendungsfall ist überschaubar, somit auch die paar Zeilen Programmcode.

Ich gehe hier nicht auf die Standard-Funktionen des Raspberrys ein, da es viele gute Anleitungen im Internet gibt.

Initialisierung

Alle benötigten Abhängigkeiten + Eventhandler (ausschalten der Status-LED) + Logging Methode. Wichtig ist hier auch noch das Audio auf 100% zu stellen. Da ich das Signal per Funk an Boxen weitergebe, ist hier wichtig dass der AUX Anschluss auf Maximum ist. Als letztes werden die IOs konfiguriert.

from time import gmtime, strftime, sleep
from datetime import datetime
import RPi.GPIO as GPIO
import os
import subprocess
import os.path
import httplib, urllib
import pysftp
import atexit
import traceback
import logging
import time

# On exit
def exit_handler():
    GPIO.output(22, False)
atexit.register(exit_handler)

# Logging
logger = logging.getLogger('doorbell')
hdlr = logging.FileHandler('/home/pi/Desktop/doorbell/web/doorbell.txt')
formatter = logging.Formatter('%(asctime)s %(levelname)s %(message)s')
hdlr.setFormatter(formatter)
logger.addHandler(hdlr)
logger.setLevel(logging.INFO)

# Start
print(strftime("%Y-%m-%d %H:%M:%S", gmtime()) + " Doorbell started")
logger.info("Doorbell started")

# Volume
cmdVolume='amixer set PCM -- 1000'
subprocess.call(cmdVolume, shell=True)

# Pins
GPIO.setmode(GPIO.BOARD)
GPIO.setup(15, GPIO.OUT)
GPIO.setup(22, GPIO.OUT)
GPIO.output(15, False)
GPIO.output(22, True)
GPIO.setup(11, GPIO.IN)

Alles eingepackt in eine While-Dauerschleife für ich folgenden Code nacheinander aus:

# Setup
now=strftime("%Y-%m-%d %H:%M:%S", gmtime())
filename=strftime("%Y-%m-%d_%H.%M.%S", gmtime())  + '.jpg'

print(now + " Button pressed")
logger.info("Button pressed")
GPIO.output( 15, True)

Hier wird einfach nur geloggt, wenn der Button gedrückt wurde (Datum, Uhrzeit) und zusätzlich die LED für den Programmablauf eingeschaltet. Ich speichere mir gleich das Datum in eine Variable um es später für die Bilddatei zu verwenden.

# Audio
print("--> Audio")
logger.info("--> Audio")
subprocess.Popen(['aplay', '/home/pi/Desktop/doorbell/ringtone.wav'])

Nun spielen wir das Audiofile (in meinem Fall eine WAV-Datei) ab. Hier ist die Besonderheit dass es parallel zum Ablauf des Scripts passiert. Dass heißt hier wird ein separater Thread gestartet. Achja, TIP: nehmt am besten einen nervigen Sound (habe mich für Super Mario 1 Theme entschieden) dass kommt in der Frauenwelt sehr gut an :^)

# Camera
print("--> Camera")
logger.info("--> Camera")
cmdCam='raspistill -o ' + '/home/pi/Desktop/doorbell/web/photos/' +  filename
subprocess.call(cmdCam, shell=True)

Der Kamera Aufruf ist denkbar einfach. Hier habe ich versucht auch im separaten Thread das Bild zu speichern, hatte aber bei jedem 10. Bild ein Problem, welches ich (noch) nicht nachvollziehen konnte. Ihr seht schon dass sich die Bilder in einem Ordner web befinden. Ich habe mich im Nachhinein dafür entschieden einen Webserver auf dem Pi laufen zu lassen. Dadurch hab ich mehr Kontrolle und kann von außen auch z.B. einen Livestream der Cam anschauen sowie die Logdatei oder einfach per SSH verbinden.

Wie oben erwähnt habe ich angedacht per SFTP das Bild auf meinen Webserver bei Uberspace zu laden. Habe ich auch getestet und das wäre der Code dafür (auskommentiert):

# Upload Foto
#print("--> Upload")
#logger.info("--> Upload")
#srv = pysftp.Connection(host="MeinServer.de", username="MyUsername",
#                        password="MyPassword", log="True")
#srv.chdir("/Mein/Ordner/Mit/Photos/Auf/Server")
#srv.put('/Mein/Ordner/Mit/Photos/Lokal/' + filename)
#srv.close()

Nun zum Teil der mir am meisten Spaß gemacht hat. Funktion ist genial und einfach zu implementieren. Der Dienst nennt sich Pushover, ist für meine Anwendung kostenlos da ich unter 7500 Pushes im Monat bleibe (außer ich bekomme sehr viel Besucher). Die API ist sehr gut dokumentiert und es gibt Beispiele für viele Sprachen.

# Pushover
print("--> Pushover")
logger.info("--> Pushover")
conn = httplib.HTTPSConnection("api.pushover.net:443")
conn.request("POST", "/1/messages.json",
             urllib.urlencode({
                              "token": "app-token",
                              "user": "user-token",
                              "title": "Doorbell",
                              "message": "KNOCK KNOCK",
                              "url": "http://irgendwo.de/photos/" + filename,
                              "url_title": "Image",
                              }),
             { "Content-type": "application/x-www-form-urlencoded" })
conn.getresponse()

Das ganze wird bei mir wie erwähnt auf Android, iPad und iPhone gepusht und dauert ca. 1-3 Sekunden nach drücken der Klingel, was mehr als ausreicht.

2013-11-30 00.11.54 2013-11-30 00.10.19  2013-11-30 00.10.23

 

Lockscreen > Pushover App Übersicht > Detail

Mit einem Tap auf Image wird mir dann auch das Bild des Besuchers angezeigt. Die Farben sind Tagsüber OK. In der nacht wird das ganze schwarz/weiß, aber die Qualität und Erkennbarkeit ist durchgehend gut.

2013-11-30 08.30.54

Hier sei erwähnt dass ich nicht die Standard Raspberry Pi Camera gekauft habe sondern die IR-Version.

Zusätzlich habe ich mir einen HTTP-Livestream gebaut, damit ich per iPhone/iPad die Kamera live betrachten kann (diente nur zum einstellen).

Anbei das ganze Script:

from time import gmtime, strftime, sleep
from datetime import datetime
import RPi.GPIO as GPIO
import os
import subprocess
import os.path
import httplib, urllib
import pysftp
import atexit
import traceback
import logging
import time

# On exit
def exit_handler():
    GPIO.output(22, False)
atexit.register(exit_handler)

# Logging
logger = logging.getLogger('doorbell')
hdlr = logging.FileHandler('/home/pi/Desktop/doorbell/web/doorbell.txt')
formatter = logging.Formatter('%(asctime)s %(levelname)s %(message)s')
hdlr.setFormatter(formatter)
logger.addHandler(hdlr)
logger.setLevel(logging.INFO)

# Start
print(strftime("%Y-%m-%d %H:%M:%S", gmtime()) + " Doorbell started")
logger.info("Doorbell started")

# Volume
cmdVolume='amixer set PCM -- 1000'
subprocess.call(cmdVolume, shell=True)

# Pins
GPIO.setmode(GPIO.BOARD)
GPIO.setup(15, GPIO.OUT)
GPIO.setup(22, GPIO.OUT)
GPIO.output(15, False)
GPIO.output(22, True)
GPIO.setup(11, GPIO.IN)

# Loop
while 1:
    if GPIO.input(11):
        try:
            # Setup
            now=strftime("%Y-%m-%d %H:%M:%S", gmtime())
            filename=strftime("%Y-%m-%d_%H.%M.%S", gmtime())  + '.jpg'

            print(now + " Button pressed")
            logger.info("Button pressed")
            GPIO.output( 15, True)

            # Audio
            print("--> Audio")
            logger.info("--> Audio")
            subprocess.Popen(['aplay', '/home/pi/Desktop/doorbell/ringtone.wav'])

            # Camera
            print("--> Camera")
            logger.info("--> Camera")
            cmdCam='raspistill -o ' + '/home/pi/Desktop/doorbell/web/photos/' +  filename
            subprocess.call(cmdCam, shell=True)

            # Pushover
            print("--> Pushover")
            logger.info("--> Pushover")
            conn = httplib.HTTPSConnection("api.pushover.net:443")
            conn.request("POST", "/1/messages.json",
                         urllib.urlencode({
                                          "token": "app-token",
                                          "user": "user-token",
                                          "title": "Doorbell",
                                          "message": "KNOCK KNOCK",
                                          "url": "http://irgendwo.de/photos/" + filename,
                                          "url_title": "Image",
                                          }),
                         { "Content-type": "application/x-www-form-urlencoded" })
            conn.getresponse()

            # Finished
            print("--> Finished")
            logger.info("--> Finished")
            time.sleep(2)

        except Exception, e:
            traceback.print_exc()
            logging.exception("!!!")
    else:
        GPIO.output( 15, False)

 

Projektübersicht

Von |2014-07-24T12:14:44+02:002013-11-30|Coding, Doorbell, Projekte, Raspberry Pi|
Nach oben