Registriert seit: 28. Feb 2011
Ort: Mannheim
1.384 Beiträge
Delphi 10.4 Sydney
|
AW: Volumen und Mittelpunkt von einem 3D-Raum berechnen?
12. Feb 2018, 09:55
Ist quasi ein räumliches N-Eck (Polyeder). Die Eingabe ist etwas aufwendiger als beim 2D N-Eck weil man zusätzlich die Begrenzungsebenen eingeben muss. Die Begrenzungsebenen müssen mathematisch positiv eingegeben werden.
Beispiel Würfel:
Delphi-Quellcode:
procedure TPolyederForm.TestButton3Click(Sender: TObject);
begin
FPolyeder.Clear;
FPolyeder.AddPoint(0, 0, 0);
FPolyeder.AddPoint(8, 0, 0);
FPolyeder.AddPoint(0, 5, 0);
FPolyeder.AddPoint(8, 5, 0);
FPolyeder.AddPoint(0, 0, 3);
FPolyeder.AddPoint(8, 0, 3);
FPolyeder.AddPoint(0, 5, 3);
FPolyeder.AddPoint(8, 5, 3);
FPolyeder.AddPlane([0, 2, 3, 1]);
FPolyeder.AddPlane([4, 5, 7, 6]);
FPolyeder.AddPlane([0, 1, 5, 4]);
FPolyeder.AddPlane([2, 6, 7, 3]);
FPolyeder.AddPlane([1, 3, 7, 5]);
FPolyeder.AddPlane([0, 4, 6, 2]);
FPolyeder.Calc;
end;
TPolyeder:
Delphi-Quellcode:
function TPolyeder.Determinant(const A, B, C: integer): double;
begin
Result := FPoints[A].X * (FPoints[B].Y * FPoints[C].Z - FPoints[B].Z * FPoints[C].Y)
- FPoints[A].Y * (FPoints[B].X * FPoints[C].Z - FPoints[B].Z * FPoints[C].X)
+ FPoints[A].Z * (FPoints[B].X * FPoints[C].Y - FPoints[B].Y * FPoints[C].X);
end;
procedure TPolyeder.Calc;
var
I, J, A, B, C: integer;
Det: double;
begin
FVolumen := 0;
FCenter.X := 0;
FCenter.Y := 0;
FCenter.Z := 0;
for I := 0 to FPlanes.Count - 1 do
begin
A := FPlanes[I].Items[0];
B := FPlanes[I].Items[1];
for J := 2 to FPlanes[I].Count - 1 do
begin
C := FPlanes[I].Items[J];
Det := Determinant(A, B, C);
FVolumen := FVolumen + Det;
FCenter.X := FCenter.X + (FPoints[A].X + FPoints[B].X + FPoints[C].X) * Det;
FCenter.Y := FCenter.Y + (FPoints[A].Y + FPoints[B].Y + FPoints[C].Y) * Det;
FCenter.Z := FCenter.Z + (FPoints[A].Z + FPoints[B].Z + FPoints[C].Z) * Det;
B := C;
end;
end;
if FVolumen <> 0 then
begin
FVolumen := FVolumen / 6;
FCenter.X := FCenter.X / 24 / FVolumen;
FCenter.Y := FCenter.Y / 24 / FVolumen;
FCenter.Z := FCenter.Z / 24 / FVolumen;
end
else
begin
FCenter.X := 0;
FCenter.Y := 0;
FCenter.Z := 0;
end;
end;
LG Thomas
|