├── .gitattributes ├── LICENSE ├── README.md ├── Screenshot.PNG └── Sources ├── Class_TransparentListBox.ahk └── TransparentListBox_sample.ahk /.gitattributes: -------------------------------------------------------------------------------- 1 | # Auto detect text files and perform LF normalization 2 | * text=auto 3 | 4 | # Custom for Visual Studio 5 | *.cs diff=csharp 6 | *.sln merge=union 7 | *.csproj merge=union 8 | *.vbproj merge=union 9 | *.fsproj merge=union 10 | *.dbproj merge=union 11 | 12 | # Standard to msysgit 13 | *.doc diff=astextplain 14 | *.DOC diff=astextplain 15 | *.docx diff=astextplain 16 | *.DOCX diff=astextplain 17 | *.dot diff=astextplain 18 | *.DOT diff=astextplain 19 | *.pdf diff=astextplain 20 | *.PDF diff=astextplain 21 | *.rtf diff=astextplain 22 | *.RTF diff=astextplain 23 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | This is free and unencumbered software released into the public domain. 2 | 3 | Anyone is free to copy, modify, publish, use, compile, sell, or 4 | distribute this software, either in source code form or as a compiled 5 | binary, for any purpose, commercial or non-commercial, and by any 6 | means. 7 | 8 | In jurisdictions that recognize copyright laws, the author or authors 9 | of this software dedicate any and all copyright interest in the 10 | software to the public domain. We make this dedication for the benefit 11 | of the public at large and to the detriment of our heirs and 12 | successors. We intend this dedication to be an overt act of 13 | relinquishment in perpetuity of all present and future rights to this 14 | software under copyright law. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 17 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 18 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR 20 | OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 21 | ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 22 | OTHER DEALINGS IN THE SOFTWARE. 23 | 24 | For more information, please refer to 25 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Class_TransparentListBox 2 | Provides transparent listbox controls for AHK GUIs. 3 | 4 | Downloaded sources should be stored as UTF-8 with BOM. 5 | 6 | ![Screenshot](https://github.com/AHK-just-me/Class_TransparentListBox/blob/master/Screenshot.PNG) 7 | -------------------------------------------------------------------------------- /Screenshot.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/AHK-just-me/Class_TransparentListBox/e082bcca347183e7303f40bb95d3467036e96b89/Screenshot.PNG -------------------------------------------------------------------------------- /Sources/Class_TransparentListBox.ahk: -------------------------------------------------------------------------------- 1 | ; ====================================================================================================================== 2 | ; Namespace: TransparentListBox 3 | ; Function: Helper object for transparent ListBoxes 4 | ; Tested with: AHK 1.1.19.01 (A32/U32/U64) 5 | ; Tested on: Win 8.1 (x64) 6 | ; Version: 0.1.01.00/2013-10-03/just me - Initial release. 7 | ; 0.1.01.00/2015-01-17/just me - Added scrolling by keys without a vertical scroll bar. 8 | ; ====================================================================================================================== 9 | ; CLASS TransparentListBox 10 | ; 11 | ; The class provides transparent background for ListBox controls. The whole stuff is done by subclassing the control. 12 | ; 13 | ; On creation via 'TLB := New TranparentListBox' you have to pass the HWNDs of the ListBox and the underlying control 14 | ; or window. Additionally you may pass a text color and a seperate color to draw selected items with. Colors have to 15 | ; be passed as RGB integer values. 16 | ; 17 | ; After you've changed the content or size of the ListBox, or if you want to change the text or selection color, you 18 | ; have to call 'TLB.Update()' once, passing the new color values if desired. Thw whole action should be enclosed by 19 | ; two calls of 'TLB.SetRedraw(False/True)' to avoid flickering as far as possible. 20 | ; 21 | ; Due to the complex way ListBoxes do their scrolling not all options of a common ListBox are supported. 22 | ; You have to keep in mind the following restrictions: 23 | ; - The new object instance has to be created before the Gui is shown. 24 | ; - The ListBox must not have a horizontal scroll bar (because I haven't a clue how to do the scrolling). 25 | ; - The Multi(select) option is not supported as yet (but it may be feasible). 26 | ; - Scrolling is not 'smooth'. 27 | ; ====================================================================================================================== 28 | Class TransparentListBox { 29 | ; ------------------------------------------------------------------------------------------------------------------- 30 | ; Constructor 31 | ; ------------------------------------------------------------------------------------------------------------------- 32 | __New(HLB, HBG, TxtColor := "", SelColor := "", SelBkGnd := "", SelBkTrans := 255) { 33 | ; ---------------------------------------------------------------------------------------------------------------- 34 | ; HLB : HWND of the ListBox. 35 | ; HBG : HWND of the control or Gui containing the background. 36 | ; TxtColor : Optional - Text color (RGB integer value, e.g. 0xRRGGBB). 37 | ; SelColor : Optional - Selected text color (RGB integer value, e.g. 0xRRGGBB). 38 | ; SelBkGnd : Optional - Color of the selection rectangel (RGB integer value, e.g. 0xRRGGBB). 39 | ; SelBkTrans : Optional - Transparency of the selection rectangle (0 - 255). 40 | ; ---------------------------------------------------------------------------------------------------------------- 41 | Static LB_GETCOUNT := 0x018B, LB_GETITEMRECT := 0x0198, WM_GETFONT := 0x0031 42 | This.HLB := HLB 43 | This.HBG := HBG 44 | This.Parent := DllCall("User32.dll\GetParent", "Ptr", HLB, "UPtr") 45 | This.CtrlID := DllCall("User32.dll\GetDlgCtrlID", "Ptr", HLB, "UPtr") 46 | HDC := DllCall("User32.dll\GetDC", "Ptr", HLB, "UPtr") 47 | If (TxtColor <> "") 48 | This.TxtColor := ((TxtColor >> 16) & 0xFF) | (TxtColor & 0x00FF00) | ((TxtColor & 0xFF) << 16) 49 | Else 50 | This.TxtColor := DllCall("Gdi32.dll\GetTextColor", "Ptr", HDC, "UInt") 51 | If (SelColor <> "") 52 | This.SelColor := ((SelColor >> 16) & 0xFF) | (SelColor & 0x00FF00) | ((SelColor & 0xFF) << 16) 53 | If (SelBkGnd <> "") { 54 | This.SelBkGnd := ((SelBkGnd >> 16) & 0xFF) | (SelBkGnd & 0x00FF00) | ((SelBkGnd & 0xFF) << 16) 55 | This.SelBkTrans := (SelBkTrans & 0xFF) 56 | } 57 | DllCall("User32.dll\ReleaseDC", "Ptr", HLB, "Ptr", HDC) 58 | VarSetCapacity(RECT, 16, 0) 59 | SendMessage, %LB_GETITEMRECT%, 0, % &RECT, , ahk_id %HLB% 60 | This.ItemWidth := NumGet(RECT, 8, "Int") - NumGet(RECT, 0, "Int") 61 | This.ItemHeight := NumGet(RECT, 12, "Int") - NumGet(RECT, 4, "Int") 62 | SendMessage, %LB_GETCOUNT%, 0, 0, , ahk_id %HLB% 63 | This.ItemCount := ErrorLevel 64 | SendMessage, %WM_GETFONT%, 0, 0, , ahk_id %HLB% 65 | This.Font := ErrorLevel 66 | ControlGet, Content, List, , , ahk_id %HLB% 67 | This.Items := StrSplit(Content, "`n") 68 | This.HasBackground := False 69 | This.TopIndex := This.CurSel := -1 70 | This.Drawing := True 71 | ControlGet, Styles, Style, , , ahk_id %HLB% 72 | If (Styles & 0x00200000) { ; WS_VSCROLL -> the lisbox has a vertical scroll bar 73 | VarSetCapacity(SI, 28, 0) ; SCROLLINFO 74 | NumPut(28, SI, 0, "UInt") ; cbSize 75 | NumPut(3, SI, 4, "UInt") ; fMask = SIF_RANGE | SIF_PAGE 76 | DllCall("User32.dll\GetScrollInfo", "Ptr", HLB, "Int", 1, "Ptr", &SI) 77 | This.SIMin := NumGet(SI, 8, "Int") ; nMin 78 | This.SIMax := NumGet(SI, 12, "Int") ; nMax 79 | This.SIPage := NumGet(SI, 16, "UInt") ; nPage 80 | } 81 | Else { 82 | DllCall("User32.dll\GetClientRect", "Ptr", HLB, "Ptr", &RECT) 83 | This.SIMin := 0 84 | This.SIPage := NumGet(RECT, 12, "Int") // This.ItemHeight 85 | This.SIMax := This.ItemCount - 1 86 | } 87 | SCCB := RegisterCallback("TransparentListBox.SubClassCallback") 88 | DllCall("Comctl32.dll\SetWindowSubclass", "Ptr", HLB, "Ptr", SCCB, "Ptr", HLB, "Ptr", &This) 89 | This.SCCB := SCCB 90 | } 91 | ; ------------------------------------------------------------------------------------------------------------------- 92 | ; Destructor 93 | ; ------------------------------------------------------------------------------------------------------------------- 94 | __Delete() { 95 | Static SRCCOPY := 0x00CC0020 96 | If (This.BMPDC) { 97 | BGDC := DllCall("User32.dll\GetDC", "Ptr", This.HBG, "UPtr") 98 | DllCall("Gdi32.dll\BitBlt", "Ptr", BGDC, "Int", This.Left, "Int", This.Top, "Int", This.Width 99 | , "Int", This.Height, "Ptr", This.BMPDC, "Int", 0, "Int", 0, "UInt", SRCCOPY) 100 | DllCall("User32.dll\ReleaseDC", "Ptr", This.HBG, "Ptr", BGDC) 101 | DllCall("Gdi32.dll\DeleteDC", "Ptr", This.BMPDC) 102 | DllCall("Gdi32.dll\DeleteObject", "Ptr", This.HBMP) 103 | This.BMPDC := This.HBMP := 0 104 | } 105 | If (This.SELDC) { 106 | DllCall("Gdi32.dll\DeleteDC", "Ptr", This.SELDC) 107 | DllCall("Gdi32.dll\DeleteObject", "Ptr", This.HSEL) 108 | } 109 | If (This.HLB) { 110 | DllCall("Comctl32.dll\RemoveWindowSubclass", "Ptr", This.HLB, "Ptr", This.SCCB, "Ptr", This.HLB) 111 | } 112 | } 113 | ; ------------------------------------------------------------------------------------------------------------------- 114 | ; Subclass callback function - for internal use only 115 | ; ------------------------------------------------------------------------------------------------------------------- 116 | SubClassCallback(uMsg, wParam, lParam, IdSubclass, RefData) { 117 | Critical 100 118 | hWnd := This ; first parameter 'hWnd' is passed as 'This' 119 | Return Object(RefData).SubClassProc(hWnd, uMsg, wParam, lParam) 120 | } 121 | ; ------------------------------------------------------------------------------------------------------------------- 122 | ; Subclassproc - for internal use only 123 | ; ------------------------------------------------------------------------------------------------------------------- 124 | SubClassProc(hWnd, uMsg, wParam, lParam) { 125 | Static LB := {GETCOUNT: 0x018B, GETCURSEL: 0x0188, GETITEMRECT: 0x0198, GETTEXT: 0x0189,GETTEXTLEN: 0x018A 126 | , GETTOPINDEX: 0x018E, ITEMFROMPOINT: 0x01A9, SETCURSEL: 0x0186} 127 | Static LBN := {SELCHANGE: 1, DBLCLK: 2} 128 | Static WM := {DESTROY: 0x0002, DRAWITEM: 0x002B, LBUTTONDBLCLK: 0x0203, ERASEBKGND: 0x0014, HSCROLL: 0x0114 129 | , KEYDOWN: 0x0100, KILLFOCUS: 0x0008, LBUTTONDOWN: 0x0201, LBUTTONUP: 0x0202, MOUSEWHEEL: 0x020A 130 | , PAINT: 0x000F, SETFOCUS: 0x0007, SETREDRAW: 0x000B, VSCROLL: 0x0115} 131 | Static VK := {DOWN: 0x28, END: 0x23, HOME: 0x24, NEXT: 0x22, PRIOR: 0x21, UP: 0x26 132 | , 0x21: 1, 0x22: 1, 0x23: 1, 0x24: 1, 0x26: 1, 0x28: 1} 133 | Static SRCCOPY := 0x00CC0020 134 | Static DrawingMsg := "" 135 | ; ---------------------------------------------------------------------------------------------------------------- 136 | ; Painting 137 | ; ---------------------------------------------------------------------------------------------------------------- 138 | ; WM_PAINT message 139 | If (uMsg = WM.PAINT) { 140 | VarSetCapacity(PAINTSTRUCT, A_PtrSize + (4 * 7) + 32 + (A_PtrSize - 4), 0) 141 | LBDC := DllCall("USer32.dll\BeginPaint", "Ptr", This.HLB, "Ptr", &PAINTSTRUCT, "UPtr") 142 | SendMessage, % LB.GETCURSEL, 0, 0, , ahk_id %hWnd% 143 | CurSel := ErrorLevel 144 | SendMessage, % LB.GETTOPINDEX, 0, 0, , ahk_id %hWnd% 145 | TopIndex := ErrorLevel 146 | This.TopIndex := TopIndex 147 | This.CurSel := CurSel 148 | DllCall("Gdi32.dll\BitBlt", "Ptr", LBDC, "Int", 0, "Int", 0, "Int", This.Width, "Int", This.Height 149 | , "Ptr", This.BMPDC, "Int", 0, "Int", 0, "UInt", SRCCOPY) 150 | HFONT := DllCall("Gdi32.dll\SelectObject", "Ptr", LBDC, "Ptr", This.Font, "UPtr") 151 | DllCall("Gdi32.dll\SetBkMode", "Ptr", LBDC, "Int", 1) ; TRANSPARENT 152 | VarSetCapacity(RECT, 16, 0) 153 | SendMessage, % LB.GETITEMRECT, %TopIndex%, &RECT, , ahk_id %hWnd% 154 | While (TopIndex < This.ItemCount) && (NumGet(RECT, 12, "Int") <= This.Height) { 155 | If (This.SELDC) && (TopIndex = CurSel) { 156 | L := NumGet(RECT, 0, "Int"), T := NumGet(RECT, 4, "Int") 157 | W := NumGet(RECT, 8, "Int") - L, H := NumGet(RECT, 12, "Int") - T 158 | If (This.SelBkTrans = 255) 159 | DllCall("Gdi32.dll\BitBlt", "Ptr", LBDC, "Int", L, "Int", T, "Int", W, "Int", H 160 | , "Ptr", This.SELDC, "Int", 0, "Int", 0, "UInt", SRCCOPY) 161 | Else 162 | DllCall("Gdi32.dll\GdiAlphaBlend", "Ptr", LBDC, "Int", L, "Int", T, "Int", W, "Int", H 163 | , "Ptr", This.SELDC, "Int", 0, "Int", 0, "Int", W, "Int", H 164 | , "UInt", (This.SelBkTrans << 16)) 165 | } 166 | Txt := This.Items[TopIndex + 1], Len := StrLen(Txt) 167 | TextColor := (TopIndex = CurSel ? This.SelColor : This.TxtColor) 168 | DllCall("Gdi32.dll\SetTextColor", "Ptr", LBDC, "UInt", TextColor) 169 | NumPut(NumGet(RECT, 0, "Int") + 3, RECT, 0, "Int") 170 | DllCall("User32.dll\DrawText", "Ptr", LBDC, "Ptr", &Txt, "Int", Len, "Ptr", &RECT, "UInt", 0x0840) 171 | NumPut(NumGet(RECT, 0, "Int") - 3, RECT, 0, "Int") 172 | DllCall("User32.dll\OffsetRect", "Ptr", &RECT, "Int", 0, "Int", This.ItemHeight) 173 | TopIndex++ 174 | } 175 | DllCall("Gdi32.dll\SelectObject", "Ptr", LBDC, "Ptr", HFONT, "UPtr") 176 | DllCall("User32.dll\EndPaint", "Ptr", &PAINTSTRUCT) 177 | Return 0 178 | } 179 | ; WM_ERASEBKGND message 180 | If (uMsg = WM.ERASEBKGND) { 181 | If (!This.HasBackground) { ; processed once after creation/update 182 | VarSetCapacity(RECT, 16, 0) 183 | DllCall("User32.dll\GetClientRect", "Ptr", This.HLB, "Ptr", &RECT) 184 | This.Width := W := NumGet(RECT, 8, "Int") 185 | This.Height := H := NumGet(RECT, 12, "Int") 186 | DllCall("User32.dll\ClientToScreen", "Ptr", This.HLB, "Ptr", &RECT) 187 | DllCall("User32.dll\ScreenToClient", "Ptr", This.HBG, "Ptr", &RECT) 188 | This.Left := L := NumGet(RECT, 0, "Int") 189 | This.Top := T := NumGet(RECT, 4, "Int") 190 | BGDC := DllCall("User32.dll\GetDC", "Ptr", This.HBG, "UPtr") 191 | BMPDC := DllCall("Gdi32.dll\CreateCompatibleDC", "Ptr", BGDC, "UPtr") 192 | HBMP := DllCall("Gdi32.dll\CreateCompatibleBitmap", "Ptr", BGDC, "Int", W, "Int", H, "UPtr") 193 | DllCall("Gdi32.dll\SelectObject", "Ptr", BMPDC, "Ptr", HBMP) 194 | DllCall("Gdi32.dll\BitBlt", "Ptr", BMPDC, "Int", 0, "Int", 0, "Int", W, "Int", H 195 | , "Ptr", BGDC, "Int", L, "Int", T, "UInt", SRCCOPY) 196 | If (This.SelBkGnd <> "") { 197 | SELDC := DllCall("Gdi32.dll\CreateCompatibleDC", "Ptr", BGDC, "UPtr") 198 | HSEL := DllCall("Gdi32.dll\CreateCompatibleBitmap", "Ptr", BGDC, "Int", This.ItemWidth 199 | , "Int", This.ItemHeight, "UPtr") 200 | DllCall("Gdi32.dll\SelectObject", "Ptr", SELDC, "Ptr", HSEL) 201 | Brush := DllCall("Gdi32.dll\CreateSolidBrush", "UInt", This.SelBkGnd, "UPtr") 202 | VarSetCapacity(RECT, 16, 0) 203 | NumPut(This.ItemWidth, RECT, 8, "Int") 204 | NumPut(This.ItemHeight, RECT, 12, "Int") 205 | DllCall("User32.dll\FillRect", "Ptr", SELDC, "Ptr", &RECT, "Ptr", Brush) 206 | DllCall("Gdi32.dll\DeleteObject", "Ptr", Brush) 207 | This.SELDC := SELDC 208 | This.HSEL := HSEL 209 | } 210 | DllCall("User32.dll\ReleaseDC", "Ptr", This.HBG, "Ptr", BGDC) 211 | This.BMPDC := BMPDC 212 | This.HBMP := HBMP 213 | LBDC := DllCall("User32.dll\GetDC", "Ptr", hWnd, "UPtr") 214 | DllCall("Gdi32.dll\BitBlt", "Ptr", LBDC, "Int", 0, "Int", 0, "Int", W, "Int", H 215 | , "Ptr", This.BMPDC, "Int", 0, "Int", 0, "UInt", SRCCOPY) 216 | DllCall("User32.dll\ReleaseDC", "Ptr", hWnd, "Ptr", LBDC) 217 | This.HasBackground := True 218 | } 219 | Return True 220 | } 221 | ; ---------------------------------------------------------------------------------------------------------------- 222 | ; Selection & Focus 223 | ; ---------------------------------------------------------------------------------------------------------------- 224 | ; WM_KILLFOCUS and WM_SETFOCUS messages 225 | If (uMsg = WM.KILLFOCUS) Or (uMsg = WM.SETFOCUS) { ; not processed 226 | Return 0 227 | } 228 | ; LB_SETCURSEL message 229 | If (uMsg = LB.SETCURSEL) { 230 | If (This.Drawing) { 231 | DrawingMsg := uMsg 232 | This.SetRedraw(False) 233 | } 234 | DllCall("Comctl32.dll\DefSubclassProc", "Ptr", hWnd, "UInt", uMsg, "Ptr", wParam, "Ptr", lParam) 235 | If (DrawingMsg = LB.SETCURSEL) { 236 | This.SetRedraw(True) 237 | DrawingMsg := "" 238 | } 239 | SendMessage, % LB.GETTOPINDEX, 0, 0, , ahk_id %hWnd% 240 | TopIndex := ErrorLevel 241 | DllCall("User32.dll\SetScrollPos", "Ptr", hWnd, "Int", 1, "Int", TopIndex, "UInt", True) 242 | Return 0 243 | } 244 | ; ---------------------------------------------------------------------------------------------------------------- 245 | ; Keyboard 246 | ; ---------------------------------------------------------------------------------------------------------------- 247 | ; WM_KEYDOWN message 248 | If (uMsg = WM.KEYDOWN) { 249 | If VK.HasKey(wParam) { 250 | CurSel := This.CurSel 251 | CurSel := (wParam = VK.DOWN) ? (CurSel + 1) 252 | : (wParam = VK.UP) ? (CurSel - 1) 253 | : (wParam = VK.Next) ? (CurSel + This.SIPage - 1) 254 | : (wParam = VK.PRIOR) ? (CurSel - This.SIPage + 1) 255 | : (wParam = VK.HOME) ? This.SIMin 256 | : (wParam = VK.END) ? This.SIMax 257 | : CurSel 258 | CurSel := (CurSel < This.SIMin) ? This.SIMin : (CurSel > This.SIMax) ? This.SIMax : CurSel 259 | If (Cursel <> This.Cursel) { 260 | If (This.Drawing) { 261 | DrawingMsg := uMsg 262 | This.SetRedraw(False) 263 | } 264 | SendMessage, % LB.SETCURSEL, %CurSel%, 0, , ahk_id %hWnd% 265 | If (DrawingMsg = WM.KEYDOWN) { 266 | This.SetRedraw(True) 267 | DrawingMsg := "" 268 | } 269 | PostMessage, 0x0111, % (This.CtrlID | (LBN.SELCHANGE << 16)), %hWnd%, , % "ahk_id " . This.Parent 270 | This.Cursel := CurSel 271 | } 272 | } 273 | Return 0 274 | } 275 | ; ---------------------------------------------------------------------------------------------------------------- 276 | ; Mouse 277 | ; ---------------------------------------------------------------------------------------------------------------- 278 | ; WM_LBUTTONDOWN message 279 | If (uMsg = WM.LBUTTONDOWN) { 280 | ControlFocus, , ahk_id %hWnd% 281 | Return 0 282 | } 283 | ; WM_LBUTTONUP message 284 | If (uMsg = WM.LBUTTONUP) { 285 | SendMessage, % LB.ITEMFROMPOINT, 0, %lParam%, , ahk_id %hWnd% 286 | Item := ErrorLevel 287 | If !(Item & 0xFFFF0000) && (Item <> This.CurSel) { 288 | If (This.Drawing) { 289 | DrawingMsg := uMsg 290 | This.SetRedraw(False) 291 | } 292 | SendMessage, % LB.SETCURSEL, %Item%, 0, , ahk_id %hWnd% 293 | If (DrawingMsg = WM.LBUTTONUP) { 294 | This.SetRedraw(True) 295 | DrawingMsg := "" 296 | } 297 | This.Cursel := Item 298 | PostMessage, 0x0111, % (This.CtrlID | (LBN.SELCHANGE << 16)), %hWnd%, , % "ahk_id " . This.Parent 299 | } 300 | Return 0 301 | } 302 | ; WM_LBUTTONDBLCLK message 303 | If (uMsg = WM.LBUTTONDBLCLK) { 304 | PostMessage, 0x0111, % (This.CtrlID | (LBN.DBLCLK << 16)), %hWnd%, , % "ahk_id " . This.Parent 305 | Return 0 306 | } 307 | ; WM_MOUSEWHEEL message 308 | If (uMsg = WM.MOUSEWHEEL) { 309 | Delta := (wParam >> 16) & 0xFFFF 310 | If ((Delta <= 0x7FFF) && (This.TopIndex > This.SIMin)) 311 | Or ((Delta > 0x7FFF) && ((This.TopIndex + This.SIPage) <= This.SIMax)) 312 | PostMessage, % WM.VSCROLL, % (Delta > 0x7FFF ? 1 : 0), 0, , ahk_id %hWnd% 313 | Return 0 314 | } 315 | ; ---------------------------------------------------------------------------------------------------------------- 316 | ; Scrolling 317 | ; ---------------------------------------------------------------------------------------------------------------- 318 | ; WM_HCROLL message 319 | If (uMsg = WM.HSCROLL) { 320 | Return 0 321 | } 322 | ; WM_VSCROLL message 323 | If (uMsg = WM.VSCROLL) { 324 | If (((wParam = 1) || (wParam = 3) || (wParam = 7)) && ((This.TopIndex + This.SIPage) > This.SIMax)) 325 | Or (((wParam = 0) || (wParam = 2) || (wParam = 6)) && (This.TopIndex <= This.SIMin)) 326 | Or (wParam = 8) || (wParam = 4) 327 | Return 0 328 | If (This.Drawing) { 329 | DrawingMsg := uMsg 330 | This.SetRedraw(False) 331 | } 332 | DllCall("Comctl32.dll\DefSubclassProc", "Ptr", hWnd, "UInt", uMsg, "Ptr", wParam, "Ptr", lParam) 333 | If (DrawingMsg = WM.VSCROLL) { 334 | This.SetRedraw(True) 335 | DrawingMsg := "" 336 | } 337 | SendMessage, % LB.GETTOPINDEX, 0, 0, , ahk_id %hWnd% 338 | This.TopIndex := ErrorLevel 339 | ; Seems that you must not return here, because DefSubClassProc apparently updates the scroll bar 340 | ; position on the second call!!! 341 | ; Seems the above isn't true. 342 | ScrollPos := DllCall("User32.dll\GetScrollPos", "Ptr", hWnd, "Int", 1, "Int") ; SB_VERT = 1 343 | DllCall("User32.dll\SetScrollPos", "Ptr", hWnd, "Int", 1, "Int", ScrollPos, "UInt", True) 344 | Return 0 345 | } 346 | ; ---------------------------------------------------------------------------------------------------------------- 347 | ; Destroy 348 | ; ---------------------------------------------------------------------------------------------------------------- 349 | ; WM_DESTROY message 350 | If (uMsg = WM.DESTROY) { 351 | This.__Delete() 352 | } 353 | Return DllCall("Comctl32.dll\DefSubclassProc", "Ptr", hWnd, "UInt", uMsg, "Ptr", wParam, "Ptr", lParam) 354 | } 355 | ; ------------------------------------------------------------------------------------------------------------------- 356 | ; Update the instance variables 357 | ; ------------------------------------------------------------------------------------------------------------------- 358 | UpDate(TxtColor := "", SelColor := "", SelBkGnd := "", SelBkTrans := "") { 359 | ; ---------------------------------------------------------------------------------------------------------------- 360 | ; Optional TxtColor : New text color (RGB integer value, e.g. 0xRRGGBB). 361 | ; Optional SelColor : New selected text color (RGB integer value, e.g. 0xRRGGBB). 362 | ; Changes of the content or the size of the ListBox will be processed automatically. 363 | ; ---------------------------------------------------------------------------------------------------------------- 364 | Drawing := This.Drawing 365 | If (Drawing) 366 | This.SetRedraw(False) 367 | This.__Delete() 368 | If (TxtColor = "") 369 | If (This.TxtColor) 370 | TxtColor := ((This.TxtColor >> 16) & 0xFF) | (This.TxtColor & 0x00FF00) | ((This.TxtColor & 0xFF) << 16) 371 | If (SelColor = "") 372 | If (This.SelColor) 373 | SelColor := ((This.SelColor >> 16) & 0xFF) | (This.SelColor & 0x00FF00) | ((This.SelColor & 0xFF) << 16) 374 | If (SelBkGnd = "") 375 | If (This.SelBkGnd) 376 | SelBkGnd := ((This.SelBkGnd >> 16) & 0xFF) | (This.SelBkGnd & 0x00FF00) | ((This.SelBkGnd & 0xFF) << 16) 377 | If (SelBkTrans = "") 378 | If (This.SelBkTrans) 379 | SelBkTrans := This.SelBkTrans 380 | This.__New(This.HLB, This.HBG, TxtColor, SelColor, SelBkGnd, SelBkTrans) 381 | If (Drawing) 382 | This.SetRedraw(True) 383 | Return True 384 | } 385 | ; ------------------------------------------------------------------------------------------------------------------- 386 | ; Set Redrawing True/False 387 | ; ------------------------------------------------------------------------------------------------------------------- 388 | SetRedraw(Mode) { 389 | ; It's highly recommended to call this function instead of using GuiControl, -/+Redraw, 390 | ; because the drawing state will be stored internally for use by other methods. 391 | Static WM_SETREDRAW := 0x000B 392 | Mode := !!Mode 393 | This.Drawing := Mode 394 | SendMessage, %WM_SETREDRAW%, %Mode%, 0, , % "ahk_id " . This.HLB 395 | If (Mode) 396 | WinSet, Redraw, , % "ahk_id " . This.HLB 397 | Return True 398 | } 399 | } -------------------------------------------------------------------------------- /Sources/TransparentListBox_sample.ahk: -------------------------------------------------------------------------------- 1 | #NoEnv 2 | Loop, %A_WinDir%\Web\Wallpaper\*.jpg, 0, 1 3 | { 4 | PicFile := A_LoopFileLongPath 5 | Break 6 | } 7 | ; PicFile := A_WinDir . "\Web\Wallpaper\Blaues Fenster.jpg" ; German Win XP 8 | ; PicFile := A_WinDir . "\Web\Wallpaper\Landscapes\img7.jpg" ; Win 7 9 | ; PicFile := A_WinDir . "\Web\Wallpaper\theme2\img10.jpg" ; Win 8.1 10 | Content := "One|Two|Three|Four|Five|Six|Seven|Eight|Nine|Ten|Eleven|Twelve|Thirteen|Fourteen|Fifteen|Sixteen" 11 | ; ---------------------------------------------------------------------------------------------------------------------- 12 | Global hMain 13 | Gui, New, hwndhMain 14 | Gui, Font, s12 15 | Gui, Add, Picture, x0 y0 w600 h400 hwndhPic, %PicFile% 16 | Gui, Add, ListBox, x50 y50 w200 r8 vLB1 gSel1 Choose1, %Content% 17 | Gui, Add, ListBox, x+100 yp wp hp hwndhLB vLB Choose1 gSelection -VScroll -E0x0200, %Content% 18 | TLB := New TransparentListBox(hLB, hPic, 0xFFFFFF, 0x000000, 0xFFFFFF, 128) 19 | Gui, Show, w600 h400, Transparent ListBox 20 | Return 21 | ; ---------------------------------------------------------------------------------------------------------------------- 22 | GuiClose: 23 | ExitApp 24 | ; ---------------------------------------------------------------------------------------------------------------------- 25 | #If WinActive("ahk_id " . hMain) 26 | !x:: 27 | Random, R, 0, % TLB.ItemCount 28 | GuiControl, %hMain%:Choose, LB, %R% 29 | Return 30 | #If 31 | ; ---------------------------------------------------------------------------------------------------------------------- 32 | Selection: 33 | GuiControlGet, LB 34 | ToolTip, Selected: %LB%`nA_GuiEvent: %A_GuiEvent%`nA_EventInfo: %A_EventInfo% 35 | SetTimer, KillTT, -750 36 | Return 37 | Sel1: 38 | GuiControlGet, LB1 39 | ToolTip, Selected: %LB1%`nA_GuiEvent: %A_GuiEvent%`nA_EventInfo: %A_EventInfo% 40 | SetTimer, KillTT, -750 41 | Return 42 | KillTT: 43 | ToolTip 44 | Return 45 | ; ---------------------------------------------------------------------------------------------------------------------- 46 | #Include Class_TransparentListBox.ahk --------------------------------------------------------------------------------