<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="de">
	<id>https://wiki-test.hshl.de/wiki/index.php?action=history&amp;feed=atom&amp;title=Software_des_NXT_3D_Laser_Scanners</id>
	<title>Software des NXT 3D Laser Scanners - Versionsgeschichte</title>
	<link rel="self" type="application/atom+xml" href="https://wiki-test.hshl.de/wiki/index.php?action=history&amp;feed=atom&amp;title=Software_des_NXT_3D_Laser_Scanners"/>
	<link rel="alternate" type="text/html" href="https://wiki-test.hshl.de/wiki/index.php?title=Software_des_NXT_3D_Laser_Scanners&amp;action=history"/>
	<updated>2026-04-29T23:28:18Z</updated>
	<subtitle>Versionsgeschichte dieser Seite in HSHL Mechatronik</subtitle>
	<generator>MediaWiki 1.43.0</generator>
	<entry>
		<id>https://wiki-test.hshl.de/wiki/index.php?title=Software_des_NXT_3D_Laser_Scanners&amp;diff=1358&amp;oldid=prev</id>
		<title>Christoph Doerner: /* Matlab code */</title>
		<link rel="alternate" type="text/html" href="https://wiki-test.hshl.de/wiki/index.php?title=Software_des_NXT_3D_Laser_Scanners&amp;diff=1358&amp;oldid=prev"/>
		<updated>2014-01-24T15:40:26Z</updated>

		<summary type="html">&lt;p&gt;&lt;span class=&quot;autocomment&quot;&gt;Matlab code&lt;/span&gt;&lt;/p&gt;
&lt;a href=&quot;https://wiki-test.hshl.de/wiki/index.php?title=Software_des_NXT_3D_Laser_Scanners&amp;amp;diff=1358&amp;amp;oldid=1356&quot;&gt;Änderungen zeigen&lt;/a&gt;</summary>
		<author><name>Christoph Doerner</name></author>
	</entry>
	<entry>
		<id>https://wiki-test.hshl.de/wiki/index.php?title=Software_des_NXT_3D_Laser_Scanners&amp;diff=1356&amp;oldid=prev</id>
		<title>Christoph Doerner: Die Seite wurde neu angelegt: „= Matlab code =  %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %    %                    Lego NXT Laser3DScanner %     In Dieser Progra…“</title>
		<link rel="alternate" type="text/html" href="https://wiki-test.hshl.de/wiki/index.php?title=Software_des_NXT_3D_Laser_Scanners&amp;diff=1356&amp;oldid=prev"/>
		<updated>2014-01-24T15:37:18Z</updated>

		<summary type="html">&lt;p&gt;Die Seite wurde neu angelegt: „= Matlab code =  %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %    %                    Lego NXT Laser3DScanner %     In Dieser Progra…“&lt;/p&gt;
&lt;p&gt;&lt;b&gt;Neue Seite&lt;/b&gt;&lt;/p&gt;&lt;div&gt;= Matlab code =&lt;br /&gt;
&lt;br /&gt;
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%&lt;br /&gt;
%   &lt;br /&gt;
%                    Lego NXT Laser3DScanner&lt;br /&gt;
%     In Dieser Programmierung soll ein NXT angesteuert werden der     &lt;br /&gt;
%     ein Objekt dreht &amp;amp; eine Webcam, die das Objektaufnimmt um es &lt;br /&gt;
%     am Computer als 3D Figur anzeigt.&lt;br /&gt;
%&lt;br /&gt;
% *  Authoren: Christoph Dörner &amp;amp; Michael Deitel&lt;br /&gt;
% *  Date: 01/12/2013 - 12/01/2014&lt;br /&gt;
% *  Hochschule Hamm-Lippstadt, www.hshl.de&lt;br /&gt;
% *  basierend auf RWTH - Mindstorms NXT Toolbox: &lt;br /&gt;
% *  http://www.mindstorms.rwth-aachen.de&lt;br /&gt;
% *  MATLAB Image Acquisition Toolbox:&lt;br /&gt;
% *  www.mathworks.com/products/imaq/?&lt;br /&gt;
%&lt;br /&gt;
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
%--------------------------Beginn Programm------------------------&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
%Hauptprogramm: &lt;br /&gt;
% 1. Sicherstellung der Installation der RWTH-Mindstorm NXT Toolbox&lt;br /&gt;
% 2. Schließen aller bestehender Handle (falls diese existieren)&lt;br /&gt;
% 3. NXT Verbindung herstellen&lt;br /&gt;
% 4. Globale Bekanntmachung des NXT Handle&lt;br /&gt;
% 5. Körper Rotieren lassen, Kamera aktivieren und Film aufnehmen&lt;br /&gt;
% 6. Kamerawinkel wird gesetzt&lt;br /&gt;
% 7. Farbe des Lasers wird gesetzt&lt;br /&gt;
% 8. Kalibrirungsbild wird zum ausgleichen der Kameraposition genommen,&lt;br /&gt;
%    falls diese schief zum Objekt steht&lt;br /&gt;
% 9. Den Motormittelpunkt auswählen&lt;br /&gt;
%10. Den Bildbereich des Objektes auswählen&lt;br /&gt;
%11. Bilder werden nach und nach in einer for-Schleife verarbeitet&lt;br /&gt;
%12. Dazu wird jedes in ein Binärbild von der Laserfarbe konvertiert&lt;br /&gt;
%    und die Position der Laserlinie analysiert&lt;br /&gt;
%13. Nach der Schleife werden die Werte verechnet und in der&lt;br /&gt;
%    3D-Grafik angezeigt&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
%----------------Anfang des Scanvorgangs---------------------------&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
% Sicherstellung, dass die RWTH - Mindstorms NXT Toolbox installiert ist&lt;br /&gt;
if verLessThan(&amp;#039;RWTHMindstormsNXT&amp;#039;, &amp;#039;2.00&amp;#039;);&lt;br /&gt;
    error(strcat(&amp;#039;This program requires the RWTH - Mindstorms NXT Toolbox &amp;#039; ...&lt;br /&gt;
        ,&amp;#039;version 2.00 or greater. Go to http://www.mindstorms.rwth-aachen.de&amp;#039; ...&lt;br /&gt;
        ,&amp;#039; and follow the installation instructions!&amp;#039;));&lt;br /&gt;
end&lt;br /&gt;
&lt;br /&gt;
% Schliessen alle bestehender Handle, falls diese existieren&lt;br /&gt;
COM_CloseNXT all&lt;br /&gt;
&lt;br /&gt;
% Vorbereitung des Arbeitsplatzes indem sicherheitshalber alle &lt;br /&gt;
% Variablen gelöscht und alle Fenster geschlossen werden&lt;br /&gt;
close all&lt;br /&gt;
clear all&lt;br /&gt;
&lt;br /&gt;
% Öffnen der NXT Bluetooth Verbindung anhand der Initialisierungsdatei &lt;br /&gt;
 &amp;#039;bluetooth.ini&amp;#039;&lt;br /&gt;
handle = COM_OpenNXT(&amp;#039;bluetooth.ini&amp;#039;);&lt;br /&gt;
&lt;br /&gt;
% Globale bekanntmachung des NXT Handle, damit alle nachfolgenden&lt;br /&gt;
% Funktionen auf dieses Handle zugreifen können.&lt;br /&gt;
COM_SetDefaultNXT(handle);&lt;br /&gt;
&lt;br /&gt;
% Motoreinstellung (Grad der Umdrehung &amp;amp; Geschwindigkeit)&lt;br /&gt;
Fahrgeschwindigkeit     = -10;                   % Prozent&lt;br /&gt;
UmdrehungenInDeg        = 360;                    % Grad&lt;br /&gt;
&lt;br /&gt;
Objekt = NXTMotor(MOTOR_A);                      % Motor A wird angesteuert&lt;br /&gt;
Objekt.SpeedRegulation    = false;               % Kein Sync Mode&lt;br /&gt;
Objekt.Power              = Fahrgeschwindigkeit; % Fahrgeschwindigkeit in Prozent&lt;br /&gt;
Objekt.TachoLimit         = UmdrehungenInDeg;    % Umdrehungen in Deg&lt;br /&gt;
Objekt.ActionAtTachoLimit = &amp;#039;Brake&amp;#039;;             % Nicht auslaufen&lt;br /&gt;
&lt;br /&gt;
% Initialisierung des Motors&lt;br /&gt;
Objekt.Stop(&amp;#039;off&amp;#039;);&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
% Öffnen der WebCam&lt;br /&gt;
vid = videoinput(&amp;#039;winvideo&amp;#039;,1,&amp;#039;YUY2_640x480&amp;#039;);&lt;br /&gt;
&lt;br /&gt;
% Bildrate festlegen&lt;br /&gt;
framerate = 30;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
% Aufnahmezeit und Anzahl der Bilder festlegen&lt;br /&gt;
set(vid,&amp;#039;FrameGrabInterval&amp;#039;,1);&lt;br /&gt;
capturetime = 5.5;&lt;br /&gt;
interval = get(vid,&amp;#039;FrameGrabInterval&amp;#039;);&lt;br /&gt;
numframes = floor(capturetime * framerate / interval)&lt;br /&gt;
set(vid,&amp;#039;FramesPerTrigger&amp;#039;,numframes);&lt;br /&gt;
set(vid,&amp;#039;LoggingMode&amp;#039;,&amp;#039;disk&amp;#039;);&lt;br /&gt;
avi = avifile(&amp;#039;Objekt&amp;#039;,&amp;#039;fps&amp;#039;,framerate);&lt;br /&gt;
set(vid,&amp;#039;DiskLogger&amp;#039;,avi);&lt;br /&gt;
start(vid);&lt;br /&gt;
pause(1.2);&lt;br /&gt;
&lt;br /&gt;
% Hier wird die Fahrt gestartet&lt;br /&gt;
Objekt.SendToNXT();&lt;br /&gt;
&lt;br /&gt;
% Warte bis die Aufnahme beendet ist und dann fortfahren&lt;br /&gt;
wait(vid,Inf);&lt;br /&gt;
avi = get(vid,&amp;#039;DiskLogger&amp;#039;);&lt;br /&gt;
avi = close(avi);&lt;br /&gt;
&lt;br /&gt;
pause(5);&lt;br /&gt;
&lt;br /&gt;
%------------------Ende des Scanvorgangs------------------------&lt;br /&gt;
%--------------Auswerten der .avi Videodatei in 3D---------------&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
% Parameter &lt;br /&gt;
&lt;br /&gt;
% Videodatei die analysiert werden soll&lt;br /&gt;
filename = &amp;#039;Objekt.avi&amp;#039;;&lt;br /&gt;
&lt;br /&gt;
% Festlegung des Kamerawinkels (pi/4 (45°) wobei pi=180°)&lt;br /&gt;
camAngle = pi/9;&lt;br /&gt;
&lt;br /&gt;
% Festlegung der Laserfarbe zum Orientieren Rot=1 Gruen=2 Blau=3&lt;br /&gt;
laserInd = 1;&lt;br /&gt;
&lt;br /&gt;
% Kalibrierungsframe&lt;br /&gt;
calFrame = 1;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
% Den Scanfilm aufrufen und den Laser herausfiltern&lt;br /&gt;
m = aviread(filename, calFrame);&lt;br /&gt;
calImg = m.cdata(:,:,laserInd);&lt;br /&gt;
&lt;br /&gt;
%Kalibrierungsbild anzeigen&lt;br /&gt;
figure(1);&lt;br /&gt;
imshow(calImg);&lt;br /&gt;
xlabel({&amp;#039;Calibrate rotation of image.&amp;#039;,&amp;#039;Draw line from top to bottom that should be verticle.&amp;#039;, &amp;#039;Left click to start. Right click to end.&amp;#039;});&lt;br /&gt;
[rotX, rotY] = getline(1);&lt;br /&gt;
rotAngle = 180/pi*atan2(rotY(2)-rotY(1),rotX(2)-rotX(1))-90;&lt;br /&gt;
&lt;br /&gt;
% Bild rotieren&lt;br /&gt;
figure(1);clf;&lt;br /&gt;
calImg = imrotate(calImg, rotAngle);&lt;br /&gt;
imshow(calImg);&lt;br /&gt;
&lt;br /&gt;
% Zentrierung bestimmen&lt;br /&gt;
xlabel(&amp;#039;Click mouse for center line&amp;#039;);&lt;br /&gt;
set(gcf, &amp;#039;Pointer&amp;#039;, &amp;#039;fullcrosshair&amp;#039;);&lt;br /&gt;
[x,y]=ginput(1);&lt;br /&gt;
line([x, x], [1,size(calImg,2)]);&lt;br /&gt;
&lt;br /&gt;
% Zu interessierende Region lokalisieren&lt;br /&gt;
xlabel(&amp;#039;Draw rectangle over region of interest&amp;#039;);&lt;br /&gt;
rect = getrect;&lt;br /&gt;
if rect(1)&amp;gt;x&lt;br /&gt;
    xoffset = rect(1)-x;&lt;br /&gt;
else    &lt;br /&gt;
    xoffset = (rect(1)+rect(3))-x;&lt;br /&gt;
end;&lt;br /&gt;
rectangle(&amp;#039;Position&amp;#039;, rect, &amp;#039;EdgeColor&amp;#039;, [1,0,0]);&lt;br /&gt;
set(gcf, &amp;#039;Pointer&amp;#039;, &amp;#039;arrow&amp;#039;);&lt;br /&gt;
&lt;br /&gt;
% Unschärfefilter erstellen um das Bild zu glätten&lt;br /&gt;
% bevor der Laser gefunden wird&lt;br /&gt;
h = ones(5,1)/5;&lt;br /&gt;
&lt;br /&gt;
% Schwelle einstellen zum finden der Laserlinie&lt;br /&gt;
threshold = 0.1;&lt;br /&gt;
&lt;br /&gt;
% Laserlinie finden&lt;br /&gt;
nfo = aviinfo(filename);&lt;br /&gt;
Nframes = 1;&lt;br /&gt;
frameTab = 1:Nframes:nfo.NumFrames;&lt;br /&gt;
for k=1:length(frameTab)&lt;br /&gt;
    disp(sprintf(&amp;#039;Analyzing frame #%d&amp;#039;, frameTab(k)));&lt;br /&gt;
    % Form vom Scanfilm erkennen&lt;br /&gt;
    m = aviread(filename,frameTab(k));&lt;br /&gt;
&lt;br /&gt;
    % Alles rausfiltern außer die Laserlinie &amp;amp; rotieren des Bildes&lt;br /&gt;
    img = imrotate(m.cdata(:,:,laserInd), rotAngle);&lt;br /&gt;
    &lt;br /&gt;
    % Bild auf die uns interessierende Region schneiden&lt;br /&gt;
    imgCrop = imcrop(img, rect);&lt;br /&gt;
    &lt;br /&gt;
    % Bild filtern &amp;amp; von uint8 nach double convertieren, da wir&lt;br /&gt;
    % eine große zahl an Bildern haben und die Funktionen mit double&lt;br /&gt;
    % arbeiten&lt;br /&gt;
    imgFilt = filter2(h,im2double(imgCrop));&lt;br /&gt;
    &lt;br /&gt;
    % für jede Zeile maximale Bildintensität finden &amp;amp; dessen x-Position&lt;br /&gt;
    [mx(k,:), rtmp(k,:)] = max(imgFilt&amp;#039;);&lt;br /&gt;
&lt;br /&gt;
    % Sollten in der Laserlinie Löcher sein werden diese ausgefüllt&lt;br /&gt;
    if (length(find(mx(k,:)&amp;gt;threshold))&amp;gt;=2)&lt;br /&gt;
        r(k,:)=interp1(find(mx(k,:)&amp;gt;threshold),...&lt;br /&gt;
            rtmp(k,find(mx(k,:)&amp;gt;threshold)),1:size(rtmp,2));&lt;br /&gt;
    else&lt;br /&gt;
        r(k,:)=zeros(1,size(rtmp,2));&lt;br /&gt;
    end;&lt;br /&gt;
    &lt;br /&gt;
    % Bild Zeichnen und Laserlinie berechnen&lt;br /&gt;
    figure(2);clf;&lt;br /&gt;
    imshow(imgFilt);&lt;br /&gt;
    hold on;&lt;br /&gt;
    plot(r(k,:),1:size(r,2),&amp;#039;r&amp;#039;);&lt;br /&gt;
end;&lt;br /&gt;
&lt;br /&gt;
% X-Position der Laserlinie und des Bildes zum realen Radius &lt;br /&gt;
% konvertieren&lt;br /&gt;
if xoffset&amp;gt;0&lt;br /&gt;
    R = (r+xoffset)./sin(camAngle);&lt;br /&gt;
else&lt;br /&gt;
    R = (rect(3)-r-xoffset)./sin(camAngle);&lt;br /&gt;
end;&lt;br /&gt;
theta = linspace(0,2*pi,length(frameTab))&amp;#039;;&lt;br /&gt;
&lt;br /&gt;
% Konvertieren zu den Oberflächenkoordinaten&lt;br /&gt;
X = R.*repmat(cos(theta),1,size(imgFilt,1));&lt;br /&gt;
Y = R.*repmat(sin(theta),1,size(imgFilt,1));&lt;br /&gt;
Z = -repmat(1:size(imgFilt,1),length(theta),1);&lt;br /&gt;
&lt;br /&gt;
% Resultat (Scan) anzeigen&lt;br /&gt;
figure(22);&lt;br /&gt;
S = surf(X,Y,Z,R);&lt;br /&gt;
set(S, &amp;#039;LineStyle&amp;#039;, &amp;#039;none&amp;#039;);&lt;br /&gt;
axis square;&lt;/div&gt;</summary>
		<author><name>Christoph Doerner</name></author>
	</entry>
</feed>