/** * fishing_bot.java * @author: Stephen Steffes * March 21, 2004 * Purpose: Fishing bot for FFXI */ import java.awt.*; import java.awt.event.*; import java.util.*; import java.io.*; import javax.swing.*; public class fishing_bot { //User variables public static int MAX_CASTS=100, SORT_INV_RATE=4, EMOTE_RATE=37, STD_DELAY=140, EQUIP_RATE=12; //Key binding variables public static int PLUS=107, LEFT=37, UP=38, RIGHT=39, DOWN=40, NUMPAD5=101, PERIOD=46, PRINT_SCREEN=154; public static boolean SCAN_TELLS=true; //System variables public static String VERSION="2.5"; public static Robot robot; public static Random r; public static Color c; public static int casts=0; public static void main(String[] args) throws AWTException{ printWelcome(); //Print welcome message //set up variables robot = new Robot(); r=new Random(System.currentTimeMillis()); getInputs(); /* //wait an initial time robot.delay(10000); robot.delay(60000); */ System.out.println("\n\n...Ready to log on"); catchCommands(); //wait for first command //switch to party chat mode press(KeyEvent.VK_SLASH); type("cm"); press(KeyEvent.VK_SPACE); type("party"); press(KeyEvent.VK_ENTER); //fish until MAX_CASTS for(casts=0;casts=COMMAND_B_MIN) && (c.getBlue()<=COMMAND_B_MAX)){ c=robot.getPixelColor(STOP_X,COMMAND_Y); //get stop pixel if((c.getRed()==COMMAND_R) && (c.getGreen()==COMMAND_G) && (c.getBlue()>=COMMAND_B_MIN) && (c.getBlue()<=COMMAND_B_MAX)) mode=STOP; else{ if(mode==PAUSE) //Toggel pause mode mode=UNPAUSE; else mode=PAUSE; } } else { c=robot.getPixelColor(MINUS_CHANGE_X,COMMAND_Y); //get -Change pixel if((c.getRed()==COMMAND_R) && (c.getGreen()==COMMAND_G) && (c.getBlue()>=COMMAND_B_MIN) && (c.getBlue()<=COMMAND_B_MAX)){ MAX_CASTS-=CAST_CHANGE; echo("sub"); }else { c=robot.getPixelColor(PLUS_CHANGE_X,COMMAND_Y); //get +Change pixel if((c.getRed()==COMMAND_R) && (c.getGreen()==COMMAND_G) && (c.getBlue()>=COMMAND_B_MIN) && (c.getBlue()<=COMMAND_B_MAX)){ MAX_CASTS+=CAST_CHANGE; echo("add"); } } } if(mode==UNPAUSE){ // System.out.println("Bot unpaused"); if(!firstPause){ echo("un"); // clearPixels(); } break; } if(mode==PAUSE){ // System.out.println("Bot paused"); if(firstPause){ if(casts!=0) echo("pau"); // clearPixels(); //clear text box if not first cast else casts++; firstPause=false; } robot.delay(1000); } if(mode==STOP){ press(KeyEvent.VK_SPACE); type("stopping"); //print message to user that command was received System.out.println("Received Stop Command"); System.exit(0); } } } /////////////////////////////////////////////// //Type a single word in echo text public static void echo(String a){ press(KeyEvent.VK_SLASH); type("echo"); press(KeyEvent.VK_SPACE); type(a); press(KeyEvent.VK_ENTER); } ////////////////////////////////////////////////// //Check to see if you have a full inventory public static int PT1_Y=985,PT1_X=106,PT2_Y=1001,PT2_X=106,PT1_R=255,PT1_G=255,PT1_B=255, PT2_R=255,PT2_G=255,PT2_B=255; public static void checkFullInv(){ //get 2 points and see if they match the full inventory case c=robot.getPixelColor(PT1_X,PT1_Y); if((c.getRed()==PT1_R) && (c.getGreen()==PT1_G) && (c.getBlue()==PT1_B)){ c=robot.getPixelColor(PT2_X,PT2_Y); if((c.getRed()==PT2_R) && (c.getGreen()==PT2_G) && (c.getBlue()==PT2_B)){ System.out.println("Inventory full"); press(KeyEvent.VK_ESCAPE); press(KeyEvent.VK_ESCAPE); robot.delay(4000); logout(); } } } ////////////////////////////////////////////////// //Looks to see if character get's a /tell, if so, send "sorry", screen grab and logout public static int SCAN_Y=997, SCAN_Y_DIFF=16, SCAN_MIN_X=21, SCAN_MAX_X=27, TELL_R=255, TELL_G=140, TELL_B=255; public static void scanForTells(){ for(int i=0;i<8;i++){ //loop over all text lines for(int x=SCAN_MIN_X;x<=SCAN_MAX_X;x++){ //loop over all pixels in first character c=robot.getPixelColor(x,SCAN_Y-SCAN_Y_DIFF*i); if((c.getRed()==TELL_R) && (c.getGreen()<=TELL_G+10) && (c.getGreen()>=TELL_G-10) && (c.getBlue()==TELL_B)){ //received a /tell combo(KeyEvent.VK_CONTROL,KeyEvent.VK_R); //reply robot.delay(1000); type("i"); press(KeyEvent.VK_SPACE); type("need"); press(KeyEvent.VK_SPACE); type("ot"); press(KeyEvent.VK_SPACE); type("go"); press(KeyEvent.VK_ENTER); combo(KeyEvent.VK_CONTROL,KeyEvent.VK_R); //reply robot.delay(1000); type("mt"); press(KeyEvent.VK_ENTER); System.out.println("Someone sent a tell"); screenGrab(); logout(); //run away } } } } /////////////////////////////////////////////////////// //clear first line in text box public static void clearPixels(){ press(KeyEvent.VK_SLASH); type("echo"); press(KeyEvent.VK_SPACE); press((int)(r.nextDouble()*25)+KeyEvent.VK_A); //type something in text box to clear pixel test area press(KeyEvent.VK_ENTER); } /////////////////////////////////////////////////////// //Cast and reel in fish public static int FISH_X=25, FISH_Y=996, FISH_MIN_R=230, FISH_MIN_G=230, FISH_MIN_B=230, equipCheck=0; public static void fish(){ clearPixels(); delay(STD_DELAY); //Cast rod command("fish"); robot.delay(2000); //wait 2 seconds to get rod out //Check bait if(equipmentCheck()){ //if need to change equipment equipCheck++; if(equipCheck>=2){ System.out.println("Out of bait"); logout(); } fish(); return; } else equipCheck=0; int j; for(j=0;j<60;j++){ //check for pixel for 60 seconds c=robot.getPixelColor(FISH_X,FISH_Y); //check that RGB values are close enough if((c.getRed()>=FISH_MIN_R) && (c.getGreen()>=FISH_MIN_G) && (c.getBlue()>=FISH_MIN_B)){ delay(3500); //wait a short while before reel in // System.out.println("reeling in"); break; //something triggered to reel in } robot.delay(1000); //wait 1 seconds in between pixel checks } if(j==60) //if never found a fish message System.out.println("Didn't see fish message"); press(KeyEvent.VK_ENTER); //reel in fish } ////////////////////////////////////////////////////// //Sort the characters inventory //Uses the 'i' key as the up key while in the inventory menu. //i.e. make sure that the 'i' key is set to be the same as the camera-up key within FFXI public static void sortInv(){ combo(KeyEvent.VK_CONTROL,KeyEvent.VK_I); delay(STD_DELAY); press(PLUS,100); delay(STD_DELAY); press(KeyEvent.VK_ENTER); delay(STD_DELAY); press(KeyEvent.VK_I); delay(STD_DELAY); press(KeyEvent.VK_ENTER); } /////////////////////////////////////////////////////// //Check equipment public static int EQUIP_X1=86, EQUIP_Y1=992, EQUIP_X2=338, EQUIP_Y2=1000, EQUIP_MIN_R=230, EQUIP_MIN_G=230, EQUIP_MIN_B=230; public static boolean equipmentCheck(){ c=robot.getPixelColor(EQUIP_X1,EQUIP_Y1); //check that RGB values are close enough if((c.getRed()>=EQUIP_MIN_R) && (c.getGreen()>=EQUIP_MIN_G) && (c.getBlue()>=EQUIP_MIN_B)){ c=robot.getPixelColor(EQUIP_X2,EQUIP_Y2); if((c.getRed()>=EQUIP_MIN_R) && (c.getGreen()>=EQUIP_MIN_G) && (c.getBlue()>=EQUIP_MIN_B)){ //out of bait equipBait(); return true; } } return false; } ////////////////////////////////////////////////////// //Equip bait public static int NO_BAIT=0,LITTLE_WORM=1,INSECT_BALL=2,BAIT_TYPE=NO_BAIT; public static void equipBait(){ if(BAIT_TYPE!=NO_BAIT){ press(KeyEvent.VK_SLASH); type("equip"); press(KeyEvent.VK_SPACE); type("ammo"); press(KeyEvent.VK_SPACE); combo(KeyEvent.VK_SHIFT,KeyEvent.VK_QUOTE); //press " if(BAIT_TYPE==LITTLE_WORM){ combo(KeyEvent.VK_SHIFT,KeyEvent.VK_L); type("ittle"); press(KeyEvent.VK_SPACE); combo(KeyEvent.VK_SHIFT,KeyEvent.VK_W); type("orm"); } if(BAIT_TYPE==INSECT_BALL){ combo(KeyEvent.VK_SHIFT,KeyEvent.VK_I); type("nsect"); press(KeyEvent.VK_SPACE); combo(KeyEvent.VK_SHIFT,KeyEvent.VK_B); type("all"); } combo(KeyEvent.VK_SHIFT,KeyEvent.VK_QUOTE); //press " press(KeyEvent.VK_ENTER); } } //////////////////////////////////////////////// //Logout out of FFXI and return to PlayOnline game menu public static void logout(){ robot.delay(2000); press(KeyEvent.VK_ESCAPE); press(KeyEvent.VK_ESCAPE); robot.delay(2000); command("logout"); System.out.println("Logging out with "+casts+" casts"); robot.delay(50000); //wait 50 seconds to logout press(KeyEvent.VK_ESCAPE); press(KeyEvent.VK_ENTER); System.exit(0); } ///////////////////////////////////////////// //Type a FFXI command (i.e. /fish, /sigh, ... ) //The command to type is /'a' //'a' cannot have any character not read in by the type() function public static void command(String a){ press(KeyEvent.VK_SLASH); type(a); delay(STD_DELAY); press(KeyEvent.VK_ENTER); delay(STD_DELAY); } ////////////////////////////////////////////// //Press c-'a', (ex. control-a) public static void combo(int c,int a){ robot.keyPress(c); press(a); robot.keyRelease(c); } ////////////////////////////////////////////// //Take a screen grab public static void screenGrab(){ press(KeyEvent.VK_ESCAPE); press(PLUS); press(KeyEvent.VK_ENTER); robot.delay(1000); combo(KeyEvent.VK_CONTROL,PRINT_SCREEN); System.out.println("Screen shot waiting on clipboard."); } ///////////////////////////////////////////////// //Type a series of letters represented in the String 'a'. //This will only type actual letters (lower case only), no white spaces or non-alphabet characters public static void type(String a){ for(int i=0; i2) temp=2; temp*=.1; //gaussian from 0 to .2 robot.delay((int)(a*(.9+temp))); //gaussian from .9a to 1.1a } //////////////////////////////////////////////// //Prints welcome message public static void printWelcome(){ System.out.println("Welcome to FFXI Fishing bot version "+VERSION); System.out.println("\n\nMake sure you are /anon and do not have a linkshell equiped"); System.out.println("Also, make sure your text box is clear of any /tell's before you unpause"); System.out.println("\nDo NOT use this bot outside of a city our you will eventually get caught"); } }