Darek855 Posted March 21, 2019 Share Posted March 21, 2019 So here is my code if (loot1 == null && !Tile1.contains(myPlayer()) && Tile2.contains(myPlayer())) { log ("going back to safe"); getWalking().walk(Tile1); new ConditionalSleep(5000, 1000) { @Override public boolean condition() { return Tile1.contains(myPosition()); } }.sleep(); } The idea is that it goes to loot and when there is no loot it runs back to safety where it can attack from distance but the problem is it missclicks? when it is moving to tile1 and clicks tile next to it and it wont run this again as it thinks its in safety for some reason even tho its not. here is picture explaining it better: So the bot thinks missclicks tile 2 when it was supposed to click tile 1 and even when it is in the orange area the above code should execute again as its not in tile 1 but it wont and i am stuck. First thing you would think that the areas/tiles are in wrong coordinates but i double checked all the coordinates and they should be correct unless you cant create rectangular area with 1x3 tiles here is also the area for Tile1: Area Tile1 = new Area (1289, 10097,1289, 10099); and Tile2 is the whole area above: Area Tile2 = new Area (1289,10093,1296,10100); I have had this same problem with others scripts before but i just fixed it by making the click area 1 tile smaller in every direction and the area that checks if i am in the correct place 1 tile bigger so even if it missclicks it still knows its in the correct place but in this case i cant do that as the area is very small and it needs to be exact. Quote Link to comment Share on other sites More sharing options...
Darek855 Posted March 21, 2019 Author Share Posted March 21, 2019 (edited) I may have just realized what the problem is, it should be .contains(myPosition()) not myPlayer hmm.. will test and update,if this is the case and i just made this post for no reason fml Edited March 21, 2019 by Darek855 Quote Link to comment Share on other sites More sharing options...
Darek855 Posted March 21, 2019 Author Share Posted March 21, 2019 (edited) 13 minutes ago, Darek855 said: I may have just realized what the problem is, it should be .contains(myPosition()) not myPlayer hmm.. will test and update,if this is the case and i just made this post for no reason fml Well it did not change anything, still missclicks 1 tile off sometimes... Maybe i should try to make the 3 tiles into positions instead of area i don't know? Edited March 21, 2019 by Darek855 Quote Link to comment Share on other sites More sharing options...
HunterRS Posted March 21, 2019 Share Posted March 21, 2019 Try using this with a random pos in the wanted area: private static boolean walkExact(Script script, Position position) { WalkingEvent event = new WalkingEvent(position); event.setMinDistanceThreshold(0); return script.execute(event).hasFinished(); } Quote Link to comment Share on other sites More sharing options...
Xx pk xX Posted March 21, 2019 Share Posted March 21, 2019 (edited) Here's what I'm using to click on exact Position that I want: /**Clicks on exact Position you set in screenClickPos parameter using screen instead of minimap. * If position is not visible on screen, it will walk first to desired position using walking.walk(..) * and then it clicks on screen exact tile. * * @param screenClickPos - Position where you want to walk * @param destPrecision - presition - when should method return - e.g. setting it to 0, will return once player * gets to desired position. Setting to to 2, it will return once you are 2 tiles away (while bot still walking) * @param rightClick - right click mouse instead of left click, and then choose an action from menu * @param rightClickAction - action in menu to click if rightClick is set to true. Can be null if rightClick is set to false * * @return true if bot walked where you wanted (including destPrecision parameter functionality), or false if it for some reason * fail to walk where you wanted **/ public boolean clickExactPosOnScreen(Position screenClickPos, int destPrecision, boolean rightClick, String rightClickAction) { if (!screenClickPos.isVisible(bot)) { walking.walk(screenClickPos); } Point p = centroid(screenClickPos.getPolygon(bot)); if (p!= null && getMouse().click((int) p.getX(), (int) p.getY(), rightClick)) { if (rightClick) Timing.waitCondition(() -> menu.isOpen(), 2000); if (rightClick && menu.isOpen()) { if (!menu.selectAction(rightClickAction)) return false; } //will wait for about 5 seconds until bot gets to the desired position. You can change //it to return sooner if !myPlayer().isMoving() or whatever else you might need new ConditionalLoop(getBot(), 50) { //will wait for about 5 seconds until bot gets to the desired position. You can change //it to check if !myPlayer().isMoving() to return sooner if you want @Override public boolean condition() { return myPosition().distance(screenClickPos) > destPrecision; }; @Override public int loop() { return 100; } }.start(); } if (myPosition().distance(screenClickPos) <= destPrecision) { return true; } return false; } public Point centroid(Polygon polygon) { int centroidX = 0, centroidY = 0; int[] xPoints = polygon.xpoints; int[] yPoints = polygon.ypoints; ArrayList<Point> knots = new ArrayList<Point>(); for(int i = 0; i < xPoints.length; i++) { knots.add(new Point(xPoints[i], yPoints[i])); } for(Point knot : knots) { centroidX += knot.getX(); centroidY += knot.getY(); } return new Point(centroidX / knots.size(), centroidY / knots.size()); } Example of usage: if (clickExactPosOnScreen(walkPosition, 0, true, "Walk here")) { //do someththing } Or in your case, this should be enough (without right mouse click) if (clickExactPosOnScreen(walkPosition, 0, false, null)) { //do someththing } It was tested before, and worked without any problems. However, I just did a few small changes, so let me know if there's a problem with it, and I will fix it. If someone knows about a simpler method to click on EXACT position in OSBot API, please let us know 19 minutes ago, HunterRS said: Try using this with a random pos in the wanted area: private static boolean walkExact(Script script, Position position) { WalkingEvent event = new WalkingEvent(position); event.setMinDistanceThreshold(0); return script.execute(event).hasFinished(); } In my experience "setMinDistanceThreshold (0);" does not always click on EXACT tile, idk why. Edited March 21, 2019 by Xx pk xX Quote Link to comment Share on other sites More sharing options...
HunterRS Posted March 21, 2019 Share Posted March 21, 2019 7 minutes ago, Xx pk xX said: Here's what I'm using to click on exact Position that I want: /**Clicks on exact Position you set in screenClickPos parameter using screen instead of minimap. * If position is not visible on screen, it will walk first to desired position using walking.walk(..) * and then it clicks on screen exact tile. * * @param screenClickPos - Position where you want to walk * @param destPrecision - presition - when should method return - e.g. setting it to 0, will return once player * gets to desired position. Setting to to 2, it will return once you are 2 tiles away (while bot still walking) * @param rightClick - right click mouse instead of left click, and then choose an action from menu * @param rightClickAction - action in menu to click if rightClick is set to true. Can be null if rightClick is set to false * * @return true if bot walked where you wanted (including destPrecision parameter functionality), or false if it for some reason * fail to walk where you wanted **/ public boolean clickExactPosOnScreen(Position screenClickPos, int destPrecision, boolean rightClick, String rightClickAction) { if (!screenClickPos.isVisible(bot)) { walking.walk(screenClickPos); } Point p = centroid(screenClickPos.getPolygon(bot)); if (p!= null && getMouse().click((int) p.getX(), (int) p.getY(), rightClick)) { if (rightClick) Timing.waitCondition(() -> menu.isOpen(), 2000); if (rightClick && menu.isOpen()) { if (!menu.selectAction(rightClickAction)) return false; } //will wait for about 5 seconds until bot gets to the desired position. You can change //it to return sooner if !myPlayer().isMoving() or whatever else you might need new ConditionalLoop(getBot(), 50) { //will wait for about 5 seconds until bot gets to the desired position. You can change //it to check if !myPlayer().isMoving() to return sooner if you want @Override public boolean condition() { return myPosition().distance(screenClickPos) > destPrecision; }; @Override public int loop() { return 100; } }.start(); } if (myPosition().distance(screenClickPos) <= destPrecision) { return true; } return false; } public Point centroid(Polygon polygon) { int centroidX = 0, centroidY = 0; int[] xPoints = polygon.xpoints; int[] yPoints = polygon.ypoints; ArrayList<Point> knots = new ArrayList<Point>(); for(int i = 0; i < xPoints.length; i++) { knots.add(new Point(xPoints[i], yPoints[i])); } for(Point knot : knots) { centroidX += knot.getX(); centroidY += knot.getY(); } return new Point(centroidX / knots.size(), centroidY / knots.size()); } Example of usage: if (clickExactPosOnScreen(walkPosition, 0, true, "Walk here")) { //do someththing } Or in your case, this should be enough (without right mouse click) if (clickExactPosOnScreen(walkPosition, 0, false, null)) { //do someththing } It was tested before, and worked without any problems. However, I just did a few small changes, so let me know if there's a problem with it, and I will fix it. If someone knows about a simpler method to click on EXACT position in OSBot API, please let us know In my experience "setMinDistanceThreshold (0);" does not always click on EXACT tile, idk why. It does sometimes missclick, what I do is simply recall it untill you reach the correct position. Quote Link to comment Share on other sites More sharing options...
d0zza Posted March 21, 2019 Share Posted March 21, 2019 The issue is that getWalking#walk has a minimum distance threshold of 2 by default, which means it will bring your character to within 2 tiles of the destination then terminate. If you want to get around this you'll have to create the walk event yourself and set the minimum distance threshold to 0 before executing it, you can use the walkExact code that HunterRS posted above to achieve this. Quote Link to comment Share on other sites More sharing options...
Darek855 Posted March 21, 2019 Author Share Posted March 21, 2019 53 minutes ago, HunterRS said: Try using this with a random pos in the wanted area: private static boolean walkExact(Script script, Position position) { WalkingEvent event = new WalkingEvent(position); event.setMinDistanceThreshold(0); return script.execute(event).hasFinished(); } Thanks again! this works perfectly, but can you give me and example how to use this i am a pretty new to this so i dont get it currently just using it like this but rather not spam this every time i want to walk i assumed it woked like this walkExact(script, Tile1) but it didn't also is there a way to make this work for bigger areas rather than just a 1 tile WalkingEvent event = new WalkingEvent(Tile1); event.setMinDistanceThreshold(0); execute(event); 1 hour ago, Xx pk xX said: Here's what I'm using to click on exact Position that I want: /**Clicks on exact Position you set in screenClickPos parameter using screen instead of minimap. * If position is not visible on screen, it will walk first to desired position using walking.walk(..) * and then it clicks on screen exact tile. * * @param screenClickPos - Position where you want to walk * @param destPrecision - presition - when should method return - e.g. setting it to 0, will return once player * gets to desired position. Setting to to 2, it will return once you are 2 tiles away (while bot still walking) * @param rightClick - right click mouse instead of left click, and then choose an action from menu * @param rightClickAction - action in menu to click if rightClick is set to true. Can be null if rightClick is set to false * * @return true if bot walked where you wanted (including destPrecision parameter functionality), or false if it for some reason * fail to walk where you wanted **/ public boolean clickExactPosOnScreen(Position screenClickPos, int destPrecision, boolean rightClick, String rightClickAction) { if (!screenClickPos.isVisible(bot)) { walking.walk(screenClickPos); } Point p = centroid(screenClickPos.getPolygon(bot)); if (p!= null && getMouse().click((int) p.getX(), (int) p.getY(), rightClick)) { if (rightClick) Timing.waitCondition(() -> menu.isOpen(), 2000); if (rightClick && menu.isOpen()) { if (!menu.selectAction(rightClickAction)) return false; } //will wait for about 5 seconds until bot gets to the desired position. You can change //it to return sooner if !myPlayer().isMoving() or whatever else you might need new ConditionalLoop(getBot(), 50) { //will wait for about 5 seconds until bot gets to the desired position. You can change @Override public boolean condition() { return myPosition().distance(screenClickPos) > destPrecision; }; @Override public int loop() { return 100; } }.start(); } if (myPosition().distance(screenClickPos) <= destPrecision) { return true; } return false; } public Point centroid(Polygon polygon) { int centroidX = 0, centroidY = 0; int[] xPoints = polygon.xpoints; int[] yPoints = polygon.ypoints; ArrayList<Point> knots = new ArrayList<Point>(); for(int i = 0; i < xPoints.length; i++) { knots.add(new Point(xPoints[i], yPoints[i])); } for(Point knot : knots) { centroidX += knot.getX(); centroidY += knot.getY(); } return new Point(centroidX / knots.size(), centroidY / knots.size()); } Example of usage: if (clickExactPosOnScreen(walkPosition, 0, true, "Walk here")) { //do someththing } Or in your case, this should be enough (without right mouse click) if (clickExactPosOnScreen(walkPosition, 0, false, null)) { //do someththing } It was tested before, and worked without any problems. However, I just did a few small changes, so let me know if there's a problem with it, and I will fix it. If someone knows about a simpler method to click on EXACT position in OSBot API, please let us know In my experience "setMinDistanceThreshold (0);" does not always click on EXACT tile, idk why. Also will give this a look if it starts missclicking Quote Link to comment Share on other sites More sharing options...
Xx pk xX Posted March 21, 2019 Share Posted March 21, 2019 (edited) If you want to add it to your script, just use: public boolean walkExact(Position position) { WalkingEvent event = new WalkingEvent(position); event.setMinDistanceThreshold(0); return execute(event).hasFinished(); } example of usage: walkExact(tile1); //or if (walkExact(tile1)) { //do Something } Edited March 21, 2019 by Xx pk xX Quote Link to comment Share on other sites More sharing options...
Darek855 Posted March 21, 2019 Author Share Posted March 21, 2019 1 minute ago, Xx pk xX said: If you want to add it to your script, just use: public boolean walkExact(Position position) { WalkingEvent event = new WalkingEvent(position); event.setMinDistanceThreshold(0); return execute(event).hasFinished(); } example of usage: walkExact(tile1); //or if (walkExact(tile1)) { //do Something } Thanks, that is what i tried in the first place but was getting errors, now it works tho those errors were unrelated to this 1 hour ago, d0zza said: The issue is that getWalking#walk has a minimum distance threshold of 2 by default, which means it will bring your character to within 2 tiles of the destination then terminate. If you want to get around this you'll have to create the walk event yourself and set the minimum distance threshold to 0 before executing it, you can use the walkExact code that HunterRS posted above to achieve this. Yup just gave the api a read again and found this is the reason it "missclicks" a bit dumb that the default is 2 but guess that is to add extra randomness to avoid patterns Quote Link to comment Share on other sites More sharing options...
zwaffel Posted March 21, 2019 Share Posted March 21, 2019 12 minutes ago, Darek855 said: also is there a way to make this work for bigger areas rather than just a 1 tile Take a loot at this. https://osbot.org/api/org/osbot/rs07/event/WalkingEvent.html Under Constructor and Description you can see it also works for Entity's and area. So you can just put in an area and it will walk exactly to that area. Same goes for everything that implements Entity, so RS2objects, NPC's , Players, GroundItems, .... Quote Link to comment Share on other sites More sharing options...
Darek855 Posted March 21, 2019 Author Share Posted March 21, 2019 8 minutes ago, zwaffel said: Take a loot at this. https://osbot.org/api/org/osbot/rs07/event/WalkingEvent.html Under Constructor and Description you can see it also works for Entity's and area. So you can just put in an area and it will walk exactly to that area. Same goes for everything that implements Entity, so RS2objects, NPC's , Players, GroundItems, .... Thanks! Quote Link to comment Share on other sites More sharing options...
Juggles Posted March 21, 2019 Share Posted March 21, 2019 Closing this since it seems you got your answer @HunterRS solution should work perfectly. 1 Quote Link to comment Share on other sites More sharing options...
Darek855 Posted March 22, 2019 Author Share Posted March 22, 2019 On 3/21/2019 at 12:27 PM, HunterRS said: Try using this with a random pos in the wanted area: private static boolean walkExact(Script script, Position position) { WalkingEvent event = new WalkingEvent(position); event.setMinDistanceThreshold(0); return script.execute(event).hasFinished(); } Just an update if anyone else needs their script to be very exact and cant afford any misscliks. above woks but if the script decides to use minimap to walk (which it does like 50% of the time) it still misses the tile sometimes so adding event.setMiniMapDistanceThreshold(0); fixes the problem completely. public boolean walkExact(Position position) { WalkingEvent event = new WalkingEvent(position); event.setMinDistanceThreshold(0); event.setMiniMapDistanceThreshold(0); return execute(event).hasFinished(); } 3 Quote Link to comment Share on other sites More sharing options...