[TABLE MANAGER] StackAndTile
btw, i appreciate everyones input and discussion here. it all helps make the program better and more efficient
xK1nGeNx, replace this line
WinGet, listft, List, ahk_class Logged in QWidget,,Full Tilt
with this:
WinGet, listft, List, Logged ahk_class QWidget,,Full Tilt
I get about 350 greg but that's not the point, i mean there is no big difference between taking 1 pixel and 10.
WinGet, listft, List, ahk_class Logged in QWidget,,Full Tilt
with this:
WinGet, listft, List, Logged ahk_class QWidget,,Full Tilt
I get about 350 greg but that's not the point, i mean there is no big difference between taking 1 pixel and 10.
thanks for your hard work greg, but I dont think flop detection is going to work with the pixel things. At least not on my computer. I thought I had a very good computer (quad core 3.0, 4g ram, nice video card) but after 10+ tables things start to slow down way too much. Thanks for your work regardless.
thank you, i am looking into fixes to speed things up
problem is scaling with various table sizes, and also different card mods. i think thats why betpot uses such a large area to scan for a card
v 1.11
http://www.overcards.com/wiki/moin.cgi/StackAndTile
i've slightly optimized the flop detection, it searches a smaller area now. from my tests, it is just as fast as if it were searching for one pixel. hopefully people can test and report back whether this is improvement or not
http://www.overcards.com/wiki/moin.cgi/StackAndTile
i've slightly optimized the flop detection, it searches a smaller area now. from my tests, it is just as fast as if it were searching for one pixel. hopefully people can test and report back whether this is improvement or not
You still look through 165 pixels while you could get same result with 1.
Anyway it looks like buffer overflow problem, check your code again for possible reasons.
Code:
PixelColorA(col_x,col_y,id) { ;critical d := "", c := "", p := "", pix := "" Display_CreateWindowCapture(d, c, p, id) pix := Display_GetPixel(c, col_x, col_y) Display_DeleteWindowCapture(d, c, p) return pix }
I dared to change your code a bit greg, just for people to test it:
Code:
; StackAndTile version := 1.11 ; ; Author: greg nice @ 2p2 (PM me if you would like to make a donation) ; Written in AHK Version: 1.0.48.05 ; Source Code License: GNU General Public License v3 ; http://www.gnu.org/licenses/gpl.html ; Credit where its due: Chris228 (StarsAssistant), Max1mums, _dave_, juk, Roland, Xander, etc ; ; ; Description: ; ; Allows you to have a stack of tables. When a table requires action, it gets ; tiled into a grid of slots on your screen. When you fold, the table returns ; to the stack. ; ; ; Latest version and documentation found here: ; ; http://www.overcards.com/wiki/moin.cgi/StackAndTile ; ; ; ; Notes, Limitations, etc: ; ; 1. Move when action required ; ; Preflop - default method from version 1.00. Tables get tiled into grid when its your turn to act starting preflop. This method is stable and preferred. ; Flop - Waits until your turn to act on the flop before moving. This method is slow. Please report bugs in 2p2 thread. Still to do: handle conflicting sites auto popup activation ; ; 2. Fold and Re-stack Hotkey ; ; The table stays in grid until you press the Fold and Re-stack Hotkey. This means a few things: ; If you go to showdown, the table stays (allowing you to see mucked cards from pt3 hud, etc). This seems ok to me, because you will soon have another preflop decision, in which you can 'Fold, re-stack' ; If you wish to Fold but keep the table in grid to view the rest of hand, you can manually click Fold with your mouse, or setup a hotkey to Fold in another script. ; ; 3. Other Notes ; ; 1. You must clear your Fold hotkey from other programs like Table Ninja or BetPot. StackAndTile will handle the Folding with its own hotkey. ; 2. If you change any settings in the GUI, you MUST click the Save button before they are used. ; 3. This script does not resize tables. Make sure all your tables are consistent size! Not included because redrawing the Stars tables is intensive. ; 4. To manually change settings, you could edit the ini file yourself and then reload the script. ; For example, custom slots locations (overlapping, etc): ; - edit ini file for slot#x and slot#y for each slot and total_slots for how many slots you want ; ; ; ; ; USERS DONT NEED TO EDIT THIS SCRIPT. ; ; ; ; ; ===================================================================== #NoEnv SendMode Input SetWorkingDir %A_ScriptDir% SetWinDelay, 10 SetTitleMatchMode, 2 ;// match string anywhere in title, needed for functions that use the ahk_groups CoordMode, Pixel, Relative OnExit, ExitSub starsfoldx := 442 ;// these are client area coordinates for each site's fold button. starsfoldy := 538 ftfoldx := 516 ;// windowspy_x - xborder = x, ftfoldy := 501 ;// windowspy_y - yborder - caption = y ini := "StackAndTile.ini" readSettingsIntoVars() if !FileExist(ini) MsgBox, Run Setup before using GroupAdd, StarsTables, ahk_class PokerStarsTableFrameClass GroupAdd, FullTiltTables, Logged In As ahk_class QWidget,,,Full Tilt Poker GroupAdd, AllTables, ahk_group StarsTables GroupAdd, AllTables, ahk_group FullTiltTables Menu, Tray, NoStandard Menu, Tray, Add, StackAndTile, menuGUI Menu, Tray, Default, StackAndTile Menu, Tray, Add Menu, Tray, Add, Exit, ExitSub Menu, Tray, Tip, StackAndTile v%version% Gui, +ToolWindow Gui, Font, cBlack, Tahoma Gui, Add, Tab2, x6 y11 w360 h360 vMyTab, Control|Settings|Sites Gui, Add, GroupBox, x26 y41 w320 h200 , Gui, Font, s16 bold underline, Tahoma Gui, Add, Button, x101 y101 w170 h80 vStartButton, Start Gui, Font, s12 norm bold, Tahoma Gui, Add, Text, x101 y191 w160 vRunningText, Gui, Font, s12 norm, Tahoma Gui, Add, Button, x101 y271 w170 h50 vSetupButton, Setup Grid Gui, Font, s8 norm, Tahoma Gui, Add, Text, x26 y326 w320 vSetupText, Gui, Tab, 2 Gui, Font, s10 underline, Tahoma Gui, Add, GroupBox, x26 y41 w320 h120 , Stack Gui, Font, s8 norm, Tahoma Gui, Add, Text, x56 y71, Stack location: Gui, Add, Radio, x156 y73 checked%StackUsesSlot% gRadioSlot vStackUsesSlot, Slot: Gui, Add, Radio, x156 y101 checked%StackUsesCustom% gRadioCustom vStackUsesCustom, Custom: Gui, Font, s8 norm, Tahoma Gui, Font, s8 norm, Tahoma Gui, Add, DropDownList, x236 y71 w60 disabled%StackUsesCustom% vDDLslot, Loop, %totalslots% GuiControl, ,DDLslot, %A_Index% GuiControl, ChooseString, DDLslot, %stackslot% Gui, Add, Text, x236 y101 w20 h20, x: Gui, Add, Text, x236 y121 w20 h20, y: Gui, Add, Edit, x251 y101 w45 h20 disabled%StackUsesSlot% vCustomStackX, %stackx% Gui, Add, Edit, x251 y121 w45 h20 disabled%StackUsesSlot% vCustomStackY, %stacky% Gui, Add, Button, x300 y111 h20 disabled%StackUsesSlot% vGetButton, Get Gui, Font, s10 underline, Tahoma Gui, Add, GroupBox, x26 y161 w320 h150 , Tile Gui, Font, s8 cNavy underline, Tahoma Gui, Add, Text, x56 y191 gTextHotkey vHotkeyText, Hotkey Gui, Font, s8 cBlack norm, Tahoma Gui, Add, Text, x99 y191 vRestackText, to 'Fold and Re-stack' : Gui, Add, Edit, x246 y191 w60 h20 vFoldHotkey, %FoldHotkey% Gui, Add, Radio, x86 y216 checked%SendActiveTable% vSendActiveTable, Send to active table Gui, Add, Radio, x86 y236 checked%SendTableUnderMouse% vSendTableUnderMouse, Send to table under mouse Gui, Add, Text, x56 y271, Move when action required: Gui, Add, DropDownList, x236 y268 w80 vMoveStreet, preflop|flop *** GuiControl, ChooseString, MoveStreet, %moveonstreet% Gui, Font, s8 cNavy underline, Tahoma Gui, Add, Text, x41 y321 h20 gText**, ** Gui, Font, s8 cBlack norm, Tahoma Gui, Add, Button, x256 y321 w90 h30 vSaveButton, Save Gui, Tab, 3 Gui, Font, s10 underline, Tahoma Gui, Add, GroupBox, x26 y41 w320 h220 , Gui, Font, s8 norm, Tahoma Gui, Add, Text, x46 y61 , Which sites would you like to StackAndTile ? Gui, Add, CheckBox, x46 y101 checked%IncludeStars% gCheckboxPokerStars vIncludeStars, PokerStars Gui, Add, CheckBox, % "x66 y122 checked" . DetectStarsAIs . " disabled" . !IncludeStars . " vDetectStarsAIs", Detect Stars All-ins ** Gui, Add, CheckBox, x46 y151 checked%IncludeFulltilt% vIncludeFulltilt, Full Tilt ** Gui, Font, s8 cNavy underline, Tahoma Gui, Add, Text, x41 y321 h20 gText**, ** Gui, Font, s8 cBlack norm, Tahoma Gui, Add, Button, x256 y321 w90 h30 vSaveButton2, Save IniRead, guix, %ini%, settings, gui_x, center IniRead, guiy, %ini%, settings, gui_y, center Gui, Show, x%guix% y%guiy% w370 h375, StackAndTile v%version% running := 0 setuprunning := 0 debug := 0 return ;// end of autoexec ; ==================== ; subs ; ==================== Text**: MsgBox,64,, These features marked ** will quite possibly slow things down.`nYou sacrifice potential lag to use them.`n`nIf things aren't working or table colors have changed, try running Setup Grid again. return TextHotkey: MsgBox,64,, Text of hotkey button must match the AHK naming system.`n`nFor the A key, enter "A"`nFor right mouse click, enter "RButton"`n`nSee this website for the full list:`nhttp://www.autohotkey.com/docs/KeyList.htm return menuGUI: Gui, Show return GuiClose: Gui, Cancel return RadioSlot: GuiControl, enable, DDLslot GuiControl, disable, GetButton GuiControl, disable, CustomStackX GuiControl, disable, CustomStackY return RadioCustom: GuiControl, disable, DDLslot GuiControl, enable, GetButton GuiControl, enable, CustomStackX GuiControl, enable, CustomStackY return CheckboxPokerStars: Gui, Submit, NoHide if (IncludeStars) ;// if checked GuiControl, enable, DetectStarsAIs else GuiControl, disable, DetectStarsAIs return ButtonSave: Gui, Submit, NoHide if StackUsesCustom { stackslot := 0 IniWrite, %CustomStackX%, %ini%, settings, stack_x IniWrite, %CustomStackY%, %ini%, settings, stack_y } else { if (DDLslot) { stackslot := DDLslot IniWrite, % coordxforslot%stackslot%, %ini%, settings, stack_x IniWrite, % coordyforslot%stackslot%, %ini%, settings, stack_y } else { MsgBox, 48,, Choose a stack slot return } } IniWrite, %stackslot%, %ini%, settings, stack_slot IniWrite, %SendTableUnderMouse%, %ini%, settings, send_table_under_mouse IniWrite, %FoldHotkey%, %ini%, settings, fold_hotkey moveonstreet := MoveStreet if (moveonstreet = "flop ***") moveonstreet := "flop" IniWrite, %moveonstreet%, %ini%, settings, move_on_street IniWrite, %IncludeStars%, %ini%, settings, include_stars IniWrite, %DetectStarsAIs%, %ini%, settings, detect_stars_allins IniWrite, %IncludeFulltilt%, %ini%, settings, include_fulltilt Reload ;// script will readSettingsIntoVars() at the start return ButtonStart: if (!running) { tablequeue := "" ;// queue of tables that need action (in the stack only) slottedlist := "" stackedlist := "" most_urgent_table := "" oldurgent := "" Loop, %totalslots% tableinslot%A_Index% := "" ;// set all slots empty Hotkey, %FoldHotkey%, on SetTimer, StackAndTile, 500 GuiControl, disable, SetupButton GuiControl, , StartButton, Stop GuiControl, , RunningText, Running... GuiControl, , MyTab, |Control running := 1 } else { Hotkey, %FoldHotkey%, off SetTimer, StackAndTile, Off GuiControl, enable, SetupButton GuiControl, ,StartButton, Start GuiControl, ,RunningText, GuiControl, , MyTab, |Control|Settings|Sites running := 0 } return ButtonGet: Gui +OwnDialogs MsgBox, Drag a poker table to the position on screen that you would like the stack to be.`nThen press F12. Hotkey, F12, getTableCoords Hotkey, F12, on return ButtonSetupGrid: if (!setuprunning) { Gui +OwnDialogs Hotkey, F10, setupTableGrid Hotkey, F10, on GuiControl, , SetupButton, Cancel GuiControl, disable, StartButton GuiControl, , MyTab, |Control MsgBox, Observe a Pokerstars table. Click on it. Press F10. GuiControl, , SetupText, Observe a Pokerstars table. Click on it. Press F10. setuprunning := 1 } else Reload return ExitSub: Gui +lastfound WinGetPos, x, y IniWrite, %x%, %ini%, settings, gui_x IniWrite, %y%, %ini%, settings, gui_y ExitApp ;// getTableCoords: grab x,y of table, store in gui fields for custom stack getTableCoords: Gui +OwnDialogs win := WinActive("ahk_group AllTables") if (win) { WinGetTitle, tablename, ahk_id %win% MsgBox, 4, ,Will use location of `n`n %tablename% `n`n OK? Yes or No? IfMsgBox Yes { WinGetPos, x, y, , , ahk_id %win% GuiControl, ,CustomStackX, %x% GuiControl, ,CustomStackY, %y% MsgBox, X,Y coords have been grabbed: %x% by %y%`nIf you want to use this location for the stack, make sure to click the cirle radio button next to 'Custom', and then click Save. } } else MsgBox, 48,,Not a poker table Hotkey, F12, off return ;// setupTableGrid: grab table dimensions, build slot grid, get fold hotkey, store in ini setupTableGrid: Gui +OwnDialogs win := WinActive("ahk_group StarsTables") if (win) { WinGetTitle, tablename, ahk_id %win% MsgBox, 4, ,We will first get the table size and setup the grid. We will use this table for this: `n`n %tablename% `n`n OK? Yes or No? IfMsgBox Yes { FileDelete, %ini% WinGetPos, , , w, h, ahk_id %win% columns := Floor(A_ScreenWidth/w) rows := Floor(A_ScreenHeight/h) totalslots := columns * rows MsgBox, Table dimensions are w%w% by h%h%. `nSlots will be start at upper left of screen and continue right, then down, as if you were reading a page.`nTotal slots for your resolution is: %totalslots% IniWrite, %totalslots%, %ini%, settings, total_slots stackslot := 0 while ((stackslot < 1) OR (stackslot > totalslots)) { if a_index > 1 ;// if while loop has been repeated MsgBox, Invalid slot number InputBox, stackslot, Stack Slot, Which slot number to use for the stack?,,280,180,,,,,1 if ErrorLevel stackslot := 1 } slot := 0 Loop, %rows% { r := a_index Loop, %columns% { c := a_index slot++ xx := (c-1) * w yy := (r-1) * h IniWrite, %xx%, %ini%, settings, slot%slot%x IniWrite, %yy%, %ini%, settings, slot%slot%y if (slot = stackslot) { stackx := xx stacky := yy } } } IniWrite, %stackslot%, %ini%, settings, stack_slot IniWrite, %stackx%, %ini%, settings, stack_x IniWrite, %stacky%, %ini%, settings, stack_y InputBox, FoldHotkey, Fold and re-stack Hotkey, Please enter the key you would like to use as a hotkey to click Fold and then re-stack the table.`n`nThis should be used as a replacement of your Fold hotkey in other programs. ,,280,180,,,,,F3 IniWrite, %FoldHotkey%, %ini%, settings, fold_hotkey sfx := starsfoldx, sfy := starsfoldy relStarsWindowPoint(win, sfx, sfy) WinActivate, ahk_id %win% PixelGetColor, stars_nofold_col, sfx, sfy IniWrite, %stars_nofold_col%, %ini%, settings, stars_nofold_pixelcol IniWrite, %IncludeStars%, %ini%, settings, include_stars } else ;// else, MsgBox = no return } else { ;// else, win not pokerstars MsgBox, 48,,Not a Pokerstars table return } Hotkey, F10, off MsgBox 4,, Include Full Tilt detection? IfMsgBox Yes { IncludeFulltilt := 1 GuiControl, , IncludeFulltilt, 1 IniWrite, %IncludeFulltilt%, %ini%, settings, include_fulltilt MsgBox, IMPORTANT!`n`nSit at a Full Tilt table and make sure its the correct size. Play a hand. When the 'Fold' button is visible, press F11. GuiControl, , SetupText, Press F11 on a Fulltilt table when 'Fold' button is visible. Hotkey, F11, setupFulltilt Hotkey, F11, on } else { IncludeFulltilt := 0 IniWrite, %IncludeFulltilt%, %ini%, settings, include_fulltilt GuiControl, , SetupText, GuiControl, enable, StartButton GuiControl, , MyTab, |Control|Settings|Sites MsgBox, Setup finished Reload } return ;// setupFulltilt: grabs the fold pixel color setupFulltilt: Gui +OwnDialogs win := WinActive("ahk_group FulltiltTables") if (win) { WinGetTitle, tablename, ahk_id %win% MsgBox, 4, ,We will use the color of the Fold button from table: `n`n %tablename% `n`n OK? Yes or No? IfMsgBox Yes { ffx := ftfoldx, ffy := ftfoldy relFullTiltWindowPoint(win, ffx, ffy) WinActivate, ahk_id %win% PixelGetColor, ft_fold_col, ffx, ffy IniWrite, %ft_fold_col%, %ini%, settings, ft_fold_pixelcol Hotkey, F11, off GuiControl, , SetupText, GuiControl, enable, StartButton GuiControl, , MyTab, |Control|Settings|Sites MsgBox, Setup finished Reload } else return } else MsgBox, 48,, Not a Full Tilt table return ;// StackAndTile: main loop that does all the dirty work StackAndTile: tables := "" if (IncludeStars) tables := tables . "," . starslist() if (IncludeFulltilt) tables := tables . "," . fulltiltlist() ;tables := alltableslist() ;// dont add all tables if dont need to ;// first, clean up lists ;// remove tables that no longer exist Loop, %totalslots% { ;// check if any slot table was manually closed, therefore set its slot to empty i := a_index if ((tableinslot%i% != "") and (!(InStr(tables, tableinslot%i%, true, 0)))) ;// if slot is not empty, and not in tables list tableinslot%i% := "" } Loop, Parse, tablequeue, `, { StringTrimLeft, this_id, A_LoopField, InStr(A_LoopField, "_") ;// trims the timestamp if (!InStr(tables, this_id)) ;// if table from queue is no longer in table list (ex: got closed) listDelItem(tablequeue, A_Loopfield) ;// remove it from queue } Loop, Parse, stackedlist, `, { if (!InStr(tables, A_Loopfield)) listDelItem(stackedlist, A_Loopfield) } Loop, Parse, slottedlist, `, { if (!InStr(tables, A_Loopfield)) listDelItem(slottedlist, A_Loopfield) } Loop, Parse, nonurgents, `, { if (!InStr(tables, A_Loopfield)) listDelItem(nonurgents, A_Loopfield) } ;// next, ;// find urgents: Loop, Parse, tables, `, { if (!InStr(stackedlist, A_LoopField)) { if (!InStr(slottedlist, A_LoopField)) { WinMove, ahk_id %A_LoopField%,, %stackx%, %stacky% ;// auto stack new tables listAdd(stackedlist, A_Loopfield) } } ;// check if urgent: if (IncludeFulltilt) { variation := 8 ;// color variation tolerance, experiment with values IfWinExist, ahk_id%A_Loopfield% ahk_group FullTiltTables { ;// if a Fulltilt table ffx := ftfoldx, ffy := ftfoldy relFullTiltWindowPoint(A_LoopField, ffx, ffy) pixel := PixelColorA(ffx, ffy, A_LoopField) if (Display_CompareColors(ft_fold_col, pixel, variation) = 1) { ; fulltilt cant use fold background color because preselect buttons cover it. so instead we compare if the current pixel is a close match to when the fold was visible during setup if (!InStr(tablequeue, A_LoopField)) { if (!InStr(slottedlist, A_LoopField)) { DllCall("QueryPerformanceCounter", "Int64 *", CurrentQPC) listAdd(tablequeue, CurrentQPC . "-" . A_TickCount . "_" . A_LoopField) listDelItem(nonurgents, A_LoopField) } } } else { if (!InStr(nonurgents, A_LoopField)) if (!InStr(slottedlist, A_LoopField)) listAdd(nonurgents, A_LoopField) if (InStr(tablequeue, A_LoopField)) listDelItem(tablequeue, A_LoopField) } } } if (IncludeStars) { IfWinExist, ahk_id%A_Loopfield% ahk_group StarsTables ;// if a stars table { ControlGet, v, Visible, , PokerStarsSliderEditorClass1, ahk_id%A_LoopField% ;// search for slider if ( v = 1 ) { if (!InStr(tablequeue, A_LoopField)) { ;//if not already in queue if (!InStr(slottedlist, A_LoopField)) { ;// and not already slotted DllCall("QueryPerformanceCounter", "Int64 *", CurrentQPC) listAdd(tablequeue, CurrentQPC . "-" . A_TickCount . "_" . A_LoopField) ;//timestamp it, add it to queue listDelItem(nonurgents, A_LoopField) } } } else { ;// slider not visible if (DetectStarsAIs) { sfx := starsfoldx, sfy := starsfoldy relStarsWindowPoint(A_LoopField, sfx, sfy) pixel := PixelColorA(sfx, sfy, A_LoopField) if (pixel != stars_nofold_col) { if (!InStr(tablequeue, A_LoopField)) { if (!InStr(slottedlist, A_LoopField)) { DllCall("QueryPerformanceCounter", "Int64 *", CurrentQPC) listAdd(tablequeue, CurrentQPC . "-" . A_TickCount . "_" . A_LoopField) listDelItem(nonurgents, A_LoopField) } } } else { ;// not urgent if (!InStr(nonurgents, A_LoopField)) if (!InStr(slottedlist, A_LoopField)) ;// dont move slotted tables to bottom listAdd(nonurgents, A_LoopField) ;// add to nonurgents list, for move to bottom of stack later if (InStr(tablequeue, A_LoopField)) ;// if tables were still waiting in queue for an open slot, but are no longer urgent listDelItem(tablequeue, A_LoopField) ;// remove them from queue } } else { if (!InStr(nonurgents, A_LoopField)) if (!InStr(slottedlist, A_LoopField)) listAdd(nonurgents, A_LoopField) if (InStr(tablequeue, A_LoopField)) listDelItem(tablequeue, A_LoopField) } } } } } ;// sort by timestamp ;// and grab most urgent: tmpvar := "" Loop, Parse, tablequeue, `, { if (InStr(A_LoopField, "0x")) listAdd(tmpvar, A_LoopField ) } Sort, tmpvar, N D`, ;// since tables are timestamped, we can sort them numerically in order tablequeue := CleanList(tmpvar) most_urgent_table := "" ;// finally, ;// move into empty slot: Loop, Parse, tablequeue, `, { StringTrimLeft, most_urgent_table, A_LoopField, InStr(A_LoopField, "_") ;// remove the timestamp, store in most_urgent if (most_urgent_table != "") { ;ToolTip, most = %most_urgent_table%`nold = %old_urgent% Loop, parse, nonurgents, `, { WinGetTitle, tit, ahk_id%a_loopfield% ;msgbox sending to bottom:`n%tit% WinSet, Bottom,, ahk_id%A_LoopField% ;// move non urgents to bottom, take care of auto popup not happening when action requred in grid (thx e306) } if (moveonstreet = "preflop") { if (moveIntoEmptySlot(most_urgent_table) = 0) { ;// if move into slot was successful listAdd(slottedlist, most_urgent_table) ;// add table to list of slotted tables listDelItem(stackedlist, most_urgent_table) ;// remove from list of stacked listDelItem(tablequeue, A_Loopfield) ;// remove table from queue. if all slots were full, then the action continues in the stack via stars auto popup on activation ;// but tablequeue stores the table in case a slot frees up } } else if (moveonstreet = "flop") { IfWinExist, ahk_id %most_urgent_table% ahk_group StarsTables { str_stars := GetStreetStars(most_urgent_table) s := "stars" } IfWinExist, ahk_id%most_urgent_table% ahk_group FullTiltTables { str_ft := GetStreetFT(most_urgent_table) s := "ft" } if (str_%s% = "flop") { ;// if on flop if (moveIntoEmptySlot(most_urgent_table) = 0) { listAdd(slottedlist, most_urgent_table) listDelItem(stackedlist, most_urgent_table) listDelItem(tablequeue, A_Loopfield) } } } } break ;// only do the first in queuelist (most urgent) } return ;// foldReStack: HOTKEY to click Fold on table, remove it from slot, re-stack it foldReStack: if SendTableUnderMouse MouseGetPos,,, win else WinGet, win, ID, A IfWinExist, ahk_id%win% ahk_group StarsTables { FoldStars(win) WinMove, ahk_id %win%,, %stackx%, %stacky% ;// re-stack it listAdd(stackedlist, win) } Else IfWinExist, ahk_id%win% ahk_group FullTiltTables { FoldFT(win) WinMove, ahk_id %win%,, %stackx%, %stacky% ;// re-stack it listAdd(stackedlist, win) } Sleep 100 Loop, %totalslots% { i := a_index if (win = tableinslot%i%) { tableinslot%i% := "" ;// remove table from slot array listDelItem(slottedlist, win) ;// and from slottedlist break } } return ; ========================= ; functions ; ========================= ;// readSettingsIntoVars: reads ini and updates the script's variables for use readSettingsIntoVars() { global ;// make all vars in this func global IniRead, totalslots, %ini%, settings, total_slots, 0 Loop, %totalslots% { i := a_index IniRead, coordxforslot%i%, %ini%, settings, slot%i%x, 0 IniRead, coordyforslot%i%, %ini%, settings, slot%i%y, 0 } IniRead, stackslot, %ini%, settings, stack_slot, 1 if (stackslot = 0) { StackUsesSlot := 0 StackUsesCustom := 1 } else { StackUsesSlot := 1 StackUsesCustom := 0 } IniRead, stackx, %ini%, settings, stack_x, 0 IniRead, stacky, %ini%, settings, stack_y, 0 IniRead, moveonstreet, %ini%, settings, move_on_street, preflop IniRead, SendTableUnderMouse, %ini%, settings, send_table_under_mouse, 1 if (SendTableUnderMouse = 1) SendActiveTable := 0 else SendActiveTable := 1 IniRead, DetectStarsAIs, %ini%, settings, detect_stars_allins, 1 IniRead, IncludeStars, %ini%, settings, include_stars, 1 IniRead, IncludeFulltilt, %ini%, settings, include_fulltilt, 0 IniRead, stars_nofold_col, %ini%, settings, stars_nofold_pixelcol, 0 IniRead, ft_fold_col, %ini%, settings, ft_fold_pixelcol, 0 IniRead, FoldHotkey, %ini%, settings, fold_hotkey, F3 Hotkey, %FoldHotkey%, foldReStack } moveIntoEmptySlot(id) { global totalslots global stackslot Loop, %totalslots% { i := a_index if (tableinslot%i% = "") { ;// if slot is empty if (i != stackslot) { ;// and not the slot used for the stack WinMove, ahk_id %id%,, coordxforslot%i%, coordyforslot%i% tableinslot%i% := id return 0 ;// slots were avail, move was successful } } } return 1 ;// return 1 if all slots full } starslist() { WinGet, list, list, ahk_group StarsTables Loop, %list% listAdd(tableids, list%a_index%) return tableids } fulltiltlist() { WinGet, list, list, ahk_group FullTiltTables Loop, %list% listAdd(tableids, list%a_index%) return tableids } alltableslist() { WinGet, list, list, ahk_group AllTables Loop, %list% listAdd(tableids, list%a_index%) return tableids } ;removes empty items (and trailing delimiters) CleanList(list, del="") { del := del="" ? "," : del Loop { StringReplace, list, list, %del%%del%, %del%, UseErrorLevel If ! ErrorLevel break } If InStr(list, del) = 1 StringTrimLeft, list, list, 1 If InStr(list, del,0,0) = StrLen(list) StringTrimRight, list, list, 1 return list } ; Some BetPot functions cp_hex2rgb(hex, del=",") { StringMid, r, hex, 1, 2 StringMid, g, hex, 3, 2 StringMid, b, hex, 5, 2 r:="0x" r, g:="0x" g, b:="0x" b r+=0 g+=0 b+=0 return R . del . G . del . B } ; finds number of specified pixels in a region GetPixelCount(x1, y1, x2, y2, color, id) { local device, context, pixs pixels := (x2 - x1 + 1)*(y2 - y1 + 1) If ( pixels <= 0 ) { ErrorLevel = 1 return } Display_CreateWindowCapture(device, context, pixs, id) count = 0 x = %x1% Loop { If ( x > x2 ) { break } y = %y1% Loop { If ( y > y2 ) { break } c := Display_GetPixel(context, x, y) If ( c = color ) { count++ } y++ } x++ } Display_DeleteWindowCapture(device, context, pixs) return count } GetStreetStars(id) { global debug device := "", context := "", pix := "" street := "pre" x1 := 382+4 y1 := 185+29 x2 := 395+4 y2 := 200+29 relStarsClientPoint(id, x1, y1) relStarsClientPoint(id, x2, y2) pixels := (x2 - x1 + 1)*(y2 - y1 + 1) if ( pixels <= 0 ) return street if (debug) debug_gui(id, x1, y1, x2, y2) Display_CreateWindowCapture(device, context, pixs, id) count = 0 x = %x1% Loop { if ( x > x2 ) break y = %y1% Loop { if ( y > y2 ) break c := Display_GetPixel(context, x, y) if ( c = 0xffffff ) { count++ if (count > 5) break } y++ } if (count > 5) break x++ } if ( count > 5 ) street := "flop" Display_DeleteWindowCapture(device, context, pixs) return street } GetStreetFT(id) { global debug device := "", context := "", pix := "" street := "pre" x1 := 378+4 y1 := 240+29 x2 := 394+4 y2 := 260+29 relFulltiltClientPoint(id, x1, y1) relFulltiltClientPoint(id, x2, y2) pixels := (x2 - x1 + 1)*(y2 - y1 + 1) if ( pixels <= 0 ) return street if (debug) debug_gui(id, x1, y1, x2, y2) Display_CreateWindowCapture(device, context, pixs, id) count = 0 x = %x1% Loop { if ( x > x2 ) break y = %y1% Loop { if ( y > y2 ) break c := Display_GetPixel(context, x, y) if ( c = 0xffffff ) { count++ if (count > 5) break } y++ } if (count > 5) break x++ } if ( count > 5 ) street := "flop" Display_DeleteWindowCapture(device, context, pixs) return street } debug_gui(id, x1, y1, x2, y2, delay=500) { WinGetPos, x, y, , , ahk_id%id% x1 += x y1 += y x2 += x y2 += y ;msgbox %x1% %y1%`n%x2% %y2% Gui, 2: +Alwaysontop +Lastfound +Owner Gui, 2: Color, cBlack WinSet, Transparent, 200 Gui, 2: -Caption w1 := x2 - x1 h1 := y2 - y1 Gui, 2: Show, w%w1% h%h1% x%x1% y%y1% NoActivate Sleep, %delay% Gui,2: Destroy } relStarsClientPoint(id, ByRef x, ByRef y) { ;// modifies x,y coords depending on your table size SysGet, xborder, 32 ;// 4 SysGet, yborder, 33 ;// 4 SysGet, caption, 4 ;// 25 ;//caption := caption + border ;// 29 ?? rw := 792 ;// stars standard table is 800x579, subtract two borders rh := 546 ;// subtract 1 caption and 2 borders WinGetPos, , , w, h, ahk_id%id% w := w - (2*xborder) h := h - (2*yborder) - caption x := Floor( (x / rw ) * w ) y := Floor( (y / rh) * h ) } relStarsWindowPoint(id, ByRef x, ByRef y) { SysGet, xborder, 32 ;// 4 SysGet, yborder, 33 ;// 4 SysGet, caption, 4 ;// 25 relStarsClientPoint(id, x, y) x := x + xborder y := y + yborder + caption } relStarsScreenPoint(id, ByRef x, ByRef y) { relStarsWindowPoint(id, x, y) WinGetPos, x1, y1, , , ahk_id%id% x += x1 y += y1 } relFullTiltClientPoint(id, ByRef x, ByRef y) { ;// modifies x,y coords depending on your table size SysGet, xborder, 32 ;// 4 SysGet, yborder, 33 ;// 4 SysGet, caption, 4 ;// 25 rw := 794 ;// ftp standard table is 802x580, subtract two borders rh := 547 ;// subtract 1 caption and 2 borders WinGetPos, , , w, h, ahk_id%id% w := w - (2*xborder) h := h - (2*yborder) - caption x := Floor( (x / rw ) * w ) y := Floor( (y / rh) * h ) } relFullTiltWindowPoint(id, ByRef x, ByRef y) { SysGet, xborder, 32 ;// 4 SysGet, yborder, 33 ;// 4 SysGet, caption, 4 ;// 25 relFullTiltClientPoint(id, x, y) x := x + xborder y := y + yborder + caption } PostLeftClick(x, y, table_id, activate=1) { ; ### JUK: Send the down left click, then the mouse-up messages. ; NOTE: This is relative to the top left of the client area and NOT the top left of the ; window (ie: It *doesn't* include the title-bar like AHK's MouseClick does!!!). If activate WinActivate, ahk_id%table_id% DllCall("SetCapture","Uint",table_id) PostMessage, 0x201, 0x0001, ((y<<16)^x), , ahk_id%table_id% PostMessage, 0x202 , 0, ((y<<16)^x), , ahk_id%table_id% DllCall("ReleaseCapture") } PostStarsClick(x, y, id) { relStarsClientPoint(id, x, y) PostLeftClick(x, y, id) } CallStars(id) { PostStarsClick(600,533,id) } RaiseStars(id) { PostStarsClick(730,520,id) } FoldStars(id) { PostStarsClick(416,501,id) Sleep, 20 PostStarsClick(412,498,id) Sleep, 20 PostStarsClick(416,478,id) } ;// PostFullTiltClick: input x,y including borders and captions (grabbed from windowspy?) PostFullTiltClick(x,y,id) { relFullTiltClientPoint(id, x, y) ;msgbox x %x% y %y% PostLeftClick(x, y, id) } FoldFT(id) { PostFullTiltClick(516, 501, id) Sleep, 20 PostFullTiltClick(546, 506, id) Sleep, 20 PostFullTiltClick(521, 535, id) } ;// input coordinates relative to full window id (coords including border and caption) same as built in PixelGetColor PixelColorA(col_x,col_y,id) { ; critical ; speed up ; d := "", c := "", p := "", pix := "" pix := "" Display_CreateWindowCapture(disp, cont, px, id) pix := Display_GetPixel(cont, col_x, col_y) Display_DeleteWindowCapture(disp, cont, px) oldfrmt := A_FormatInteger SetFormat, IntegerFast, hex pix += 0 ; Sets Var (which previously contained 11) to be 0xb. pix .= "" ; Necessary due to the "fast" mode. SetFormat, IntegerFast, %oldfrmt% return pix } ; based off Xander and Max1mums Display_CreateWindowCapture(ByRef device, ByRef context, ByRef pixels, id, redraw="1") { WinGetPos, , , w, h, ahk_id %id% device := DllCall("GetDC", "UInt", id) context := DllCall("gdi32.dll\CreateCompatibleDC", "UInt", device) ;pixels := DllCall("gdi32.dll\CreateCompatibleBitmap", "UInt", device, "Int", w, "Int", h) ;//DIB seems to have slightly better performance than Bitmap when grabbing multiple pixels at a time pixels := CreateDIBSection(device, w, h) DllCall("gdi32.dll\SelectObject", "UInt", context, "UInt", pixels) DllCall("PrintWindow", "UInt", id, "UInt", context, "UInt", 0) WinGet,ctrls,ControlList,ahk_id %id% Loop,Parse,ctrls,`n { class:=A_LoopField ControlGet,ctrlid,Hwnd,,%class%,ahk_id %id% ControlGet,visible,Visible,,,ahk_id %ctrlid% If visible=1 DllCall("RedrawWindow","UInt",ctrlid,"UInt",0,"UInt",0,"UInt", 1|16|64|2048) } DllCall("RedrawWindow","UInt",id,"UInt",0,"UInt",0,"UInt", 1|16|64|1024) } Display_DeleteWindowCapture(ByRef device, ByRef context, ByRef pixels) { DllCall("gdi32.dll\ReleaseDC", "UInt", device) DllCall("gdi32.dll\DeleteDC", "UInt", device) DllCall("gdi32.dll\DeleteDC", "UInt", context) DllCall("gdi32.dll\DeleteObject", "UInt", pixels) } Display_GetPixel(ByRef context, x, y) { pix := DllCall("GetPixel", "UInt", context, "Int", x, "Int", y) return pix } Display_CompareColors(ByRef bgr1, ByRef bgr2, ByRef variation) { c1 := bgr1 & 0xff c2 := bgr2 & 0xff if (abs(c1 - c2) > variation) return false c1 := (bgr1 >> 8) & 0xff c2 := (bgr2 >> 8) & 0xff if (abs(c1 - c2) > variation) return false c1 := (bgr1 >> 16) & 0xff c2 := (bgr2 >> 16) & 0xff if (abs(c1 - c2) > variation) return false return true } CreateDIBSection(hDC, nW, nH, bpp = 32, ByRef pBits = "") { NumPut(VarSetCapacity(bi, 40, 0), bi) NumPut(nW, bi, 4) NumPut(nH, bi, 8) NumPut(bpp, NumPut(1, bi, 12, "UShort"), 0, "Ushort") NumPut(0, bi,16) Return DllCall("gdi32\CreateDIBSection", "Uint", hDC, "Uint", &bi, "Uint", 0, "UintP", pBits, "Uint", 0, "Uint", 0) } ; From Rolands functions ; add item to the end of list listAdd( byRef list, item, del="," ) { list:=( list!="" ? ( list . del . item ) : item ) return list } ;removes said item from said list listDelItem( byRef list, item, del=",") { ifEqual, item,, return list list:=del . list . del StringReplace, list, list, %item%%del% StringTrimLeft, list, list, 1 StringTrimRight, list, list, 1 return list }
One thing I wanted to mention is your resolution detection is not advanced enough.My screen resolution is 1280 x 800 and if I minimize the poker table to the smallest it can go I can fit 4 tables.However if I mover my task bar to the side instead of the bottom I can increase the table size and still fit 4 tables with zero overlap but your software does not seem to recognize the new space and still says I can only fit 2 tables.With TOI I can run 4 of these sized tables.Just figured I would mention it.Thanks
thx Max, what was i not clearing? was i missing that extra DeleteDC? ppl please try his code and see if you get the lag
Well can anyone report on last version? It doesn't get "super laggy" for me with 30 tables opened.
Version 1.10 really focked up my computer.
I am runnig windows XP via boot camp on a mac pro with a good processor and 5gb ram and good video card.
I was using the function to move tables whenever action is required with 6 sng's open. It worked really well for the first 10-15 minutes. After that things really went bad.
At first it began lagging and the script stopped or something with the result of tables remaining in grid and i wasn't able to send them back to stack. I tried to stop the script and run it again but nothing worked.
I was just running pokerstars and firefox and i was using pokerstars black theme.
I am runnig windows XP via boot camp on a mac pro with a good processor and 5gb ram and good video card.
I was using the function to move tables whenever action is required with 6 sng's open. It worked really well for the first 10-15 minutes. After that things really went bad.
At first it began lagging and the script stopped or something with the result of tables remaining in grid and i wasn't able to send them back to stack. I tried to stop the script and run it again but nothing worked.
I was just running pokerstars and firefox and i was using pokerstars black theme.
Not 1.10, fixed version i posted on previous page.
Version 1.10 really focked up my computer.
I am runnig windows XP via boot camp on a mac pro with a good processor and 5gb ram and good video card.
I was using the function to move tables whenever action is required with 6 sng's open. It worked really well for the first 10-15 minutes. After that things really went bad.
At first it began lagging and the script stopped or something with the result of tables remaining in grid and i wasn't able to send them back to stack. I tried to stop the script and run it again but nothing worked.
I was just running pokerstars and firefox and i was using pokerstars black theme.
I am runnig windows XP via boot camp on a mac pro with a good processor and 5gb ram and good video card.
I was using the function to move tables whenever action is required with 6 sng's open. It worked really well for the first 10-15 minutes. After that things really went bad.
At first it began lagging and the script stopped or something with the result of tables remaining in grid and i wasn't able to send them back to stack. I tried to stop the script and run it again but nothing worked.
I was just running pokerstars and firefox and i was using pokerstars black theme.
Also, is there a way to close the script, or stop it? The "Start" "Stop" button has no effect on turning off the hotkey, RButton will still move the tables regardless which is fine, but I cant use right click for anything else on my computer and the only way I can stop the script is to Alt+Ctrl+Del and stop it.
EDIT: Well if I open, Start/Then Stop it will work so its fine.
EDIT: Well if I open, Start/Then Stop it will work so its fine.
i am running the new script and there is absolutely no lag, but it dosent detect when alot of the hands goto flop
after thinking about it, i think it is because my stack 0 and stack 1 is the same stack. so if stack 1 is available then it wont move the postflop TOI.
But seems the Max1mums has solved the lag problem
after thinking about it, i think it is because my stack 0 and stack 1 is the same stack. so if stack 1 is available then it wont move the postflop TOI.
But seems the Max1mums has solved the lag problem
Yeah I agree, LAG problem seems to be gone. I just 16 tabled for about 25 minutes and the program worked flawlessly. Now if I could just learn to 16 table a bit better...
Well I just wanted to help greg solve problems with pixelsearch function because he found it in some of my posts (and prove that it isn't hopeless ), I won't interrupt greg's work on his script any more if lag problem is gone.
its no interruption at all, i appreciate the help. this is what open source is all about.
"Stop" button should turn off hotkey..
i will try to implement Max's solutions
"Stop" button should turn off hotkey..
i will try to implement Max's solutions
Boo to open source!! I need to work like 24/7 to keep up with you guys!!!
Nice project! I have promised myself to never look in your code, because that would be not right (stealing free open-source code then selling), so no worries...
BTW Sorry to bump your thread, but do you guys have any idea what TableNinja uses instead of pixeldetection? I mean... it has no lag and stuff. Is it because its written in a more advanced language, or does he read the pokerstars log file or what? I absolutely hate pixel detection, it's so primitive.
Nice project! I have promised myself to never look in your code, because that would be not right (stealing free open-source code then selling), so no worries...
BTW Sorry to bump your thread, but do you guys have any idea what TableNinja uses instead of pixeldetection? I mean... it has no lag and stuff. Is it because its written in a more advanced language, or does he read the pokerstars log file or what? I absolutely hate pixel detection, it's so primitive.
And which tableninja functions may require pixelsearch at all? Timebank and I am back clicker? Or are you talking about FT version? It is always possible to track which files tableninja reads
p.s. you are always free to look at code cause it's free source and supposed to be opened for everyone.
p.s. you are always free to look at code cause it's free source and supposed to be opened for everyone.
im not into stars (and ft flickers on my machine) but i noticed the table that got put back into the stack got stacked on top...which seems a bummer to me...
+wait for bb clicker
Feedback is used for internal purposes. LEARN MORE