Log in

View Full Version : Function Request. [Reflection]



Home
02-28-2011, 01:44 PM
SecondClosestObj(IDs: TIntegerArray; objType, MaxDist: Integer): TRSObject;


Hey.

Could someone create me a function wich Results Second Nearest Object.
Or even better:

Finds second Nearest Object what we are NOT Interacting.

Thanks.


~Home

Floor66
02-28-2011, 01:54 PM
Something I quickly threw together;

function SecondClosestObj(IDs: TIntegerArray; objType, MaxDist: Integer): TRSObject;
var
i, j : Integer;
p, dest_tile : TTile;
dists : TIntegerArray;
t : TRSObjectArray;
obj_tiles : TPointArray;
begin
t := GetObjectsByIDEx(IDs, objType, MaxDist);
SetArrayLength(dists, GetArrayLength(t));
SetArrayLength(objs, GetArrayLength(t));
for i := 0 to High(t) do
obj_tiles[i] := t[i].Tile;
for i := 0 to High(obj_tiles) do
dists[i] := 500;
p := GetMyPos;
for i := 0 to High(obj_tiles) do
begin
if not TileOnMS(obj_tiles[i], 2) then
Continue;
dists[i] := Distance(p.x, p.y, obj_tiles[i].x, obj_tiles[i].y);
if i > 0 then
begin
if dists[i] < dists[i - 1] then
j := i;
end else
j := i;
end;
Result := t[j + 1];
end;


It'll sort the objects by distance, closest first, and then take the second closest (I hope :P). It's based off of my own function for finding the closest tree. Didn't test it yet.
For the non-interacting bit, you could save the tile of the rock you're currently mining as a global var and do something like...

if (not TileOnMS(obj_tiles[i], 2)) and ((CurrentRockTile.x <> obj_tiles[i].x) and (CurrentRockTile.y <> obj_tiles[i].y)) then
Continue;

Home
02-28-2011, 02:04 PM
Something I quickly threw together;

function SecondClosestObj(IDs: TIntegerArray; objType, MaxDist: Integer): TRSObject;
var
i, j : Integer;
p, dest_tile : TTile;
dists : TIntegerArray;
t : TRSObjectArray;
obj_tiles : TPointArray;
begin
t := GetObjectsByIDEx(IDs, objType, MaxDist);
SetArrayLength(dists, GetArrayLength(t));
SetArrayLength(objs, GetArrayLength(t));
for i := 0 to High(t) do
obj_tiles[i] := t[i].Tile;
for i := 0 to High(obj_tiles) do
dists[i] := 500;
p := GetMyPos;
for i := 0 to High(obj_tiles) do
begin
if not TileOnMS(obj_tiles[i], 2) then
Continue;
dists[i] := Distance(p.x, p.y, obj_tiles[i].x, obj_tiles[i].y);
if i > 0 then
begin
if dists[i] < dists[i - 1] then
j := i;
end else
j := i;
end;
Result := t[j + 1];
end;


It'll sort the objects by distance, closest first, and then take the second closest (I hope :P). Didn't test it yet.
For the non-interacting bit, you could save the tile of the rock you're currently mining as a global var and do something like...

if (not TileOnMS(obj_tiles[i], 2)) and ((CurrentRockTile.x <> obj_tiles[i].x) and (CurrentRockTile.y <> obj_tiles[i].y)) then
Continue;


Thanks a lot!

Haha, how did you guess that i'm working with mining script :)

~Home

Floor66
02-28-2011, 02:05 PM
I guessed it was for your M1D1 script :P

Also, test it first. I can't test it ATM but I'm not 100% sure it works right now.
Looking over it, it might have to be Result := t[(j - 1)]; hmmm :S

Home
02-28-2011, 02:15 PM
I guessed it was for your M1D1 script :P

Also, test it first. I can't test it ATM but I'm not 100% sure it works right now.
Looking over it, it might have to be Result := t[(j - 1)]; hmmm :S

I get:
Error: Out Of Range at line 168

Line 168: Result := t[j + 1];



~Home

Floor66
02-28-2011, 02:18 PM
Ah ok u got it.
If it still doesn't work for some reason, try:

function SecondClosestObj(IDs: TIntegerArray; objType, MaxDist: Integer): TRSObject;
var
i, c : Integer;
p, dest_tile : TTile;
dists, j : TIntegerArray;
t : TRSObjectArray;
obj_tiles : TPointArray;
begin
t := GetObjectsByIDEx(IDs, objType, MaxDist);
SetArrayLength(dists, GetArrayLength(t));
SetArrayLength(objs, GetArrayLength(t));
SetArrayLength(j, GetArrayLength(t));
for i := 0 to High(t) do
obj_tiles[i] := t[i].Tile;
for i := 0 to High(obj_tiles) do
dists[i] := 500;
p := GetMyPos;
for i := 0 to High(obj_tiles) do
begin
if (not TileOnMS(obj_tiles[i], 2)) then
Continue;
dists[i] := Distance(p.x, p.y, obj_tiles[i].x, obj_tiles[i].y);
if i > 0 then
begin
if dists[i] < dists[i - 1] then
begin
j[c] := i;
Inc(c);
end;
end else
begin
j[c] := i;
Inc(c);
end;
end;
Result := t[j[c - 1]];
end;


I made up some numbers for the distances in my head so in theory it should work now :)
Previously, 'c' was affected no matter what. Now it's just affected when 'j' changes.

For the closest rock I didn't need to save any of the other distances, but for this one I had to make 'j' an array ;)

Home
02-28-2011, 02:33 PM
Ah ok u got it.
If it still doesn't work for some reason, try:

function SecondClosestObj(IDs: TIntegerArray; objType, MaxDist: Integer): TRSObject;
var
i, c : Integer;
p, dest_tile : TTile;
dists, j : TIntegerArray;
t : TRSObjectArray;
obj_tiles : TPointArray;
begin
t := GetObjectsByIDEx(IDs, objType, MaxDist);
SetArrayLength(dists, GetArrayLength(t));
SetArrayLength(objs, GetArrayLength(t));
SetArrayLength(j, GetArrayLength(t));
for i := 0 to High(t) do
obj_tiles[i] := t[i].Tile;
for i := 0 to High(obj_tiles) do
dists[i] := 500;
p := GetMyPos;
for i := 0 to High(obj_tiles) do
begin
if (not TileOnMS(obj_tiles[i], 2)) then
Continue;
dists[i] := Distance(p.x, p.y, obj_tiles[i].x, obj_tiles[i].y);
if i > 0 then
begin
if dists[i] < dists[i - 1] then
begin
j[c] := i;
Inc(c);
end;
end else
begin
j[c] := i;
Inc(c);
end;
end;
Result := t[j[c - 1]];
end;


I made up some numbers for the distances in my head so in theory it should work now :)
Previously, 'c' was affected no matter what. Now it's just affected when 'j' changes.

For the closest rock I didn't need to save any of the other distances, but for this one I had to make 'j' an array ;)


Ok Thanks :)
I will do some tweaking into it.

Rep+.

Flight
02-28-2011, 03:18 PM
Ah I'll bet you'll be using the second nearest Obj ID to hover your mouse at it's X/Y while mining your current rock, saves the time of moving the mouse to the next obj in line. :p Smart, but for an M1D1 I think it's better to hover the mouse in the inventory and wait for the ore to appear, for faster dropping.

Or atleast that's how I'd do it.

Home
02-28-2011, 03:19 PM
Ah I'll bet you'll be using the second nearest Obj ID to hover your mouse at it's X/Y while mining your current rock, saves the time of moving the mouse to the next obj in line. :p Smart, but for an M1D1 I think it's better to hover the mouse in the inventory and wait for the ore to appear, for faster dropping.

Or atleast that's how I'd do it.

You got that right ;) And yeah it's not coming for my M1D1 Script.

I have no idea what i could do more into it. It should be fastest. (Beats RsBots.Nets ;))

~Home

Flight
02-28-2011, 03:28 PM
I've tried thinking of any possible way to improve my M1D1 but there's only so far you can really go with reflection. It's hard to detect if your player has stopped using the mining animation or if the rock still has ore in it while you're mining it. I had a theory of to record a color's X/Y coordinates when you click on them and as long as the color still exists in that specific point then there's still ore in the rock, otherwise someone else got the ore while we're still waiting for it to show up in the inventory. This would be easy in reflection as the object id would change completely if it becomes empty. Have you any ideas about this?

Also I'm sorry for the spam, but I like to bounce ideas around, it seems progress is multiplied when we do so. :)

Home
02-28-2011, 03:42 PM
I've tried thinking of any possible way to improve my M1D1 but there's only so far you can really go with reflection. It's hard to detect if your player has stopped using the mining animation or if the rock still has ore in it while you're mining it. I had a theory of to record a color's X/Y coordinates when you click on them and as long as the color still exists in that specific point then there's still ore in the rock, otherwise someone else got the ore while we're still waiting for it to show up in the inventory. This would be easy in reflection as the object id would change completely if it becomes empty. Have you any ideas about this?

Also I'm sorry for the spam, but I like to bounce ideas around, it seems progress is multiplied when we do so. :)

Your should check out PixelShift Function :)

~Home

HyperSecret
02-28-2011, 04:52 PM
Isn't there a getNearestObj or something of the sort in reflection already? you could just edit that to return nearestArray[1] instead of nearestArray[0]...

I could be wrong but I would think there should be

Train
02-28-2011, 07:47 PM
Offtopic: If you use RRL do r_GetAllObjectsByIDOptimized instead of closest, sArr := r_SortObjects(..);
then
if (GetArrayLength(sArr) > 1) then
Result := sArr[1];


Isn't there a getNearestObj or something of the sort in reflection already? you could just edit that to return nearestArray[1] instead of nearestArray[0]...

I could be wrong but I would think there should be

The get all functions object in srl-reflection auto sorts, you'd just have to use [1], no need for making your own function/editing.