Verfasst am: 21.11.2012, 17:14
Titel: Abstand Objekt zu Oberfläche in Pixel bestimmen!
Hallo
Ich bin bei Matlab blutiger Anfänger. Vielleicht könnt ihr mir trotzdem helfen.
Ich habe 2 Bilder eingeladen per Schleife (for, end) diese Bilder auch in 2 binäre Bilder (im2bw) umgewandelt und per Kantenerkennung (edge 'sobel') verändert, dass ich nurnoch 2 Linien zu erkennen sind.
Soweit alles okay. Jetzt will ich den Abstand zwischen dem Kreis und der Oberfläche in Pixeln bestimmen. Wie kann ich das realisieren und vernünftig ausgeben?
Ich hab die beiden Bilder angehängt.
Hoffe meine Fragestellung war klar genug. Danke schonmal im Vorraus!!
Verfasst am: 21.11.2012, 18:11
Titel: Re: Abstand Objekt zu Oberfläche in Pixel bestimmen!
Hallo Highspeed,
Geht es um zwei Bilder, oder soll dies automatisch mit 4000 Bildern geschehen?
Bei zwei Bildern würde ich das mit der Lupe im Photoshop machen und per Hand abzählen.
Bei vielen Bildern wäre es ein Ansatz, eine Gerade und einen Kreis an die Daten zu fitten und deren Abstand analytisch berechnen. Bei der großen Anzahl an Punkten pro Objekt bekommst Du ein Ergebnis mit Sub-Pixel-Genauigkeit.
Bitte erkläre die Aufgabe also noch genauer.
Gruß, Jan
Highspeed
Gast
Beiträge: ---
Anmeldedatum: ---
Wohnort: ---
Version: ---
Verfasst am: 22.11.2012, 09:55
Titel:
Hallo Jan S und natürlich alle anderen!
Klar bei zwei Bildern würde es deutlich schneller gehen wenn man die Pixel per Hand zählt.
Es sind so ca. 2000 Bilder. Eine Sequenz aus Hochgeschwindigkeitsaufnahmen von einem "Festklopfprozess". Das ist eine mechanische Oberflächenbehandlung bei der ein Roboterarm die Oberfläche abrastert und durch plastische Verformung diese sowohl glättet als auch härtet. Bisschen vergleichbar mit Kugelstrahlen.
Ich möchte eine automatische Auswertung der Bilder. Als Ergebnis die Verschiebung bzw. den Geschwindigkeitsverlauf bestimmen.
Code:
% Das ist mein Programm bisher
verz_in = 'C:\Users\Thorsten\Documents\MATLAB\Bilder';
name_in = '01_0Spalt5_75f_10kHz0000';
von = 44;
bis = 45;
% Schleife über alle auszuwertenden Bilder for ii = von:bis
% for ii = von:bis % zur Wartung können gezielte Bilder ausgewählt werden
wenn du dir die Bildzeile in halber Höhe ausgeben lässt, bekommst du die fortlaufenden Dichtewerte, die mit 0 beginnen. Dann folgen vielleicht 2 Pixelwerte mit 1 und dann werden die von dir gesuchten Pixelwerte in 0 ausgeben. Es müsste doch möglich sein, dass irgendwie in eine Formel zu schreiben. Da es sich nicht um Grautöne handelt, sondern nur um 0 + 1 wären die Ergebnisse eindeutig.
In B sind dann Kreissegment und Gerade enthalten. Über eine simple Min-Betrachtung in x-Richtung des Kreissegmentes erhält man den Abstand.
2. Moore-Nachbarschaft verwenden
Verwende die Moore-Nachbarschaft, um das Kreissegement zu erkennen. Über eine simple Min-Betrachtung in x-Richtung des Kreissegmentes erhält man den Abstand.
3. Vielleicht eine noch einfachere Variante
Starte mittig rechts im Bild. Gehe soweit nach links, bis du auf ein weißes Pixel triffst. Überprüfe den oberen Bereich der Moore-Nachbarschaft des Pixels. Wenn du darin ein Pixel findest, dass nach rechts versetzt ist, gehe nach unten, umgekehrt analog. Mache das solange, bis ein Richtungswechsel stattfindet. Speichere währenddessen immer das aktuelle Minimum.
Beginne oben links und gehe jede Zeile durch. Gehe in der aktuellen Zeile jede Spalte durch. Wenn du auf ein weißes Pixel triffst, beginne zu zählen. Triffst du erneut auf ein weißes Pixel, stoppe das Zählen. Wenn in einer Zeile nicht gleichsam begonnen und gestoppt werden kann, ist diese Zeile ungültig. Der minimale Zählwert ist der Abstand.
Highspeed
Gast
Beiträge: ---
Anmeldedatum: ---
Wohnort: ---
Version: ---
Verfasst am: 22.11.2012, 15:37
Titel:
MaFam hat Folgendes geschrieben:
Und noch einfacher:
Beginne oben links und gehe jede Zeile durch. Gehe in der aktuellen Zeile jede Spalte durch. Wenn du auf ein weißes Pixel triffst, beginne zu zählen. Triffst du erneut auf ein weißes Pixel, stoppe das Zählen. Wenn in einer Zeile nicht gleichsam begonnen und gestoppt werden kann, ist diese Zeile ungültig. Der minimale Zählwert ist der Abstand.
Das klingt sehr interessant. Aber ich brauch Hilfe beim Anfangen.
Mein "bild4" entspricht einer 248x83 Matrix im Format "logical", besteht also nur aus 0 und 1.
Wie lade ich die Matrix und wie beginne ich dann von links oben an zu zählen und höre bei der zweiten 1 auf?
Hab den ganzen morgen danach gesucht aber nichts brauchbares gefunden.
for i=1:k
start_p=false;
end_p=false;
first=false;
for j=1:m
if(bild4(i,j)==0) if(~first)
start_p=true;
first=true;
pixelstart=j;
else
end_p=true;
pixelend=j;
end elseif(bild4(i,j)==1 && first)
pixelstart=j;
end end
first=false;
if(start_p && end_p)
curdis=pixelend-pixelend;
bestdis=min(bestdis,curdis);
end
start_p=false;
end_p=false;
end
Ich hatte den Code zwischenzeitlich verändert, da die ursprüngliche Version darauf ausgerichtet war, dass die Kanten höchsten eine Dicke von einem Pixel haben. Das trifft bei deinem Beispiel offensichtlich nicht zu. Ich würde allerdings eh zur zweiten Variante meines Codes raten...
Es kommt 14 raus. Auch die Variante ist nicht wirklich schön, weil direkt aufeinander folgende Pixel mit max(diff(curind))>1 gefiltert werden. Das bedeutet, dass ein Abstand der kleiner ist als eine Gruppe von direkt aufeinander folgenden Pixeln nicht erfasst werden kann. Daher müsste man diese Gruppen zuvor identifizieren und rausfiltern.
Highspeed
Gast
Beiträge: ---
Anmeldedatum: ---
Wohnort: ---
Version: ---
Verfasst am: 23.11.2012, 12:21
Titel:
Schonmal vielen Dank für die viele Mühe. Habe noch ein paar Fragen zu deinem Code, weil wenn ich schon nicht die Arbeit habe, will ich es doch verstehen
Code:
[k,m]=size(bild4); %Größe vom Bild wird ausgelesen und in die Variablen k und m aufgeteilt
bestdis=m; %bestdis ist dann nachher mein Ergebnis?
v0=find(bild4'==0); %was genau macht dieser Befehl? Suche im bild4 nach 0? Wieso macht man==?
for i=1:k
curind=v0((v0<=(i-1)*k+m) == (v0>(i-2)*k+m));
if(numel(curind)>=2)%hier berücksichtigst du den Fall, dass ich mehr als 2 Pixel in einer Zeile habe?
bestdis=min(bestdis, max(diff(curind)));
end end
Bitte meine letzte Variante verwenden. Ich hatte noch einige Fehler in den anderen Varianten und konnte erst heute selbst mal testen.
Ich kann die Zeilen gerne noch kommentieren später...
Highspeed
Gast
Beiträge: ---
Anmeldedatum: ---
Wohnort: ---
Version: ---
Verfasst am: 23.11.2012, 12:34
Titel:
[quote="MaFam"]Hier eine wirklich funktionierende Variante:
[code]
Oh da war ich zu langsam Wird gleich getestet!! Danke
Einstellungen und Berechtigungen
Du kannst Beiträge in dieses Forum schreiben. Du kannst auf Beiträge in diesem Forum antworten. Du kannst deine Beiträge in diesem Forum nicht bearbeiten. Du kannst deine Beiträge in diesem Forum nicht löschen. Du kannst an Umfragen in diesem Forum nicht mitmachen. Du kannst Dateien in diesem Forum posten Du kannst Dateien in diesem Forum herunterladen
MATLAB, Simulink, Stateflow, Handle Graphics, Real-Time Workshop, SimBiology, SimHydraulics, SimEvents, and xPC TargetBox are registered trademarks and The MathWorks, the L-shaped membrane logo, and Embedded MATLAB are trademarks of The MathWorks, Inc.