Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Sonstige Fragen zu Delphi (https://www.delphipraxis.net/19-sonstige-fragen-zu-delphi/)
-   -   Überprüfung eines Image (https://www.delphipraxis.net/82462-ueberpruefung-eines-image.html)

MisterScary 13. Dez 2006 17:37


Überprüfung eines Image
 
Wir sollen in der Schule ein Programm schreiben das Häuser malt. Die Werte (Breite, Hoehe, X-koordinate, Y-koordinate) werden in 4 Editfeldern eingetragen und dann zeichnet Delphi das Haus in das Image. Soweit kein Problem... Jetzt zu meiner Frage:

Wie kann ich überprüfen ob auf einer Stelle schon ein Haus gebaut/gemalt wurde, so dass Delphi eine Meldung ausgibt, dass an dieser Stelle bereits ein Haus gebaut ist ?

Wäre nett wenn jmd. mir schnell eine Lösung sagen könnte! Ich hab keine Ahnung wie ich das machen soll :-)

Danke im voraus ;-)

Jowo 13. Dez 2006 18:13

Re: Überprüfung eines Image
 
Hallo und herzlich Willkommen in der Delphi-PRAXiS!

Zu deiner Frage:
Du könntest einfach mit z.B.
Delphi-Quellcode:
Image1.Canvas.Pixels[x,y]<>clwhite
überprüfen, ob sich an der Stelle ein Pixel befindet der nicht weiß ist und dann eine entsprechende Meldung ausgeben.

MisterScary 13. Dez 2006 18:30

Re: Überprüfung eines Image
 
Hmm soweit so gut ;-)

Bin jetzt auch schon weiter als zu dem Zeitpunkt wo ich dir die PM geschickt habe ;-)!


Das Problem ist folgendes:

Das funktioniert zwar wenn man das Haus mit den gleichen Maßen auf den selben Punkt bauen will aber nicht wenn man das Haus etwas nach rechts verrückt. Dann wird ein Haus auf das andere gebaut ;-)! Es sollte aber so sein, dass man NICHTS übermalt. Wie mach ich das ?

[Edit]

Nochmal genauer die Frage: Wie überprüfe ich ALLE Pixel auf denen ein neues haus gemalt werden soll ob sie weiß sind oder nicht ?


Ps: danke für die freundliche Aufnahme ;-)

Mfg Scary

shmia 13. Dez 2006 18:34

Re: Überprüfung eines Image
 
Du musst eine Liste führen, in der alle Koordinaten (Typ: TRect) aller bisherigen Häuser enthalten sind.
Mit der Funktion IntersectRect() lässt sich prüfen, ob 2 Rechtecke sich überschneiden.

Jowo 13. Dez 2006 18:39

Re: Überprüfung eines Image
 
Oder du könntest in zwei for-Schleifen alle Pixel durchlaufen lassen, die im Bereich des neuen Hauses wären und sobald einer davon nicht weiß ist, gibt es den Fehler...

Antigo 13. Dez 2006 18:39

Re: Überprüfung eines Image
 
ich würde einfach speichern, wo ich ein Haus hinmale. Und zwar mit den werten left, top (bzw. x,y) und width height. damit hast du dann einen Bereich des Bildschirms in dem schon ein uas gemalt ist. Und zwar wäre das wen die koordinaten x und y den linken unteren punkt des Hauses angeben würden, der bereich von x bis x+width in der horizontalen und y bis y+height in der vertikalen.

Wenn du jetzt ein neues Haus zeichnen willst, guckst du wieder welchen Bereich das Haus einnehmen würde und guckst ob sich dieser Bereich mit dem eines bereits vorhandenen Hauses überschneidet.

Wenn du objektorientiert arbeitest, speicherst du die Haus Objekte in einem Array und schreibst dir eine Funktion die das o.g. überschneiden prüft. Dann erstellst du ein temporäres Haus und überprüfst es mit jedem bereits vorhanden auf Überschneidung. Andernfalls nimmst du ein Array mit 4 Werten, in denen du dann x,y,breite,höhe speicherst und gleichst das dann miteinander ab.

MisterScary 13. Dez 2006 18:44

Re: Überprüfung eines Image
 
Hilfe *G*


Danke für eure Hilfe ^^

Aber könntet ihr mir mal einen Beispielcode schreiben ?

Das hört sich in der theorie nicht so schwer an aber wie ich das dann genau schreiben soll ist die andere Frage *G*

Mfg Scary

Jowo 13. Dez 2006 18:53

Re: Überprüfung eines Image
 
Zitat:

Zitat von Jowo
Oder du könntest in zwei for-Schleifen alle Pixel durchlaufen lassen, die im Bereich des neuen Hauses wären und sobald einer davon nicht weiß ist, gibt es den Fehler...

Zum Beispiel so, wenn du das am besten findest:
Delphi-Quellcode:
var x1,x2,y1,y2,i,j: integer;
    fehler: boolean;
begin
    fehler := false;
    for i := x1 to x2 do begin
        for j := y1 to y2 do begin
            if Image1.Canvas.Pixels[i,j] <> clwhite then fehler := true;
        end;
    end;
   
    if fehler = true then Application.MessageBox("Fehler...","Fehler");
end;

Oder so ähnlich...
Und x1,x2,y1,y2 sind die Anfangs- und End-Koordinaten auf der x- und y-Achse!


[edit]i und j zu Deklaration hinzugefügt[/edit]

MisterScary 13. Dez 2006 18:58

Re: Überprüfung eines Image
 
Hmm erst einmal bedanke ich mir sehr das ihr euch alle damit so sehr beschäftigt!

@ Jowo : Delphi unterstreicht bei mir das "i" und das "j" !

Muss man das evt. auch als Variable angeben ?

Jowo 13. Dez 2006 19:03

Re: Überprüfung eines Image
 
Ja, sorry habe ich vergessen. Das sind auch nur ganz normale Integer-Variablen, die zuerst deklariert werden müssen. Für solche Schleifen fängt man halt normalerweise mit i wie integer als Variable an.

MisterScary 13. Dez 2006 19:07

Re: Überprüfung eines Image
 
Delphi-Quellcode:
For i := xstelle to xstelle+breite do
begin
  For j := ystelle to ystelle - hoehe - (breite div 2) do
  begin
    ImBebauung.Canvas.Pixels[i,j]<> clwhite;
  end;
end;
Das hab ich am Anfang in die Prozedur eingefügt die ein Haus bauen soll. Aber wenn ich das Programm jetzt ausführen möchte kommt folgendes:

Zitat:

[Error] mBebauung.pas(96): E1019 For loop control variable must be simple local variable
[Error] mBebauung.pas(98): E1019 For loop control variable must be simple local variable
[Error] mBebauung.pas(139): E1019 For loop control variable must be simple local variable
[Error] mBebauung.pas(141): E1019 For loop control variable must be simple local variable
[Error] mBebauung.pas(183): E1019 For loop control variable must be simple local variable
[Error] mBebauung.pas(185): E1019 For loop control variable must be simple local variable
[Fatal Error] pBebauung.dpr(5): F2063 Could not compile used unit 'mBebauung.pas'

Jowo 13. Dez 2006 19:11

Re: Überprüfung eines Image
 
Die Fehlermeldung kenne ich, allerdings auf deutsch:
"Die for-Schleifenvariable muss eine einfache, lokale Variable sein"

Diese hatte ich als ich anfing zu programmieren dauernd.
Du musst wahrscheinlich die Variablen i und j in der Prozedur deklarieren, in der deine for-Schleife steht.
Zeig mal etwas mehr Quelltext!

MisterScary 13. Dez 2006 19:13

Re: Überprüfung eines Image
 
Na gut dann poste ich am besten mal alles *G*

Delphi-Quellcode:
unit mBebauung;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, ExtCtrls;

type
  TBebauung = class(TForm)
    ImBebauung: TImage;
    BtStrasse: TButton;
    BtRotes_Haus: TButton;
    BtSchwarzes_Haus: TButton;
    BtGelbes_Haus: TButton;
    Label1: TLabel;
    Label2: TLabel;
    Label3: TLabel;
    Label4: TLabel;
    Edxstelle: TEdit;
    Edystelle: TEdit;
    Edbreite: TEdit;
    Edhoehe: TEdit;
    BtZuruecksetzen: TButton;
    BtBeenden: TButton;
    Label5: TLabel;
    procedure BtBeendenClick(Sender: TObject);
    procedure BtZuruecksetzenClick(Sender: TObject);
    procedure BtGelbes_HausClick(Sender: TObject);
    procedure BtRotes_HausClick(Sender: TObject);
    procedure BtSchwarzes_HausClick(Sender: TObject);
    procedure BtStrasseClick(Sender: TObject);
  private
    { Private declarations }
    var xstelle : Integer;
    var ystelle : Integer;
    var breite : Integer;
    var hoehe : Integer;
    var abstand : Integer;
    var i : Integer;
    var j : Integer;
  public
    { Public declarations }
  end;

var
  Bebauung: TBebauung;

implementation

{$R *.dfm}

procedure TBebauung.BtStrasseClick(Sender: TObject);
begin
 with ImBebauung.Canvas do
  begin
   abstand:= 20;
   MoveTo (0,480);
   Brush.Color:=clBlack;
   Rectangle (0,480,1000,420);
   Pen.Color:=clWhite;
   MoveTo (abstand-20,450);
   LineTo (abstand,450);
   repeat
   begin
   abstand:= abstand +20;
   MoveTo (abstand,450);
   abstand:= abstand + 20;
   LineTo (abstand,450)
   end
   until abstand > 1000;
   Brush.Color:=clWhite;
   Pen.Color:=clBlack;
   Pen.Width:=0
  end;
end;

procedure TBebauung.BtSchwarzes_HausClick(Sender: TObject);
begin

try
  strtoint(Edxstelle.text);
  strtoint(Edystelle.text);
  strtoint(Edhoehe.text);
  strtoint(Edbreite.text)
except
  showmessage('Bitte geben sie jeweils eine Zahl für Xstelle, Ystelle, Breite und Hoehe an!');
  exit
end;

xstelle:= StrToInt(Edxstelle.text);
ystelle:= StrToInt(Edystelle.text);
breite:= StrToInt(Edbreite.text);
hoehe:= StrToInt(Edhoehe.text);

For i := xstelle to xstelle+breite do
begin
  For j := ystelle to ystelle - hoehe - (breite div 2) do
  begin
    If ImBebauung.Canvas.Pixels[i,j]<> clwhite then showmessage ('Bauplatz ist nicht frei! Das Haus konnte nicht gebaut werden!');
  end;
end;


 with ImBebauung.Canvas do
  begin
   Brush.COlor:=clBlack;
   Pen.COlor:=clBlack;
   Pen.Width:=2;
   Rectangle(xstelle,ystelle,xstelle+breite,ystelle-hoehe);
   MoveTo(xstelle,ystelle-hoehe);
   LineTo(xstelle+breite div 2,ystelle-hoehe-breite div 2);
   LineTo(xstelle+breite,ystelle -hoehe);
   Brush.Color:=clWhite;
   Pen.Color:=clBlack;
   Pen.Width:=0
  end

end;

procedure TBebauung.BtRotes_HausClick(Sender: TObject);
begin

try
  strtoint(Edxstelle.text);
  strtoint(Edystelle.text);
  strtoint(Edhoehe.text);
  strtoint(Edbreite.text)
except
  showmessage('Bitte geben sie jeweils eine Zahl für Xstelle, Ystelle, Breite und Hoehe an!');
  exit
end;

xstelle:= StrToInt(Edxstelle.text);
ystelle:= StrToInt(Edystelle.text);
breite:= StrToInt(Edbreite.text);
hoehe:= StrToInt(Edhoehe.text);

For i := xstelle to xstelle+breite do
begin
  For j := ystelle to ystelle - hoehe - (breite div 2) do
  begin
    ImBebauung.Canvas.Pixels[i,j]<> clwhite;
  end;
end;


 with ImBebauung.Canvas do
  begin
   Brush.COlor:=clRed;
   Pen.COlor:=clRed;
   Pen.Width:=2;
   Pen.Width:=2;
   Rectangle(xstelle,ystelle,xstelle+breite,ystelle-hoehe);
   MoveTo(xstelle,ystelle-hoehe);
   LineTo(xstelle+breite div 2,ystelle-hoehe-breite div 2);
   LineTo(xstelle+breite,ystelle -hoehe);
   Brush.Color:=clWhite;
   Pen.Color:=clBlack;
   Pen.Width:=0
  end;

end;

procedure TBebauung.BtGelbes_HausClick(Sender: TObject);
begin

try
  strtoint(Edxstelle.text);
  strtoint(Edystelle.text);
  strtoint(Edhoehe.text);
  strtoint(Edbreite.text)
except
  showmessage('Bitte geben sie jeweils eine Zahl für Xstelle, Ystelle, Breite und Hoehe an!');
  exit
end;

xstelle:= StrToInt(Edxstelle.text);
ystelle:= StrToInt(Edystelle.text);
breite:= StrToInt(Edbreite.text);
hoehe:= StrToInt(Edhoehe.text);

For i := xstelle to xstelle+breite do
begin
  For j := ystelle to ystelle - hoehe - (breite div 2) do
  begin
    ImBebauung.Canvas.Pixels[i,j]<> clwhite;
  end;
end;


 with ImBebauung.Canvas do
  begin
   Brush.COlor:=clYellow;
   Pen.COlor:=clYellow;
   Pen.Width:=2;
   Pen.Width:=2;
   Rectangle(xstelle,ystelle,xstelle+breite,ystelle-hoehe);
   MoveTo(xstelle,ystelle-hoehe);
   LineTo(xstelle+breite div 2,ystelle-hoehe-breite div 2);
   LineTo(xstelle+breite,ystelle -hoehe);
   Brush.Color:=clWhite;
   Pen.Color:=clBlack;
   Pen.Width:=0
  end;

end;

procedure TBebauung.BtZuruecksetzenClick(Sender: TObject);
begin
 with ImBebauung.Canvas do
  begin
   Brush.Color:=clWhite;
   Pen.Color:=clWhite;
   Rectangle(0,500,1000,0);
   Pen.Color:=clBlack;
  end;
end;

procedure TBebauung.BtBeendenClick(Sender: TObject);
begin
 close
end;

end.

MisterScary 13. Dez 2006 19:17

Re: Überprüfung eines Image
 
Hehe du hattest recht ;-) Thx :thumb:


[Edit]
:cry: Aber Es funktioniert nicht richtig... Die Häuser werden immer noch übereinander gemalt !

Jowo 13. Dez 2006 19:17

Re: Überprüfung eines Image
 
Delphi-Quellcode:
procedure TBebauung.BtSchwarzes_HausClick(Sender: TObject);
----->var i,j: integer;<-----
begin

try
  strtoint(Edxstelle.text);
  strtoint(Edystelle.text);
  strtoint(Edhoehe.text);
  strtoint(Edbreite.text)
except
  showmessage('Bitte geben sie jeweils eine Zahl für Xstelle, Ystelle, Breite und Hoehe an!');
  exit
end;

xstelle:= StrToInt(Edxstelle.text);
ystelle:= StrToInt(Edystelle.text);
breite:= StrToInt(Edbreite.text);
hoehe:= StrToInt(Edhoehe.text);

For i := xstelle to xstelle+breite do
begin
  For j := ystelle to ystelle - hoehe - (breite div 2) do
  begin
    If ImBebauung.Canvas.Pixels[i,j]<> clwhite then showmessage ('Bauplatz ist nicht frei! Das Haus konnte nicht gebaut werden!');
  end;
end;
Die Variablen dürfen nicht oben unter private deklariert werden. Dies muss in der Prozedur selbst geschehen!

Jowo 13. Dez 2006 19:18

Re: Überprüfung eines Image
 
OK. Bitteschön :-D

DP-Maintenance 14. Dez 2006 08:42

DP-Maintenance
 
Dieses Thema wurde von "alcaeus" von "Programmieren allgemein" nach "Sonstige Fragen zu Delphi" verschoben.
Ist eine Delphi-Frage ;)


Alle Zeitangaben in WEZ +1. Es ist jetzt 14:12 Uhr.

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz