"final" xform support - part 1...

This commit is contained in:
zueuk 2006-03-02 17:27:20 +00:00
parent 023b72b70f
commit 1270d58d49
10 changed files with 407 additions and 262 deletions

View File

@ -1893,11 +1893,11 @@ object AboutForm: TAboutForm
object Label4: TLabel object Label4: TLabel
Left = 120 Left = 120
Top = 72 Top = 72
Width = 123 Width = 204
Height = 13 Height = 13
Cursor = crHandPoint Cursor = crHandPoint
Hint = 'http://www.apophysis.org' Hint = 'http://sourceforge.net/projects/apophysis/'
Caption = 'http://www.apophysis.org' Caption = 'http://sourceforge.net/projects/apophysis/'
Font.Charset = DEFAULT_CHARSET Font.Charset = DEFAULT_CHARSET
Font.Color = clBlue Font.Color = clBlue
Font.Height = -11 Font.Height = -11

View File

@ -1,5 +1,6 @@
{ {
Apophysis Copyright (C) 2001-2004 Mark Townsend Apophysis Copyright (C) 2001-2004 Mark Townsend
Apophysis Copyright (C) 2005-2006 Ronald Hordijk, Piotr Boris, Peter Sdobnov
This program is free software; you can redistribute it and/or modify This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by it under the terms of the GNU General Public License as published by

View File

@ -173,7 +173,7 @@ object AdjustForm: TAdjustForm
Top = 131 Top = 131
Width = 388 Width = 388
Height = 130 Height = 130
ActivePage = TabSheet2 ActivePage = TabSheet1
Align = alBottom Align = alBottom
TabOrder = 1 TabOrder = 1
object TabSheet1: TTabSheet object TabSheet1: TTabSheet

View File

@ -4,7 +4,7 @@ interface
uses uses
Classes, Windows, Classes, Windows,
ControlPoint, Render; ControlPoint, Render, XForm;
type type
TBucketFillerThread = class(TThread) TBucketFillerThread = class(TThread)
@ -17,9 +17,17 @@ type
BucketWidth: Int64; BucketWidth: Int64;
BucketHeight: Int64; BucketHeight: Int64;
{
bounds: array[0..3] of extended; bounds: array[0..3] of extended;
size: array[0..1] of extended; size: array[0..1] of extended;
RotationCenter: array[0..1] of extended; RotationCenter: array[0..1] of extended;
}
FinalXform: ^TXform;
UseFinalXform: boolean;
camX0, camY0, camW, camH,
bws, bhs, cosa, sina, rcX, rcY: double;
Buckets: PBucketArray; Buckets: PBucketArray;
ColorMap: TColorMapArray; ColorMap: TColorMapArray;
CriticalSection: TRTLCriticalSection; CriticalSection: TRTLCriticalSection;
@ -29,8 +37,10 @@ type
procedure Execute; override; procedure Execute; override;
procedure AddPointsToBuckets(const points: TPointsArray); overload; procedure AddPointsToBuckets(const points: TPointsArray);
procedure AddPointsToBucketsAngle(const points: TPointsArray); overload; procedure AddPointsToBucketsAngle(const points: TPointsArray);
procedure AddPointsWithFX(const points: TPointsArray);
procedure AddPointsWithAngleFX(const points: TPointsArray);
end; end;
implementation implementation
@ -42,29 +52,21 @@ procedure TBucketFillerThread.AddPointsToBuckets(const points: TPointsArray);
var var
i: integer; i: integer;
px, py: double; px, py: double;
bws, bhs: double; // R: double;
bx, by: double; // V1, v2, v3: integer;
wx, wy: double;
Bucket: PBucket; Bucket: PBucket;
MapColor: PColorMapColor; MapColor: PColorMapColor;
begin begin
bws := (BucketWidth - 0.5) * size[0];
bhs := (BucketHeight - 0.5) * size[1];
bx := bounds[0];
by := bounds[1];
wx := bounds[2] - bounds[0];
wy := bounds[3] - bounds[1];
for i := SUB_BATCH_SIZE - 1 downto 0 do begin for i := SUB_BATCH_SIZE - 1 downto 0 do begin
px := points[i].x - bx; // if FStop then Exit;
py := points[i].y - by;
if ((px < 0) or (px > wx) or px := points[i].x - camX0;
(py < 0) or (py > wy)) then if (px < 0) or (px > camW) then continue;
continue; py := points[i].y - camY0;
if (py < 0) or (py > camH) then continue;
Bucket := @TBucketArray(buckets^)[Round(bws * px) + Round(bhs * py) * BucketWidth];
MapColor := @ColorMap[Round(points[i].c * 255)]; MapColor := @ColorMap[Round(points[i].c * 255)];
Bucket := @TbucketArray(buckets^)[Round(bws * px) + Round(bhs * py) * BucketWidth];
Inc(Bucket.Red, MapColor.Red); Inc(Bucket.Red, MapColor.Red);
Inc(Bucket.Green, MapColor.Green); Inc(Bucket.Green, MapColor.Green);
@ -73,51 +75,90 @@ begin
end; end;
end; end;
/////////////////////////////////////////////////////////////////////////////// procedure TBucketFillerThread.AddPointsWithFX(const points: TPointsArray);
procedure TBucketFillerThread.AddPointsToBucketsAngle(const points: TPointsArray);
var var
i: integer; i: integer;
px, py: double; px, py: double;
ca,sa: double;
nx, ny: double;
bws, bhs: double;
bx, by: double;
wx, wy: double;
Bucket: PBucket; Bucket: PBucket;
MapColor: PColorMapColor; MapColor: PColorMapColor;
begin begin
bws := (BucketWidth - 0.5) * size[0]; try
bhs := (BucketHeight - 0.5) * size[1];
bx := bounds[0];
by := bounds[1];
wx := bounds[2] - bounds[0];
wy := bounds[3] - bounds[1];
ca := cos(FCP.FAngle);
sa := sin(FCP.FAngle);
for i := SUB_BATCH_SIZE - 1 downto 0 do begin for i := SUB_BATCH_SIZE - 1 downto 0 do begin
px := points[i].x - RotationCenter[0]; // if FStop then Exit;
py := points[i].y - RotationCenter[1];
nx := px * ca + py * sa; FinalXform.NextPoint(points[i]);
ny := -px * sa + py * ca;
px := nx + FCP.Center[0] - bx; px := points[i].x - camX0;
py := ny + FCP.Center[1] - by; if (px < 0) or (px > camW) then continue;
py := points[i].y - camY0;
if ((px < 0) or (px > wx) or if (py < 0) or (py > camH) then continue;
(py < 0) or (py > wy)) then
continue;
Bucket := @TBucketArray(buckets^)[Round(bws * px) + Round(bhs * py) * BucketWidth];
MapColor := @ColorMap[Round(points[i].c * 255)]; MapColor := @ColorMap[Round(points[i].c * 255)];
Bucket := @TbucketArray(buckets^)[Round(bws * px) + Round(bhs * py) * BucketWidth];
Inc(Bucket.Red, MapColor.Red); Inc(Bucket.Red, MapColor.Red);
Inc(Bucket.Green, MapColor.Green); Inc(Bucket.Green, MapColor.Green);
Inc(Bucket.Blue, MapColor.Blue); Inc(Bucket.Blue, MapColor.Blue);
Inc(Bucket.Count); Inc(Bucket.Count);
end; end;
except
end
end;
///////////////////////////////////////////////////////////////////////////////
procedure TBucketFillerThread.AddPointsToBucketsAngle(const points: TPointsArray);
var
i: integer;
px, py: double;
Bucket: PBucket;
MapColor: PColorMapColor;
begin
for i := SUB_BATCH_SIZE - 1 downto 0 do begin
// if FStop then Exit;
px := points[i].x * cosa + points[i].y * sina + rcX;
if (px < 0) or (px > camW) then continue;
py := points[i].y * cosa - points[i].x * sina + rcY;
if (py < 0) or (py > camH) then continue;
Bucket := @TBucketArray(buckets^)[Round(bws * px) + Round(bhs * py) * BucketWidth];
MapColor := @ColorMap[Round(points[i].c * 255)];
Inc(Bucket.Red, MapColor.Red);
Inc(Bucket.Green, MapColor.Green);
Inc(Bucket.Blue, MapColor.Blue);
Inc(Bucket.Count);
end;
end;
procedure TBucketFillerThread.AddPointsWithAngleFX(const points: TPointsArray);
var
i: integer;
px, py: double;
Bucket: PBucket;
MapColor: PColorMapColor;
begin
try
for i := SUB_BATCH_SIZE - 1 downto 0 do
begin
// if FStop then Exit;
FinalXform.NextPoint(points[i]);
px := points[i].x * cosa + points[i].y * sina + rcX;
if (px < 0) or (px > camW) then continue;
py := points[i].y * cosa - points[i].x * sina + rcY;
if (py < 0) or (py > camH) then continue;
Bucket := @TBucketArray(buckets^)[Round(bws * px) + Round(bhs * py) * BucketWidth];
MapColor := @ColorMap[Round(points[i].c * 255)];
Inc(Bucket.Red, MapColor.Red);
Inc(Bucket.Green, MapColor.Green);
Inc(Bucket.Blue, MapColor.Blue);
Inc(Bucket.Count);
end;
except
end
end; end;
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -129,6 +170,9 @@ begin
Fcp := cp.Clone; Fcp := cp.Clone;
SetLength(Points, SUB_BATCH_SIZE); SetLength(Points, SUB_BATCH_SIZE);
FinalXForm := @fcp.xform[fcp.NumXForms];
UseFinalXForm := fcp.finalXformEnabled and fcp.HasFinalXform;
end; end;
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -143,19 +187,30 @@ end;
procedure TBucketFillerThread.Execute; procedure TBucketFillerThread.Execute;
var var
bc: integer; bc: integer;
AddPointsProc: procedure (const points: TPointsArray) of object;
begin begin
inherited; inherited;
if FCP.FAngle = 0 then begin
if UseFinalXForm then
AddPointsProc := AddPointsWithFX
else
AddPointsProc := AddPointsToBuckets;
end
else begin
if UseFinalXForm then
AddPointsProc := AddPointsWithAngleFX
else
AddPointsProc := AddPointsToBucketsAngle;
end;
bc := 0; bc := 0;
while (not Terminated) and (bc < Nrbatches) do begin while (not Terminated) and (bc < Nrbatches) do begin
fcp.iterateXYC(SUB_BATCH_SIZE, points); fcp.iterateXYC(SUB_BATCH_SIZE, points);
try try
EnterCriticalSection(CriticalSection); EnterCriticalSection(CriticalSection);
if FCP.FAngle = 0 then AddPointsProc(Points);
AddPointsToBuckets(Points)
else
AddPointsToBucketsAngle(Points);
Inc(batchcounter^); Inc(batchcounter^);
bc := batchcounter^ bc := batchcounter^

View File

@ -38,9 +38,15 @@ const
// ---- MyTypes ---- // ---- MyTypes ----
type type
TCoefsArray= array[0..2, 0..1] of double;
pCoefsArray= ^TCoefsArray;
TTriangle = record TTriangle = record
x: array[0..2] of double; x: array[0..2] of double;
y: array[0..2] of double; y: array[0..2] of double;
{ color: integer;
locked, visible: boolean;
pCoefs: pCoefsArray;
pXform: ^TXform; }
end; end;
TTriangles = array[-1..NXFORMS] of TTriangle; TTriangles = array[-1..NXFORMS] of TTriangle;
TSPoint = record TSPoint = record
@ -48,9 +54,9 @@ type
y: double; y: double;
end; end;
TMapPalette = record TMapPalette = record
Red: array[0..255] of byte; Red: array[0..255] of byte;
Green: array[0..255] of byte; Green: array[0..255] of byte;
Blue: array[0..255] of byte; Blue: array[0..255] of byte;
end; end;
TColorMaps = record TColorMaps = record
Identifier: string; Identifier: string;
@ -86,7 +92,9 @@ type
TControlPoint = class TControlPoint = class
public public
xform: array[0..NXFORMS - 1] of TXForm; xform: array[0..NXFORMS] of TXForm;
// finalxform: TXForm;
finalXformEnabled: boolean;
variation: TVariation; variation: TVariation;
cmap: TColorMap; cmap: TColorMap;
cmapindex: integer; cmapindex: integer;
@ -141,7 +149,7 @@ type
class function interpolate(cp1, cp2: TControlPoint; Time: double): TControlPoint; /// just for now class function interpolate(cp1, cp2: TControlPoint; Time: double): TControlPoint; /// just for now
procedure InterpolateX(cp1, cp2: TControlPoint; Tm: double); procedure InterpolateX(cp1, cp2: TControlPoint; Tm: double);
procedure Iterate_Old(NrPoints: integer; var Points: TPointsArray); // procedure Iterate_Old(NrPoints: integer; var Points: TPointsArray);
procedure IterateXY(NrPoints: integer; var Points: TPointsXYArray); procedure IterateXY(NrPoints: integer; var Points: TPointsXYArray);
procedure IterateXYC(NrPoints: integer; var Points: TPointsArray); procedure IterateXYC(NrPoints: integer; var Points: TPointsArray);
procedure IterateXYCC(NrPoints: integer; var Points: T2CPointsArray); procedure IterateXYCC(NrPoints: integer; var Points: T2CPointsArray);
@ -152,8 +160,9 @@ type
procedure Copy(cp1: TControlPoint); procedure Copy(cp1: TControlPoint);
function HasNewVariants: boolean; function HasNewVariants: boolean;
function HasFinalXForm: boolean;
// CP-specific functions moved from unit Main // CP-specific functions moved from unit Main
function NumXForms: integer; function NumXForms: integer;
function TrianglesFromCP(var Triangles: TTriangles): integer; function TrianglesFromCP(var Triangles: TTriangles): integer;
procedure GetFromTriangles(const Triangles: TTriangles; const t: integer); procedure GetFromTriangles(const Triangles: TTriangles; const t: integer);
@ -203,9 +212,10 @@ constructor TControlPoint.Create;
var var
i: Integer; i: Integer;
begin begin
for i := 0 to NXFORMS - 1 do begin for i := 0 to NXFORMS do begin
xform[i] := TXForm.Create; xform[i] := TXForm.Create;
end; end;
// finalxform := TXForm.Create;
pulse[0][0] := 0; pulse[0][0] := 0;
pulse[0][1] := 60; pulse[0][1] := 60;
@ -253,6 +263,7 @@ var
begin begin
for i := 0 to NXFORMS - 1 do for i := 0 to NXFORMS - 1 do
xform[i].Free; xform[i].Free;
// finalxform.Free;
inherited; inherited;
end; end;
@ -285,6 +296,7 @@ begin
end; end;
end; end;
(*
procedure TControlPoint.Iterate_Old(NrPoints: integer; var Points: TPointsArray); procedure TControlPoint.Iterate_Old(NrPoints: integer; var Points: TPointsArray);
var var
i: Integer; i: Integer;
@ -516,6 +528,7 @@ begin
end end
end; end;
end; end;
*)
procedure TControlPoint.IterateXY(NrPoints: integer; var Points: TPointsXYArray); procedure TControlPoint.IterateXY(NrPoints: integer; var Points: TPointsXYArray);
var var
@ -743,6 +756,9 @@ begin
if AnsiCompareText(CurrentToken, 'xform') = 0 then begin if AnsiCompareText(CurrentToken, 'xform') = 0 then begin
Inc(ParsePos); Inc(ParsePos);
CurrentXForm := StrToInt(ParseValues[ParsePos]); CurrentXForm := StrToInt(ParseValues[ParsePos]);
end else if AnsiCompareText(CurrentToken, 'finalxformenabled') = 0 then begin
Inc(ParsePos);
finalxformenabled := StrToInt(ParseValues[ParsePos]) <> 0;
end else if AnsiCompareText(CurrentToken, 'time') = 0 then begin end else if AnsiCompareText(CurrentToken, 'time') = 0 then begin
Inc(ParsePos); Inc(ParsePos);
time := StrToFloat(ParseValues[ParsePos]); time := StrToFloat(ParseValues[ParsePos]);
@ -1087,10 +1103,12 @@ begin
// RandSeed := 1234567; // RandSeed := 1234567;
try try
SetLength(Points, SUB_BATCH_SIZE); SetLength(Points, SUB_BATCH_SIZE);
case compatibility of { case compatibility of
0: iterate_Old(SUB_BATCH_SIZE, points); 0: iterate_Old(SUB_BATCH_SIZE, points);
1: iterateXYC(SUB_BATCH_SIZE, points); 1: iterateXYC(SUB_BATCH_SIZE, points);
end; end;
}
IterateXYC(SUB_BATCH_SIZE, points);
LimitOutSidePoints := Round(0.05 * SUB_BATCH_SIZE); LimitOutSidePoints := Round(0.05 * SUB_BATCH_SIZE);
@ -1546,10 +1564,11 @@ begin
[nbatches, white_level, background[0], background[1], background[2]])); [nbatches, white_level, background[0], background[1], background[2]]));
sl.add(format('brightness %f gamma %f vibrancy %f hue_rotation %f cmap_inter %d', sl.add(format('brightness %f gamma %f vibrancy %f hue_rotation %f cmap_inter %d',
[brightness * BRIGHT_ADJUST, gamma, vibrancy, hue_rotation, cmap_inter])); [brightness * BRIGHT_ADJUST, gamma, vibrancy, hue_rotation, cmap_inter]));
sl.add(format('finalxformenabled %d', [ifthen(finalxformenabled, 1, 0)]));
for i := 0 to NXFORMS - 1 do for i := 0 to NXFORMS do
with xform[i] do begin with xform[i] do begin
if density = 0 then continue; //if density = 0 then continue; - FinalXform has weight=0
sl.add(format('xform %d density %g color %g symmetry %g', [i, density, color, symmetry])); sl.add(format('xform %d density %g color %g symmetry %g', [i, density, color, symmetry]));
s := 'vars'; s := 'vars';
@ -1568,7 +1587,6 @@ begin
sl.Add(format('post %.6f %.6f %.6f %.6f %.6f %.6f', sl.Add(format('post %.6f %.6f %.6f %.6f %.6f %.6f',
[p[0][0], p[0][1], p[1][0], p[1][1], p[2][0], p[2][1]])); [p[0][0], p[0][1], p[1][0], p[1][1], p[2][0], p[2][1]]));
end; end;
DecimalSeparator := OldDecimalSperator; DecimalSeparator := OldDecimalSperator;
end; end;
@ -1612,8 +1630,9 @@ begin
nick := cp1.nick; nick := cp1.nick;
url := cp1.url; url := cp1.url;
for i := 0 to NXFORMS - 1 do for i := 0 to NXFORMS do // was: NXFORMS-1
xform[i].assign(cp1.xform[i]); xform[i].assign(cp1.xform[i]);
finalXformEnabled := cp1.finalXformEnabled;
sl.Free; sl.Free;
end; end;
@ -1623,6 +1642,7 @@ var
s: string; s: string;
i: integer; i: integer;
begin begin
finalXformEnabled := false;
for i := 0 to sl.Count - 1 do begin for i := 0 to sl.Count - 1 do begin
s := s + sl[i] + ' '; s := s + sl[i] + ' ';
end; end;
@ -1634,7 +1654,9 @@ var
i, j: Integer; i, j: Integer;
begin begin
symmetry := 0; symmetry := 0;
for i := 0 to NXFORMS - 1 do begin for i := 0 to NXFORMS do begin
xform[i].Clear;
{
xform[i].density := 0; xform[i].density := 0;
xform[i].symmetry := 0; xform[i].symmetry := 0;
xform[i].color := 0; xform[i].color := 0;
@ -1642,10 +1664,29 @@ begin
for j := 1 to NRVAR - 1 do begin for j := 1 to NRVAR - 1 do begin
xform[i].vars[j] := 0; xform[i].vars[j] := 0;
end; end;
}
end; end;
zoom := 0; zoom := 0;
end; end;
function TControlPoint.HasFinalXForm: boolean;
var
i: integer;
begin
// if finalXformEnabled then Result := true else
with xform[NumXForms] do
begin
Result := (c[0,0]<>1) or (c[0,1]<>0) or(c[1,0]<>0) or (c[1,1]<>1) or (c[2,0]<>0) or (c[2,1]<>0) or
(p[0,0]<>1) or (p[0,1]<>0) or(p[1,0]<>0) or (p[1,1]<>1) or (p[2,0]<>0) or (p[2,1]<>0) or
(symmetry <> 1);
if Result = false then
begin
Result := Result or (vars[0] <> 1);
for i := 1 to NRVAR-1 do Result := Result or (vars[i] <> 0);
end
end;
end;
function add_symmetry_to_control_point(var cp: TControlPoint; sym: integer): integer; function add_symmetry_to_control_point(var cp: TControlPoint; sym: integer): integer;
const const
sym_distrib: array[0..14] of integer = ( sym_distrib: array[0..14] of integer = (
@ -1911,7 +1952,6 @@ var
i, j: integer; i, j: integer;
temp_x, temp_y, xset, yset: double; temp_x, temp_y, xset, yset: double;
left, top, bottom, right: double; left, top, bottom, right: double;
a, b, c, d, e, f: double;
begin begin
top := 0; bottom := 0; right := 0; left := 0; top := 0; bottom := 0; right := 0; left := 0;
Result := NumXForms; Result := NumXForms;
@ -1919,18 +1959,12 @@ begin
begin begin
for i := 0 to Result-1 do for i := 0 to Result-1 do
begin begin
a := xform[i].c[0][0];
b := xform[i].c[0][1];
c := xform[i].c[1][0];
d := xform[i].c[1][1];
e := xform[i].c[2][0];
f := xform[i].c[2][1];
xset := 1.0; xset := 1.0;
yset := 1.0; yset := 1.0;
for j := 0 to 5 do for j := 0 to 5 do
begin with xform[i] do begin
temp_x := xset * a + yset * c + e; temp_x := xset * c[0][0] + yset * c[1][0] + c[2][0];
temp_y := xset * b + yset * d + f; temp_y := xset * c[0][1] + yset * c[1][1] + c[2][1];
xset := temp_x; xset := temp_x;
yset := temp_y; yset := temp_y;
end; end;
@ -1975,25 +2009,20 @@ begin
Triangles[-1].x[2] := 0; Triangles[-1].y[2] := -1; // "y" Triangles[-1].x[2] := 0; Triangles[-1].y[2] := -1; // "y"
end; end;
for j := 0 to Result-1 do for j := 0 to Result do
begin begin
a := xform[j].c[0][0];
b := xform[j].c[0][1];
c := xform[j].c[1][0];
d := xform[j].c[1][1];
e := xform[j].c[2][0];
f := xform[j].c[2][1];
for i := 0 to 2 do for i := 0 to 2 do
begin with xform[j] do begin
triangles[j].x[i] := Triangles[-1].x[i] * a + Triangles[-1].y[i] * c + e; Triangles[j].x[i] := Triangles[-1].x[i] * c[0][0] + Triangles[-1].y[i] * c[1][0] + c[2][0];
triangles[j].y[i] := Triangles[-1].x[i] * b + Triangles[-1].y[i] * d + f; Triangles[j].y[i] := Triangles[-1].x[i] * c[0][1] + Triangles[-1].y[i] * c[1][1] + c[2][1];
end; end;
end; end;
EnableFinalXform := FinalXformEnabled;
// I don't like this... :-/ // I don't like this... :-/
for j := -1 to Result-1 do for j := -1 to Result do // was: Result-1
for i := 0 to 2 do for i := 0 to 2 do
triangles[j].y[i] := -triangles[j].y[i]; Triangles[j].y[i] := -Triangles[j].y[i];
end; end;
procedure TControlPoint.EqualizeWeights; procedure TControlPoint.EqualizeWeights;
@ -2051,7 +2080,7 @@ procedure TControlPoint.GetFromTriangles(const Triangles: TTriangles; const t: i
var var
i: integer; i: integer;
begin begin
for i := 0 to t-1 do for i := 0 to t do
begin begin
solve3(Triangles[-1].x[0], -Triangles[-1].y[0], Triangles[i].x[0], solve3(Triangles[-1].x[0], -Triangles[-1].y[0], Triangles[i].x[0],
Triangles[-1].x[1], -Triangles[-1].y[1], Triangles[i].x[1], Triangles[-1].x[1], -Triangles[-1].y[1], Triangles[i].x[1],
@ -2063,6 +2092,7 @@ begin
Triangles[-1].x[2], -Triangles[-1].y[2], -Triangles[i].y[2], Triangles[-1].x[2], -Triangles[-1].y[2], -Triangles[i].y[2],
xform[i].c[0][1], xform[i].c[1][1], xform[i].c[2][1]); xform[i].c[0][1], xform[i].c[1][1], xform[i].c[2][1]);
end; end;
FinalXformEnabled := EnableFinalXform;
end; end;
procedure TControlPoint.AdjustScale(w, h: integer); procedure TControlPoint.AdjustScale(w, h: integer);

View File

@ -252,9 +252,28 @@ object EditForm: TEditForm
ImageIndex = 14 ImageIndex = 14
Style = tbsSeparator Style = tbsSeparator
end end
object tbVarPreview: TToolButton object tbEnableFinalXform: TToolButton
Left = 332 Left = 332
Top = 0 Top = 0
Hint = 'Enable final transform'
Caption = 'Show Final Xform'
ImageIndex = 15
ParentShowHint = False
ShowHint = True
Style = tbsCheck
OnClick = tbEnableFinalXformClick
end
object ToolButton3: TToolButton
Left = 357
Top = 0
Width = 8
Caption = 'ToolButton3'
ImageIndex = 16
Style = tbsSeparator
end
object tbVarPreview: TToolButton
Left = 365
Top = 0
Hint = 'Show/hide variation preview' Hint = 'Show/hide variation preview'
Caption = 'Variation Preview' Caption = 'Variation Preview'
ImageIndex = 14 ImageIndex = 14
@ -1134,7 +1153,7 @@ object EditForm: TEditForm
end end
object tabXForm: TTabSheet object tabXForm: TTabSheet
Caption = 'Transform' Caption = 'Transform'
object Label6: TLabel object lblWeight: TLabel
Left = 10 Left = 10
Top = 126 Top = 126
Width = 38 Width = 38
@ -1220,10 +1239,8 @@ object EditForm: TEditForm
Height = 21 Height = 21
Hint = 'Reset vector X' Hint = 'Reset vector X'
Caption = 'X' Caption = 'X'
Enabled = False
ParentShowHint = False ParentShowHint = False
ShowHint = True ShowHint = True
Visible = False
OnClick = btnXpostClick OnClick = btnXpostClick
end end
object btnYpost: TSpeedButton object btnYpost: TSpeedButton
@ -1233,10 +1250,8 @@ object EditForm: TEditForm
Height = 21 Height = 21
Hint = 'Reset vector Y' Hint = 'Reset vector Y'
Caption = 'Y' Caption = 'Y'
Enabled = False
ParentShowHint = False ParentShowHint = False
ShowHint = True ShowHint = True
Visible = False
OnClick = btnYpostClick OnClick = btnYpostClick
end end
object btnOpost: TSpeedButton object btnOpost: TSpeedButton
@ -1246,10 +1261,8 @@ object EditForm: TEditForm
Height = 21 Height = 21
Hint = 'Reset vector O' Hint = 'Reset vector O'
Caption = 'O' Caption = 'O'
Enabled = False
ParentShowHint = False ParentShowHint = False
ShowHint = True ShowHint = True
Visible = False
OnClick = btnOpostClick OnClick = btnOpostClick
end end
object btnResetPostXForm: TSpeedButton object btnResetPostXForm: TSpeedButton
@ -1259,10 +1272,8 @@ object EditForm: TEditForm
Height = 22 Height = 22
Hint = 'Reset post-transform vectors to defaults' Hint = 'Reset post-transform vectors to defaults'
Caption = 'Reset post-transform' Caption = 'Reset post-transform'
Enabled = False
ParentShowHint = False ParentShowHint = False
ShowHint = True ShowHint = True
Visible = False
OnClick = btnResetPostXFormClick OnClick = btnResetPostXFormClick
end end
object btnSwapXforms: TSpeedButton object btnSwapXforms: TSpeedButton
@ -1272,7 +1283,6 @@ object EditForm: TEditForm
Height = 22 Height = 22
Hint = 'Swap Xform with PostXform' Hint = 'Swap Xform with PostXform'
Caption = '[ Xform <-> PostXform ]' Caption = '[ Xform <-> PostXform ]'
Enabled = False
Flat = True Flat = True
Font.Charset = ANSI_CHARSET Font.Charset = ANSI_CHARSET
Font.Color = clWindowText Font.Color = clWindowText
@ -1282,7 +1292,6 @@ object EditForm: TEditForm
ParentFont = False ParentFont = False
ParentShowHint = False ParentShowHint = False
ShowHint = True ShowHint = True
Visible = False
OnClick = btnSwapXformsClick OnClick = btnSwapXformsClick
end end
object txtA: TEdit object txtA: TEdit
@ -1376,10 +1385,8 @@ object EditForm: TEditForm
Top = 188 Top = 188
Width = 57 Width = 57
Height = 21 Height = 21
Enabled = False
TabOrder = 8 TabOrder = 8
Text = '0' Text = '0'
Visible = False
OnExit = PostCoefValidate OnExit = PostCoefValidate
OnKeyPress = PostCoefKeypress OnKeyPress = PostCoefKeypress
end end
@ -1388,10 +1395,8 @@ object EditForm: TEditForm
Top = 188 Top = 188
Width = 57 Width = 57
Height = 21 Height = 21
Enabled = False
TabOrder = 9 TabOrder = 9
Text = '0' Text = '0'
Visible = False
OnExit = PostCoefValidate OnExit = PostCoefValidate
OnKeyPress = PostCoefKeypress OnKeyPress = PostCoefKeypress
end end
@ -1400,10 +1405,8 @@ object EditForm: TEditForm
Top = 212 Top = 212
Width = 57 Width = 57
Height = 21 Height = 21
Enabled = False
TabOrder = 10 TabOrder = 10
Text = '0' Text = '0'
Visible = False
OnExit = PostCoefValidate OnExit = PostCoefValidate
OnKeyPress = PostCoefKeypress OnKeyPress = PostCoefKeypress
end end
@ -1412,10 +1415,8 @@ object EditForm: TEditForm
Top = 212 Top = 212
Width = 57 Width = 57
Height = 21 Height = 21
Enabled = False
TabOrder = 11 TabOrder = 11
Text = '0' Text = '0'
Visible = False
OnExit = PostCoefValidate OnExit = PostCoefValidate
OnKeyPress = PostCoefKeypress OnKeyPress = PostCoefKeypress
end end
@ -1424,10 +1425,8 @@ object EditForm: TEditForm
Top = 236 Top = 236
Width = 57 Width = 57
Height = 21 Height = 21
Enabled = False
TabOrder = 12 TabOrder = 12
Text = '0' Text = '0'
Visible = False
OnExit = PostCoefValidate OnExit = PostCoefValidate
OnKeyPress = PostCoefKeypress OnKeyPress = PostCoefKeypress
end end
@ -1436,10 +1435,8 @@ object EditForm: TEditForm
Top = 236 Top = 236
Width = 57 Width = 57
Height = 21 Height = 21
Enabled = False
TabOrder = 13 TabOrder = 13
Text = '0' Text = '0'
Visible = False
OnExit = PostCoefValidate OnExit = PostCoefValidate
OnKeyPress = PostCoefKeypress OnKeyPress = PostCoefKeypress
end end
@ -1450,7 +1447,7 @@ object EditForm: TEditForm
Left = 0 Left = 0
Top = 0 Top = 0
Width = 162 Width = 162
Height = 289 Height = 287
Align = alClient Align = alClient
ScrollBars = ssVertical ScrollBars = ssVertical
TabOrder = 0 TabOrder = 0
@ -1458,6 +1455,7 @@ object EditForm: TEditForm
'Variation' 'Variation'
'Value') 'Value')
OnDblClick = VEVarsDblClick OnDblClick = VEVarsDblClick
OnDrawCell = VEVarsDrawCell
OnExit = VEVarsChange OnExit = VEVarsChange
OnKeyPress = VEVarsKeyPress OnKeyPress = VEVarsKeyPress
OnMouseDown = VEVarsMouseDown OnMouseDown = VEVarsMouseDown
@ -1476,7 +1474,7 @@ object EditForm: TEditForm
Left = 0 Left = 0
Top = 0 Top = 0
Width = 162 Width = 162
Height = 289 Height = 287
Align = alClient Align = alClient
ScrollBars = ssVertical ScrollBars = ssVertical
TabOrder = 0 TabOrder = 0
@ -1572,15 +1570,6 @@ object EditForm: TEditForm
Height = 13 Height = 13
Caption = 'Variation preview' Caption = 'Variation preview'
end end
object chkUseXFormColor: TCheckBox
Left = 8
Top = 16
Width = 129
Height = 17
Caption = 'Use transform color'
TabOrder = 0
OnClick = chkUseXFormColorClick
end
object chkHelpers: TCheckBox object chkHelpers: TCheckBox
Left = 8 Left = 8
Top = 36 Top = 36
@ -1589,7 +1578,7 @@ object EditForm: TEditForm
Caption = 'Helper lines' Caption = 'Helper lines'
Checked = True Checked = True
State = cbChecked State = cbChecked
TabOrder = 1 TabOrder = 0
OnClick = chkHelpersClick OnClick = chkHelpersClick
end end
object trkVarPreviewDensity: TTrackBar object trkVarPreviewDensity: TTrackBar
@ -1603,7 +1592,7 @@ object EditForm: TEditForm
PageSize = 1 PageSize = 1
Position = 2 Position = 2
ShowHint = True ShowHint = True
TabOrder = 2 TabOrder = 1
TabStop = False TabStop = False
ThumbLength = 15 ThumbLength = 15
OnChange = trkVarPreviewDensityChange OnChange = trkVarPreviewDensityChange
@ -1618,7 +1607,7 @@ object EditForm: TEditForm
PageSize = 1 PageSize = 1
Position = 2 Position = 2
ShowHint = True ShowHint = True
TabOrder = 3 TabOrder = 2
TabStop = False TabStop = False
ThumbLength = 15 ThumbLength = 15
OnChange = trkVarPreviewRangeChange OnChange = trkVarPreviewRangeChange
@ -1634,11 +1623,20 @@ object EditForm: TEditForm
PageSize = 1 PageSize = 1
Position = 1 Position = 1
ShowHint = True ShowHint = True
TabOrder = 4 TabOrder = 3
TabStop = False TabStop = False
ThumbLength = 15 ThumbLength = 15
OnChange = trkVarPreviewDepthChange OnChange = trkVarPreviewDepthChange
end end
object chkUseXFormColor: TCheckBox
Left = 8
Top = 16
Width = 129
Height = 17
Caption = 'Use transform color'
TabOrder = 4
OnClick = chkUseXFormColorClick
end
end end
end end
end end
@ -1759,7 +1757,7 @@ object EditForm: TEditForm
Left = 353 Left = 353
Top = 80 Top = 80
Bitmap = { Bitmap = {
494C01010F001300040010001000FFFFFFFFFF10FFFFFFFFFFFFFFFF424D3600 494C010110001300040010001000FFFFFFFFFF10FFFFFFFFFFFFFFFF424D3600
0000000000003600000028000000400000005000000001002000000000000050 0000000000003600000028000000400000005000000001002000000000000050
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
@ -1951,57 +1949,57 @@ object EditForm: TEditForm
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000EBEBEB00EBEBEB00EBEBEB000000000000000000EBEBEB00EBEBEB00EBEB 0000EBEBEB00EBEBEB00EBEBEB000000000000000000EBEBEB00EBEBEB00EBEB
EB00000000000000000000000000000000000000000000000000000000000000 EB00000000000000000000000000000000000000000000000000FFFFFF000000
0000000000000000000000000000000000000000000000000000000000000000 00000000000000000000000000000000000000000000FFFFFF00000000000000
0000000000000000000000000000000000000000000000000000000000000000 000000000000FFFFFF0000000000000000000000000000000000000000000000
0000000000000000000000000000000000008000800000000000000000000000 0000000000000000000000000000000000008000800000000000000000000000
0000000000000000000000000000000000008000800080008000800080008000 0000000000000000000000000000000000008000800080008000800080008000
8000000000000000000080008000800080008000800080008000800080008000 8000000000000000000080008000800080008000800080008000800080008000
8000800080008000800080008000800080000000000000000000000000000000 8000800080008000800080008000800080000000000000000000000000000000
0000EBEBEB00EBEBEB00EBEBEB000000000000000000EBEBEB00EBEBEB00EBEB 0000EBEBEB00EBEBEB00EBEBEB000000000000000000EBEBEB00EBEBEB00EBEB
EB00000000000000000000000000000000000000000000000000000000000000 EB00000000000000000000000000000000000000000000000000FFFFFF000000
0000000000000000000000000000000000000000000000000000000000000000 00000000000000000000000000000000000000000000FFFFFF00000000000000
0000000000000000000000000000000000000000000000000000000000000000 000000000000FFFFFF0000000000000000000000000000000000000000000000
0000000000000000000000000000000000008000800000000000000000000000 0000000000000000000000000000000000008000800000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
00000000000000000000000000000000000049004B0000000000000000000000 00000000000000000000000000000000000049004B0000000000000000000000
00000000000000000000EBEBEB00A0A0A000A0A0A000EBEBEB00000000000000 00000000000000000000EBEBEB00A0A0A000A0A0A000EBEBEB00000000000000
000000000000000000000000000049004B000000000000000000000000000000 000000000000000000000000000049004B000000000000000000FFFFFF000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000FFFFFF000000
0000000000000000000000000000000000000000000000000000000000000000 0000FFFFFF000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
000000000000000000000000000000000000000000000000000049004B000000 000000000000000000000000000000000000000000000000000049004B000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
00000000000049004B0000000000000000000000000000000000000000000000 00000000000049004B0000000000000000000000000000000000FFFFFF00FFFF
0000000000000000000000000000000000000000000000000000000000000000 FF00FFFFFF00000000000000000000000000000000000000000000000000FFFF
0000000000000000000000000000000000000000000000000000000000000000 FF00000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
000049004B000000000000000000000000000000000000000000000000004900 000049004B000000000000000000000000000000000000000000000000004900
4B00000000000000000000000000000000000000000000000000000000000000 4B00000000000000000000000000000000000000000000000000FFFFFF000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000FFFFFF000000
0000000000000000000000000000000000000000000000000000000000000000 0000FFFFFF000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000008000800000000000000000000000 0000000000000000000000000000000000008000800000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
00000000000000000000000000000000000049004B0000000000000000000000 00000000000000000000000000000000000049004B0000000000000000000000
0000000000000000000049004B00000000000000000049004B00000000000000 0000000000000000000049004B00000000000000000049004B00000000000000
000000000000000000000000000049004B000000000000000000000000000000 000000000000000000000000000049004B000000000000000000FFFFFF000000
0000000000000000000000000000000000000000000000000000000000000000 00000000000000000000000000000000000000000000FFFFFF00000000000000
0000000000000000000000000000000000000000000000000000000000000000 000000000000FFFFFF0000000000000000000000000000000000000000000000
0000000000000000000000000000000000008000800000000000000000000000 0000000000000000000000000000000000008000800000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000004900 0000000000000000000000000000000000000000000000000000000000004900
4B00000000000000000000000000000000000000000000000000000000000000 4B00000000000000000000000000000000000000000000000000000000000000
000049004B000000000000000000000000000000000000000000000000000000 000049004B000000000000000000000000000000000000000000FFFFFF00FFFF
0000000000000000000000000000000000000000000000000000000000000000 FF00FFFFFF00FFFFFF00000000000000000000000000FFFFFF00000000000000
0000000000000000000000000000000000000000000000000000000000000000 000000000000FFFFFF0000000000000000000000000000000000000000000000
0000000000000000000000000000000000008000800000000000000000000000 0000000000000000000000000000000000008000800000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
@ -2407,11 +2405,11 @@ object EditForm: TEditForm
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000000000000000000000000000 0000000000000000000000000000000000000000000000000000000000000000
00000000000000000000000000000000FF7FFFFFFFFF0000FF7FFFFFFDBF0000 00000000000000000000000000000000FF7FFFFFFFFFFFFFFF7FFFFFFDBFE1B7
FF7FFFFFEFF70000E00FF3E77DBE0000E007E1E7F7EF0000FF63C0E7DC3B0000 FF7FFFFFEFF7EDA7E00FF3E77DBEED97E007E1E7F7EFE1B7FF63C0E7DC3BFFFF
FF73F3E7700E0000FF73F3E7E0070000FB730000E0070000F363F3E7700E0000 FF73F3E7700E8F11FF73F3E7E0078F11FB730000E0078F11F363F3E7700E8383
E007F3E7DC3B0000E00FF1C7F7EF0000F37FF80F7DBE0000FB7FFC1FEFF70000 E007F3E7DC3B83C7E00FF1C7F7EF8383F37FF80F7DBE8111FB7FFC1FEFF78111
FF7FFFFFFDBF0000FF7FFFFFFFFF0000FFFFFFFFFFFFFFFFF0070001FEFF8003 FF7FFFFFFDBF8111FF7FFFFFFFFFFFFFFFFFFFFFFFFFFFFFF0070001FEFF8003
F9F79FFD7FFDCFE7FCF7C8053EF9E7CFF277E4F51FF1F39FEF37F2754EE5F93F F9F79FFD7FFDCFE7FCF7C8053EF9E7CFF277E4F51FF1F39FEF37F2754EE5F93F
EF97F93567CDFC7FDFC7FC95729DFEFFDFE7FE45793D5555DFF7FF25729DFEFF EF97F93567CDFC7FDFC7FC95729DFEFFDFE7FE45793D5555DFF7FF25729DFEFF
DFFFFF9567CDFC7FEFC3FFCD4EE5F93FEFF3FFE51FF1F39FF3CBFFF13EF9E7CF DFFFFF9567CDFC7FEFC3FFCD4EE5F93FEFF3FFE51FF1F39FF3CBFFF13EF9E7CF

View File

@ -24,7 +24,7 @@ uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs, Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
ExtCtrls, StdCtrls, ComCtrls, Math, Menus, ToolWin, Registry, ExtCtrls, StdCtrls, ComCtrls, Math, Menus, ToolWin, Registry,
ControlPoint, Render, cmap, Grids, ValEdit, Buttons, ImgList, CustomDrawControl, ControlPoint, Render, cmap, Grids, ValEdit, Buttons, ImgList, CustomDrawControl,
Types; Types, xform;
const const
// PixelCountMax = 32768; // PixelCountMax = 32768;
@ -35,6 +35,7 @@ const
crEditRotate = 22; crEditRotate = 22;
crEditScale = 23; crEditScale = 23;
type PXForm = ^TXForm;
type type
TEditForm = class(TForm) TEditForm = class(TForm)
GrphPnl: TPanel; GrphPnl: TPanel;
@ -65,7 +66,7 @@ type
PageControl: TPageControl; PageControl: TPageControl;
TriangleTab: TTabSheet; TriangleTab: TTabSheet;
tabXForm: TTabSheet; tabXForm: TTabSheet;
Label6: TLabel; lblWeight: TLabel;
txtA: TEdit; txtA: TEdit;
txtB: TEdit; txtB: TEdit;
txtC: TEdit; txtC: TEdit;
@ -81,7 +82,6 @@ type
pnlXFormColor: TPanel; pnlXFormColor: TPanel;
txtXFormColor: TEdit; txtXFormColor: TEdit;
GroupBox2: TGroupBox; GroupBox2: TGroupBox;
chkUseXFormColor: TCheckBox;
chkHelpers: TCheckBox; chkHelpers: TCheckBox;
TriangleScrollBox: TScrollBox; TriangleScrollBox: TScrollBox;
TrianglePanel: TPanel; TrianglePanel: TPanel;
@ -164,6 +164,9 @@ type
btnResetPivot: TSpeedButton; btnResetPivot: TSpeedButton;
btnPickPivot: TSpeedButton; btnPickPivot: TSpeedButton;
btnPivotMode: TSpeedButton; btnPivotMode: TSpeedButton;
tbEnableFinalXform: TToolButton;
chkUseXFormColor: TCheckBox;
ToolButton3: TToolButton;
procedure ValidateVariable; procedure ValidateVariable;
procedure vleVariablesValidate(Sender: TObject; ACol, ARow: Integer; const KeyName, KeyValue: string); procedure vleVariablesValidate(Sender: TObject; ACol, ARow: Integer; const KeyName, KeyValue: string);
procedure vleVariablesKeyPress(Sender: TObject; var Key: Char); procedure vleVariablesKeyPress(Sender: TObject; var Key: Char);
@ -290,6 +293,9 @@ type
procedure PivotKeyPress(Sender: TObject; var Key: Char); procedure PivotKeyPress(Sender: TObject; var Key: Char);
procedure btnResetPivotClick(Sender: TObject); procedure btnResetPivotClick(Sender: TObject);
procedure btnPickPivotClick(Sender: TObject); procedure btnPickPivotClick(Sender: TObject);
procedure VEVarsDrawCell(Sender: TObject; ACol, ARow: Integer;
Rect: TRect; State: TGridDrawState);
procedure tbEnableFinalXformClick(Sender: TObject);
private private
TriangleView: TCustomDrawControl; TriangleView: TCustomDrawControl;
@ -368,6 +374,8 @@ type
procedure UpdateDisplay(PreviewOnly: boolean = false); //(?) procedure UpdateDisplay(PreviewOnly: boolean = false); //(?)
function GetTriangleColor(n: integer): TColor; function GetTriangleColor(n: integer): TColor;
function LastTriangle: integer;
function InsideTriangle(x, y: double): integer;
end; end;
const const
@ -507,25 +515,6 @@ begin
end; end;
end; end;
{
procedure ScaleAll;
var
i, j: integer;
begin
for i := 0 to 2 do
begin
MainTriangles[-1].y[i] := MainTriangles[-1].y[i] * 0.2;
MainTriangles[-1].x[i] := MainTriangles[-1].x[i] * 0.2;
end;
for j := 0 to Transforms - 1 do
for i := 0 to 2 do
begin
MainTriangles[j].y[i] := MainTriangles[j].y[i] * 0.2;
MainTriangles[j].x[i] := MainTriangles[j].x[i] * 0.2;
end;
end;
}
function RotateTriangleCenter(t: TTriangle; rad: double): TTriangle; function RotateTriangleCenter(t: TTriangle; rad: double): TTriangle;
var var
i: integer; i: integer;
@ -610,12 +599,16 @@ begin
end; end;
} }
cp.copy(MainCp); cp.copy(MainCp);
if SelectedTriangle >= NumXForms(cp) then
if SelectedTriangle > LastTriangle{???} then//NumXForms(cp) then
begin begin
SelectedTriangle := NumXForms(cp)-1; SelectedTriangle := NumXForms(cp)-1;
mouseOverTriangle := -1; mouseOverTriangle := -1;
end; end;
EnableFinalXform := cp.finalXformEnabled;
tbEnableFinalXform.Down := EnableFinalXform;
UpdatePreview; UpdatePreview;
if PreviewOnly then exit; if PreviewOnly then exit;
@ -625,6 +618,7 @@ begin
cbTransforms.Clear; cbTransforms.Clear;
for i := 1 to Transforms do cbTransforms.Items.Add(IntToStr(i)); for i := 1 to Transforms do cbTransforms.Items.Add(IntToStr(i));
if cp.HasFinalXForm then cbTransforms.Items.Add('Final');
// just in case: // just in case:
SetCaptureControl(nil); SetCaptureControl(nil);
@ -699,7 +693,7 @@ var
v: double; v: double;
strval: string; strval: string;
begin begin
if (SelectedTriangle >= Transforms) then SelectedTriangle := Transforms - 1; if (SelectedTriangle > LastTriangle) then SelectedTriangle := LastTriangle;
cbTransforms.ItemIndex := SelectedTriangle; cbTransforms.ItemIndex := SelectedTriangle;
cbTransforms.Refresh; cbTransforms.Refresh;
@ -745,7 +739,17 @@ begin
txtPost21.text := Format('%.6g', [arctan2(-p[2][1], p[2][0])*180/PI]); txtPost21.text := Format('%.6g', [arctan2(-p[2][1], p[2][0])*180/PI]);
end; end;
txtP.text := Format('%.6g', [density]); if SelectedTriangle < Transforms then
begin
txtP.text := Format('%.6g', [density]);
txtP.Enabled := true;
end
else begin
txtP.Enabled := false;
txtP.Text := 'n/a';
end;
tbEnableFinalXform.Down := EnableFinalXform;
txtSymmetry.text := Format('%.6g', [symmetry]); txtSymmetry.text := Format('%.6g', [symmetry]);
pnlXFormColor.Color := ColorValToColor(cp.cmap, color); pnlXFormColor.Color := ColorValToColor(cp.cmap, color);
@ -779,6 +783,8 @@ begin
editPivotY.Text := Format('%.6g', [WorldPivot.y]); editPivotY.Text := Format('%.6g', [WorldPivot.y]);
end; end;
if cp.finalXformEnabled then tbEnableFinalXform.Down := true;
PageControl.Refresh; PageControl.Refresh;
end; end;
@ -829,7 +835,7 @@ procedure TEditForm.UpdateFlameX;
var var
i: integer; i: integer;
begin begin
for i := 0 to Transforms - 1 do for i := 0 to Transforms do
begin begin
// CP_compute(cp1, Triangles[i], Triangles[-1], i); // CP_compute(cp1, Triangles[i], Triangles[-1], i);
solve3(MainTriangles[-1].x[0], MainTriangles[-1].y[0], MainTriangles[i].x[0], solve3(MainTriangles[-1].x[0], MainTriangles[-1].y[0], MainTriangles[i].x[0],
@ -842,9 +848,8 @@ begin
MainTriangles[-1].x[2], MainTriangles[-1].y[2], MainTriangles[i].y[2], MainTriangles[-1].x[2], MainTriangles[-1].y[2], MainTriangles[i].y[2],
cp.xform[i].c[0][1], cp.xform[i].c[1][1], cp.xform[i].c[2][1]); cp.xform[i].c[0][1], cp.xform[i].c[1][1], cp.xform[i].c[2][1]);
end; end;
cp.GetFromTriangles(MainTriangles, Transforms); cp.GetFromTriangles(MainTriangles, Transforms);
if not chkPreserve.checked then cp.ComputeWeights(MainTriangles, transforms); if not chkPreserve.checked then cp.ComputeWeights(MainTriangles, Transforms);
DrawPreview; DrawPreview;
ShowSelectedInfo; ShowSelectedInfo;
TriangleView.Refresh;; TriangleView.Refresh;;
@ -854,7 +859,7 @@ procedure TEditForm.UpdateFlame(DrawMain: boolean);
begin begin
//; MainForm.StopThread; //; MainForm.StopThread;
StatusBar.Panels[2].Text := Format('Zoom: %f', [GraphZoom]); StatusBar.Panels[2].Text := Format('Zoom: %f', [GraphZoom]);
cp.GetFromTriangles(MainTriangles, transforms); cp.GetFromTriangles(MainTriangles, Transforms);
// if not chkPreserve.Checked then ComputeWeights(cp, MainTriangles, transforms); // if not chkPreserve.Checked then ComputeWeights(cp, MainTriangles, transforms);
DrawPreview; DrawPreview;
ShowSelectedInfo; ShowSelectedInfo;
@ -878,38 +883,47 @@ procedure TEditForm.DeleteTriangle(t: integer);
var var
i, j: integer; i, j: integer;
begin begin
if Transforms > 2 then if (t = Transforms ) then
{ Can't have less than 2 transofms}
begin begin
assert(cp.HasFinalXForm);
MainForm.UpdateUndo;
EnableFinalXform := false;
cp.finalXformEnabled := false;
cp.xform[Transforms].Clear;
cp.xform[Transforms].symmetry := 1;
assert(cp.HasFinalXForm = false);
MainTriangles[Transforms] := MainTriangles[-1];
tbEnableFinalXform.Down := false;
if (SelectedTriangle = Transforms ) then Dec(SelectedTriangle);
end
else
if (Transforms <= 2) then exit
else begin
MainForm.UpdateUndo; MainForm.UpdateUndo;
if t = (Transforms - 1) then if t = (Transforms - 1) then
{ Last triangle...just reduce number}
begin begin
Transforms := Transforms - 1; MainTriangles[t] := MainTriangles[Transforms];
SelectedTriangle := Transforms - 1; Dec(SelectedTriangle);
cp.xform[transforms].density := 0;
cbTransforms.Clear;
UpdateFlame(True);
end end
else else begin
begin for i := t to Transforms-1 do // was: -2
for i := t to Transforms - 2 do
begin begin
{ copy higher transforms down } { copy higher transforms down }
MainTriangles[i] := MainTriangles[i + 1]; MainTriangles[i] := MainTriangles[i + 1];
cp.xform[i].Assign(cp.xform[i + 1]); cp.xform[i].Assign(cp.xform[i + 1]);
end; end;
Transforms := Transforms - 1;
cp.xform[transforms].density := 0;
UpdateFlame(True);
end; end;
cbTransforms.clear; Dec(Transforms);
for i := 1 to Transforms do cbTransforms.Items.Add(IntToStr(i)); assert(cp.xform[transforms].density = 0); // cp.xform[transforms].density := 0;
cbTransforms.ItemIndex := SelectedTriangle;
end; end;
UpdateFlame(True);
cbTransforms.clear;
for i := 1 to Transforms do cbTransforms.Items.Add(IntToStr(i));
if cp.HasFinalXForm then cbTransforms.Items.Add('Final');
cbTransforms.ItemIndex := SelectedTriangle;
end; end;
function InsideTriangle(x, y: double): integer; function TEditForm.InsideTriangle(x, y: double): integer;
var var
i, j, k: integer; i, j, k: integer;
inside: boolean; inside: boolean;
@ -918,7 +932,7 @@ begin
Result := -1; Result := -1;
inside := False; inside := False;
j := 2; j := 2;
for k := Transforms - 1 downto 0 do for k := LastTriangle downto 0 do
begin begin
for i := 0 to 2 do for i := 0 to 2 do
begin begin
@ -940,11 +954,19 @@ end;
function TEditForm.GetTriangleColor(n: integer): TColor; function TEditForm.GetTriangleColor(n: integer): TColor;
begin begin
if n = Transforms then Result := clWhite
else
if chkUseXFormColor.checked then if chkUseXFormColor.checked then
Result := ColorValToColor(MainCp.cmap, cp.xform[n].color) Result := ColorValToColor(MainCp.cmap, cp.xform[n].color)
else Result := TrgColors[n mod 14]; else Result := TrgColors[n mod 14];
end; end;
function TEditForm.LastTriangle: integer;
begin
if EnableFinalXform or cp.HasFinalXForm then Result := Transforms
else Result := Transforms-1;
end;
procedure TEditForm.TriangleViewPaint(Sender: TObject); procedure TEditForm.TriangleViewPaint(Sender: TObject);
const const
foc_ofs = 4; foc_ofs = 4;
@ -981,7 +1003,7 @@ var
end; end;
end; end;
var var
i, n, tc: integer; i, n, tc, tn: integer;
d, d1: double; d, d1: double;
tx, ty: double; tx, ty: double;
@ -996,7 +1018,7 @@ label DrawCorner;
begin begin
assert(SelectedTriangle >= 0); assert(SelectedTriangle >= 0);
assert(TCustomDrawControl(Sender) = TriangleView); assert(TCustomDrawControl(Sender) = TriangleView);
if SelectedTriangle >= Transforms then SelectedTriangle := Transforms-1; if SelectedTriangle > LastTriangle then SelectedTriangle := LastTriangle;
BitMap := TBitMap.Create; BitMap := TBitMap.Create;
Width := TriangleView.Width; Width := TriangleView.Width;
@ -1066,13 +1088,13 @@ begin
brush.Color := EditorBkgColor; brush.Color := EditorBkgColor;
Font.color := Pen.color; Font.color := Pen.color;
TextOut(c.x-9, c.y-12, 'Y'); TextOut(c.x-9, c.y-12, 'Y');
TextOut(b.x-8, b.y+1, 'O');
TextOut(a.x+2, a.y+1, 'X'); TextOut(a.x+2, a.y+1, 'X');
TextOut(b.x-8, b.y+1, 'O');
Pen.Style := psSolid; Pen.Style := psSolid;
{Transforms} // Draw Triangles
for i := 0 to Transforms - 1 do for i := 0 to LastTriangle do
begin begin
if i <> SelectedTriangle then Pen.Style := psDot; if i <> SelectedTriangle then Pen.Style := psDot;
@ -1119,8 +1141,8 @@ end;
Font.color := Pen.color; Font.color := Pen.color;
TextOut(c.x+2, c.y+1, 'Y'); TextOut(c.x+2, c.y+1, 'Y');
TextOut(b.x+2, b.y+1, 'O');
TextOut(a.x+2, a.y+1, 'X'); TextOut(a.x+2, a.y+1, 'X');
TextOut(b.x+2, b.y+1, 'O');
end; end;
if tbVarPreview.Down then if tbVarPreview.Down then
@ -1129,6 +1151,7 @@ end;
assert(trkVarPreviewDensity.position > 0); assert(trkVarPreviewDensity.position > 0);
cp.xform[SelectedTriangle].prepare; cp.xform[SelectedTriangle].prepare;
n := trkVarPreviewRange.position * trkVarPreviewDensity.position * 5; n := trkVarPreviewRange.position * trkVarPreviewDensity.position * 5;
d1 := trkVarPreviewDensity.position * 5; d1 := trkVarPreviewDensity.position * 5;
tc := GetTriangleColor(SelectedTriangle); tc := GetTriangleColor(SelectedTriangle);
@ -1464,7 +1487,7 @@ begin
if SelectMode then if SelectMode then
begin begin
i0:=0; i0:=0;
i1:=Transforms-1; i1:=LastTriangle;//Transforms-1;
end end
else begin else begin
i0:=SelectedTriangle; i0:=SelectedTriangle;
@ -1786,7 +1809,7 @@ begin
if SelectMode then if SelectMode then
begin begin
i0:=0; i0:=0;
i1:=Transforms-1; i1:=LastTriangle;
end end
else begin // Only check selected triangle else begin // Only check selected triangle
i0:=SelectedTriangle; i0:=SelectedTriangle;
@ -1923,40 +1946,19 @@ begin
begin begin
UseTransformColors := False; UseTransformColors := False;
end; end;
(*
if Registry.ValueExists('UseFlameBackground') then
begin
UseFlameBackground := Registry.ReadBool('UseFlameBackground');
end
else
begin
UseFlameBackground := False;
end;
if Registry.ValueExists('BackgroundColor') then
BackgroundColor := Registry.ReadInteger('BackgroundColor')
else
BackgroundColor := integer(clBlack);
if Registry.ValueExists('GridColor1') then
GridColor1 := Registry.ReadInteger('GridColor1')
else
GridColor1 := $444444;
if Registry.ValueExists('GridColor2') then
GridColor2 := Registry.ReadInteger('GridColor2')
else
GridColor2 := $333333;
if Registry.ValueExists('HelpersColor') then
HelpersColor := Registry.ReadInteger('HelpersColor')
else
HelpersColor := $808080;
if Registry.ValueExists('ReferenceTriangleColor') then
ReferenceTriangleColor := Registry.ReadInteger('ReferenceTriangleColor')
else
ReferenceTriangleColor := $7f7f7f;
*)
if Registry.ValueExists('ResetLocation') then if Registry.ValueExists('ResetLocation') then
mnuResetLoc.checked := Registry.ReadBool('ResetLocation') mnuResetLoc.checked := Registry.ReadBool('ResetLocation')
else mnuResetLoc.checked := true; else mnuResetLoc.checked := true;
//tbResetLoc.Down := mnuResetLoc.checked; //tbResetLoc.Down := mnuResetLoc.checked;
if Registry.ValueExists('HelpersEnabled') then
begin
HelpersEnabled := Registry.ReadBool('HelpersEnabled');
end
else
begin
HelpersEnabled := False;
end;
if Registry.ValueExists('VariationPreview') then if Registry.ValueExists('VariationPreview') then
tbVarPreview.Down := Registry.ReadBool('VariationPreview') tbVarPreview.Down := Registry.ReadBool('VariationPreview')
@ -1971,33 +1973,19 @@ begin
else begin else begin
UseTransformColors := False; UseTransformColors := False;
UseFlameBackground := False; UseFlameBackground := False;
// BackgroundColor := $000000;
// GridColor1 := $444444;
// GridColor2 := $333333;
// HelpersColor := $808080;
// ReferenceTriangleColor := integer(clGray);
mnuResetLoc.checked := true; mnuResetLoc.checked := true;
//tbResetLoc.Down := true;
end; end;
Registry.CloseKey; Registry.CloseKey;
finally finally
Registry.Free; Registry.Free;
end; end;
chkUseXFormColor.checked := UseTransformColors; chkUseXFormColor.checked := UseTransformColors;
// chkFlameBack.checked := UseFlameBackground;
{
GrphPnl.Color := TColor(BackgroundColor);
pnlBackColor.Color := TColor(EditorBkgColor);
pnlGridColor1.Color := GridColor1;
pnlGridColor2.Color := GridColor2;
pnlReference.color := TColor(ReferenceTriangleColor);
}
UpdateDisplay; UpdateDisplay;
end; end;
procedure TEditForm.mnuDeleteClick(Sender: TObject); procedure TEditForm.mnuDeleteClick(Sender: TObject);
begin begin
if SelectedTriangle > -1 then DeleteTriangle(SelectedTriangle); if (SelectedTriangle > -1) then DeleteTriangle(SelectedTriangle);
end; end;
procedure TEditForm.mnuAddClick(Sender: TObject); procedure TEditForm.mnuAddClick(Sender: TObject);
@ -2007,6 +1995,8 @@ begin
if Transforms < NXFORMS then if Transforms < NXFORMS then
begin begin
MainForm.UpdateUndo; MainForm.UpdateUndo;
MainTriangles[Transforms+1] := MainTriangles[Transforms];
cp.xform[Transforms+1].Assign(cp.xform[Transforms]);
MainTriangles[Transforms] := MainTriangles[-1]; MainTriangles[Transforms] := MainTriangles[-1];
SelectedTriangle := Transforms; SelectedTriangle := Transforms;
cp.xform[Transforms].density := 0.5; cp.xform[Transforms].density := 0.5;
@ -2016,6 +2006,7 @@ begin
Inc(Transforms); Inc(Transforms);
cbTransforms.clear; cbTransforms.clear;
for i := 1 to Transforms do cbTransforms.Items.Add(IntToStr(i)); for i := 1 to Transforms do cbTransforms.Items.Add(IntToStr(i));
if cp.HasFinalXForm = true then cbTransforms.Items.Add('Final');
UpdateFlame(True); UpdateFlame(True);
end; end;
end; end;
@ -2027,6 +2018,8 @@ begin
if Transforms < NXFORMS then if Transforms < NXFORMS then
begin begin
MainForm.UpdateUndo; MainForm.UpdateUndo;
MainTriangles[Transforms+1] := MainTriangles[Transforms];
cp.xform[Transforms+1].Assign(cp.xform[Transforms]);
MainTriangles[Transforms] := MainTriangles[SelectedTriangle]; MainTriangles[Transforms] := MainTriangles[SelectedTriangle];
cp.xform[Transforms].Assign(cp.xform[SelectedTriangle]); cp.xform[Transforms].Assign(cp.xform[SelectedTriangle]);
SelectedTriangle := Transforms; SelectedTriangle := Transforms;
@ -2073,7 +2066,8 @@ begin
else if Sender = txtCy then else if Sender = txtCy then
Val := Format('%.6f', [MainTriangles[SelectedTriangle].y[2]]) Val := Format('%.6f', [MainTriangles[SelectedTriangle].y[2]])
else if Sender = txtP then else if Sender = txtP then
val := Format('%.6f', [cp.xform[SelectedTriangle].density]); if SelectedTriangle < Transforms then
val := Format('%.6f', [cp.xform[SelectedTriangle].density]);
OldText := Val; OldText := Val;
{ Test that it's a valid floating point number } { Test that it's a valid floating point number }
try try
@ -2181,6 +2175,7 @@ var
Allow: boolean; Allow: boolean;
NewVal, OldVal: double; NewVal, OldVal: double;
begin begin
if SelectedTriangle >= Transforms then key := #0;
if key = #13 then if key = #13 then
begin begin
{ Stop the beep } { Stop the beep }
@ -2437,7 +2432,7 @@ begin
FillRect(Rect); FillRect(Rect);
Font.Color := clWhite; Font.Color := clWhite;
TextOut(Rect.Left+h+2, Rect.Top, IntToStr(Index+1)); TextOut(Rect.Left+h+2, Rect.Top, cbTransforms.Items[Index]);//IntToStr(Index+1));
pen.Color := TrgColor; pen.Color := TrgColor;
brush.Color := pen.Color shr 1 and $7f7f7f; brush.Color := pen.Color shr 1 and $7f7f7f;
@ -3265,7 +3260,7 @@ procedure TEditForm.EditKeyDown(Sender: TObject; var Key: Word;
begin begin
case key of case key of
VK_ADD: VK_ADD:
if SelectedTriangle < Transforms-1 then begin if SelectedTriangle < LastTriangle then begin
Inc(SelectedTriangle); Inc(SelectedTriangle);
TriangleView.Invalidate; TriangleView.Invalidate;
ShowSelectedInfo; ShowSelectedInfo;
@ -3815,5 +3810,49 @@ begin
UpdateFlame(true); UpdateFlame(true);
end; end;
procedure TEditForm.VEVarsDrawCell(Sender: TObject; ACol, ARow: Integer;
Rect: TRect; State: TGridDrawState);
var
c: TColor;
begin
// if ARow = 0 then exit;
if (ARow > NRLOCVAR) then
begin
// if ARow and 1 = 1 then c := c shr 1;
VEVars.canvas.brush.Color := $ffe0e0;
VEVars.canvas.fillRect(Rect);
VEVars.canvas.TextOut(Rect.Left+2, Rect.Top, VEVars.Cells[ACol,ARow]);
end;
end;
procedure TEditForm.tbEnableFinalXformClick(Sender: TObject);
var
i: integer;
begin
MainForm.UpdateUndo;
EnableFinalXform := tbEnableFinalXform.Down;
if (cp.HasFinalXForm = false) then
begin
if (EnableFinalXform = true) then
begin
//cp.xform[Transforms].Clear;
//cp.xform[Transforms].Symmetry := 1;
cbTransforms.Items.Add('Final');
SelectedTriangle := Transforms;
if (mouseOverTriangle > LastTriangle) then mouseOverTriangle := -1;
end
else begin
//cp.xform[Transforms].Clear;
//cp.xform[Transforms].Symmetry := 1;
if cbTransforms.Items.Count = Transforms+1 then
cbTransforms.Items.Delete(Transforms);
if SelectedTriangle >= Transforms then SelectedTriangle := Transforms-1;
end;
end;
cp.finalXformEnabled := EnableFinalXform;
UpdateFlame(True);
TriangleView.Invalidate;
end;
end. end.

View File

@ -467,8 +467,19 @@ object RenderForm: TRenderForm
Caption = 'Post render' Caption = 'Post render'
TabOrder = 9 TabOrder = 9
end end
object chkSaveIncompleteRenders: TCheckBox
Left = 272
Top = 328
Width = 145
Height = 17
Alignment = taLeftJustify
Caption = 'Save incomplete renders'
TabOrder = 13
Visible = False
OnClick = chkSaveIncompleteRendersClick
end
object SaveDialog: TSaveDialog object SaveDialog: TSaveDialog
Left = 376 Left = 376
Top = 320 Top = 304
end end
end end

View File

@ -64,6 +64,7 @@ type
chkShutdown: TCheckBox; chkShutdown: TCheckBox;
cbPostProcess: TCheckBox; cbPostProcess: TCheckBox;
txtDensity: TComboBox; txtDensity: TComboBox;
chkSaveIncompleteRenders: TCheckBox;
procedure FormCreate(Sender: TObject); procedure FormCreate(Sender: TObject);
procedure FormDestroy(Sender: TObject); procedure FormDestroy(Sender: TObject);
procedure btnRenderClick(Sender: TObject); procedure btnRenderClick(Sender: TObject);
@ -84,9 +85,11 @@ type
procedure btnDeletePresetClick(Sender: TObject); procedure btnDeletePresetClick(Sender: TObject);
procedure cmbPresetChange(Sender: TObject); procedure cmbPresetChange(Sender: TObject);
procedure chkMaintainClick(Sender: TObject); procedure chkMaintainClick(Sender: TObject);
procedure chkSaveIncompleteRendersClick(Sender: TObject);
private private
StartTime, oldElapsed, edt: TDateTime; StartTime, oldElapsed, edt: TDateTime;
oldProg: double; oldProg: double;
SaveIncompleteRenders: boolean;
procedure DoPostProcess; procedure DoPostProcess;
@ -180,6 +183,8 @@ procedure TRenderForm.HandleThreadTermination(var Message: TMessage);
begin begin
if Assigned(Renderer) then if Assigned(Renderer) then
begin begin
if SaveIncompleteRenders then Renderer.SaveImage(FileName);
Renderer.Free; Renderer.Free;
Renderer := nil; Renderer := nil;
ResetControls; ResetControls;
@ -760,5 +765,10 @@ begin
Result := ExitWindowsEx(RebootParam, 0); Result := ExitWindowsEx(RebootParam, 0);
end; end;
procedure TRenderForm.chkSaveIncompleteRendersClick(Sender: TObject);
begin
SaveIncompleteRenders := chkSaveIncompleteRenders.Checked;
end;
end. end.

View File

@ -59,6 +59,7 @@ var
ConfirmDelete: boolean; // Flag confirmation of entry deletion ConfirmDelete: boolean; // Flag confirmation of entry deletion
// FlameTitle: string; // FlameTitle: string;
Transforms: integer; // Count of Tranforms Transforms: integer; // Count of Tranforms
EnableFinalXform: boolean;
AppPath: string; // Path of applicatio file AppPath: string; // Path of applicatio file
OpenFile: string; // Name of currently open file OpenFile: string; // Name of currently open file
CanDrawOnResize: boolean; CanDrawOnResize: boolean;