marpis
2009-05-13 00:46:22
This function is extremely accurate, but very slow. It might take over 10 seconds to find the color, but it still does find it. It looks like it doesn't get confused of other players very easily.
It ignores colors found on the borders of the MM, like white color on the compass etc.
I wonder if the same thing could be done a faster way without making it any more inaccurate?
PS. I noticed that walls don't have just 1 color at the same time on MM, if you pick the colors of walls around MM you can find them different.
EDIT: I did some testing with various different tolerances and things, and came to this conclusion:
Browsing through RGB values is the best option to do this. Why? because high tolerances sometimes pick the color of grass etc, and if they fail they may pick almost black colors. My function returns either some almost white color, or total black (color 0) so its easier to check if AutoColor has been successful. I bet no tolerancemonster can get more accurate than this. (Im going to take some pictures that show where this function has found the right color, and i also post if it has given an invalid color)
test program:
i tested more than 6 times but here are some shots:

edit: minor bugfix
edit: major bug, will be fixing it tomorroow
edit: final conclusion: i took the old function back (the slow one)
edit: minor bugfix
It ignores colors found on the borders of the MM, like white color on the compass etc.
I wonder if the same thing could be done a faster way without making it any more inaccurate?
PS. I noticed that walls don't have just 1 color at the same time on MM, if you pick the colors of walls around MM you can find them different.
EDIT: I did some testing with various different tolerances and things, and came to this conclusion:
Browsing through RGB values is the best option to do this. Why? because high tolerances sometimes pick the color of grass etc, and if they fail they may pick almost black colors. My function returns either some almost white color, or total black (color 0) so its easier to check if AutoColor has been successful. I bet no tolerancemonster can get more accurate than this. (Im going to take some pictures that show where this function has found the right color, and i also post if it has given an invalid color)
test program:
program New;
{.include SRL/SRL.scar}
var
gATPA: T2DPointArray;
Function DebugATPA(aPoints: Array Of TPointArray; BmpName: String): Boolean;
Var
Width, Height, ClientBMP, I, L, C, Col: Integer;
xs, ys, xe, ye: Integer;
OuterPoints: TPointArray;
Begin
For I := 0 To High(aPoints) Do
L := L + Length(aPoints[i]);
SetLength(OuterPoints, L + 1);
C := 0;
For I := 0 To High(aPoints) Do
For L := 0 To High(aPoints[i]) Do
Begin
C := C + 1;
OuterPoints[C] := aPoints[i][L];
End;
Try
Begin
xe := xs xor xs;
ye := ys xor ys;
xs := 1 shl 20;
ys := 1 shl 20;
For I := 0 To High(OuterPoints) Do
Begin
xs := Min(xs, OuterPoints[i].X);
ys := Min(ys, OuterPoints[i].Y);
xe := Max(xe, OuterPoints[i].X);
ye := Max(ye, OuterPoints[i].Y);
End;
Width := xe - xs;
Height := ye - ys;
DisplayDebugImgWindow(0, 0);
DisplayDebugImgWindow(Width, Height);
ClientBMP := BitmapFromString(Width, Height, '');
CopyClientToBitmap(ClientBMP, xs, ys, xe, ye)
For I := 0 To High(aPoints) Do
Begin
Col := RGBtoColor(0, 255, 0);
For L := 0 To High(aPoints[i]) Do
FastSetPixel(ClientBMP, aPoints[i][L].X - xs, aPoints[i][L].Y - ys, Col);
End;
SafeDrawBitmap(ClientBMP, GetDebugCanvas, 0, 0);
DisplayDebugImgWindow(Width, Height);
If BmpName <> '' Then
SaveBitmap(ClientBMP, ScriptPath + BmpName + '.bmp');
FreeBitmap(ClientBMP);
End
Except
FreeBitmap(ClientBMP);
End;
Result := True;
End;
function AutoColorWall: integer;
var
TPA: TPointArray;
R, G, B, R2, G2, B2, hi, i, ii, DTM, x, y, hi: integer;
angle: extended;
dtmMainPoint: TDTMPointDef;
dtmSubPoints: Array [0..4] of TDTMPointDef;
TempTDTM: TDTM;
begin
writeln('AutoColoring Walls...');
for R:= 83 downto 73 do
for G:= 83 downto 73 do
for B:= 83 downto 73 do
begin
R2:= R*3;
G2:= G*3;
B2:= B*3;
if not FindColorTolerance(x, y, RGBToColor(R2, G2, B2), MMX1, MMY1, MMX2, MMY2, 2) then Continue;
FindColorsTolerance(TPA, RGBtoColor(R2, G2, B2), MMX1, MMY1, MMX2, MMY2, 2);
if Length(TPA) < 30 then continue;
hi := High(TPA);
for i:= 0 to hi do
begin
dtmMainPoint.x := TPA[i].x;
dtmMainPoint.y := TPA[i].y;
dtmMainPoint.AreaSize := 0;
dtmMainPoint.AreaShape := 0;
dtmMainPoint.Color := RGBToColor(R2, G2, B2);
dtmMainPoint.Tolerance := 2;
for ii:= 1 to 5 do
begin
dtmSubPoints[ii-1].x := dtmMainPoint.x;
dtmSubPoints[ii-1].y := dtmMainPoint.y-ii;
dtmSubPoints[ii-1].AreaSize := 0;
dtmSubPoints[ii-1].AreaShape := 0;
dtmSubPoints[ii-1].Color := RGBToColor(R2, G2, B2);
dtmSubPoints[ii-1].Tolerance := 2;
end;
TempTDTM.MainPoint := dtmMainPoint;
TempTDTM.SubPoints := dtmSubPoints;
DTM:= AddDTM(TempTDTM);
if FindDTMRotated(DTM, x, y, MMX1, MMY1, MMX2, MMY2, 0, Pi, 0.01, angle) then
if InCircle(MMCX, MMCY, x, y, 72) then
begin
result:= GetColor(x, y);
exit;
end else
continue;
end;
end;
writeln('AutoColorWall Failed! Result = 0');
end;
var
t, c: integer;
begin
SetupSRL;
SetLength(gATPA, 1);
MarkTime(t);
c:= AutoColorWall;
writeln('Time elapsed: '+inttostr(TimeFromMark(t))+' ms');
writeln('Wallcolor = '+inttostr(c));
FindColorsTolerance(gATPA[0], c, mmx1, mmy1, mmx2, mmy2, 10);
DebugATPA(gATPA, '');
end.
i tested more than 6 times but here are some shots:

edit: minor bugfix
edit: major bug, will be fixing it tomorroow
edit: final conclusion: i took the old function back (the slow one)
edit: minor bugfix