|
-
Jan 16th, 2010, 09:26 AM
#1
Set root folder of DirListBox
I'd really like to use a DirListBox, but I need to be able to set its root folder to something other than "C:\". Anyone know how to do this?
Specifically, I want to create an empty folder tree under Application Data to use as a placeholder. The user will then navigate this temporary folder tree using a DirListBox to select a folder. When done, I delete the temporary folder tree.
The user interface has very little room, making the DirListBox control highly preferable to a treeview. The regular DirListBox shows all parent paths, which in this case will end up being very confusing since the ultimate root folder will appear below the user's Application Data folder.
I'm hoping there is an API command that can simply overwrite the DirListBox's internal "RootPath" variable with whatever the programmer wants. Probably as simple as using SendMessage API.
Last edited by Ellis Dee; Jan 16th, 2010 at 09:52 AM.
-
Jan 16th, 2010, 02:16 PM
#2
Re: Set root folder of DirListBox
I doubt there is an api. The DirListBox is simply a windows listbox, owner drawn. Since VB designed it for navigation, internally, VB will always show the root drive. You might have more success in designing your own or using the BrowseForFolder API which I believe can do what you want. Here's an example:
Code:
Option Explicit
Private Declare Sub CoTaskMemFree Lib "ole32.dll" (ByVal hMem As Long)
Private Declare Function SHParseDisplayName Lib "shell32.dll" (ByVal pszName As Long, ByVal pbc As Long, ByRef ppidl As Long, ByVal sfgaoIn As Long, ByRef psfgaoOut As Long) As Long
Private Declare Function SHBrowseForFolder Lib "Shell32" (lpbi As BrowseInfo) As Long
Private Declare Function SHGetPathFromIDList Lib "Shell32" (ByVal pidList As Long, ByVal lpBuffer As String) As Long
Private Const BIF_RETURNONLYFSDIRS = 1
Private Const MAX_PATH = 260
Private Type BrowseInfo
hwndOwner As Long
pIDLRoot As Long
pszDisplayName As Long
lpszTitle As Long
ulFlags As Long
lpfnCallback As Long
lParam As Long
iImage As Long
End Type
Private Function BrowseForFolder(Optional Title As String, Optional StartupDir As String) As String
Dim lpIDList As Long
Dim sBuffer As String
Dim szTitle() As Byte
Dim tBrowseInfo As BrowseInfo
szTitle() = StrConv(Title & vbNullChar, vbFromUnicode)
With tBrowseInfo
.hwndOwner = Me.hWnd
.lpszTitle = VarPtr(szTitle(0))
.ulFlags = BIF_RETURNONLYFSDIRS
If Len(StartupDir) Then
Call SHParseDisplayName(StrPtr(StartupDir), ByVal 0&, .pIDLRoot, ByVal 0&, ByVal 0&)
End If
End With
lpIDList = SHBrowseForFolder(tBrowseInfo)
If tBrowseInfo.pIDLRoot Then Call CoTaskMemFree(tBrowseInfo.pIDLRoot)
If (lpIDList) Then
sBuffer = Space(MAX_PATH)
SHGetPathFromIDList lpIDList, sBuffer
sBuffer = Left(sBuffer, InStr(sBuffer, vbNullChar) - 1)
Call CoTaskMemFree(lpIDList)
BrowseForFolder = sBuffer
End If
End Function
Private Sub Command1_Click()
Debug.Print BrowseForFolder("Select Folder", "C:\Program Files")
End Sub
Edited: P.S. And if form real estate is a concern, you can't beat this option. A button, label, or menu can trigger it.
Last edited by LaVolpe; Jan 16th, 2010 at 02:35 PM.
-
Jan 16th, 2010, 02:45 PM
#3
Re: Set root folder of DirListBox
I appreciate the response. I figured if anyone would know, it'd be you.
I already have the BrowseFolder code in my xp library. While it is indeed extremely space-efficient, it's too cumbersome to use for this specific implementation. As in it would require too many mouse clicks. A listbox is so much smoother, GUI-wise, at least for this.
My app is almost finished, and so far it's reference- and component-free, meaning I would hate to add dependencies just for a listbox. So that makes the imagelist+treeview alternative less than ideal.
I think instead I'll just use a regular listbox and deal with the folder structure manually, basically by adding a few spaces of indentation to the begininning of the List() item for each subfolder level, and simply repopulate the listbox after every mouse click. I was really hoping to have the folder icons, but it'll still work without them.
Thanks much for your time.
EDIT: In looking more closely I find your BrowseForFolder solution intriguing, though not for this specific app. Mine uses CSIDL instead of a string for the default folder.
Last edited by Ellis Dee; Jan 16th, 2010 at 02:48 PM.
-
Jan 16th, 2010, 08:37 PM
#4
Re: Set root folder of DirListBox
i found i could cheat the dirlistbox
if i found the index for a folder to be root, i could limit the topindex
this may not be suitable for what you want, but you can have a look
vb Code:
'declare ti at form level Dir1.Path = Environ("appdata") i = 0 Do Until Dir1.List(i) = "" i = i - 1 Loop ti = Abs(i + 2) Private Sub Dir1_Scroll() If Dir1.TopIndex < ti Then Dir1.TopIndex = ti End Sub
i do my best to test code works before i post it, but sometimes am unable to do so for some reason, and usually say so if this is the case.
Note code snippets posted are just that and do not include error handling that is required in real world applications, but avoid On Error Resume Next
dim all variables as required as often i have done so elsewhere in my code but only posted the relevant part
come back and mark your original post as resolved if your problem is fixed
pete
-
Jan 17th, 2010, 09:27 AM
#5
Re: Set root folder of DirListBox
That looks very promising, but I'm a little confused by the code. First off, shouldn't it throw a runtime error pretty much immediately when you subtract 1 from i, meaning the second iteration of the Do...Loop tries to reference Dir1.List(-1)?
Then what's going on with the Abs() deal?
I tried to do what you describe on my own with no love, so I'm thinking the weirdness in your code is deliberate and necessary. I'd love to understand it better.
-
Jan 17th, 2010, 03:17 PM
#6
Re: Set root folder of DirListBox
my testing showed dir1.list(0) to be the first item below dir1.path
so dir1.path and all upwards items are negative
vb Code:
for i = 0 to dir1.listcount debug.print dir1.list(i) next
will print all items below the path
you do not need to use environ to set a path, just a very easy way to fill the dir list
don't know why you were having a problem with the code, i just put a dir list, the 1st code can be in form load
don't need to use abs, as always negative, could use ti = -i -2
in my case using appdata as the path, c:\ was dir1.list(-5), so ti needed to be 3
where is your code failing?
i do my best to test code works before i post it, but sometimes am unable to do so for some reason, and usually say so if this is the case.
Note code snippets posted are just that and do not include error handling that is required in real world applications, but avoid On Error Resume Next
dim all variables as required as often i have done so elsewhere in my code but only posted the relevant part
come back and mark your original post as resolved if your problem is fixed
pete
-
Jan 18th, 2010, 12:20 PM
#7
Re: Set root folder of DirListBox
One more option. Here is a complex Solution... but doable...
Use a DirListBox (Which will be hidden) and a treeview and set the parent node to "..." and set it's sub node to the default folder that you want... When the user clicks the "..." then display the DirListBox and hide the treeview.
This way you will control the treeview from the Dirlistbox. You can also set the icons of the treeview...
Well, just a thought...
A good exercise for the Heart is to bend down and help another up...
Please Mark your Thread " Resolved", if the query is solved
MyGear:
★ CPU ★ Ryzen 5 5800X
★ GPU ★ NVIDIA GeForce RTX 3080 TI Founder Edition
★ RAM ★ G. Skill Trident Z RGB 32GB 3600MHz
★ MB ★ ASUS TUF GAMING X570 (WI-FI) ATX Gaming
★ Storage ★ SSD SB-ROCKET-1TB + SEAGATE 2TB Barracuda IHD
★ Cooling ★ NOCTUA NH-D15 CHROMAX BLACK 140mm + 10 of Noctua NF-F12 PWM
★ PSU ★ ANTEC HCG-1000-EXTREME 1000 Watt 80 Plus Gold Fully Modular PSU
★ Case ★ LIAN LI PC-O11 DYNAMIC XL ROG (BLACK) (G99.O11DXL-X)
★ Monitor ★ LG Ultragear 27" 240Hz Gaming Monitor
★ Keyboard ★ TVS Electronics Gold Keyboard
★ Mouse ★ Logitech G502 Hero
-
Jan 18th, 2010, 12:39 PM
#8
Re: Set root folder of DirListBox
The treeview control is far superior to the DirListBox, so once you introduce the treeview the solution is complete. The only reasons I'm not using a treeview are 1) because the DirListBox is more space-efficient in the GUI, and 2) my otherwise complete project doesn't have a single component or reference, so adding a dependency for what amounts to a single listbox seems rather pointless.
Without dependencies, you don't need any installation routine for pretty much any version of Windows after 2000, and since several parts of my app already require XP or higher anyway the lack of needing any installation is a big plus.
EDIT: One of the very few legitimate reasons to program in VB6 at all is not needing any installation.
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|