WinBatch Tech Support Home

Database Search

If you can't find the information using the categories below, post a question over in our WinBatch Tech Support Forum.

TechHome

Samples

Can't find the information you are looking for here? Then leave a message over on our WinBatch Tech Support Forum.

Horizontal Scroll Bars


Answer:

I read some earlier posts about winbatch not supporting scroll bar capability. I need to display a list of strings that can be up to 512 characters long. Scrolling down is supportted with an itemlistbox, however I can not scroll horizontally.....

Any suggestions are greatly appreciated!

Answer #1:

There are many ways to do it.

One of these ways...
You might like to check out a couple of UDFs I made a while ago to display a plain Multiline Edit box with horizontal scroll bar inside a WinBatch Dialog. Nothing fancy, but you can Set and Get the text in a basic way too.

They can be found at :

http://winbatch.hpdd.de/MyWbtHelp/htm/Dialog.EditboxWithScrollbars.htm

Answer #2:

MSHTML inside a Winbatch Dialog can do it...

;Topic:  Scroll bar Capability? (1 of 2), Read 15 times
;Conf:  WinBatch Dialogs
;From:  sports65g gheathcote@commpower.com
;Date:  Wednesday, March 01, 2006 04:03 PM
;
;I read some earlier posts about winbatch not supporting scroll bar capability. I need to display a list of strings that
;can be up to 512 characters long. Scrolling down is supportted with an itemlistbox, however I can not scroll horizontally.....
;
;Any suggestions are greatly appreciated!
;
;Thanks,
;Garrett

;   MSHTML can handle that for you...

#DefineSubRoutine MyDialogCallbackProc(MyDialog_Handle,MyDialog_Message,MyDialog_ID,MyDialog_EventInfo,rsvd)

   MSG_INIT=0                ; The one-time initialization
   MSG_TIMER=1               ; Timer event
   ;Return code constants
   RET_DO_CANCEL=0           ; Cancels dialog
   RET_DO_DEFAULT= -1        ; Continue with default processing for control
   RET_DO_NOT_EXIT= -2       ; Do not exit the dialog
   MSG_BUTTONPUSHED=2        ; Pushbutton or Picturebutton
   MSG_COMEVENT=14           ; COMCONTROL Event notification from DialogObject (NOT DialogProcOptions)

   Switch MyDialog_Message                                  ; Switch based on Dialog Message type
      Case MSG_INIT                                         ; Standard Initialization message
         DialogProcOptions(MyDialog_Handle,MSG_TIMER,1000)
;         DialogProcOptions(MyDialog_Handle,MSG_BUTTONPUSHED,@TRUE)
;         DialogObject(MyDialog_Handle,003,DLGOBJECT_ADDEVENT,"ComEventName",1000)

         document = DialogObject(MyDialog_Handle, 003, 3)
         document.writeln(`<h3>Please View Text</h3>`)
         document.writeln(`<TEXTAREA id="MyTextArea" rows="20" cols="625"></TEXTAREA>`)
         document.close()

         document.bgcolor = "Powderblue"
         document.body.style.border = ".25mm solid blue"
         document.body.all.MyTextArea.style.backgroundColor = "Whitesmoke"
         document.body.all.MyTextArea.Value = PopulateTextArea()  ;<-- set the text...

         Return(RET_DO_DEFAULT)

     Case MSG_BUTTONPUSHED
        Switch MyDialog_ID
           Case 001                                        ; ID 001  OK
              Return(RET_DO_DEFAULT)

           Case 002                                        ; ID 002  Cancel
              Return(RET_DO_DEFAULT)

        EndSwitch                                          ; MyDialog_ID
        Return(RET_DO_DEFAULT)

     Case MSG_COMEVENT                                     ; ID 003  COM Control 1
        Return(RET_DO_DEFAULT)

   EndSwitch                                                ; MyDialog_Message
   Return(RET_DO_DEFAULT)
#EndSubRoutine                                              ; End of Dialog Callback MyDialogCallbackProc

;============================================================

#DefineFunction PopulateTextArea()
   TextForTA = ""
   For x = 1 To 30
      ThisLine = ""
      For y = 1 To 300
         ThisLine = ItemInsert("X", -1, ThisLine, " ")
      Next
      TextForTA = ItemInsert(ThisLine, -1, TextForTA, @LF)
   Next
   Return(TextForTA)
#EndFunction

;============================================================
;============================================================

MyDialogFormat=`WWWDLGED,6.1`

MyDialogCaption=`TextArea with Scrollbars`
MyDialogX=002
MyDialogY=033
MyDialogWidth=406
MyDialogHeight=252
MyDialogNumControls=003
MyDialogProcedure=`MyDialogCallbackProc`
MyDialogFont=`DEFAULT`
MyDialogTextColor=`DEFAULT`
MyDialogBackground=`DEFAULT,DEFAULT`
MyDialogConfig=0

MyDialog001=`111,231,036,012,PUSHBUTTON,DEFAULT,"OK",1,1,32,DEFAULT,DEFAULT,DEFAULT`
MyDialog002=`259,231,036,012,PUSHBUTTON,DEFAULT,"Cancel",0,2,DEFAULT,DEFAULT,DEFAULT,DEFAULT`
MyDialog003=`007,005,388,220,COMCONTROL,DEFAULT,"MSHTML:",DEFAULT,3,DEFAULT,DEFAULT,DEFAULT,DEFAULT`

ButtonPushed=Dialog("MyDialog")

Answer #3:

The attached script implements two methods of displaying truncated lines in a listbox.
  1. Displays item under the mouse in a static/vary text control.
  2. Uses a Tooltip control which returns the item to the caller.
The second method uses a cut down version of udfTTAddEx. udfTTAddEx can: The last feature allows you to define tooltips for controls that cannot receive the focus.

If anyone is interested in udfTTAddEx I'd be happy to post it along with a Wizard that can create and modify the text file. The Wizard is a bit rough around the edges yet in that it will not automatically add the required loading code to your dialogs initialization event.

; This script implements two methods of displaying truncated lines in a
; listbox.
; ...1) Displays item under the mouse in a static/vary text control.
; ...2) Uses a Tooltip control which returns the item to the caller.
;
; The second method uses a cut down version of udfTTAddEx.
; udfTTAddEx  can:
; ...change the fonts used in a tooltip (including color)
; ...change the background color
; ...change timing parameters
; ...add a title and or icon
; ...automatically load tooltips from a text file
; ...create tracking areas on a dialog
; The last feature allows you to define tooltips for controls that
; cannot receive the focus.
;
; If anyone is interested in udfTTAddEx I'd be happy to post it along
; with a Wizard that can create and modify the text file.  The Wizard
; is a bit rough around the edges yet in that it will not automatically
; add the required loading code to your dialogs initialization event.
;
; Thu 3/2/2006
; George Vagenas gvag@shaw.ca

;------------------------------------------------------------------------------------------
; #BEGINUDFDOCS
; Sometimes you may want the fully qualified names of files in a
; directory. udfFileItemizeEx returns this list and will optionally
; strip the root from the filenames.
; Syntax:
;    udfFileItemizeEx(Dir, Mask, StripRoot)
; Parameters:
;    (s)Dir:                     Directory of interest or a null string
;                                for the current directory.
;    (s)Mask:                    File mask as per FileItemize or null
;                                string for all files, "*.*"
;    (b)StripRoot:               Strips initial "Drv
; Returns:
;    (s)                         Tab delimited list of full file names.
; Keywords:
;    FileItemize fully-qualified li
; #ENDUDFDOCS
#DefineFunction udfFileItemizeEx(Dir, Mask, StripRoot)
   If Dir=='' Then dir = DirGet()
   If StrSub(Dir, StrLen(Dir), 1)!='\' Then Dir = StrCat(Dir, '\')
   If Mask=='' Then Mask = '*.*'
   If StripRoot=='' Then StripRoot = @FALSE

    Bare = FileItemize(StrCat(Dir, Mask))
    Rtn = ''
    Cnts = ItemCount(Bare, @TAB)
    For Cnt = 1 To Cnts
       Rtn = ItemInsert(StrCat(Dir, ItemExtract(Cnt, Bare, @TAB)), -1, Rtn, @TAB)
    Next ;Cnt

    Return Rtn
#EndFunction ;udfFileItemizeEx

;------------------------------------------------------------------------------------------
#DefineFunction udfIsMouseOverCtrl(hParent, CtrlID)
   User32 = StrCat(DirWindows(1), "User32.DLL")
   RECT   = BinaryAlloc(16)
   hCtrl  = DllCall(User32, long:"GetDlgItem", long:hParent, long:CtrlID)
   Coords = MouseInfo(3)             ; Mouse screen coordinates in pixels

   ; Fill buffer with control coordinates.
   DllCall(StrCat(DirWindows(1), "User32.DLL"), long:"GetWindowRect", long:hCtrl, lpbinary:RECT)
   ; Is the mouse over the control?
   Rtn = DllCall(User32, long:"PtInRect", lpbinary:RECT, long:ItemExtract(1, Coords, ' '), long:ItemExtract(2, Coords, ' '))
   BinaryFree(RECT)
   Return Rtn
#EndFunction ;udfIsMouseOverCtrl

;------------------------------------------------------------------------------------------
; #BEGINUDFDOCS
; Sometimes you may want the fully qualified names of files in a
; directory. udfFileItemizeEx returns this list and will optionally strip
; the root from the filenames.
; Syntax:
;    udfFileItemizeEx(Dir, Mask, StripRoot)
; Parameters:
;    (s)Dir:               Directory of interest or "" for the current
;                          directory.
;    (s)Mask:              File mask as per FileItemize or null string for
;                          all files, "*.*"
;    (b)StripRoot:         Strips initial "Drv
; Returns:
;    (s)                   Tab delimited list of full file names.
; Keywords:
;    FileItemize fully-qualified li
; #ENDUDFDOCS
#DefineFunction udfFileItemizeEx(Dir, Mask, StripRoot)
   If Dir=='' Then dir = DirGet()
   If StrSub(Dir, StrLen(Dir), 1)!='\' Then Dir = StrCat(Dir, '\')
   If Mask=='' Then Mask = '*.*'
   If StripRoot=='' Then StripRoot = @FALSE

    Bare = FileItemize(StrCat(Dir, Mask))
    Rtn = ''
    Cnts = ItemCount(Bare, @TAB)
    For Cnt = 1 To Cnts
       Rtn = ItemInsert(StrCat(Dir, ItemExtract(Cnt, Bare, @TAB)), -1, Rtn, @TAB)
    Next ;Cnt

    Return Rtn
#EndFunction ;udfFileItemizeEx

;------------------------------------------------------------------------------------------
; Thanks to Guido for the inspiration of his original Tooltip procedures.
; #BEGINUDFDOCS
; Syntax:
;    udfTTTrack(hTT, hParent, CtrlID, sRqst)
; Parameters:
;    (i)hTT:                    Initial call an integer <=0. Subsequent
;                               calls handle to a Tooltip, see Notes.
;    (i)hParent:                Handle to a dialog.
;    (i)CtrlID:                 A control ID, see Notes.
;    (s)sRqst:                  A request string, see Notes.
; Returns:
;    (i/s)                      A handle to the Tooltip window or text from a
;                               list box item.
; Keywords:
;    Tooltip  dialog adding extended listbox filelistbox
;
; Notes:
; I have edited the notes to reflect udfTTTrack capabilites but not
; changed the reference to udfTTAddEx.
; hTT      Numeric value that must be <=0 on the initial call or the
;          handle returned from the initial call.  -1 to -999 sets the
;          desired character width of the window.  If not present a
;          single line tip is created.  A value of -1000 will create a
;          balloon tip.  Add the two values e.g. -1032 will create a
;          multiline balloon tip with a width of 32 characters.
;             hTT = udfTTAddEx(-1000-32, hParent, CtrlID, sRqst)
;
; CtrlID   Numeric or string value.  If numeric it must be ID as reported
;          by RoboScripter.  If you manually add a control to the dialog
;          after implementing your Tooltips there is a good chance the
;          IDs will be changed.
;
; sRqst    udfTTAddEx implements optional parameters in sRqst.  Either a
;          fully formated request:
;                Rqst1 Sep RqstParam1 [Sep2 Rqst2 Sep RqstParam2...]
;          or a short form:
;                Text [Sep2 Rqst2 Sep RqstParam2...]
;          The script converts the short form to:
;                1 Sep Text [Sep2 Rqst2 Sep RqstParam2...]
;          i.e. an Add request which is determined from the value in
;          CtrlID.  An integer value defaults to 1 (add control).
;          Long Form:
;             sRqst = "1%Sep%This adds a control."
;             hTT   = udfTTAddEx(-1000-32, hParent, 100, sRqst)
;
;          NB!  udfTTAddEx expects these delimiters.
;             ; Separator for request parameters, a simple list.
;             Sep  = num2char(160)
;             ; Separator for optional parameters, a list of lists.
;             Sep2 = num2char(182)
;
;          Or'able (pronunciation: "horrible")
;          Flags for sRqst parameters.
;          * Items are not implemented in udfTTTrack.
;             1     Add control/area.
;             2     Modify text in control.
;            *4     Change the Tooltip font.
;            *8     Add an area to the tool.
;           *16     Change timing parameters.
;           *32     Add a title and or icon.
;           *64     change background color
;          *128     change foreground color
;          1024     Removes a control from the tool.
;          2048     Destroy the Tooltip.
;         *4096     Changing an area control's rectangle
;          8192     Tracking control for items in ITEM and FILELIST boxes
; #ENDUDFDOCS
#DefineFunction udfTTTrack(hTT, hParent, CtrlID, sRqst)
   GoSub Init
   If hTT==0
      GoSub Create
      Rtn = hTT
      If IsDefined(MaxWidth) Then DllCall(user32, long:"SendMessageA", long:hTT, long:1024|24, long:0, long:MaxWidth)    ; TTM_SETMAXTIPWIDTH=1024+24
   EndIf

   Module = 'Main'
   ;Always fill cbSize and hWnd
   BinaryPoke4(TOOLINFO, 0, 44)
   BinaryPoke4(TOOLINFO, 8, hParent)
   Select 1
      ; Tracking control for clipped lines in ITEM and FILELIST boxes.
      Case (Flags&8192)==8192
         If !IsInt(fParam8192) || fParam8192<=0 Then Break

         ; Don't want to interfere with item selection.
         If IsKeyDown(@CTRL | @SHIFT) Then Break

         BinaryPoke4(TOOLINFO, 12, DllCall(user32, long:"GetDlgItem", long:hParent, long:CtrlID))

         ;Send a TTM_GETTOOLINFOA=1024|8 message to set AddTool or ChangeText flag.
         If !DllCall(User32, long:"SendMessageA", long:hTT, long:1024|8, long:0, lpbinary:TOOLINFO) Then Flags = Flags|1
            Else Flags = Flags|2
         uFlags = 1|32|128    ;TTF_IDISHWND=1, TTF_TRACK=32, TTF_ABSOLUTE=128
         @Tracking = @TRUE

         hLbx = DllCall(user32, long:"GetDlgItem", long:hParent, long:CtrlID)
         RECT = BinaryAlloc(16)

         ; Fill buffer with listbox coordinates and get offfsets of initial point.
         DllCall(User32, long:"GetWindowRect", long:hLbx, lpbinary:RECT)
         XX = BinaryPeek4(RECT, 0)
         YY = BinaryPeek4(RECT, 4)

         ; Is the mouse over the listbox?
         Coords = MouseInfo(3)                  ; Mouse screen coordinates in pixels
         mX  = ItemExtract(1, Coords, ' ')
         mY  = ItemExtract(2, Coords, ' ')
         If !DllCall(User32, long:"PtInRect", lpbinary:RECT, long:mX, long:mY) Then Break

         TimeDelay(0.4)
         chkCoords = MouseInfo(3)
         If chkCoords!=Coords Then Break

         ; Get the client area which excludes the vertical scroll bar.
         DllCall(User32, long:"GetClientRect", long:hLbx, lpbinary:RECT)

         ;Used to determine if the item text is truncated.
         ttCliWidth = BinaryPeek4(RECT, 8)-BinaryPeek4(RECT, 0)
         ; Get the visible line count and adjust for zero based indexing.
         lbxLnHeight = DllCall(User32, long:"SendMessageA", long:hLbx, long:417, long:0, long:0)  ;LB_GETITEMHEIGHT=417
         lbxLns = BinaryPeek4(RECT, 12)/lbxLnHeight-1

         ; Convert the client area coordinates back to absolute coordinates.
         BinaryPoke4(RECT, 0, BinaryPeek4(RECT, 0)+XX)
         BinaryPoke4(RECT, 8, BinaryPeek4(RECT, 8)+XX)
         BinaryPoke4(RECT, 4, BinaryPeek4(RECT, 4)+YY)
         BinaryPoke4(RECT, 12, BinaryPeek4(RECT, 12)+YY)

         Match  = @FALSE
         Ndx = DllCall(User32, long:"SendMessageA", long:hLbx, long:398, long:0, long:0)  ;LB_GETTOPINDEX=398
         For Cnt = 0 To lbxLns
            DllCall(User32, long:"SendMessageA", long:hLbx, long:408, long:Cnt+Ndx, lpbinary:RECT) ;LB_GETITEMRECT=408
            BinaryPoke4(RECT, 0, BinaryPeek4(RECT, 0)+XX)
            BinaryPoke4(RECT, 8, BinaryPeek4(RECT, 8)+XX)
            BinaryPoke4(RECT, 4, BinaryPeek4(RECT, 4)+YY)
            BinaryPoke4(RECT, 12, BinaryPeek4(RECT, 12)+YY)
            Match = DllCall(User32, long:"PtInRect", lpbinary:RECT, long:mX, long:mY)
            If Match Then Break
         Next
         If !Match Then Goto Getout                   ; Less items than lines and the mouse is not over an item.

         txtBuf = BinaryAlloc(1025)
         BinaryEodSet(txtBuf, 1025)
         Len = DllCall(User32, long:"SendMessageA", long:hLbx, long:393, long:Ndx+Cnt, lpbinary:txtBuf)  ;LB_GETTEXT=393
         Text = BinaryPeekStr(txtBuf, 0, Len)
         BinaryFree(txtBuf)
         Rtn = Text
         Continue

      ; Adding a control or changing its text.
      Case (Flags&1)==1 || (Flags&2)==2
         ; Either TTF_SUBCLASS=16 | TTF_IDISHWND=1
         ; or TTF_IDISHWND=1 | TTF_TRACK=32 | TTF_ABSOLUTE=128.
         BinaryPoke4(TOOLINFO, 4, uFlags)

         ; Get control handle from its ID and put it here.
         BinaryPoke4(TOOLINFO, 12, DllCall(user32, long:"GetDlgItem", long:hParent, long:CtrlID))
         Continue

      Case (Flags&1)==1 || (Flags&2)==2     ; Dealing with the text.
         txtBuf = BinaryAlloc(StrLen(text) + 1)
         BinaryPokeStr(txtBuf, 0, Text)
         ptxtBuf = IntControl(42, txtBuf, 0, 0, 0)
         BinaryPoke4(TOOLINFO, 36, ptxtBuf)
         Continue

      ; Adding a control.
      Case (Flags&1)==1
         r = DllCall(user32, long:"SendMessageA", long:hTT, long:1028, long:0,lpbinary:TOOLINFO)   ;TTM_ADDTOOL
         Continue

      ; Changing a control's text.
      Case (Flags&2)==2
         ; Hack for changing an area control's text.
         If CtrlID<0
            BinaryPoke4(TOOLINFO, 4, 16) ; TTF_SUBCLASS
            BinaryPoke4(TOOLINFO, 12, CtrlID)
         EndIf
         r = DllCall(user32, long:"SendMessageA", long:hTT, long:1036, long:0, lpbinary:TOOLINFO)  ;TTM_UPDATETIPTEXTA
         Continue

      ; Removing an control from the tool.
      Case (Flags&1024)==1024
         If CtrlID>0 Then CtrlID = DllCall(user32, long:"GetDlgItem", long:hParent, long:CtrlID)
         BinaryPoke4(TOOLINFO, 12, CtrlID)
         r = DllCall(user32, long:"SendMessageA", long:hTT, long:1029, long:0, lpbinary:TOOLINFO) ;TTM_DELTOOL=1029
         Break

      ; Destroy the Tooltip window! Frees resources?
      Case (Flags&2048)==2048
         r = DllCall(user32, long:"DestroyWindow", long:hTT)
         Break

      ; Timed activation for a tracking control.
      Case (Flags&8192)==8192 && @Tracking
         XX = BinaryPeek4(RECT, 0)+3
         YY = BinaryPeek4(RECT, 4)+3
         ; Set the tip rectangle's initial display position.
         r = DllCall(User32, long:"SendMessageA", long:hTT, long:1042, long:0, long:XX<<32|YY<<16)   ;TTM_TRACKPOSITION=1024|18

         ; Display the tip.
         DllCall(User32, long:"SendMessageA", long:hTT, long:1041, long:@TRUE, lpbinary:TOOLINFO)  ;TTM_TRACKACTIVATE=1024|17

         ; Get the size of the tip rectangle.
         ttSize = DllCall(User32, long:"SendMessageA", long:hTT, long:1024|30, long:0, lpbinary:TOOLINFO)  ;TTM_GETBUBBLESIZE=1024|30

         ; Hack to prevent clipping of tip at right side of screen.
         ; Trying to get the bubble size of a control that is NOT activated causes an
         ; error in Comctl32 and the API text width functions are iffy.
         ; So activate the control, get its width and then deactivate it if it is NOT
         ; clipped.  Uuugh!
         y1 = ttSize>>16
         x1 = (ttSize-(y1<<16))>>32
         ; Uncomment to attempt display-only-if-truncated functionality.  Its still iffy.
         ; if x1<=ttCliWidth then goto TrackOut

         ; Center the rectangle vertically on the item.
         If lbxLnHeight<y1 Then YY = YY-(y1-lbxLnHeight)/2

         scrX = WinMetrics(0)
         ; Adjustment to prevent clipping of long text at the screen edge.
         If (XX+x1)>scrX Then XX = XX-Abs(scrX - (XX+x1))-4

         ; Set the new display position.
         r = DllCall(User32, long:"SendMessageA", long:hTT, long:1042, long:0, long:XX<<32|YY<<16)   ;TTM_TRACKPOSITION=1024|18

         ; Display the tip for the requested time.
         Ticks  = GetTickCount()
         While MouseInfo(3)==Coords
            If GetTickCount()>Ticks+fParam8192 || (MouseInfo(8)&4) || IsKeyDown(@CTRL | @SHIFT) Then Break
         EndWhile

         :TrackOut   ; Stop displaying the tip.
         DllCall(User32, long:"SendMessageA", long:hTT, long:1041, long:@FALSE, lpbinary:TOOLINFO)  ;TTM_TRACKACTIVATE=1024|17         break
         Break

   EndSelect
   If !IsDefined(Rtn) Then Rtn = r

   :GetOut
   If IsDefined(TOOLINFO) Then BinaryFree(TOOLINFO)
   If IsDefined(RECT) Then BinaryFree(RECT)
   If IsDefined(txtBuf)   Then BinaryFree(txtBuf)

   Return Rtn

 ;------------------------------------------------------------------------------------------
 :Init
   Module = 'Init'
   IntControl(73,1,0,0,0)        ; Use goto ErrorHndlr
   thisVer = 'TTTrack 1.0'

   Rtn      = 0
   Balloon  = @FALSE
   User32   = StrCat(DirWindows(1), "User32.DLL")
   Sep      = Num2Char(160)
   Sep2     = Num2Char(182)
   uFlags   = 16|1               ;TTF_SUBCLASS=16, TTF_IDISHWND=1
   @Tracking = @FALSE

   TOOLINFO = BinaryAlloc(44)

   ; Creates a proper AddControl request, if the caller just passed a
   ; string in sRqst.
   Chk = ItemExtract(1, sRqst, Sep)
   If !IsInt(Chk)
      If IsInt(CtrlID)
         sRqst = StrCat(1, Sep, sRqst)
      Else
         sRqst = StrCat(8, Sep, sRqst)
      EndIf
   EndIf

   Flags = 0
   Cnts = ItemCount(sRqst, Sep2)
   For Cnt = 1 To Cnts
      Flag = ItemExtract(1, ItemExtract(Cnt, sRqst, Sep2), Sep)
      Flags       = Flags | ItemExtract(1, Flag, Sep)
      ; Create a named parameter.
      fParam%Flag% = ItemExtract(2, ItemExtract(Cnt, sRqst, Sep2), Sep)
   Next

   If IsDefined(fParam1) Then Text = fParam1
   If IsDefined(fParam2) Then Text = fParam2

   If hTT<0
      hTT = Abs(hTT)
      If hTT>=1000 && hTT<10000
         Balloon = @TRUE
         hTT = hTT-1000
      EndIf
      If hTT<10000 Then Tracking = @FALSE
         Else hTT = hTT-10000
      If hTT Then MaxWidth = hTT*(DllCall(user32, long:"GetDialogBaseUnits")&65535)    ; Width is in the low word.
      hTT = 0
   EndIf

   Return   ;local


 ;------------------------------------------------------------------------------------------
 :Create
   Module = 'Create'

   ; Init common controls
   CCSTRUCT = BinaryAlloc(8)
   BinaryPoke4(CCSTRUCT, 0, 8)            ; SizeOf
   BinaryPoke4(CCSTRUCT, 4, 4)            ;ICC_BAR_CLASSES=4
   f00 = DllCall(StrCat(DirWindows(1),"comctl32.dll"), long:"InitCommonControlsEx", lpbinary:CCSTRUCT)

   ; Create toolwindow
   If balloon Then TTS_BALLOON = 64    ;TTS_BALLOON=64
      Else TTS_BALLOON = 0
   ;                                                                            TTS_ALWAYSTIP=1, TTS_NOPREFIX=2
   hTT = DllCall(User32, long:"CreateWindowExA", lpnull, lpstr:"tooltips_class32", lpnull, long:1|2|TTS_BALLOON, long:2147483648, long:2147483648, long:2147483648, long:2147483648, long:hParent, lpnull, long:DllHinst(''), lpnull)

   ;                                      HWND_TOPMOST=-1,   SWP_NOSIZE=1, SWP_NOMOVE=2, SWP_NOACTIVATE=16)
   DllCall(User32, long:"SetWindowPos", long:hTT, long:-1,    long:0, long:0, long:0, long:0, long:1|2|16)

   BinaryFree(CCSTRUCT)
   Drop(CCSTRUCT, cwDefault, hInst, Style)

   Return   ;local

 ;------------------------------------------------------------------------------------------
 :WBERRORHANDLER
   ErrInfo = StrCat('Error: #', LastError(), ': ', wberrortextstring, @CRLF, 'Script: ', wberrorhandlerline, @CRLF, 'Assignment: ', wberrorhandlerassignment, @CRLF, 'File: ', wberrorhandlerfile, @CRLF, 'Procedure: ', wberrorinsegment, @CRLF, 'Line No. ', wberrorhandlerlinenumber, @CRLF)
   ClipPut(ErrInfo)
   Pause('Error Message on Clipboard', ErrInfo)

   Exit
#EndFunction ;udfTTTrack

;------------------------------------------------------------------------------------------
; #BEGINUDFDOCS
;    Gets the text from the Listbox item under the mouse, if the pointer
;    doesn't move for ~0.5 seconds.
; Syntax:
;    udfLBTrackMouse(hParent, CtlID)
; Parameters:
;    (i)hParent:                          parent of the Listbox control
;    (i)CtlID:                            control ID
; Returns:
;    (s)                                  text from the item under the
;                                         mouse or a null string
; Calls:
;    udfCtrlFromPt
; Keywords:
;    listbox itembox text mouse tracki
; #ENDUDFDOCS
#DefineFunction udfLBTrackMouse(hParent, CtlID)
   ; Don't want to interfere with item selection.
   If IsKeyDown(@CTRL | @SHIFT) Then Goto Getout

   User32 = StrCat(DirWindows(1), "User32.DLL")
   Coords = MouseInfo(3)                  ; Mouse screen coordinates in pixels
   hLbx   = DllCall(User32, long:"GetDlgItem", long:hParent, long:CtlID)
   RECT   = BinaryAlloc(16)
   Text   = ''

   DllCall(User32, long:"GetWindowRect", long:hLbx, lpbinary:RECT)
   mX  = ItemExtract(1, Coords, ' ')
   mY  = ItemExtract(2, Coords, ' ')
   ; Is the mouse over the control?
   If !DllCall(User32, long:"PtInRect", lpbinary:RECT, long:mX, long:mY) Then Goto Getout

   XX = mX-BinaryPeek4(RECT, 0)
   YY = mY-BinaryPeek4(RECT, 4)

   TimeDelay(0.4)
   chkCoords = MouseInfo(3)
   If chkCoords!=Coords Then Goto Getout

   ndx = DllCall(user32, long:"SendMessageA", long:hLbx, long:425, long:0, long: YY<<16|XX<<32) ;LB_ITEMFROMPOINT=425
   If ndx>>16==0
      txtBuf = BinaryAlloc(1025)
      BinaryEodSet(txtBuf, 1025)
      Len = DllCall(User32, long:"SendMessageA", long:hLbx, long:393, long:ndx>>32, lpbinary:txtBuf)  ;LB_GETTEXT=393
      Text = BinaryPeekStr(txtBuf, 0, Len)
      BinaryFree(txtBuf)
  EndIf

 :Getout
   If IsDefined(RECT) Then BinaryFree(RECT)
   Return Text

#EndFunction ;udfLBTrackMouse

;------------------------------------------------------------------------------------------
#DefineSubRoutine lbDemo1(lbHndl, lbEvnt, lbCtrlNum, lbRsvd1, lbRsvd2)
   Select lbEvnt
      ;:00InitDialog
      Case 0
         lbxHome   =  001
         lbxSys    =  002
         lblFName  =  003
         btnOK     =  004
         btnCancel =  005
         DialogProcOptions(lbHndl, 1, 1000)       ; Timer event.
         DialogProcOptions(lbHndl, 2, @TRUE)     ; Button Clicked.

         HomeID = lbxHome+99
         SysID = lbxSys+99
         Return -1

      ;:0Timer
      Case 1
         If !udfIsMouseOverCtrl(lbHndl, HomeID) && !udfIsMouseOverCtrl(lbHndl, SysID) Then Return -1
         If udfIsMouseOverCtrl(lbHndl, HomeID)
            lbFName = udfLBTrackMouse(lbHndl, HomeID)
            DialogControlSet(lbHndl, lblFName, 4, lbFName)
          Else
            lbFName = udfLBTrackMouse(lbHndl, SysID)
            DialogControlSet(lbHndl, lblFName, 4, lbFName)
         EndIf
         Return -1

      ;:0Button Clicked
      Case 2
         Return -1

   EndSelect ;lbEvnt
   Return -1

#EndSubRoutine ;lbDemo1

;------------------------------------------------------------------------------------------
#DefineSubRoutine lbDemo2(lbHndl, lbEvnt, lbCtrlNum, lbRsvd1, lbRsvd2)
   Select lbEvnt
      ;:00InitDialog
      Case 0
         lbxHome   =  001
         lbxSys    =  002
         lblFName  =  003
         btnToggle =  004
         btnClose  =  005
         Sep       = Num2Char(160)
         Sep2      = Num2Char(182)

         DialogProcOptions(lbHndl, 1, 250)       ; Timer event.
         DialogProcOptions(lbHndl, 2, @TRUE)     ; Button Clicked.

;          hLblFName = dllcall(strcat(dirwindows(1), 'User32.dll'), long:"GetDlgItem", long:lbHndl, long:lblFName+99)
         HomeID = lbxHome+99
         SysID = lbxSys+99
         hTT = udfTTTrack(-1000, lbHndl, btnToggle+99, StrCat(1, sep, 'Toggle Listbox tracking.')) ; Init tooltip and add control.
         udfTTTrack(hTT, lbHndl, btnClose+99, StrCat(1, sep, 'Closes the dialog.'))    ; Add a control.
         hTrack = udfTTTrack(0, lbHndl, 0, 0)                                                ; Init the tracking tooltip.
         lbTracking = @TRUE
         Return -1

      ;:0Timer
      Case 1
         If lbTracking
            Text = ''
            Rslt = udfTTTrack(hTrack, lbHndl, lbxHome+99, StrCat(8192, sep, 7000))
            If !IsInt(Rslt) Then Text = Rslt
            Rslt = udfTTTrack(hTrack, lbHndl, lbxSys+99, StrCat(8192, sep, 7000))
            If !IsInt(Rslt) Then Text = Rslt
            If Text!='' Then DialogControlSet(lbHndl, lblFName, 4, Text)
         EndIf
         Return -1

      ;:0Button Clicked
      Case 2
         If lbCtrlNum==btnClose Then Return -1
         lbTracking = !lbTracking
         Return -2

   EndSelect ;lbEvnt
   Return -1

#EndSubRoutine ;lbDemo2

#DefineFunction lbDemoTmplt(lbLst1, lbLst2, Method)
   If Method==1
      Hide = 1
      lbCaption = `Listbox Mouse Tracking`
    Else
      lbCaption = `Listbox Tooltips`
      Hide = 'DEFAULT'
   EndIf

   lbFormat=`WWWDLGED,6.1`

   lbCaption=lbCaption
   lbX=-999
   lbY=-999
   lbWidth=212
   lbHeight=164
   lbNumControls=005
   lbProcedure=`lbDemo%Method%`
   lbFont=`DEFAULT`
   lbTextColor=`DEFAULT`
   lbBackground=`DEFAULT,DEFAULT`
   lbConfig=0

   lb001=`003,007,96,114,ITEMBOX,lbLst1,DEFAULT,DEFAULT,1,DEFAULT,"Microsoft Sans Serif|6144|40|34","0|0|0","255|255|225"`  ;lbxHome
   lb002=`109,007,96,114,ITEMBOX,lbLst2,DEFAULT,DEFAULT,2,DEFAULT,"Microsoft Sans Serif|6144|40|34","0|0|0","255|255|225"`  ;lbxSys
   lb003=`003,127,200,012,VARYTEXT,lbFName,DEFAULT,DEFAULT,3,DEFAULT,DEFAULT,DEFAULT,"255|255|255"`                         ;lblFName
   lb004=`003,147,036,012,PUSHBUTTON,DEFAULT,"Toggle",1,4,%Hide%,DEFAULT,DEFAULT,DEFAULT`                                  ;btnToggle
   lb005=`169,147,036,012,PUSHBUTTON,DEFAULT,"Close",0,5,DEFAULT,DEFAULT,DEFAULT,DEFAULT`                                   ;btnClose

   Btn=Dialog("lb")
 :CANCEL
   Return Btn
#EndFunction ;lbDemoTmplt


;------------------------------------------------------------------------------------------
;: Demo
Sys  = udfFileItemizeEx(DirHome(), '*.*', @FALSE)
Home = udfFileItemizeEx(StrSub(DirHome(),1, StrIndexNC(DirHome(), '\system', 0, @FWDSCAN)), '*.*', @FALSE)

lbDemoTmplt(Home, Sys, 1)
lbDemoTmplt(Home, Sys, 2)

Article ID:   W16946
File Created: 2011:01:12:09:33:16
Last Updated: 2011:01:12:09:33:16