Results 1 to 23 of 23

Thread: Syntax Highlighter

  1. #1
    Join Date
    Sep 2006
    Posts
    6,089
    Mentioned
    77 Post(s)
    Quoted
    43 Post(s)

    Default Syntax Highlighter

    Hey,

    In the past I have once attempted to create a syntax highlighter in SCAR. I can't really remember what actually happened to it. But after seeing the SCAR Notepad by Dan Cardin I decided to give it another try.

    It highlights keywords, strings, comments, numbers just like SCAR would. I did my best to not let it flicker much.



    SCAR Code:
    program New;

    const
      Keywords = 'const|type|var|begin|end|array|set|record|string|if|then|else|while|' +
                 'for|to|downto|do|with|repeat|until|case|of|goto|label|procedure|'     +
                 'function|nil|and|or|not|xor|div|mod|external|stdcall|cdecl|raise|'    +
                 'try|except|on|finally|as|in|is|out|program|shr|shl|forward';
                 
      re_KeyWords = '(\b('+Keywords+')\b)';
      re_String   = '('#39')';
      re_Comment  = '(([{]|[(][*]|[/][/]))';
      re_Numbers  = '(\d)';
      re_Regex    = re_KeyWords+'|'+re_String+'|'+re_Comment+'|'+re_Numbers;
     
      clKeyword = clBlack;
      clString = clFuchsia;
      clInteger = clNavy;
      clComment = clGreen;

    var
      f: TForm;
      r: TRichEdit;
      PALL: Boolean;
     
    function MinNoZero(a, b: Integer): Integer; //Idea from Ron
    begin
      Result := a;
      if (a <= 0) or ((b > 0) and (b < a)) then
        Result := b;
    end;

    procedure ParseIt(OffSet: Integer; s: string);
    var
      sStart, sLen: Integer;
      t, c, pStart, pEnd: Integer;
      DotFound: Boolean;
    begin
      t := GetTickCount;
      s := LowerCase(s);
      c := -2;
      with r do
      begin
        //Lines.BeginUpdate;
        sStart := SelStart;
        sLen := SelLength;
        SelStart := OffSet - 1;
        SelLength := Length(s) + 2;
        SelAttributes.Style := [];
        SelAttributes.Color := clBlack;

        pStart := RegexPos(s, re_Regex);
        while (pStart > 0) do
        begin
          pEnd := pStart;
          case s[pStart] of
            'a'..'z':
              begin
                while (pEnd <= Length(s)) do
                  case s[pEnd] of
                    'a'..'z': Inc(pEnd);
                    else Break;
                  end;
                SelStart := pStart + OffSet + c;
                SelLength := Max(pEnd - pStart, 1);
                SelAttributes.Style := [fsBold];
                SelAttributes.Color := clKeyword;
              end;
            '0'..'9':
              begin
                DotFound := False;
                while (pEnd <= Length(s)) do
                  case s[pEnd] of
                    '0'..'9': Inc(pEnd);
                    '.':
                      begin
                        DotFound := True;
                        Inc(pEnd);
                      end;
                    else Break;
                  end;
                if (not DotFound) then
                begin
                  SelStart := pStart + OffSet + c;
                  SelLength := Max(pEnd - pStart, 1);
                  SelAttributes.Style := [];
                  SelAttributes.Color := clInteger;
                end;
              end;
            '(', '{', '/':
              begin
                case s[pStart] of
                  '(': pEnd := MinNoZero(PosEx('*)', s, pStart), Length(s) + 1) + 1;
                  '{': pEnd := MinNoZero(PosEx('}', s, pStart), Length(s) + 1) + 1;
                  '/': pEnd := MinNoZero(PosEx(#13, s, pStart), Length(s) + 1) + 1;
                end;
                SelStart := pStart + OffSet + c;
                if (not PALL) then
                  SelLength := Max(pEnd - pStart, 1) + 1
                else
                  SelLength := Max(pEnd - pStart, 1);
                if (s[pStart] = '{') then
                  Dec(pEnd);
                SelAttributes.Style := [];
                SelAttributes.Color := clComment;
              end;
            #39:
              begin
                pEnd := MinNoZero(PosEx(#39, s, pStart + 1), PosEx(#13, s, pStart + 1)) + 1;
                if (pEnd <= 0) then
                  pEnd := Length(s) + 1;
                SelStart := pStart + OffSet + c;
                SelLength := Max(pEnd - pStart, 1);
                SelAttributes.Style := [];
                SelAttributes.Color := clString;
              end;
          end;
          Delete(s, 1, pEnd - 1);
          c := c + pEnd - 1;
          pStart := RegexPos(s, re_Regex);
        end;
     
        SelStart := sStart;
        SelLength := sLen;
        //Lines.EndUpdate;
      end;
      WriteLn('ParseIt took: '+IntToStr(GetTickCount - t)+'ms');
    end;

    function InComment(p: Integer): string;
    var
      a, b, sStart, sLen: Integer;
      t: string;
    begin
      Result := '';
      with r do
      begin
        t := Lines.Text;
        //Lines.BeginUpdate;
        sStart := SelStart;
        sLen := SelLength;

        a := MinNoZero(Pos('{', t), Pos('(*', t));
        while (a > 0) do
        begin
          if (a > p) then
            Break;
          SelStart := a;
          SelLength := 1;
          if (SelAttributes.Color <> clString) then
          begin
            case t[a] of
              '{': b := PosEx('}', t, a + 1);
              '(': b := PosEx('*)', t, a + 1);
            end;
            if ((p < b) or (b <= 0)) then
            begin
              case t[a] of
                '{': Result := '{';
                '(': Result := '(*';
              end;
              Break;
            end;
            a := MinNoZero(PosEx('{', t, b), PosEx('(*', t, b));
            Continue;
          end;

          a := MinNoZero(PosEx('{', t, a + 1), PosEx('(*', t, a + 1));
        end;

        SelStart := sStart;
        SelLength := sLen;
        //Lines.EndUpdate;
      end;
    end;

    procedure ParseLine;
    var
      cLine, LineStart: Integer;
      s, t: string;
    begin
      with r do
      begin
        cLine := Perform($00C9, SelStart, 0);
        s := Lines[cLine];
        Delete(s, Length(s) - 1, 2);
        if (Trim(s) = '') then
          Exit;
        LineStart := Perform($00BB, cLine, 0);

        t := InComment(LineStart);
        if (t <> '') then
        begin
          Insert(InComment(LineStart), s, 1);
          LineStart := LineStart - Length(t);
        end;
        ParseIt(LineStart + 1, s);
      end;
    end;


    procedure OnChange(Sender: TObject);
    var
      Mask: Integer;
    begin
      with r do
      begin
        Mask := Perform($0400 + 69, 0, 0); //EM_SETEVENTMASK
        Perform($000B, 0, 0); //WM_SetRedraw
        Lines.BeginUpdate;

         if PALL then
           ParseIt(1, Lines.Text)
         else
           ParseLine;
        PALL := False;

        Lines.EndUpdate;
        Perform($000B, 1, 0);
        Invalidate;
        Perform($0400 + 69, 0, Mask);
      end;
    end;

    procedure OnKeyDown(Sender: TObject; var Key: Word; Shift: TShiftState);
    begin
      with r do
      begin
        if (ssShift in Shift) then
        begin
          if ((Key = 221) or (Key = 219)) then
            PALL := True
          else

          if (Key = 57) then
          begin
            if (SelStart > 0) and (SelStart < GetTextLen) then
              if (Lines.Text[SelStart + 1] = '*') then
                PALL := True;
          end
          else

          if (Key = 56) then
          begin
            if (SelStart > 0) then
              if (Lines.Text[SelStart] = '(') then
                PALL := True;
          end
        end
        else

        if (Key = 86) and (ssCtrl in Shift) then
          PALL := True
        else

        if (SelLength > 0) then
        begin
          if ((Pos('{', SelText) > 0) and (Pos('}', SelText) <= 0)) or
             ((Pos('(*', SelText) > 0) and (Pos('*)', SelText) <= 0)) then
            PALL := True;
        end
        else

        if (Key = 8) then
        begin
          if (SelStart > 0) then
            if (Lines.Text[SelStart] = '{') or (Lines.Text[SelStart] = '}') then
              PALL := True;
          if (not PALL) and (SelStart > 1) and (SelStart < GetTextLen) then
            if ((Lines.Text[SelStart] = '*') and (Lines.Text[SelStart - 1] = '(')) or
               ((Lines.Text[SelStart] = '(') and (Lines.Text[SelStart + 1] = '*')) or
               ((Lines.Text[SelStart] = '*') and (Lines.Text[SelStart + 1] = ')')) or
               ((Lines.Text[SelStart] = ')') and (Lines.Text[SelStart - 1] = '*')) then
              PALL := True;
        end
        else

        if (Key = 46) then
        begin
          SelLength := 1;
          if (SelStart > 0) and (SelStart < GetTextLen) then
            if (Lines.Text[SelStart + 1] = '{') or (Lines.Text[SelStart + 1] = '}') then
              PALL := True;
          if (not PALL) and (SelStart > 0) and (SelStart < GetTextLen - 1) then
            if ((Lines.Text[SelStart + 1] = '(') and (Lines.Text[SelStart + 2] = '*')) or
               ((Lines.Text[SelStart]     = '(') and (Lines.Text[SelStart + 1] = '*')) or
               ((Lines.Text[SelStart + 1] = '*') and (Lines.Text[SelStart + 2] = ')')) or
               ((Lines.Text[SelStart]     = '*') and (Lines.Text[SelStart + 1] = ')')) then
              PALL := True;
        end
        else
          PALL := False;
      end;
    end;

    procedure LoadForm;
    begin
      f := CreateForm;
      with f do
      begin
        Position := poDesktopCenter;
        ClientWidth := 600;
        ClientHeight := 400;
        Caption := 'Syntax Highligter';
      end;

      r := TRichEdit.Create(f);
      with r do
      begin
        Align := alClient;
        Parent := f;
        Font.Name := 'Courier New';
        Font.Size := 10;
        ScrollBars := ssBoth;
        HideScrollBars := False;
        WordWrap := False;
        OnChange := @OnChange;
        OnKeyDown := @OnKeyDown;
      end;
     
      f.ShowModal;
    end;

    var
      v: TVariantArray;
    begin
      ThreadSafeCall('LoadForm', v);
    end.

    ~Nielsie95
    Hup Holland Hup!

  2. #2
    Join Date
    Feb 2007
    Location
    SparklesProd.com
    Posts
    2,406
    Mentioned
    1 Post(s)
    Quoted
    0 Post(s)

    Default

    Really great job, I like it. Doesn't flicker at all for me + all the syntax seems perfect.

    I'm not sure of the use of it, but I'm sure you learnt a bit/it was fun making it? :P

  3. #3
    Join Date
    Jun 2007
    Location
    Wednesday
    Posts
    2,446
    Mentioned
    3 Post(s)
    Quoted
    1 Post(s)

    Default

    Looks awesome, but when you do an apostrophe, et sets everything before it pink as well as what you put between the 2 apostrophes (though the text stays black until you close the first apostrophe), though if it's on the same line, then the formatting goes back to normal after closing. That's the only bug there seems to be, so good job
    By reading this signature you agree that mixster is superior to you in each and every way except the bad ways but including the really bad ways.

  4. #4
    Join Date
    Apr 2007
    Posts
    3,152
    Mentioned
    3 Post(s)
    Quoted
    1 Post(s)

    Default

    use this list of keywords, you left some out
    SCAR Code:
    [' begin ', ' end ', ' else ', ' try ', ' except ', ' finally ', ' finally ',
                    ' repeat ', ' until ', ' procedure ', ' function ', ' var ', ' const ', ' if ', ' string ',
                    ' and ', ' array ', ' as ', ' case ', ' class ', ' const ', ' div ', ' do ', ' downto ', ' end ',
                    ' for ', ' goto ', ' in ', ' is' , ' mod ', ' not ', ' object ', ' of ', ' on ', ' or ', ' procedure ',
                    ' program ', ' record ', ' repeat ', ' set ', ' shl ', ' shr ', ' then ', ' to ', ' type ', ' while ',
                    ' with ', ' xor '];
    good job, works a lot better than mine and flickers like 20 times less than mine . hope you can get the words in between the apostrophes working
    SCAR Tutorials: The Form Tutorial | Types, Arrays, and Classes
    Programming Projects: NotePad | Tetris | Chess


  5. #5
    Join Date
    Sep 2006
    Posts
    6,089
    Mentioned
    77 Post(s)
    Quoted
    43 Post(s)

    Default

    What exactly do you mean with the apostrophes? Could you give an example? It seems to be working good for me.
    Hup Holland Hup!

  6. #6
    Join Date
    Nov 2007
    Location
    Chile
    Posts
    1,901
    Mentioned
    0 Post(s)
    Quoted
    0 Post(s)

    Default

    There is another word called 'as' and its highlighted. Overall good job


  7. #7
    Join Date
    Oct 2006
    Posts
    2,297
    Mentioned
    1 Post(s)
    Quoted
    0 Post(s)

    Default

    Good job Niels! How the hell do you guys manage do make that?

    -Tsn!
    [QUOTE=Santa_Clause;277761]I love you too TSN :p[/QUOTE]
    [CENTER][URL="http://www.stats.srl-forums.com/sigs"][IMG]http://www.stats.srl-forums.com/sigs/1324.png[/IMG][/URL][/CENTER]

  8. #8
    Join Date
    Apr 2007
    Posts
    3,152
    Mentioned
    3 Post(s)
    Quoted
    1 Post(s)

    Default

    type some stuff in, press enter a few times then try using them, it will make them pink. and

    @cazax as is in my list , he's also missing finally and apparently like 4-5 others, cuz i have ~43 and his has 32
    SCAR Tutorials: The Form Tutorial | Types, Arrays, and Classes
    Programming Projects: NotePad | Tetris | Chess


  9. #9
    Join Date
    Aug 2006
    Location
    London
    Posts
    2,021
    Mentioned
    2 Post(s)
    Quoted
    0 Post(s)

    Default

    could you post a screenshot of it?
    there were some issues with scar for me, nothing to do with your script...
    Join the Official SRL IRC channel. Learn how to Here.

  10. #10
    Join Date
    Sep 2006
    Posts
    6,089
    Mentioned
    77 Post(s)
    Quoted
    43 Post(s)

    Default

    Thanks for pointing out Dan
    I reuploaded a new version which hopefully has that fixed, along with some new keywords. I don't want to add all of SCAR's keywords, as SCAR doesn't support them all and it will just slow things down.

    Also added screenshot to the first post, yakman
    Hup Holland Hup!

  11. #11
    Join Date
    Apr 2007
    Posts
    3,152
    Mentioned
    3 Post(s)
    Quoted
    1 Post(s)

    Default

    im pretty sure my list of keywords is all of the used ones, cuz i deleted ones that i hadnt used ever .

    forward, is a used bolded that i didnt have either, and i was playing around and did [4..5] and noticed that when you put a period(.) after a number it turns it black, though you can barely see it .

    also wondering- why did you make this? jw, cuz its tempting me to want to use it but i want to try and make my own work . plus its not mine .

    EDIT: whats
    SCAR Code:
    const punct = '[!"%&''()*+,-./:;<=>?@[\]_`{|}~]';
    do?
    SCAR Tutorials: The Form Tutorial | Types, Arrays, and Classes
    Programming Projects: NotePad | Tetris | Chess


  12. #12
    Join Date
    Sep 2006
    Posts
    6,089
    Mentioned
    77 Post(s)
    Quoted
    43 Post(s)

    Default

    Oh yeah, I forgot about forward (and when I think of it also external).
    The punct is for the Regular Expression.

    I made a highlighter before, but I can't remember if I even finished it or how it looked like, etc. So after seeing your notepad, which has the option to highlight, I decided to give it another shot.
    Hup Holland Hup!

  13. #13
    Join Date
    Sep 2006
    Posts
    6,089
    Mentioned
    77 Post(s)
    Quoted
    43 Post(s)

    Default

    Updated!

    This version should be faster and can handle all kinds of comments
    Hup Holland Hup!

  14. #14
    Join Date
    May 2006
    Location
    Amsterdam
    Posts
    3,620
    Mentioned
    5 Post(s)
    Quoted
    0 Post(s)

    Default

    Double post ^_^.
    Verrekte Koekwous

  15. #15
    Join Date
    Mar 2007
    Posts
    4,810
    Mentioned
    3 Post(s)
    Quoted
    3 Post(s)

    Default

    ^ Spam

  16. #16
    Join Date
    Apr 2007
    Posts
    3,152
    Mentioned
    3 Post(s)
    Quoted
    1 Post(s)

    Default

    yay! its faster better, and is shorter .

    /me tries melding it, but you changed lots of stuff, and its taking Dan longer than he expected, went from 2 mins to 6.46 minutes .

    EDIT: multi line comments dont work
    EDIT EDIT: well they only go one after in your script, but they seem to not work after putting them in mine =\
    SCAR Tutorials: The Form Tutorial | Types, Arrays, and Classes
    Programming Projects: NotePad | Tetris | Chess


  17. #17
    Join Date
    Sep 2006
    Posts
    6,089
    Mentioned
    77 Post(s)
    Quoted
    43 Post(s)

    Default

    So.. do they work? I can't really make it up from your post.
    If not, could you post an example?
    Hup Holland Hup!

  18. #18
    Join Date
    Apr 2007
    Posts
    3,152
    Mentioned
    3 Post(s)
    Quoted
    1 Post(s)

    Default

    lol sry .

    on yours it highlights on character after the end of a multiline quote.

    the bigger problem that i can see is that when you have a full script in there(lots of lines), it weirds out because its tries to highlight everything after that until you close the brackets, so maybe you should limit it to x number of lines until you close the bracket?
    SCAR Tutorials: The Form Tutorial | Types, Arrays, and Classes
    Programming Projects: NotePad | Tetris | Chess


  19. #19
    Join Date
    May 2007
    Location
    NSW, Australia
    Posts
    2,823
    Mentioned
    3 Post(s)
    Quoted
    25 Post(s)

    Default

    I pasted my script in there, but it like just stops after my walking procedure:

    Last lines:
    SCAR Code:
    procedure WalkToWillows;
    begin
      if not (LoggedIn) then
        Exit;
      makeCompass('s');
      ResetVars;
      if (RunCB.Checked) then
      begin
        RunPercentage(20);
      end else
      begin
        case Random(3) of
          0: SetRun(true);
          1: Setrun(false);
          2: ;
        end;
      end;
      if (FindRockDDTM(588, 12, 639, 58)) then
      begin
        Post('Found', ' The RockDTM');
        Mouse(x + 30, y + 5, 9, 12, true);
        FFlag(2);
        Exit;
      end;
      Post('Error', ' Couldnt Find RockDDTM (using backup)');

  20. #20
    Join Date
    Sep 2006
    Posts
    6,089
    Mentioned
    77 Post(s)
    Quoted
    43 Post(s)

    Default

    Lol, this is weird. I took the script in your signature and it worked fine.
    Hup Holland Hup!

  21. #21
    Join Date
    May 2007
    Location
    NSW, Australia
    Posts
    2,823
    Mentioned
    3 Post(s)
    Quoted
    25 Post(s)

    Default

    Quote Originally Posted by nielsie95 View Post
    Lol, this is weird. I took the script in your signature and it worked fine.
    Thats a diffrent one, heres the one:
    [SCAR]
    SCAR Code:
    program DraynorWillowCutter;
    {.include SRL/SRL/Misc/Smart.scar}
    {.include SRL/SRL.scar}
    {.include SRL/SRL/Reflection/Reflection.scar}
    {.include srl/srl/misc/users.scar}
    {.include SRL\SRL\Skill\Woodcutting.SCAR}
    {.include SRL\SRL\Skill\Magic.SCAR}
    const
      Vers = '6.25'; //DO NOT TOUCH.
      {[~~~~~~~[Instructions]~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~]
     [~ How To set up:                                                          ]
     [~                                                                         ]
     [~ 1. Put players in Draynor bank                                          ]
     [~ 2. Have axes in first slot of invent                                    ]
     [~ 3. Start Script and fill in the Players Form.                           ]
     [~ 4. Drag cross hair into RS and press start                              ]
     [~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~]

    }


    const
      ClearBug = True; //Clear the debug every proggie?
      SRLIDBH = ''; //SRL-Stats ID
      SRLPass = ''; //SRL-Stats PW
    var
      x, y, HP, HPTime, willowlog, Chopped, Banked, Bankedd, xC, yC, BankDTM,
        Axe, responded, LapTime, BestLapTimeBH, II, I, BrokenAxeDTM, Answer,
        dsx, dsy: Integer;
      Timer, AB: LongInt;
      WalkAngle: Extended;
      B1, B2, B3, B4, ColorSign: string;
      TheEnt: TNPC;


      EndLearningToolBH: Boolean;
      BHForm: TForm;
      Top1, BywhoL, WorldL, CurrentVersionL, LastestVersionL, CurrentVersionL1, LatestVersionL1: TLabel;
      ExtraBox, VersionBox: TGroupBox;
      UseAutoResponderCB, RunCB, AntibanCB: TCheckBox;
      WorldE: TEdit;
      PlayerSetup, DownLoadB, StartB: TButton;
      Memo1: TMemo;
      versionBH, version1, Outdated: string;
      BHWillows, AxeDTM: integer;

    // When the form is closed, this code will be executed.



    function ConvertTime(TheTimer: integer): string;
    var
      RHours, Minutes, Seconds, RMinutes, RSeconds: LongInt;
      Time: string;
    begin
      Seconds := TheTimer div 1000;
      Minutes := Seconds div 60;
      RHours := Minutes div 60;
      Time := IntToStr(Seconds) + ' Seconds';
      if Minutes <> 0 then
      begin
        RSeconds := Seconds mod (Minutes * 60);
        Time := IntToStr(Minutes) + ' Minutes and ' + IntToStr(RSeconds) +
          ' Seconds';
      end;
      if RHours <> 0 then
      begin
        RMinutes := Minutes mod (RHours * 60);
        RSeconds := Seconds mod (Minutes * 60);
        Time := IntToStr(RHours) + ' Hours, ' + IntToStr(RMinutes) +
          ' Minutes and ' + IntToStr(RSeconds) + ' Seconds';
      end;
      Result := Time;
    end;

    function GetMarkedTime(TheInteger: Integer): integer;
    begin
      Result := GetSystemTime - TheInteger;
    end;

    procedure BeatRecordTiming(TheLapTimeBH: integer);
    begin
      if BestLapTimeBH = 0 then
      begin
        BestLapTimeBH := GetMarkedTime(TheLapTimeBH);
        exit;
      end;
      if GetMarkedTime(TheLapTimeBH) <= BestLapTimeBH then
      begin
        BestLapTimeBH := GetMarkedTime(TheLapTimeBH);
      end;
    end;

    procedure LearningToolBHOnClose(Sender: TObject; var Action: TCloseAction);
    begin
      if (not (BHForm.ModalResult = 1)) then
        EndLearningToolBH := True;
    end;

    procedure ResetVars;
    begin
      X := 0; Y := 0; Xc := 0; Yc := 0;
    end;

    procedure PlayerForm;
    begin
      SRLPlayerForm(True, [], ['Loads', 'Bank Pin'], [], []);
      Writeln('Current Players Loads ' + IntToStr(Players[CurrentPlayer].Integers[0]));
      Writeln('Current Players Bank Pin ' + IntToStr(Players[CurrentPlayer].Integers[1]));
    end;

    function CalculateDecsions: boolean;
    begin
      if (RunCB.Checked) then
      begin
        Result := True;
        Writeln('Using Always Run');
      end;
      if (UseAutoResponderCB.Checked) then
      begin
        Result := True;
        Writeln('Using AutoResponder');
      end;
      if (AntibanCB.Checked) then
      begin
        Result := True;
        Writeln('Using Higher Antiban');
      end;

    end;

    function AccessDenied: boolean;
    var
      I: integer;
    begin
      for i := 1 to 10 do
        if GetDebugLine(I) = 'Access to outgoing connection denied by user' then
        begin
          ClearDebug;
          Result := True;
        end;
    end;

    procedure CheckVersion;
    begin
      Writeln('Checking Version...')
        Version1 := GetPage('http://bh-draynor-willow.freehostia.com/willowcutter.txt');
      if (AccessDenied) then
      begin
        Writeln('Cant access Version checker, Checking = Terminated...');
        Writeln('Continuing with version ' + Vers);
        Exit;
      end;
      VersionBH := Between('/*', '/*', Version1);
      B1 := '//';
      B2 := '^^';
      B3 := '//^';
      B4 := '*^';
      Outdated := Between(B1 + B2, B3 + B4, Version1);

      if (Vers = VersionBH) then
      begin
        writeln('You have the Latest Version: ' + Vers);
        Exit;
      end else
        Writeln('You are OUTDATED, Updating script..');
      BHWillows := RewriteFile(AppPath + 'BH Draynor Willow Cutter ' + VersionBH + '.scar', false);
      WriteFileString(BHWillows, Outdated);
      Writeln('SuccessFully Downloaded');
      Writeln('Script In: ' + ScriptPath + 'BH Draynor Willow Cutter ' + VersionBH);
    end;

    procedure HandleButtons(Senders: TObject);
    begin

      case Senders of

        PlayerSetup:
          begin
            PlayerForm;
            StartB.Enabled := true;
          end;
        StartB:
          begin
            BHForm.ModalResult := mrOk;
          end;
        DownLoadB:
          begin
            Version1 := GetPage('http://bh-draynor-willow.freehostia.com/willowcutter.txt');
            if (AccessDenied) then
            begin
              Writeln('Cant access Version checker, Checking = Terminated...');
              Writeln('Continuing with version ' + Vers);
              Exit;
            end;
            VersionBH := Between('/*', '/*', Version1);

            B1 := '//';
            B2 := '^^';
            B3 := '//^';
            B4 := '*^';
            Outdated := Between(B1 + B2, B3 + B4, Version1);


            BHWillows := RewriteFile(ScriptPath + 'BH Draynor Willow Cutter ' + VersionBH + '.scar', false);
            WriteFileString(BHWillows, Outdated);
            Writeln('SuccessFully Downloaded');
            Writeln('Script In: ' + ScriptPath + 'BH Draynor Willow Cutter ' + VersionBH);
          end;
      end;
    end;



    procedure DrawImages(Sender: TObject);
    var
      Picture: Integer;
      Canvas: TCanvas;

    begin
      //Form Title
      Picture := BitmapFromString(484, 364, 'beNrtvXuQHNWV7tty+P7h' +
        'CM4NBDF2TNy4uCU1BCjUegw+ngc+ZnyvHb7mHubEzHhG5oCvwICNp' +
        'UGWkISkVqvVUrdoqZGQGBnzEsg2jwEEGGxs87ANNg9hkDFYYIxHIP' +
        'M0AxaIY8O9cfyH7yqt6pUr9yt3ZmVVZ1V9K77oyM7alZWVtfNXu76' +
        '99t7bj1073meo9+ie951Q0wdOruvPT+05/pT3098V430rrPKsS4b+' +
        'Pq/GtvaJtm5xaO/evaPnf7yw6On6JUTDHq3yaEladH2mz+j50Ek9d' +
        'Hxn+cGxeaKh8RNFG5XGNycaHfq4U3LxSaPLPm5r6p8d3ds37YT+fv' +
        'o7tuLk1KOrEk3p6Zl6RA+fNkn2j62eJxpdOZeljzm6du76gTmJhhM' +
        'NrZ0tGtkwXTQwPM2p4XXly3hfcg763AYG+t1ansg4zspFsxw6163l' +
        'Z8xkUWVYuWAWadWSJT5ReSq2/AszWcah6AQ+dVyP74UC0vUkpvzAe' +
        'f2ZGlo0O5d8x/Fet4mLQKJrsmTBCXWdloj2nz//eFt598cUoIeW/v' +
        '3/zlrxj8eIVv/zh23tPRyDp/USZG5d0MN/H7rov+TdZkzRhrHNB6c' +
        'N+kuS1yXMDozNMMSgJhyxCNTMarukT5G4Xj82gzW20aESWD1xKHkh' +
        'Q/qc9VfPigjFsHpjGtFuVo98PJEL1HVcC2PXnCwitLL0TpJmNeP6p' +
        'Dk16e+C8ZETRWPD80TJMYfnEa5FmtUpjc3I1NDI9MIKHFbel/e1Ir' +
        'i9cuksOQ5tJ8rP6hCoF8zie5yRbotAXTuBBV6mOWXXE2exvNzOy2o' +
        'ft/OyOgzbBpWX1bQzzGqNXN7mf2O2ecO5vf60I/kvi4lNcrKaKwAR' +
        'm1sazGpSPKsjiQ1WO1ktv2j0bUjbNqt9MlhN7cZ4VmtVnNXyvhpkt' +
        'RyneawOULowq331BKzOKwF1TLuaca1ZTRvC4QLbgmve5n/pJWJYTV' +
        'WXbRD5vc+sPnHBMSRd0vi3ALGbxGrxcHiD6rC+nWVP9VnNp8p/C7M' +
        '6Ufuz2v40Q68Vx2q3Fs3i14pkdSOgTqkQq3U9CbDavi/A6sKsFg9E' +
        'iF3KtjTUGddhVpOomOHjGXy2uV0M181gtc9vl5td2iGV9UBqWvVx9' +
        'jAN3nYzq/Vn12xWx/jAMazOB+qcHgiJEMf1hDZ8ZQTUzvsCrG6Q1c' +
        'X86kwfm0DNL8Ty0ZXKDCg/UCitFQlqvoNCnYwbZ/i0t1D4/HbjZrd' +
        'xLbrAI4PVsq35nJfVAW7z72Kjz3Fs/cm55ONzjMYumufUutG5TsVw' +
        'u7Dszy77O0Kx2sftTFAHfOC8rJbyJB+rdRkt3e9miOuJuX9BIj5b3' +
        '30R9kbK6k90sppv2Hb3QAr41QEfWzew41ktPp7he8zv74mHdiOsHl' +
        'sXIetZPr/d5++B1dVnte+zawar433gvAbI5LLad19MIqvhV9vbxVh' +
        'ti+FMrNZmddjHXt8Irgux2ue3+/y9yrLaKcIvn3aAzx/5q4/+7Sc/' +
        'QX8LsFqeG2Y1n0MMq8N9BwVYrT+7ZrM67ANngprTP5rNarcsVvvuC' +
        '7C6gn41bxdmtTCZWR3wrieX1SzDb9e3MPt76/2/BcDqqrHa/uyifP' +
        'KiHgj3LdZznhd5feMwqKvGapaZT56VHwJWV4TVvkpOZXx9PQPD0xb' +
        'O7LHHO9T4fPgvbzgVwLVzvMPImulODa+a5pQel0ESv13vpLfAvxkD' +
        '/Vkx3KZLJH2Rq0fnkphFjbB67KKTE3k4rH+bOwtM/bOjmbek3r5pv' +
        'tdKaQLUgefq89fnsGFsnsgeJBXu5y0g/uwKsDrF5wtnJfKwevl5M/' +
        'm1aMPH6jCoSdzw9uE3l3xM1szxlTFOO8knL2nsTF4+6++Rssa8ZI6' +
        'FCenvE2lW+7gtHohO2yilY9FwsLl7sZ5uXQarzT5HD6hbz2rx21vA' +
        'as2i5rHa7vMyCvCoQ+Etif6NZHX4uU5QG7h2strXz9vurM5sVJcI6' +
        'nJZneSTV5jVLVVRVjejb9EeF1PPtS7EaqccfY6usca5cN0gq52KyR' +
        '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' +
        'QduzFFwXYHXz/Gq9zXVmaOVsknGh7LxTH0iff/bxdmQ147qRkP5Hw' +
        'sLCmXVW63b16EginqEuntXOPLotl1yS7mQ8FOgNtF9LWP3fhz77wG' +
        'P3ykNOVl/3zTMeuP/SAwce/e1rz+hXpD3bLt3e2zedTsyZs/eqKk/' +
        'x40eu1X2L+vporpLuvm+bPOuVV582HiWZYzrUQ6ObPvbjB6+hZ9XH' +
        'bb176Kl9d3/1q//s5nOQ1Vfs+MIjD9383C9TZCM2EuuuvuyySFYTA' +
        'O3Gj9xTX9k4/+EnEs+ZcM1OSOZi6KLvffvb+uBPPfFEZvObTl6j+9' +
        'Khf/Kt8/jU43dLse/eujVmhEvhsTCa2zHtaidmd4yc+cYbbzz7VOo' +
        'jo38fuu8mPVbIPo4eWLRj6Mzz/z7E6vu/lbKeXt93b9ivvvWatVL4' +
        'rTdf8fnSe3Z89rUn7vgfrz0rhf/ne+8QVJ/9ztizt63ds/UzXJ45T' +
        'KC2v9TsvFOfB3LXjeNtyuoGOd8aVht5dMYRbvq383Kx+vKr/+75V/' +
        'YbD/Hny4i++qq/o+Y6MTkze/DhPbucrN59+4r0cNdDkaw+eDDxSP/' +
        'tlmXxrNaQN139n94Sz+rdNw69+4eMN/7uH/4gjdi8rKZ76uMnT3vx' +
        'RfP6s3EtTkgMqzdv2GCclV3mX7ds0WUMS+S7N2/1sVpfhE2rP908V' +
        'hsq4IHceOXaP/w+4yOjAlTMiet777hKit1721VhVv/ut78xjhz2q1' +
        '/6adKvR+C1y+y7Ycnv/2N/5o3G5fkm5ZUNbVYbeaeCqZ89dGfS0Pr' +
        'DO02CbXuxWtQkVoueffZefQRq+spDOufZyWoCtRPCmtW5kr1/9vNb' +
        'nWNhjGI7r/9iJquv/ea5Gu82qH2slra0Lx54YGcMq3/9q0fi3zg1s' +
        '51mtc76sG+oGZ+a9vZbB+2j6RExMaBmEZ/1QYjMxtN125v7H6/ftS' +
        't5C/seca7zSHBWXwGHIgk8Kaw2GtLhoML2EZ577jkp8OZvXwywevx' +
        'fPuaw/Yf+IuAz65KPX/bPRhlqTkeeOZcnDssStEYBzjtlk602LniC' +
        'UTs3n5PK7dyxxF5A3HlA2e8rb+x3sjpQvsX7J4vVd39/VB/hwIFHx' +
        'ScxUuns1/K1ljmv22A1Fd6zZ9fXv366vDS14enlTA5//XSb1XufuD' +
        'X1C/2ZezJZ/e/790j5x/bujmS1flYgNmz4mzCrX34pBfw333zpG1c' +
        'uGVz6l+xXD69eTW1pbSDwgMFwTrUN5IMHDzpPT4CZOeKGM/FYT/30' +
        'bn0Qbidr4GtPm00SeiO+7whB63dv3Zo86/G7K8vqF/fvS31kr794z' +
        'SVfufCs/8z+JG1QW9qYO4WeYh9HF3jiiSd8hueBAwfsD+4XN1/o85' +
        'kJjLYBImUI3Waz56E7v7dsGpfZsW7+3mvPFVeEn6vXCrfZqPtBuMx' +
        'dN45TQ1rKfGXjfI0vo7xxQH0cZ3ljf8z5xBynSft9rNZrfDeD1QTP' +
        'VKL1a8+wQ2LnPBuv9fOf3yoQptb4lVecynnFZ33uLwznhArc8a0LI' +
        'xv2Tzxxq70O4xU7P2d+fJs+5sSvuM268JZLT4lh9Y8fvEbjnZ7Fn9' +
        'TyHefaTesAq40W9SM/uVkPWtT8NLrnDh06FJjrwziHR39Uz1h+59D' +
        'By7ZduGnZpxmSlw7908BZ/ayYhWZEt167LtXUT7eTjYa3+Db6G2fz' +
        'hg32nCR0nOTX97XrcrN6kZKnpG/eP6Nk0v94xvGJXC3qh+67yYd0e' +
        'sjZupbG86+e/Ik8+s2Lz/ONhXl5/1M2qwmnPr/6tSfuSAaKPnKdUe' +
        'b5H12RanH98HJnrvXPrzn7rRcekwa5j9W6b/Efzv/PP7jjcvp2kEf' +
        'ffucg7dTsMvoi7QM2GPbxfa/bmv2TxWrb3HDmPNvFdDu83ms5kVds' +
        'oDg8gJEgn5oP8LVnnGvmHnzrJV3sW99eH2C1pq6zV9HJajFMmO06C' +
        'W3H7jHnTAi2rtu1NDX++jf7UqPLrTwQY8zgNy5d4supdp7t/T+8tz' +
        '7Pv8JjJKgNVtvjXPSj677814ZDwkegBrYNcP1E/azaF0r1WE3t58z' +
        'WcqAFTk/XrL75axcmiVUPf8cJ6rWfn+Xjks+v/p/vvaMNEKPM//f7' +
        'g4bLETM3iI/Vvjh46OCmzRdKn6N2CXRfZOmsto/ve93W7K8mqzldx' +
        'FnMALVTdg5wzAk4WX3vD7anqs3BlwKsfleZM85eRR+rBdQGq//6nL' +
        '8ITHGg9bs3U98p2zZ+Nsxqo8Puzddf8uVUO1xuwyJWrI4EtR7eSNI' +
        'jVmqDVjafLce8bsdSo2PRHh1jZ4/oUTZ0cKPPsams/tfx5ZGsNpyN' +
        'zav+IcxqKqDLv/3Wm/Raoq9feZE89P++9y7vNFhN7e3ke3//U3/84' +
        'x+1CWz71T/e/H9KAcKy7WnbvYeR6zDGs/q9P7xz143j0udoHMHYXy' +
        '6r7eP7Xrc1+6vDap3Xp+dcMoq99dbLmaB25gAXY/XYxWaF9DkbBOf' +
        'MXkUfqy+78nNGmaG1szlnOIbVm8Y+HW5UO/Orjab1RUs/5ZzrwziB' +
        'OvossR1KuC7AavFV6o327+yUw9K20RNqJ5DY2SN69DoPXW8Nq5mQR' +
        'knaY7N63b98Mlej2tm0Jj5rXBO9k6bC17fJfmE1tbelwO1XrtLzbD' +
        'x87/W2X60tDtq2PW0zk/zacyPnBsmLViL2D+64PG8iR+OsrloeiOT' +
        'u6jEXmtU2t23K+eZ60jKWEXeiknDN8hFV9xI614Xxzec8NjzPkHFk' +
        '31t++ul7UhXy8d1GAbtX0S6jZbzuffdus8vQR8B5aEbhgeX9Isn9u' +
        'P8HO3WZ3dcNxcxZbQzc/uG3r5Y8vdpAdQ+rOZ/Z8D24RR0DaimvBz' +
        'kajeeXX3haitF2wvD77vMlkBgDHvXXkEwJ5VzT3Ly8i/t9Mlm9yMF' +
        'zH6tJRl/kj+5MJTnv3rlyxenHkHT+hi1tdNRMiT0/1Kz+xc8Ti/6h' +
        'B+7SD/Hgl1RtP7N///4k0e7VF5+1feb33krs4n03LLG9aJ3OVzfSb' +
        '1sbnickJkfu4gtPoXb+zx66U/cqMrGNJJCuytnTuJ5EVr/33iHeGd' +
        'P8DrPaN59zYVbfcvMy41RtVhu9ipduPyWe1c4yuVht9CqmDBD/nNW' +
        'GDfLcvodjWG37HvGgNljtM6Vrb3OimN55w2UX6FfRlrUxR59+ljHV' +
        '6mSxWlrXrOd+8RNdZvuaU2JYTa3lVGv8wHMayN+94xvJCJffvqQfI' +
        'u3c8N+1AULoJlzb+c/iLX9v2TRtgDj9Z22S6ME1tL+AX+2kEzWnDW' +
        'LTT4A2YnXpbXvGdctYTSA94XOp1c1eeGFPWay253P+5Fl9F1+z6pd' +
        'P3/NCMDUuQFcjS5DobbD6sb27kybKq08HDhXPalYMq999N3V68XNW' +
        '62f98Y9/NAbCRLI6xqM2QM3Sx9HtZ8Yywfyrw6mUsA2L/kY/Xedd6' +
        'zn6dPa1LGFgq0FW1/2cNKsZ1z5Wa1y/m56WmUEdZrX9RSC+tMj3uk' +
        'ar+/5vXcYtbT0uZs+Oz+rx5oREnYnn85+NVBCJ3//H/rtuHM/lV/v' +
        'yinesm2/g+tZr1rZLfnUzfJiacd0SVjNIT1ma+ka+88GbI1nt6ygU' +
        'VrM4r35s+EJ7eF0BVj+oEjwo9u/fY7Ba9yrST8vwoH7n60YWLlAmf' +
        'uqkYicQP+wlwGrtS9fGad5/C7H69l3DiSn9+0PG0zXJ9Rx9OiPRsE' +
        '0yr0BeVie4jmO14Nook8lqJ43tg1NzOnGkb7pCP0RgTxo8//IxZrU' +
        'eby6ONP/V+XLX71gSmOtDU90IapAf+OHlkX51IN+YmnZvvXPQHrpY' +
        '/fzqBlltHN+J61wtQ+lzZOm+SFv8vbPhspTztnzHub7y9vU/vE76P' +
        'IeUv7Hza5/TdlwUqwfm+LRpgzna66KNJ8m1uunfVK/iu4d4Zzwf9E' +
        'P2SwdgIo26wAFzkapwmQKgNrRz/ByjB7PWcr4jsUP3P/PI0DmzDTm' +
        '9Dp16bcx8kvnuhpbO9sl3HQYX9xoK47TmHp/zYZPVnnRolq/lbDyR' +
        '2Pv965MkT2pIy7OI28m1/e1vGNSDp/VeO5oYIwdf/41A1Zh/w0a04' +
        'UXv3HxOYJj5e2+98vNrzrab1rnymQ1iUKM9M786bz5zxfOrW89q/u' +
        'p5fN/j+gifPKsvF6vpCAFW3/iNL5m15d1DP3ts9/W7vrhp8GPrl89' +
        'hxbOa9OrLqR/p99yzTa7VK68kDz322C2NEzKe1Q3itGWsDoPatqbZ' +
        '8XjxQHL737N7m81qArhhWRtDGotdARvUgetQgNVh5AZAnclqPYRcJ' +
        '/U9vueHtgFCrCalft5++Ugm8A/uuFx2PvOzH9krczm96H03LHnrhc' +
        'd8xN6z47Nhvzqcbzx33pG68PPPPp6ZX503n7ni+dWtZ/XUI3qO+mj' +
        'qsr/42vO1U4pmNf/KCLDasJef2XfP6Nq5LAF1XlbfcsMyI9GaL9Ql' +
        'Wz+TypL1zMBcmH4xhY0pNYqx2jlvUimsDiP6uA/28F/Dsv7+LanJG' +
        'C/fMN9mNQE8+ZZ84Bbao5NbXvnN0yV+Fs6SNqgjWa0diQCrw5B/9/' +
        'dv2/Odaidckvp0Oh+1sTWrX3n+KW3f8aper774rGEOS6Pa+Vf70nu' +
        '2fubhe683hslwXHzhKWEPJJxvnFnebhjnymeueH5161lN+pnqiavd' +
        'hpePBQr7sqB9rP7Rvdt9oG6E1SSjC2/XrnPpQlFD2pkA3EpWG7NAy' +
        '+C+sIw8EN/JN8jqzOa0sNqA87vpeedsUJMI4AmZDzxNe/Y9lswucs' +
        '+3tnEHYgVZ/eKB51J5IMtPiQG1kQfy3JM/sVn91COpJGrnMBnN6rt' +
        'vSGyTx35wA0HgCZVgIz0UxOH1px0ZILbtY1OD3LgUrz1xRyN5F5nl' +
        'Oz5nr0Cutd07puka5vyl208xnr5p7GPFsyayzIpNGz6m+RxgdcCrZ' +
        'D32aGrIBv07tHJ2avCXa3XXFrDaWLjQN2N/OL/a1w3XCKuHT59Gis' +
        'E1SYPXCOaw1sgXp7N0Mfr3vT8krcqrN586cv50VjNYPbx0migvq7U' +
        'pUUtuv3u3s5ghKpb6yCbcDK0btn45saz33EU0fuiBu2wTm0FNumz1' +
        'f9WWNe359lXJ4Pen99zOiKa/xAcb12Ef28D1e2+9UpiNxmx7YHULW' +
        'P1qevLP664ZayjDLaszrrazJFZffqkJk5dffjnTQ2gBq41ZoAOJao' +
        'Fxiz73pjCrGdSRrLb7ClNfi4f9DSerXz3wi2QAyPcvT6F7AtQkXwO' +
        '7MKtH1kxvhNW6retMh3ZKp3nodA4tI2ua2Kuf9d07viFHE1ynhuUu' +
        '/i+vPp+0q2/ZtkBYzbh2strnY9/55SMDAMzFRgP7zqVhwOoSWb0/n' +
        'eF88OBLYVA3zuoS29XUij74u5d8PMlMD2seq43khxgbxDBAAuvSFm' +
        'C1UDqS1SQmsHYwUn1e31jvY7XB58T7evwum9V1LZ1dIqvr69/5WT3' +
        '4pV4neLWHbIwKd8owQDidg17axrWeTO9bV60Kf3EQq//9Fw9KgR/f' +
        '+bXU7XYY0VrcuhZohL1re86QAvnVxloDkgfSbfNXt4zVV17xOb1gC' +
        'gftLJ3V76Vd5ad/cY9N6UsvOuXVl54uwOo7b13vY7UxPq7FrNYDQG' +
        'Ka1kajOuDe5Dpbg9J5WU1Mdl7bS1Z9xsfq6y45w/mUu765OsDqzOy' +
        'OvO1qxjVz22a1E9d6mGFM09qYzvTCHec5QW1kTeuuxl8/+2SmtaLL' +
        'UwPbZrWB67B3rQc/UvDMqJH51Ts3n0MyZkZtu/zqcvenWD0xJo4Xr' +
        '7Tl9Rk81vQ3d5774APXOJujN123zPcqGa8V1N6f7jaesu/nd1+0+i' +
        'S+PXd97dzHHr7FeXffdPUyvpdl4ojaeOQ0ruk4zudG9iryIiyB0SX' +
        'FUMnPPXQo9SX1xhtv+I75VLrzSE4+fiyM/HzWcoKaNPL56ZkaO28G' +
        '6WtrTnZeXn507MxE+rnOp+xY/XHN6pSWJ2qI1aumkZjPIuK2k9VOX' +
        'Bs9jDoj2hx1uOcuXfLRfT+pfTu4PgXDgtahDZCAIRNw0Q1cv77vXh' +
        'lC6PSudT6JDI1sfEwfv2iX51cXY3WByAR1YVZf+dXPRZ7Dvp/dnU5' +
        'aO3T5pvlhVpOcq6JE9irWaridf6Ia/DZaM2FSW8h+YtDcyweeNkaU' +
        '7N459MTElKG+dWHkOM60MeMEJH+gGawm6c7B+vwDv3wwzGptWU+0u' +
        '96utbrzs3ps3Yy8rBZiz+/vCbSrazqzprAF/fZbbxIhr7h0kB+ljW' +
        '9dterg66kVEp954Sl5rboDY30Wzgovh83MIQyU17iWVu7PHrqTOPz' +
        'za84W73rfDUv0Ork1w/OFx4vNX20EvVbk/NWdnV/dAlZTG/vSi0/J' +
        'BHVhVpOoJR8+h3ffPXTTrlor+uAbjgb/v//yER+r6RLpuZEjexXpi' +
        'cxhd65g2p/hYjGsJjhrULN+/Uzu9RYDoG49q3+597vGK/7ots1hVu' +
        '/98Y0Os7ooq1n6OhOWSQFWMzCJn2yGhFltE9toXYeDW9T0WnTBnZT' +
        'mk3l6z+3GE199/omAwfLrZ580ygc8GcF1/GlTA7vY/NWpL7J3Dhrz' +
        '7HVzfnVTWU2UvuWGZXyEprKadN9d3jXB9//qkbolsmg2NaTtAr974' +
        'yUnq6XRazRNA72K+rnevG7LTg8U1uMWbVCzbr12nTF7v+M9vvmmXs' +
        'c8MG6uxay+/cpFxiveuO3zYVbvvsJ8Cu1pkNVaYVaL9cGsDnggmtU' +
        'pndZrN54dt8/rvxm9diXzmVntw3VtPMu1K42nf/uqrwRYbZjnmWmE' +
        'uVj97HfGCs9fTY325599vDZ5lJqvqWvnRHWyWsumaDyf9//6kX1P3' +
        'X3Pd7ddsukzgT67gMweQKOAvyuQgPzYw7ccnFgwhTboX3Y5tC998Z' +
        'r/6xd779aN6tuvG7ZZrd0JI5/Z2atoG7++d+Sw3KOnTrLneavp8Gx' +
        'IV20++9Ef3aKXHeSG9KMPP2zMklEKq+3362S15q1Tlyw056qlPbQ/' +
        'MBeWMXaj9pSl82psX+LRykQxrGbZJZnhooUze5xUH144ra6zE2lWS' +
        'zP1m6P/be8Prt3/i1RyGv1LO+kh3btHr+Xs9SPxd8ffftmcJWbT2R' +
        '+mR33sveLSwXjDRHBNx6QTe/nll6kZ//q+e/VseO+99QrtuevG8Tu' +
        '/fKRv/mqoBazW7d6wori6sgEtzSmVD6B9aZ9sUBszuTl7FTWZi103' +
        '3zV0zt3kZLW9bkvARQ/PHSRj4vR4NwPUzupUgNVOOY8fqMb0N5LVA' +
        'ThnysdqnR+SgDqC1fEKsFqIbXja+tGYXO4Yae9acziQdw3MVpDVMX' +
        '1tmazmxJUYVttrLJbFaptyev4Nu1cxDOoYVjveS4VZrUFq/MhlXNu' +
        'sjqmNTlDr49v+p4Hr2kFayGpRC1idCWpmNW/7ioU5LITXe8K4jsm7' +
        'zlTV8pmrm19dBqvzThkRALWsqR1mtW+NxcZZbSNOT3Fv9ypmgjqT1' +
        'd73UklW2y1euSV5gwpoVhdoPwSOb7xWLK47mtXCWGZ1GNcxR5Njxr' +
        'SuM/Ouwx931fKZ2yK/2qdM/hScM9Oa2l2Duo7rCd7anXG+NRZTIyC' +
        'Cc/g41+PLHCFo9CrW6qpnRI9v3WF7HQffe8nwQzxrvzbCauc4C81q' +
        'Z4uXN+TfvQ2HE9H6VZwE0M81+VwSq70MV32Xm5dMFW08R+n0RJp1q' +
        'ejpcSsuFs7sKXzNhc/aQok0Q6hiOP2QTL+6avnM7ZJfXYzVhSeiN3' +
        'AtrUqNa9r2sdq3xmIkpe31+CKHB+pexVoNH5jTOKt976VSrLZbvEb' +
        'nUeQP3ngZI5fl9o8xQ9qC1UzIEpXpaQckJ2P73mFc8zd4wLsOux+V' +
        'ymeufn41fyKaz/rfAKsbAbWBa81qxrW2oG1W22ss8tts/JQCQ7N1r' +
        '2Id1EFW81vIZLXvvThZzcdsJatta8K3pl652771/jJ97Dquq81qw+' +
        'zNqxj85n0unZLte2d2NcoPLv5Ct/2QsKqWz9wW+dXMZ5vbPlaXBUP' +
        'dViQs0zl/6jjTdvbNxcRrLPLbJJUOamO+I+lVTEDtZ7X+jRBmNct4' +
        'L86cEH3M1rA64CHbnqThJze47ZuEM/O5fMJVZnWDoM6kbrHnOn3vz' +
        'MwQ7Y8JruNZDeXKAzF8qkg/pEQkat+YQH3SHNN2Xn/+HJb9XEIclS' +
        'eVDmpjGg3pVTQ8au11iGzvfd3oXJZvHWHGNb8X51xV9jHdfkhOVod' +
        '9D2eL2pi72PCTS9l2zo0cfq7hmY8P9CXaUI58rN6y5ihWpDlMuK7C' +
        '7e9rXRteSjauJ/pMa7g+0/SugdnSc/Zsn6plrBZcB1jteyK1RZvEa' +
        'mMhP+5VtDsTfaC2vfdMVst7sVntO6aP1eHVxmM8ameLWuDpW4PPaB' +
        'UX3g6s8ed77qSzml60tnFBos1fmpro/0lUHQLE+N4xedca12B1U1k' +
        'tPpVhVhdg9Uf+6qN/+8lP0N8CuDYQnauLsAVyZn2EWa29d4PVdk61' +
        'TgvR+w1W62M6WR0GdQyrYzzqqm1rOLSe1XVQu1hdcQiEuxqL4TrXC' +
        'SCPOj6/WlrRzOoArjNZPfXPjmZWk3r7puXOu64qpQPpeU4PhLR6dC' +
        '5776sn3A/Nal9OtW+/eNd1P9+fE1Ibh75gViOsjvSoq7Zt+NWtZHU' +
        'C6jSr26XNlonryFGNGtdGBibyq0vIr1a3PP32sdOefbIJQHA+ob9f' +
        'WE2if8WLrhp7G2H1ujR+RYNj80TDW/vYz6GNke3HiobGTyT5cqq9u' +
        'dYTfggfs8Zt1feqB/IMnJV9qRv3qKu2Hfart24sR5rbW0aOEjlZ3V' +
        '4/sb24PutIVl5cywRWyK8uLb+6bFYLqA1cc6uvHSltt6UbZ7Uvp9q' +
        'bax3B6tqnGfedWK5HXZHtSrG6HR1RB67PSuE6H7EjWI086nz51dFw' +
        'LtCuZmlWt4DYAf8kl7USyMeLZLXIZrUvp9qba22tX2awOh7U1HjuG' +
        'I860q9uMavbtwPLZrWN63hi16AdZDXyqPPlV5fKahKxWuOa9tisbp' +
        'IlYndN+pRN6WDudOOsZhk51RvHT2SZudautSb13K3xoPaxuk096ki' +
        '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' +
        '9WS4t4MVguom8pqxnWA2Darbc85ntV2TojsjGc1a0pPD1V+rvYk6X' +
        'ZsO1b7NnQxlpPV8qjd2LZBbR/K2DY8kLCHpj1/9lqJ4YkBkt8DIUo' +
        'zqwO4zvRAuG+Rz8foW4zxQAjLzGoD104PhMT1mV6rVlcXZ8uotzao' +
        'I1mdytlrsgdCyGVWR+Jat4FL8UC4P5Gvc4E8al+fQont6oSTis8rT' +
        'j8m0T+WI/rlRZo9vYc3ZJv+rjjrGC2fj+F1SFxiVgcKpFitleY2VX' +
        's+W81breUe6Xk/JE+vlal6kaw2IOxsNn/igz0in2HibIdzgaFlJ+l' +
        't1polf8MKvwuNYv79ngK1Uu06nzuLlHHA5f0LZ/bQX9LQ2tkiSeoz' +
        'fOzVafyyapVnbB6fD21o6WK+djthmc4hzGfjHq97botmJRMyBCX1d' +
        'vDMXtH6s450auM5U0Wa2/Q2JetPs1ozysfqFUpLtrpl5OzRNYlvUR' +
        'veclms5uuc1/ewzyeez6TzzzieVRarMa4f0XbRtaymdnWnstrnLU8' +
        'Wq33nUzqrE1z7WY1JyRBtPcWZwWpRg6x2avVhQ7v2MzDI6kzfw/fb' +
        'OZLViZrDan6P5bI6V6PaMRdKGawukPvhO58YVrP/UxarQWlEBxC7Z' +
        'azW7atOZbV+j61ntYi95Vx9i9wLVi6rJfeDzyevR83EJlDT30xW14' +
        '3i0x0CqBGdhGvur5T7yMdtH2P1HFBOhjtyoTP5rM7Be49/YabImwP' +
        'gkWb14GmJ1p92ZCLNbdX/qFk9smY6y36PzvmBW8Bq9ivWRI9/0eOD' +
        'Co8lT/FZ5SEMruite2IreuN9DyO3vDCrAWpE5+Fa87AYq3myPh+oH' +
        'bnQbctqQrTgWoPafo/VZ7UxPqgirBZic255FKjBakQXsLp2+zTGag' +
        'a1PefGan/edSar6+nilWS14NpmtX6Pk8LqzLmeDPdDjw9qBqtF8aw' +
        '+7oM1RNNfYvX5848vxmqAGtGZuG6A1QJq55wb0sBm39LoW4yZ66Oa' +
        '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' +
        'SrtRftZLUt3EHdwOp6uvXybFALq3lMui4p/4LVCITcccxnvl8E1Hv' +
        '37nV6ICz2omlDDJBMVsMD6QZWp/oyolmt+WxwO8DqwDZqGqJTWc0a' +
        '33zixvG6iNWyTRpSGhybx/4GbQxv7cvU2IRwB3U2q+2+DKOAg9WH9' +
        'xvzXeungNUIhGa1Mc8wWI3Iy2pfX0YMq4XYRj0EqxEIm9XUqGZKx7' +
        'SrRWA1WG2zOjVPSByrZb5r3ka7GoGw7ziiNLNa4xqsRuT1QFj1vHr' +
        'XQ2EPhDaY1RrXYDUCIXfcqiVLFs6ss1q3qzWuhzwa2X5svHAHdQOr' +
        '67maEaA2PJD1A3OoHhqTQYHVCESY1UbrGqxGgNUIxKSzmuRkteA6k' +
        'tX1OavB6i5mdaT7YYJ6+RznQnJgNQIRyWrGdQyrU3NWg9VgNViNQD' +
        'SB1SQD0ZrJe/1hg9qHa9xB3cnqEKgHMgRWIxC5WB1oVxOufbm1YHW' +
        'Xszqw4EvzWD1lyhTUNERns9rAdSSrpVFt59aC1V3LaiefOTfPSKv2' +
        'UZqrUF5WE6hvvm03ahoCrPb51WyGcG4t+ha7nNXhJRQ5d7qeU+0Hd' +
        'QFWM6jBakQ3sFrjOi+rKThfy+ds4w7qBlaHKZ0aQm4gemLBZW2mgd' +
        'UIhI/VgutcrGYxq9Gu7lpWZ65LTkx2zPuhWG2YafGsJlA/NP9/YaG' +
        'mIbqE1YzrAqzGWJiuZXUmpQXU9Xk/Biyz2mI1KS+r+z7z1yTUNET3' +
        'sJoEViNiWB1DaQ1q2mBWm7geTon7PsBqBCKT1ZG4dnJ7jUu4gzqs5' +
        'kRSugbqNIdrY8mHTTjrxSxGx/sY1EMXXxspZvXR/9v/SkJNQ3Qbq3' +
        'MRG6wGqzMp3WxWw69GdPAdt3H8xExcO4n9vhPqpiJv6IRqsLrLWT0' +
        '6MtdJ6YAMVrPiWc24vvm23Zu2jKOmIbqZ1Qauic/Cagb18ae8X3AN' +
        'Vnctq4nSrMliNXL2EB3M6gK4ZlB/6KS6CNRgdbfVHFlJWSSgNuTkc' +
        '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');
      Canvas := GetBitmapCanvas(Picture);
      CopyCanvas(Canvas, BHForm.Canvas, 0, 0, 484, 364, 0, 0, 484, 364);
    end;
    // This form was parsed using: DFM Form Parser v.23 by Ron.

    procedure LearningToolBH;
    var
      TimeLearningToolBH: Integer;
    begin
      TimeLearningToolBH := GetSystemTime;
      BHForm := CreateForm;
      with BHForm do
      begin
        OnClose := @LearningToolBHOnClose;
        OnPaint := @DrawImages;
        Position := poScreenCenter;
        BorderStyle := bsSingle;
        BorderIcons := [biMinimize, biSystemMenu];
        ClientWidth := 485;
        ClientHeight := 365;
        Caption := 'BH - Draynor Willow Cutter';
        Color := clBtnFace;
        Font.Color := clWindowText;
        Font.Height := -11;
        Font.Name := 'MS Sans Serif';
        Font.Style := [];
        PixelsPerInch := 96;
      end;
      Top1 := TLabel.Create(BHForm);
      with Top1 do
      begin
        Parent := BHForm;
        Left := 0;
        Top := 0;
        Width := 487;
        Height := 57;
        Caption := 'BH - Draynor Willows';
        Font.Color := clWhite;
        Font.Height := -47;
        Font.Name := 'Lucida Sans Unicode';
        Font.Style := [];
        ParentFont := False;
      end;
      BywhoL := TLabel.Create(BHForm);
      with BywhoL do
      begin
        Parent := BHForm;
        Left := 24;
        Top := 344;
        Width := 258;
        Height := 13;
        Caption := 'Script Created by: BobboHobbo for SRL-Forums ONLY';
      end;
      ExtraBox := TGroupBox.Create(BHForm);
      with ExtraBox do
      begin
        Parent := BHForm;
        Left := 24;
        Top := 216;
        Width := 233;
        Height := 113;
        Caption := 'Extra'#39's';
        ParentColor := False;
        TabOrder := 0;
      end;
      WorldL := TLabel.Create(ExtraBox);
      with WorldL do
      begin
        Parent := ExtraBox;
        Left := 56;
        Top := 96;
        Width := 34;
        Height := 13;
        ParentColor := False;
        Caption := 'World?';
      end;
      UseAutoResponderCB := TCheckBox.Create(ExtraBox);
      with UseAutoResponderCB do
      begin
        Parent := ExtraBox;
        Left := 16;
        Top := 24;
        Width := 201;
        Height := 17;
        ParentColor := False;
        Caption := 'Use Auto Responder? *BETA*';
        TabOrder := 0;
      end;
      RunCB := TCheckBox.Create(ExtraBox);
      with RunCB do
      begin
        Parent := ExtraBox;
        Left := 16;
        Top := 48;
        Width := 89;
        Height := 17;
        Caption := 'Always Run?';
        ParentColor := False;
        TabOrder := 1;
      end;
      AntibanCB := TCheckBox.Create(ExtraBox);
      with AntibanCB do
      begin
        Parent := ExtraBox;
        Left := 16;
        Top := 72;
        Width := 121;
        Height := 17;
        Caption := 'Use more Antiban?';
        ParentColor := False;
        TabOrder := 2;
      end;
      WorldE := TEdit.Create(ExtraBox);
      with WorldE do
      begin
        Parent := ExtraBox;
        Left := 16;
        Top := 88;
        Width := 33;
        Height := 21;
        MaxLength := 3;
        TabOrder := 3;
        ParentColor := False;
        Text := '108';
      end;
      PlayerSetup := TButton.Create(BHForm);
      with PlayerSetup do
      begin
        Parent := BHForm;
        Left := 304;
        Top := 232;
        Width := 137;
        Height := 25;
        Caption := 'Player Setup';
        TabOrder := 1;
        OnClick := @HandleButtons;
      end;
      Memo1 := TMemo.Create(BHForm);
      with Memo1 do
      begin
        Parent := BHForm;
        Left := 16;
        Top := 80;
        Width := 225;
        Height := 113;
        with Memo1.Lines do
        begin
          Add('Thank you, for trying out BH - Draynor Willow ');
          Add('Cutter.');
          Add('');
          Add('Need Help?');
          Add('Post onto my thread:');
          Add('http://www.srl-forums.com/forum/bh-draynor-');
          Add('willow-t28864.html');
        end;
        ReadOnly := True;
        TabOrder := 2;
      end;
      VersionBox := TGroupBox.Create(BHForm);
      with VersionBox do
      begin
        Parent := BHForm;
        Left := 264;
        Top := 88;
        Width := 209;
        Height := 105;
        Caption := 'Script Details';
        TabOrder := 3;
      end;
      CurrentVersionL := TLabel.Create(VersionBox);
      with CurrentVersionL do
      begin
        Parent := VersionBox;
        Left := 136;
        Top := 24;
        Width := 21;
        Height := 13;
        Caption := Vers;
      end;
      LastestVersionL := TLabel.Create(VersionBox);
      with LastestVersionL do
      begin
        Parent := VersionBox;
        Left := 136;
        Top := 40;
        Width := 21;
        Height := 13;
        Caption := VersionBH;
      end;
      CurrentVersionL1 := TLabel.Create(VersionBox);
      with CurrentVersionL1 do
      begin
        Parent := VersionBox;
        Left := 8;
        Top := 24;
        Width := 122;
        Height := 13;
        Caption := 'Your Current Version:';
        Font.Color := clWindowText;
        Font.Height := -11;
        Font.Name := 'MS Sans Serif';
        Font.Style := [fsBold];
        ParentFont := False;
      end;
      LatestVersionL1 := TLabel.Create(VersionBox);
      with LatestVersionL1 do
      begin
        Parent := VersionBox;
        Left := 8;
        Top := 40;
        Width := 122;
        Height := 13;
        Caption := 'Latest Version Out   :';
        Font.Color := clWindowText;
        Font.Height := -11;
        Font.Name := 'MS Sans Serif';
        Font.Style := [fsBold];
        ParentFont := False;
      end;
      DownLoadB := TButton.Create(VersionBox);
      with DownLoadB do
      begin
        Parent := VersionBox;
        Left := 48;
        Top := 64;
        Width := 105;
        Height := 25;
        Caption := 'Download Latest';
        TabOrder := 0;
        OnClick := @HandleButtons;
      end;
      StartB := TButton.Create(BHForm);
      with StartB do
      begin
        Parent := BHForm;
        Left := 304;
        Top := 272;
        Width := 137;
        Enabled := False;
        Height := 25;
        Caption := 'Click here to Start';
        TabOrder := 4;
        OnClick := @HandleButtons;
      end;
      WriteLn('Form compiled in ' + IntToStr(GetSystemTime - TimeLearningToolBH) + ' milliseconds!');
    end;

    procedure SafeLearningToolBH;
    var
      V: TVariantArray;
    begin
      SetArrayLength(V, 0);
      ThreadSafeCall('LearningToolBH', V);
    end;

    procedure ShowLearningToolBHModal;
    begin
      BHForm.ShowModal;
    end;

    procedure SafeShowLearningToolBHModal;
    var
      V: TVariantArray;
    begin
      SetArrayLength(V, 0);
      ThreadSafeCall('ShowLearningToolBHModal', V);
    end;

    procedure MainLearningToolBH;
    begin
      try
        SafeLearningToolBH;
        SafeShowLearningToolBHModal;
      finally
        CalculateDecsions;
      except
        WriteLn('An error seems to have occurred in: LearningToolBH');
      end;
    end;

    procedure WalkToBank; forward;
    procedure Banking(BAxe: boolean); forward;
    procedure FastMouseFlag(PosX, PosY, Ranx, Rany: integer); forward;
    function GetCurrentLevel(Skill: string): Integer; forward;
    procedure Setup2; forward;
    procedure WalkToWillows; forward;
    procedure RelocatePlayer(PlayersLocation: string); forward;
    Function FindAxeBH:boolean; forward;


    procedure Post(say, Use: string);
    begin
      Writeln('   ' + say + ':' + use);
      Players[CurrentPlayer].Loc := Use;
    end;

    function DeathWalk: TPointArray;
    begin
      SetLength(Result, 21);

      Result[0] := Point(3229, 3217);
      Result[1] := Point(3236, 3217);
      Result[2] := Point(3235, 3226);
      Result[3] := Point(3228, 3232);
      Result[4] := Point(3222, 3239);
      Result[5] := Point(3218, 3246);
      Result[6] := Point(3209, 3246);
      Result[7] := Point(3200, 3246);
      Result[8] := Point(3188, 3243);
      Result[9] := Point(3177, 3244);
      Result[10] := Point(3171, 3237);
      Result[11] := Point(3162, 3239);
      Result[12] := Point(3157, 3233);
      Result[13] := Point(3144, 3229);
      Result[14] := Point(3130, 3224);
      Result[15] := Point(3120, 3219);
      Result[16] := Point(3111, 3222);
      Result[17] := Point(3107, 3233);
      Result[18] := Point(3105, 3244);
      Result[19] := Point(3096, 3248);
      Result[20] := Point(3092, 3241);

      for II := 0 to High(Result) do
        if not (WalkToTile(Result[II], 1, 1)) then
        begin
          II := 0;
          WalkToTile(Result[II], 3, 2);
          I := I + 1;
          if i > 5 then
          begin
            Break;
            Logout;
            Writeln('Reflection Failed - Logging out');
            Exit;
          end;
        end else
          continue;
    end;

    function IsWoodcutting: boolean;
    begin
      Result := InRange(GetMe.Animation, 867, 879);
    end;
    {
    [===================================================================]
    [ function FindChats(Messages: tstringarray): Boolean;
    [ Description: Finds the chat in the last line.
    [===================================================================]
    }

    var
      Talked: integer;

    function InChatMulti(Text: TStringArray): Boolean;
    var
      s: string;
      i, n: Integer;
    begin
      if GetLastChatText(s) then
      begin
        n := Length(Text) - 1;
        for i := 0 to n do
          if (Pos(Text[i], s) > 0) then
          begin
            Result := True;
            SaveToChatLog;
            Marktime(Talked);
            Exit;
          end;
      end;
    end;


    procedure AutoResponder;
    var
      OldName: string;

    begin
      SaveToChatLog;
      if (TimeFromMark(Talked) > 25000) then
        Exit;
      if (OldLine = TheLine) or (TheName = OldName) or (pos(Players[CurrentPlayer].Nick, TheName) > 0) then
        Exit;
      if InChatMulti(['hello', 'hi', 'yo', 'sup', 'hey']) then
      begin
        Wait(1000 + Random(500));
        case Random(6) of
          0: Typesend('hello');
          1: Typesend('hey sup?');
          2: Typesend('yo');
          3: Typesend('hey');
          4: Typesend('sup');
          5: Typesend('heey');
          6: Typesend('gooday');
        end;
        Responded := Responded + 1;
        MarkTime(Talked);
      end;
      if InChatMulti([Players[CurrentPlayer].Nick]) then
      begin
        Wait(1000 + Random(500));
        case Random(6) of
          0: Typesend('hello');
          1: Typesend('hey');
          2: Typesend('yo');
          3: Typesend('heyz');
          4: Typesend('sup');
          5: Typesend('hi');
          6: Typesend('?');
        end;
        Responded := Responded + 1;
        MarkTime(Talked);
      end;
      if InChatMulti(['wc', 'woodcut', 'cut']) and
        InChatMulti(['lv', 'leve']) and
        not (InChatMulti(['Cong', 'lations'])) then
      begin
        Wait(1000 + Random(500));
        case Random(4) of
          0: TypeSend(IntToStr(Players[CurrentPlayer].Integers[2]));
          1: TypeSend(IntToStr(Players[CurrentPlayer].Integers[2]) + ' u?');
          2: TypeSend(IntToStr(Players[CurrentPlayer].Integers[2]) + ' here');
          3: TypeSend(IntToStr(Players[CurrentPlayer].Integers[2]) + ' :)');
        end;
        Responded := Responded + 1;
        MarkTime(Talked);
      end;
    end;

    {
    [===================================================================]
    [ function InFight: Boolean;
    [ Description: Finds a fight.
    [ By Frozen Soul.
    [===================================================================]
    }


    function InFight: Boolean; //Credits to Frozen Soul
    begin
      if not (LoggedIn) then
        Exit;
      if Players[CurrentPlayer].Integers[4] = 0 then
      begin
        Players[CurrentPlayer].Integers[4] := SmartGetFieldArrayInt(0, CurrentLevels, 3);
      end else
        if Players[CurrentPlayer].Integers[4] > HP then
          if TimeFromMark(HPTime) >= 60000 then
          begin
            x := TimeFromMark(HPTime) - 60000;
            MarkTime(HPTime);
            DecEx(HPTime, x);
            Inc(HP);
          end;
      if FindColor(x, y, 65280, 217, 129, 297, 209) then
      begin
        x := GetMMLevels('hp', ColorSign);
        if x = -1 then
        begin
          Result := FindFight;
          Exit;
        end;
        if (x < HP) then
        begin
          Result := True;
          WriteLn('******** FOUND FIGHTING RANDOM ********');
          WriteFileString(TheFile, '******** FOUND FIGHTING RANDOM ********' + Chr(13));
          TakeScreen('Found Fight');
          Inc(Fights);
          MarkTime(HPTime);
          HP := GetMMLevels('hp', ColorSign);
          if HP = -1 then
            HP := Players[CurrentPlayer].Integers[4];
        end;
      end;
    end;

    function FindLost: boolean;
    begin
      if not (LoggedIn) then
        Exit;
      if not TileOnMM(Point(3092, 3247)) and not TileOnMM(Point(3090, 3231)) then
      begin
        Result := true;
      end;
    end;
    {
    [===================================================================]
    [ procedure FindRandoms;
    [ Description: Finds all the possible randoms
    [===================================================================]
    }


    procedure FindRandoms;
    begin
      if (not (LoggedIn)) then
        Exit;

      FindNormalRandoms;
      if (UseAutoResponderCB.Checked) then
      begin
        AutoResponder;
      end;
      if (FindDead) or (FindLost) then
      begin
        Post('Note:', ' Player is lost relocating...');
        RelocatePlayer('Lost');
      end;
      if (InFight) then
      begin
        RunTo('W', True)
          FFlag(3);
        Wait(100 + random(500));
        if FindSymbol(x, y, 'fish') then
        begin
          mouse(x, y + 20, 6, 6, true);
          Post('Found', ' Fish Symbol');
          FFlag(2);
          Exit;
        end else
        begin
          Post('Error', ' Running Back from fight.');
          Logout;
        end;
      end;
    end;
    {
    [===================================================================]
    [ Procedure Post(say, Use: string);
    [ Description: Quickly writes the line and the location.
    [===================================================================]
    }


    function FindEntReflectionBH(React: boolean): boolean;
    var
      EntxBH, EntyBH: integer;
    begin
      if not (LoggedIn) then
        Exit;
      if (IsWoodCutting) and (FindColorTolerance(EntxBH, EntyBH, 195836, 595, 109, 602, 118, 15)) then
      begin
        if (FindNPC('Tree', TheEnt)) then
        begin
          Writeln('Found a Ent');
          if (React) then
          begin
            FastMouseFlag(MMcx + 3, MMcy, 8, 8);
          end;
          Inc(EntsAvoided);
          Result := True;
        end;
      end;
    end;

    procedure XtremeWait(WaitTime: integer);
    var
    WW:integer;
    begin
    MarkTime(WW);
     repeat
      FindRandoms;
      FindEntReflectionBH(true);
      wait(100 + random(50));
      Until(TimeFromMark(WW) > WaitTime - 150);
    end;

    procedure MouseAntiBan;
    var
      B, D: Integer;
    begin
      if not (LoggedIn) then
        Exit;
      D := MouseSpeed;
      MouseSpeed := MouseSpeed + random(15);
      repeat
        MMouse(x - 312 + random(1100), y + random(400), 2, 2);
        Inc(B);
        XtremeWait(1000 + random(1000));
      until (not IsWoodCutting or (B > 3) or not LoggedIn)
        MouseSpeed := D;
    end;

    function GetBestAxeBH: Boolean;
    var
      InvAxe, Ix, Iy: Integer;
    begin
      if not LoggedIn then exit;
      srl_LoadBitmaps([47, 48, 49, 50, 51, 52, 53, 54]);

      for InvAxe := 1 to 8 do
        if FindBitmapToleranceIn(srl_GetBitmap(55 - InvAxe), Ix, Iy, MIX1, MIY1, MIX2, MIY2, 10) then
        begin
          break;
          Mouse(Ix, Iy, 5, 5, true);
        end;
      if (InvAxe = 0) then
      begin
        Result := False;
        Writeln('No axe was found.');
        srl_FreeBitmaps;
        Exit;
      end;

      case (InvAxe) of
        1: begin
            Players[CurrentPlayer].Strings[0] := 'Dragon';
            WriteLn('Best Dragon axe');
          end;
        2: begin
            Players[CurrentPlayer].Strings[0] := 'Rune';
            WriteLn('Best Rune axe');
          end;
        3: begin
            Players[CurrentPlayer].Strings[0] := 'Addy';
            WriteLn('Best Addy axe');
          end;
        4: begin
            Players[CurrentPlayer].Strings[0] := 'Mith';
            WriteLn('Best Mith axe');
          end;
        5: begin
            Players[CurrentPlayer].Strings[0] := 'Black';
            WriteLn('Best Black axe');
          end;
        6: begin
            Players[CurrentPlayer].Strings[0] := 'Steel';
            WriteLn('Best Steel axe');
          end;
        7: begin
            Players[CurrentPlayer].Strings[0] := 'Iron';
            WriteLn('Best Iron axe');
          end;
        8: begin
            Players[CurrentPlayer].Strings[0] := 'Bronze';
            WriteLn('Best Bronze axe');
          end;
      end;

      Result := True;
      srl_FreeBitmaps;
    end;

    procedure AntiBanBH;
    begin
      if not (LoggedIn) then
        Exit;
      if TimeFromMark(AB) < 5000 then
        exit;
      if not IsWoodCutting then
        exit;

      case random(20) of

        0: begin
            IdleTime(1000 + Random(1000), 500, 0.5);
            Wait(200 + random(800));
          end;
        2: if (AntibanCB.Checked) then
          begin
            PickupMouse;
          end;

        1: begin
            HoverSkill('random', false);
            if (AntibanCB.Checked) then
              GameTab(1 + random(10));
            Wait(300 + random(100));
            GameTab(4);
            MarkTime(AB);
          end;

        13: begin
            PickUpMouse;
            MarkTime(AB);
          end;
        5,6,7,12: MouseAntiBan;
        4: begin
            GameTab(1 + Random(12));
            wait(800 + random(500));
            GameTab(4)
              MarkTime(AB);
          end;

        8: begin
            RandomRClick;
            wait(500 + random(500));
            MarkTime(AB);
          end;
        9: begin
            GameTab(1 + random(10));
            wait(100 + random(1000));
            GameTab(1 + random(10));
            wait(100 + random(1000));
            GameTab(4);
            MarkTime(AB);
          end;
        10: if (AntibanCB.Checked) then
          begin
            IdleTime(2000 + Random(3000), 500, 0.5);
          end;
      end;
    end;
    {
    [===================================================================]
    [ function RockDDTM: Integer;
    [ Description: Loads the RockDDTM.
    [===================================================================]
    }


    function RockDDTM: Integer;
    var
      dtmMainPoint: TDTMPointDef;
      dtmSubPoints: array[0..2] of TDTMPointDef;
      TempTDTM: TDTM;
    begin
      dtmMainPoint.x := 629;
      dtmMainPoint.y := 35;
      dtmMainPoint.AreaSize := 0;
      dtmMainPoint.AreaShape := 0;
      dtmMainPoint.Color := 5134671;
      dtmMainPoint.Tolerance := 50;

      dtmSubPoints[0].x := 625;
      dtmSubPoints[0].y := 33;
      dtmSubPoints[0].AreaSize := 1;
      dtmSubPoints[0].AreaShape := 0;
      dtmSubPoints[0].Color := 3029039;
      dtmSubPoints[0].Tolerance := 50;

      dtmSubPoints[1].x := 630;
      dtmSubPoints[1].y := 38;
      dtmSubPoints[1].AreaSize := 1;
      dtmSubPoints[1].AreaShape := 0;
      dtmSubPoints[1].Color := 4344899;
      dtmSubPoints[1].Tolerance := 50;

      dtmSubPoints[2].x := 631;
      dtmSubPoints[2].y := 32;
      dtmSubPoints[2].AreaSize := 1;
      dtmSubPoints[2].AreaShape := 0;
      dtmSubPoints[2].Color := 1713179;
      dtmSubPoints[2].Tolerance := 50;

      TempTDTM.MainPoint := dtmMainPoint;
      TempTDTM.SubPoints := dtmSubPoints;
      Result := AddDTM(TempTDTM);
    end;

    {
    [===================================================================]
    [ function FindRockDDTM(A, B, C, D: integer): boolean;
    [ Description: Finds the RockDDTM in a percific area.
    [===================================================================]
    }


    function FindRockDDTM(A, B, C, D: integer): boolean;
    var TheDTM: Integer;
    begin
      TheDTM := RockDDTM;
      Result := FindDTMRotated(TheDTM, X, Y, A, B, C, D, -Pi, Pi, 0.1, WalkAngle);
      FreeDTM(TheDTM);
    end;

    {
    [===================================================================]
    [ procedure AxeBroken;
    [ Description: Detects broken axes and banks and gets a new one.
    [===================================================================]
    }


    procedure AxeBroken;
    begin
      {if not (LoggedIn) then
        Exit;
      FindRandoms;
      if not FindDTMRotated(AxeDTM, X, Y,MIx1,MIy1,MIx2,MIy2, -Pi, Pi, 0.1, WalkAngle) then
      begin
        Writeln('Ent Broke the axe.');
        WalkToBank;
        Banking(true);
        WalkToWillows;
      end;  }

    end;
    {
    [===================================================================]
    [ procedure RelocatePlayer(PlayersLocation: string);
    [ Description: When message sent to here it fixes the problem by relocating.
    [===================================================================]
    }


    procedure RelocatePlayer(PlayersLocation: string);
    var
      TimesBH: integer;
    begin
      if not (LoggedIn) then
        Exit;
      case PlayersLocation of
        'NormalTree': begin
            if FindSymbol(x, y, 'fish') then
            begin
              mouse(x, y + 20, 6, 6, true);
              Post('Found', ' Fish Symbol');
              FFlag(2);
              Exit;
            end;
          end;
        'Lost':
          begin
            if not TileOnMM(Point(3222, 3217)) then
            begin
              CastSpell(1);
              repeat
                Wait(2000);
                Inc(TimesBH);
              until (TileOnMM(Point(3222, 3217)) or (TimesBH > 10) or not LoggedIn);
              if (TimesBH > 10) or not LoggedIn then
              begin
                Logout;
                Post('Lost', ' Lost');
                Exit;
              end;
            end else
            begin
              DeathWalk;
              if TileOnMM(Point(3092, 3241)) then
              begin
                Writeln('Made it back from being Lost!');
                Setup2;
                WalkToWillows;
              end else
              begin
                Post('Failed', '  Failed Walk back from Lost.');
              end;
            end;
          end;
      end;
    end;
    {
    [===================================================================]
    [ function DetectNormalTree: boolean;
    [ Description: If finds a NormalTree it sends information to RelocatePlayer.
    [===================================================================]
    }


    function DetectNormalTree: boolean;
    begin
      Result := IsUpText('Tre');
      FindRandoms;
      if (Result) then
      begin
        RelocatePlayer('NormalTree');
      end;
    end;
    {
    [===================================================================]
    [ procedure PlayerStats;
    [ Description: Goes with the progress report.
    [===================================================================]
    }


    procedure PlayerStats;
    var
      Active: string;
      Loc: string;
      i: Integer;
    begin
      if Players[CurrentPlayer].Integers[2] = 0 then
      begin
        Players[CurrentPlayer].Integers[2] := GetCurrentLevel('WoodCutting');
      end else
      begin
        if Players[CurrentPlayer].Active = True then
          Active := 'True'
        else
          Active := 'False';
        Writeln('  Name         : ' + Players[CurrentPlayer].Name);
        Writeln('  Player       : ' + inttostr(CurrentPlayer));
        Writeln('  Active       : ' + Active);
        if Players[CurrentPlayer].loc = '' then
          Writeln('  Location     : Unknown')
        else
          Writeln('  Location     : ' + Players[CurrentPlayer].loc);
        Writeln('  Using a      : ' + Players[CurrentPlayer].Strings[0] + ' Axe.');
        Writeln('  Start WC Lv  : ' + IntToStr(Players[CurrentPlayer].Integers[2]));
        Writeln('  Total WC Lvs Gained : ' + IntToStr(Answer));
        WriteLn('[===================================================================================]');

        for I := 0 to HowManyPlayers - 1 do
        begin
          if Players[i].loc = '' then
          begin
            loc := 'Unknown';
          end;
          if Players[i].Active then
            Active := 'True '
          else
            Active := 'False ';
          Writeln('  ' + (IntToStr(I)) + ': ' + Players[I].Name + ' = ' + Active +
            + 'WC Lv: ' + IntToStr(Players[I].Integers[2]) + ' '
            + 'Worked: ' + IntToStr(Players[i].Worked) + ' min. '
            + 'Axe: ' + Players[CurrentPlayer].Strings[0] + ' '
            + 'Location:' + Players[i].loc
            + ' Random In: ' + Players[i].Rand);
        end;
        WriteLn('[===================================================================================]');
      end;
    end;

    {
    [===================================================================]
    [ procedure ProgressReport;
    [ Description: Reports the scripts stats.
    [===================================================================]
    }


    function PadEx(S: string; I: Integer): string;
    var
      II: Integer;
    begin
      for II := 1 to I do
        Result := Result + S;
    end;

    procedure ProgressReport;
    begin
      if clearbug then
      begin
        ClearDebug;
      end;
      SRLRandomsReport;
      WriteLn('[=======================================================]');
      WriteLn('[       ~ Progress Report ~  V ' + Vers + '                    ]');
      WriteLn('[=======================================================]');
      Writeln('[ Script Worked for ' + TimeRunning + PadEx(' ', 36 - Length(TimeRunning)) + ']');
      Writeln('[ Banked ' + +IntToStr(Banked) + ' load[s].' + PadEx(' ', 38 - Length(IntToStr(Banked))) + ']');
      Writeln('[ Chopped ' + IntToStr(Chopped) + ' Log[s].' + PadEx(' ', 38 - Length(IntToStr(Chopped))) + ']');
      if Responded > 0 then
        Writeln('[ Responed ' + IntToStr(responded) + PadEx(' ', 45 - Length(IntToStr(Responded))) + ']');
      if Answer > 0 then
        Writeln('[ Gained ' + IntToStr(Answer) + ' Total WC Levels' + PadEx(' ', 31 - Length(IntToStr(Answer))) + ']');
      if Axe > 0 then
        Writeln('[ Ents Broke the Axe ' + IntToStr(Axe) + ' Time[s].' + PadEx(' ', 26 - Length(IntToStr(Axe))) + ']');
        Writeln('[ Fastest Load ' + ConvertTime(BestLapTimeBH));
      writeln('[=======================================================]');
      PlayerStats;
    end;

    procedure RunPercentage(HowMuchPercent: integer);
    var
      RunPercent: Integer;
      ColourSign: string;
    begin
      RunPercent := GetMMLevels('run', ColourSign);
      if (RunPercent > HowMuchPercent) then
      begin
        SetRun(True);
      end;
    end;


    {
    [===================================================================]
    [ procedure WalkToWillows;
    [ Description: Walks to the willows in draynor from the bank.
    [===================================================================]
    }


    procedure WalkToWillows;
    begin
      if not (LoggedIn) then
        Exit;
      makeCompass('s');
      ResetVars;
      if (RunCB.Checked) then
      begin
        RunPercentage(20);
      end else
      begin
        case Random(3) of
          0: SetRun(true);
          1: Setrun(false);
          2: ;
        end;
      end;
      if (FindRockDDTM(588, 12, 639, 58)) then
      begin
        Post('Found', ' The RockDTM');
        Mouse(x + 30, y + 5, 9, 12, true);
        FFlag(2);
        Exit;
      end;
      Post('Error', ' Couldnt Find RockDDTM (using backup)');
      if FindSymbol(x, y, 'fish') then
      begin
        mouse(x, y + 20, 6, 6, true);
        Post('Found', ' Fish Symbol');
        FFlag(2);
        Exit;
      end;
      Post('Error', ' Symbol Walk Failed Using last chance backup');
      if RadialWalk(FindWaterColor, 25, 78, 68, -25, -5) then
      begin
        Post('Found', ' Used RadialWalk');
        wait(5000);
        FFlag(2);
        Exit;
      end;
      BankDTM := DTMFromString('78DA634C666260A86240017FFE30317001694' +
        '620FE0F048C203525A86AFEFD1386AB0101007A1109D6');

      if FindDTMRotated(BankDTM, x, y, MMX1, MMY1, MMX2, MMY2, -Pi, Pi, 0.1, WalkAngle) or FindSymbol(x, y, 'bank') then
      begin
        Mouse(647, 46, 10, 10, true);
        wait(500);
        FreeDTM(BankDTM);
        FFlag(2);
        WalkToWillows;
        Exit;
      end;
      FreeDTM(BankDTM);
      Post('Error', ' BackupWalk Failed, Relocating..');
      RelocatePlayer('Lost');
    end;

    procedure FastMouseFlag(PosX, PosY, Ranx, Rany: integer);
    var
      Repeated: integer;
    begin
      if (not LoggedIn) then Exit;
      repeat
        Mouse(PosX, PosY, Ranx, Rany, true);
        PosX := PosX + 1;
        PosY := PosY + 1;
        Repeated := Repeated + 1;
        Wait(100 + random(100));
      until (FlagPresent or (Repeated = 25));
    end;

    {
    [===================================================================]
    [ function EntFinderBHText: boolean;
    [ Description: Finds Ents by IsUpText.
    [===================================================================]
    }


    function EntFinderBHText(react: boolean): boolean;
    var
      BHX, BHY: integer;
    begin
      if (InvFull) or (not LoggedIn) then
        Exit;
      Result := FindColorTolerance(BHX, BHY, 388075, 80, 6, 127, 20, 30);
      if (Result) and IsUpText('hop') then
      begin
        if React then
        begin
          FastMouseFlag(MMcx + 3, MMcy, 2, 2);
          EntsAvoided := EntsAvoided + 1;
        end;
      end;
    end;

    function FindObjTPAEx(var x, y: integer; color, tol, cts, ObjWidth, ObjHeight, minCount: Integer; UpText: tstringarray): Boolean;
    var
      I, j, tcts: Integer;
      myPoint: TPoint;
      Points: TPointArray;
      aPoints: T2DPointArray;
      s: string;
    begin
      FindRandoms;
      tcts := GetColorToleranceSpeed;
      if CTS * 9 mod 3 <> 0 then
        CTS := 1;
      ColorToleranceSpeed(cts);
      FindColorsSpiralTolerance(x, y, Points, Color, MSX1, MSY1, MSX2, MSY2, Tol);
      aPoints := TPAtoATPAEx(Points, ObjWidth, ObjHeight);
      SetLength(Points, 0);
      for I := 0 to Length(aPoints) - 1 do
      begin
        FindRandoms;
        if Length(aPoints[I]) < minCount then
          Continue;
        myPoint := MiddleTPA(aPoints[I]);
        FindRandoms;
        MMouse(myPoint.X, myPoint.Y, 0, 0);
        Wait(100 + Random(50));
        ColorToleranceSpeed(1);
        s := rs_getuptext;
        for j := 0 to high(uptext) do
          if pos(uptext[j], s) <> 0 then
          begin
            x := myPoint.X;
            y := myPoint.Y;
            Result := True;
            ColorToleranceSpeed(tcts);
            Exit;
          end;
        ColorToleranceSpeed(cts);
      end;
      ColorToleranceSpeed(tcts);
    end;

    function FindWillowTPA(Click: boolean): boolean;
    var
      hhx, hhy: integer;
    begin
      Result := FindObjTPAEx(hhx, hhy, 2244145, 11, -1, 8, 8, 15, ['illo']);
      if (Result) then
      begin
        if (Click) then
        begin
          if not (EntFinderBHText(False)) and IsupText('illo') then
          begin
            Mouse(hhx, hhy, 2, 2, true);
            Writeln('Found Tree at X: ' + IntToStr(HHx) + ' Y: ' + IntToStr(HHy));
            FFlag(0);
          end;
        end;
        hhx := dsx;
        hhy := dsy;
      end;
    end;



    {
    [===================================================================]
    [ procedure FindGainedLevel;
    [ Description: Adds 1 to the progress report if gains a level.
    [===================================================================]
    }


    procedure FindGainedLevel;
    var
      StartLevel, EndLevel: integer;
    begin
      StartLevel := Players[CurrentPlayer].Integers[2];
      EndLevel := Players[CurrentPlayer].Integers[3];
      Answer := EndLevel - StartLevel;
    end;
    {
    [===================================================================]
    [ function EntFinderBH: boolean;
    [ Description: Finds ent by SRL's ent.
    [===================================================================]
    }



    {
    [===================================================================]
    [ procedure CuttingStuff;
    [ Description: The Cutting loop.
    [===================================================================]
    }


    procedure CuttingStuff;

    begin
      if not (LoggedIn) then
        Exit;
      repeat
        if FindWillowTPA(true) then
        begin
          DetectNormalTree;
          MarkTime(Timer);
          FFlag(0);
          repeat
          If not LoggedIn then Break;
            Wait(1000 + Random(2000));
            FindEntReflectionBH(true);
            wait(500 + random(200));
            AntibanBH;
            AxeBroken;
            wait(500 + random(200));
            FindRandoms;
            Wait(1000 + random(1000));
          until (invfull or (TimeFromMark(Timer) > 25000 + Random(15000)) or not IsWoodCutting);
          Post('Notice', ' Tree Gone.');
        end else
        begin
          Continue;
        end;
      until (InvFull or not LoggedIn);
    end;



    {
    [===================================================================]
    [ procedure WalkToBank;
    [ Description: Walks to the bank in draynor from the willows.
    [===================================================================]
    }


    procedure WalkToBank;
    begin
      if not (LoggedIn) then
        Exit;

      wait(10 + random(10));
      if not (RunCB.Checked) then
      begin
        case Random(3) of
          0: SetRun(true);
          1: Setrun(false);
          2: wait(100 + random(10));
        end;

      end;

      FindRandoms;
      wait(100 + random(10));
      ResetVars;
      if FindDTMRotated(BankDTM, x, y, MMX1, MMY1, MMX2, MMY2, -Pi, Pi, 0.1, WalkAngle) then
      begin
        Mouse(x - 7, y, 3, 6, true);
        Post('Found', ' Bank DTM');
        FFlag(0);
        Exit;
      end;
      FindRandoms;
      Post('Error', ' Couldnt find DTM using backup');
      if FindSymbol(x, y, 'bank') then
      begin
        mouse(x, y, 2, 2, true);
        Post('Found', ' Bank Symbol');
        FFlag(2);
        Exit;
      end;
      FindRandoms;
      if FindSymbol(x, y, 'fish') then
      begin
        mouse(x, y + 20, 6, 6, true);
        Post('Found', ' Fish Symbol');
        FFlag(2);
        WalkToBank;
        Exit;
      end;
      FindRandoms;
      Post('Error', ' Couldnt find Bank Symbol and DTM Relocating..');
      RelocatePlayer('Lost');
    end;

    {
    [===================================================================]
    [ function CountItemDTM(DTM: Integer): boolean;
    [ Description: Counts the dtm selected.
    [===================================================================]
    }


    function CountItemDTM(DTM: Integer): boolean;
    var
      i, x, y: Integer;
      TB: Tbox;
    begin
      GameTab(4);
      for i := 1 to 28 do
      begin
        TB := InvBox(i);
        if ExistsItem(i) then
          if FindDTM(DTM, x, y, TB.x1, TB.y1, TB.x2, TB.y2) then
            Inc(Chopped);
        Result := true;
      end;
    end;
    {
    [===================================================================]
    [ function CountItemDTM1(DTM: Integer): boolean;
    [ Description: Counts the dtm selected. (Returns as an integer)
    [===================================================================]
    }


    function CountItemDTM1(DTM: Integer): Integer;
    var
      i, x, y: Integer;
      TB: Tbox;
    begin
      GameTab(4);
      for i := 1 to 28 do
      begin
        TB := InvBox(i);
        if ExistsItem(i) then
          if FindDTM(DTM, x, y, TB.x1, TB.y1, TB.x2, TB.y2) then
            Inc(Result);
      end;
    end;

    {
    [===================================================================]
    [ procedure Banking(BAxe: boolean);
    [ Description: Banks, true if is banking a broken axe and false if not
    [===================================================================]
    }



    procedure DoTheMath;
    begin
      Banked := Banked + 1;
      Bankedd := Bankedd + 1;
      ReportVars[2] := 1;
      Players[CurrentPlayer].Integers[3] := GetCurrentLevel('WoodCutting');
    end;

    procedure Banking(BAxe: boolean);
    var
      Zz: integer;
    begin
      if not (LoggedIn) then
        Exit;
      FindRandoms;
      repeat
        OpenBankFast('db');
        FindRandoms;
        Inc(Zz);
        if Zz > 1 then
        begin
          MakeCompass('S');
          if FindDTMRotated(BankDTM, x, y, MMX1, MMY1, MMX2, MMY2, -Pi, Pi, 0.1, WalkAngle) then
          begin
            Mouse(x - 7, y, 3, 6, true);
            Post('Found', ' Bank DTM');
            FFlag(0);
          end else
          begin
            if FindSymbol(x, y, 'fish') then
            begin
              mouse(x, y + 20, 6, 6, true);
              Post('Found', ' Fish Symbol');
              FFlag(0);
            end;
          end;
          if FindDTMRotated(BankDTM, x, y, MMX1, MMY1, MMX2, MMY2, -Pi, Pi, 0.1, WalkAngle) then
          begin
            Mouse(x - 7, y, 3, 6, true);
            Post('Found', ' Bank DTM');
            FFlag(0);
          end;
        end;
      until ((BankScreen) or (PinScreen) or (zz = 3));
      if Zz = 3 then
      begin
        Logout;
        Post('Error', '  Failed to Open Bank (FSB1)');
        Exit;
      end;
      if (PinScreen) then
      begin
        InPin(IntToStr(Players[CurrentPlayer].Integers[1]));
        Wait(500 + Random(250));
      end;

      if (BAxe) then
      begin
        if (BankScreen) then
        begin
          BrokenAxedtm := BitmapFromString(6, 12, 'z78DA3330200CDC700003' +
            'A2F552A206972CF12EA1AE6B315562EAA2DCCDB80000FF8D5941');
          if (FindBitmapMaskTolerance(BrokenAxedtm, x, y, MIX1, MIY1, MIX2, MIY2, 5, 5)) then
          begin
            Mouse(x, y, 1, 1, true);
            wait(1000 + random(100));
          end;
          FreeBitmap(BrokenAxeDTM);

          if GetBestAxeBH then
          begin
            CloseBank;
            Axe := Axe + 1;
            ReportVars[1] := 1;
            Exit;
          end;
          Post('Error', '  No Spare Axe!');
          Logout;
          Exit;
        end;
      end;
      if (BankScreen) then
      begin
        WillowLog := DTMFromString('78DA639CC6C4C0F08C0105B8DA49304802694' +
          '620FE0F048C1D40356F18D000231209A47B816AEE1050331FA8E6' +
          '2601358B89B06B0A50CD07FC6A00A65B0DB2');
        CountItemDTM(WillowLog);
        ReportVars[0] := CountItemDTM1(WillowLog);
        Deposit(2, 28, true);
        wait(20 + random(20));
        FreeDTM(WillowLog);
        wait(20 + random(20));
        CloseBank;
        BeatRecordTiming(LapTime);
        DoTheMath;
        FindGainedLevel;
        ProgressReport;
        Disguise('Done [' + IntToStr(Bankedd) + '/' + IntToStr(Players[CurrentPlayer].Integers[0]) + '] Loads');
        Exit;
      end else
      begin
        Post('Error', '  Cant Find Bank.');
        Logout;
      end;
    end;


    function FindAxeBH:boolean;
    var
      InvAxe, WieldAxe, Ix, Iy: Integer;
    begin
      if not LoggedIn then exit;
      srl_LoadBitmaps([47, 48, 49, 50, 51, 52, 53, 54]);

      GameTab(5);
      for WieldAxe := 0 to 7 do
        if FindBitmapToleranceIn(srl_GetBitmap(54 - WieldAxe), Ix, Iy, 566, 285, 606, 327, 10) then
        begin
          break;
        end else
        begin
          GameTab(4)
            for InvAxe := 0 to 7 do
            if FindBitmapToleranceIn(srl_GetBitmap(54 - InvAxe), Ix, Iy, MIX1, MIY1, MIX2, MIY2, 10) then
              break;
        end;
      if (InvAxe = 8) and (WieldAxe = 8) then
      begin
        Result := False;
        Writeln('No axe was found.');
        srl_FreeBitmaps;
        Exit;
      end;

      EquipAxe := (WieldAxe - InvAxe < 0);

      case Min(WieldAxe, InvAxe) of
        0: begin
            Players[CurrentPlayer].Strings[0] := 'Dragon';
            WriteLn('Using Dragon axe');
          end;
        1: begin
            Players[CurrentPlayer].Strings[0] := 'Rune';
            WriteLn('Using Rune axe');
          end;
        2: begin
            Players[CurrentPlayer].Strings[0] := 'Addy';
            WriteLn('Using Addy axe');
          end;
        3: begin
            Players[CurrentPlayer].Strings[0] := 'Mith';
            WriteLn('Using Mith axe');
          end;
        4: begin
            Players[CurrentPlayer].Strings[0] := 'Black';
            WriteLn('Using Black axe');
          end;
        5: begin
            Players[CurrentPlayer].Strings[0] := 'Steel';
            WriteLn('Using Steel axe');
          end;
        6: begin
            Players[CurrentPlayer].Strings[0] := 'Iron';
            WriteLn('Using Iron axe');
          end;
        7: begin
            Players[CurrentPlayer].Strings[0] := 'Bronze';
            WriteLn('Using Bronze axe');
          end;
      end;

      Result := True;
      srl_FreeBitmaps;
    end;

    procedure Setup;
    begin
      ClearDebug;
      CheckVersion;
      MainLearningToolBH;
      if (EndLearningToolBH) then
        TerminateScript;

      SmartSetupEx(StrToInt(WorldE.Text), True, True, False);
      SetTargetDC(SmartGetDC);
      SetupSRL;
      ScriptID := '669';
      SRLID := SRLIDBH;
      SRLPassword := SRLPass;
      wait(1000);
      if (not (LoggedIn)) then
        LoginPlayer;
      AxeDTM := DTMFromString('78DA63CC60616058CCC8800C9A93051824813' +
        '448F43F10301603D52C455503918591403A01A866270135E94035' +
        'F309A84902AA59835F0D002D200A83');
    end;
    {*******************************************************************
    Function GetCurrentLevel(Skill: String): Integer;
    By: n3ss3s Modded by BH.
    Description: Returns the current level of the skill Skill.
    ********************************************************************}


    function GetCurrentLevel(Skill: string): Integer;
    begin
      Result := SmartGetFieldArrayInt(0, CurrentLevels, 8);
    end;

    function AllPlayersFalse: boolean; // Thanks to Mickaliscious =D
    var ActivePlayers, i: byte;
    begin
      for i := 0 to High(Players) do
        if Players[i].Active then Inc(ActivePlayers);
      if ActivePlayers = 0 then Result := True;
    end;

    procedure Setup2;
    begin
      if (UseAutoResponderCB.Checked) then
      begin
        SetChat('on', 1);
      end;
      MarkTime(LapTime);
      SetAngle(true);
      FindRandoms;
      Disguise('Done [' + IntToStr(Bankedd) + '/' + IntToStr(Players[CurrentPlayer].Integers[0]) + '] Loads');
      if Players[CurrentPlayer].Integers[2] = 0 then
      begin
        Players[CurrentPlayer].Integers[2] := GetCurrentLevel('Woodcutting');
      end;
      BankDTM := DTMFromString('78DA634C666260A86240017FFE30317001694' +
        '620FE0F048C203525A86AFEFD1386AB0101007A1109D6');

      if not (FindAxeBH) then
      begin
        OpenBankFast('db');
        if GetBestAxeBH then
        begin
          CloseBank;
          Exit;
        end else
        begin
          Post('Error', '  Cant find an axe, Logging out.');
          Logout;
        end;
      end;
    end;

    begin
      Setup;
      repeat
        repeat
          Setup2;
          WalkToWillows;
          CuttingStuff;
          WalkToBank;
          Banking(False);
        until (Bankedd >= (Players[CurrentPlayer].Integers[0])) or (not (LoggedIn));
        if (Bankedd >= (Players[CurrentPlayer].Integers[0])) then
        begin
          writeln('Loads done, Chaning player');
          Players[CurrentPlayer].Loc := 'Bank. Loads done.';
          ProgressReport;
          Logout;
          NextPlayer(true);
          Bankedd := 0;
        end;
        if not (LoggedIn) then
        begin
          Writeln('Choosing Next Player');
          NextPlayer(false);
          Bankedd := 0;
        end;
      until (AllPlayersFalse);
      FreeForm(BHForm);
      FreeDTM(AxeDTM);
    end.

  22. #22
    Join Date
    Sep 2006
    Posts
    6,089
    Mentioned
    77 Post(s)
    Quoted
    43 Post(s)

    Default

    Ah, ok. I think that's a character limit, because you can't enter any text anymore either It did highlight good though, right?
    Hup Holland Hup!

  23. #23
    Join Date
    May 2007
    Location
    NSW, Australia
    Posts
    2,823
    Mentioned
    3 Post(s)
    Quoted
    25 Post(s)

Thread Information

Users Browsing this Thread

There are currently 1 users browsing this thread. (0 members and 1 guests)

Similar Threads

  1. SRL 4 Syntax for Disguising
    By Macros in forum OSR Help
    Replies: 1
    Last Post: 09-28-2008, 11:19 PM
  2. Syntax error...
    By faster789 in forum OSR Help
    Replies: 2
    Last Post: 03-24-2008, 02:29 PM
  3. Syntax
    By hihi12340 in forum OSR Help
    Replies: 4
    Last Post: 06-18-2007, 01:21 PM
  4. Syntax Error
    By me_ntal in forum OSR Help
    Replies: 1
    Last Post: 02-14-2007, 02:44 AM

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •