Delphi-PRAXiS
Seite 2 von 2     12   

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Programmieren allgemein (https://www.delphipraxis.net/40-programmieren-allgemein/)
-   -   Bug: IntersectRect liefert falsche Resultate (https://www.delphipraxis.net/189059-bug-intersectrect-liefert-falsche-resultate.html)

himitsu 30. Apr 2016 12:04

AW: Bug: IntersectRect liefert falsche Resultate
 
Hatte ich hier nicht schonmal geantwortet?

Also, das Problem ist, dass diese TRect-Funktionen eigentlich richtig funktionieren, aber die Zeichenfunktionen den Endpunkt nicht einbeziehen (was ich eher als Fehler erachte, aber das ist halt schon seit vielen Jahrzehnten so)

TCanvas.Rectangle, TCanvas.Line, TCanvas.PolyLine usw. sind im Entpunkt der Operation um ein Pixel verschoben, wie ihr schon bemerkt habt.
Aber dennoch arbeitet IntersectRect eigentlich richtig, nur halt nicht so, wie es die Zeichenfunktiopnen vorgeben, sondern nur auf den eigentlichen Wertebereich bezogen.

Medium 30. Apr 2016 12:50

AW: Bug: IntersectRect liefert falsche Resultate
 
Es ist halt wirklich nur eine Definitionsfrage, und beide vorgehensweisen sind gleichermaßen richtig. Man muss sich nur durchgängig auf eins von beidem einigen, um innerhalb seiner "Welt" konsistent zu bleiben. Dieser Interpretationsspielraum ergibt sich allerdings auch nur, so lange man Pixel als kleinste Einheit hat. Ein Pixel hat nämlich, im Gegensatz zu einem Punkt, eine Fläche! Das alleine macht einen gewaltigen Unterschied, da zwei Geraden, die sich so nah liegen wie es nur eben in ihrem System geht, bei Pixeln 2 Einheiten breite belegen, bei reellen Koordinaten aber unendlich dünn sind.
Deshalb muss man im Falle von Pixeln ganz klar definieren, ob meine Beschreibungen die Endpunkte beinhalten oder um eins darüber hinaus gehen. Das eine beschreibt sozusagen die Innenkante, das andere die Aussenkante - weil die Kante hat immer auch eine Breite von mindestens 1, die ich nicht weg bekomme.
Das ist übrigens sicher auch viel Ursache für anfängliche Schwierigkeiten, wenn man auf ein Mal auf FMX umsteigt. Dort werden nämlich reelle Koordinaten benutzt, wo die eigentlichen Kantenmitten (bei Breite 1) auf den n,5-Koordinaten liegen, während man beim VCL Canvas es immer nur mit ganzen Zahlen zu tun hatte. (Demnach wäre es übrigens gerade für FMX richtig, wenn zwei aneinander grenzene Rechtecke eine nicht leere Region einer Strecke gemeinsam haben, hier gibt's nicht mehr groß was zu interpretieren.)

Sir Rufo 30. Apr 2016 14:07

AW: Bug: IntersectRect liefert falsche Resultate
 
Wenn Right und Bottom mitgezeichnet würden, wie würde man denn dann ein NULL-Rechteck repräsentieren?

Ein Rechteck mit der Breite und Höhe von 1 ist ein Punkt. Ein Rechteck mit der Breite und Höhe von 0 ist Nichts (=NULL).

Mit der himitsu Definition würde man so ein NULL-Rechteck nicht definieren können. Mit der aktuellen Definition geht das problemlos. Das ist der Grund für diese Definition.

Amateurprofi 30. Apr 2016 19:51

AW: Bug: IntersectRect liefert falsche Resultate
 
Zitat:

Zitat von himitsu (Beitrag 1337188)
Hatte ich hier nicht schonmal geantwortet?

Also, das Problem ist, dass diese TRect-Funktionen eigentlich richtig funktionieren, aber die Zeichenfunktionen den Endpunkt nicht einbeziehen (was ich eher als Fehler erachte, aber das ist halt schon seit vielen Jahrzehnten so)

TCanvas.Rectangle, TCanvas.Line, TCanvas.PolyLine usw. sind im Entpunkt der Operation um ein Pixel verschoben, wie ihr schon bemerkt habt.
Aber dennoch arbeitet IntersectRect eigentlich richtig, nur halt nicht so, wie es die Zeichenfunktiopnen vorgeben, sondern nur auf den eigentlichen Wertebereich bezogen.

Nein, es ist genau umgekehrt.
Die Zeichenfunktionen arbeiten korrekt und IntersectRect und IntersectsWith arbeiten falsch.
Den Funktionen werden als Parameter TRect's übergeben und TRect ist nun einmal so definiert, dass Right und Bottom außerhalb der Fläche liegen.
Merke:
Eine Funktion arbeitet dann korrekt wenn sie das macht was der zugehörigen Dokumentation steht.
Ob dass dann auch den persönlichen Erwartungen entspricht, ist eine andere Sache.
Ein (zugegebenermaßen weit hergeholtes) Beispiel:

Delphi-Quellcode:
// Beschreibung: Mod gibt die Summe von A und B zurück
FUNCTION Mod(A,B:Integer):Integer;
begin
   Result:=A+B:
end;
Wenn nun Mod(15,3) = 18 ergibt, dann arbeitet sie korrekt, denn sie macht das, was in der Dokumentation steht.
Wenn der Anwender, der wahrscheinlich das Ergebnis 0 erwartet meint, sie arbeitet falsch, dann irrt der.
Und in der Beschreibung von zum Beispiel TRect.IntersectsWith steht
"returns true if any part of the rect covers R"
Im Fall dass die beiden Rechtecke aneinander Grenzen, machen spwohl IntersectRect und TRect.IntersectsWith nicht das, was in der Dokumentation steht, also arbeiten sie falsch und nicht "eigentlich richtig".

Allerdings ist die weitere Diskussion überflüssig, denn, wie Uwe schrieb, wurden die Funktionen in späteren Delphi Versionen korrigiert.


Alle Zeitangaben in WEZ +1. Es ist jetzt 03:57 Uhr.
Seite 2 von 2     12   

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