Code: Alles auswählen
unit Unit1;
{$mode objfpc}{$H+}
interface
uses
Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, Buttons,
StdCtrls, Time,
Unix, BaseUnix,
Process
;
type
{ TForm1 }
TForm1 = class(TForm)
Memo: TMemo;
Process: TProcess;
sbBeenden: TSpeedButton;
sbPascal: TSpeedButton;
sbLeeren: TSpeedButton;
sbPython: TSpeedButton;
procedure OnCreate(Sender: TObject);
procedure OnShow(Sender: TObject);
procedure sbBeendenClick(Sender: TObject);
procedure sbPascalClick(Sender: TObject);
procedure sbLeerenClick(Sender: TObject);
procedure sbPythonClick(Sender: TObject);
private
{ private declarations }
public
{ public declarations }
sPath : string;
TRIG : integer;
ECHO : integer;
PULSE : real;
BURST : integer;
SPEED_2 : integer;
procedure Init_ultra(Pin_T : integer; Pin_E : integer);
function Pin_Get(Pin_E : integer):integer;
end;
const
PIN_ON : PChar = '1';
PIN_OFF : PChar = '0';
OUT_DIRECTION : PChar = 'out';
IN_DIRECTION : PChar = 'in';
var
Form1: TForm1;
implementation
{$R *.lfm}
{ TForm1 }
procedure TForm1.Init_ultra(Pin_T : integer; Pin_E : integer);
var
fileDesc : integer;
gReturnCode : integer;
cPIN : PChar;
begin
// Trigger als Ausgang
cPIN := PChar(IntToStr(Pin_T));
try
fileDesc := fpopen('/sys/class/gpio/export', O_WrOnly);
gReturnCode := fpwrite(fileDesc, cPin[0], 2);
finally
gReturnCode := fpclose(fileDesc);
end;
try
fileDesc := fpopen('/sys/class/gpio/gpio' + IntToStr(Pin_T) + '/direction' , O_WrOnly);
gReturnCode := fpwrite(fileDesc, OUT_DIRECTION[0], 3);
finally
gReturnCode := fpclose(fileDesc);
end;
// Echo als Eingang
cPIN := PChar(IntToStr(Pin_E));
try
fileDesc := fpopen('/sys/class/gpio/export', O_WrOnly);
gReturnCode := fpwrite(fileDesc, cPin[0], 2);
finally
gReturnCode := fpclose(fileDesc);
end;
try
fileDesc := fpopen('/sys/class/gpio/gpio' + IntToStr(Pin_E) + '/direction' , O_WrOnly);
gReturnCode := fpwrite(fileDesc, IN_DIRECTION[0], 2);
finally
gReturnCode := fpclose(fileDesc);
end;
end;
function TForm1.Pin_Get(Pin_E : integer):integer;
var
cPin : PChar;
fileDesc : integer;
gReturnCode : integer;
pinStatus : string[1] = '1';
iStatus : integer;
begin
cPin := PChar(IntToStr(Pin_E));
try
fileDesc := fpopen('/sys/class/gpio/gpio' + cPin + '/value' , O_RdOnly);
gReturnCode := fpread(fileDesc, pinStatus[1], 1);
finally
gReturnCode := fpclose(fileDesc);
end ;
result:= StrToInt(pinStatus);
end;
procedure TForm1.sbLeerenClick(Sender: TObject);
begin
Memo.Clear;
end;
procedure TForm1.sbPythonClick(Sender: TObject);
var
AProcess : TProcess;
AStringList : TStringList;
begin
AProcess := TProcess.Create(nil);
AStringList := TStringList.Create;
try
AProcess.CommandLine:='sudo ' + sPath + 'ultrasonic.py';
AProcess.Options:= AProcess.Options + [poWaitOnExit, poUsePipes];
AProcess.Execute;
AStringList.LoadFromStream(AProcess.Output);
Memo.Lines.Add(AStringList.Strings[0]);
finally
AProcess.Free;
AStringList.Free;
end;
end;
procedure TForm1.sbBeendenClick(Sender: TObject);
begin
Close();
end;
procedure TForm1.OnShow(Sender: TObject);
begin
TRIG := 18;
ECHO := 17;
PULSE := 0.00001;
BURST := 25;
SPEED_2 := 17015; // Schallgeschwindigkeit/2
Init_ultra(TRIG, ECHO);
end;
procedure TForm1.OnCreate(Sender: TObject);
begin
GetDir(0,sPath);
if (Length(sPath)>3 ) then sPath := sPath + '/';
end;
procedure TForm1.sbPascalClick(Sender: TObject);
var
cPin : PChar;
fileDesc : integer;
gReturnCode : integer;
distance : real;
delta : real;
starttime : TTime;
start, stopp : TTime;
begin
//GPIO.output(TRIG, True) # Trigger-Impuls
cPin := PChar(IntToStr(18));
try
fileDesc := fpopen('/sys/class/gpio/gpio' + cPin + '/value' , O_WrOnly);
gReturnCode := fpwrite(fileDesc, PIN_ON[0], 1);
finally
gReturnCode := fpclose(fileDesc);
end ;
//sleep(PULSE);
try
fileDesc := fpopen('/sys/class/gpio/gpio' + cPin + '/value' , O_WrOnly);
gReturnCode := fpwrite(fileDesc, PIN_OFF[0], 1);
finally
gReturnCode := fpclose(fileDesc);
end ;
sleep(1);
starttime := Time.CurrentSec100OfDay(); // Zeit initialisieren
stopp := starttime;
start := starttime;
// (Busy) Warten auf steigende Flanke, max. 2 Sekunden
while ((Pin_Get(17) = 0) and (start < (starttime + 2))) do
start := Time.CurrentSec100OfDay(); // Startzeit
// (Busy) Warten auf fallende Flanke, max. 2 Sekunden
while ( (Pin_Get(17) = 1) and (stopp < (starttime + 2))) do
stopp := Time.CurrentSec100OfDay(); // Endezeit
delta := stopp - start; // Zeitdifferenz und Entfernung berechnen
distance := delta * SPEED_2;
Memo.Lines.Add(FloatToStr(distance));
end;
end.
hier der python ultrasonic.py
Code: Alles auswählen
#!/usr/bin/python
import RPi.GPIO as GPIO
import time
import datetime
# GPIOs fuer den US-Sensor
TRIG = 18
ECHO = 17
# Dauer Trigger-Impuls
PULSE = 0.00001
# Anzahl Messwerte fuer Mittelwertbildung
BURST = 25
# Schallgeschwindigkeit/2
SPEED_2 = 17015
# BCM GPIO-Referenen verwenden (anstelle der Pin-Nummern)
# und GPIO-Eingang definieren
GPIO.setmode(GPIO.BCM)
GPIO.setup(TRIG,GPIO.OUT)
GPIO.setup(ECHO,GPIO.IN)
GPIO.output(TRIG, False)
time.sleep(1) # Setup-Zeit fuer Sensor
def measure(): # Messung ausfuehren
GPIO.output(TRIG, True) # Trigger-Impuls
time.sleep(PULSE)
GPIO.output(TRIG, False)
starttime = time.time() # Zeit initialisieren
stopp = starttime
start = starttime
# (Busy) Warten auf steigende Flanke, max. 2 Sekunden
while GPIO.input(ECHO) == 0 and start < starttime + 2:
start = time.time() # Startzeit
# (Busy) Warten auf fallende Flanke, max. 2 Sekunden
while GPIO.input(ECHO) == 1 and stopp < starttime + 2:
stopp = time.time() # Endezeit
delta = stopp - start # Zeitdifferenz und Entfernung berechnen
distance = delta * SPEED_2
return distance
def measure_range(): # Bildet Mittelwert von BURST Messungen
values = []
sum = 0
for i in range(0, BURST):
values.append(measure()) # Messung starten
sum = sum + values[i] # Wert im Array speichern und aufsummieren
time.sleep(0.05)
return sum/BURST; # Mittelwert zurueckgeben
# do it
try:
Distance = measure_range()
Distance = Distance*10
print("%1.0f" % Distance)
time.sleep(1)
# reset GPIO settings if user pressed Ctrl+C
except :
print("Bye")
GPIO.cleanup()
Der Python müsste auch überarbeitet werde. Habe aber keine Ahnung.
Grüße aus Berlin