Click to See Complete Forum and Search --> : File search


Andrew R.
September 7th, 2001, 10:25 AM
Does anybody have a ready code to do file search on the hard drive?
I would really appreciate your help as I'm in the time shortage right now.
Thank you.

DSJ
September 7th, 2001, 10:30 AM
'Create a form with a command button (command1), a list box (list1)
'and four text boxes (text1, text2, text3 and text4).
'Type in the first textbox a startingpath like c:\
'and in the second textbox you put a pattern like *.* or *.txt

private Declare Function FindFirstFile Lib "kernel32" Alias "FindFirstFileA" (byval lpFileName as string, lpFindFileData as WIN32_FIND_DATA) as Long
private Declare Function FindNextFile Lib "kernel32" Alias "FindNextFileA" (byval hFindFile as Long, lpFindFileData as WIN32_FIND_DATA) as Long
private Declare Function GetFileAttributes Lib "kernel32" Alias "GetFileAttributesA" (byval lpFileName as string) as Long
private Declare Function FindClose Lib "kernel32" (byval hFindFile as Long) as Long

Const MAX_PATH = 260
Const MAXDWORD = &HFFFF
Const INVALID_HANDLE_VALUE = -1
Const FILE_ATTRIBUTE_ARCHIVE = &H20
Const FILE_ATTRIBUTE_DIRECTORY = &H10
Const FILE_ATTRIBUTE_HIDDEN = &H2
Const FILE_ATTRIBUTE_NORMAL = &H80
Const FILE_ATTRIBUTE_READONLY = &H1
Const FILE_ATTRIBUTE_SYSTEM = &H4
Const FILE_ATTRIBUTE_TEMPORARY = &H100

private Type FILETIME
dwLowDateTime as Long
dwHighDateTime as Long
End Type

private Type WIN32_FIND_DATA
dwFileAttributes as Long
ftCreationTime as FILETIME
ftLastAccessTime as FILETIME
ftLastWriteTime as FILETIME
nFileSizeHigh as Long
nFileSizeLow as Long
dwReserved0 as Long
dwReserved1 as Long
cFileName as string * MAX_PATH
cAlternate as string * 14
End Type
Function StripNulls(OriginalStr as string) as string
If (InStr(OriginalStr, Chr(0)) > 0) then
OriginalStr = Left(OriginalStr, InStr(OriginalStr, Chr(0)) - 1)
End If
StripNulls = OriginalStr
End Function

Function FindFilesAPI(path as string, SearchStr as string, FileCount as Integer, DirCount as Integer)
'KPD-Team 1999
'E-Mail: KPDTeam@Allapi.net
'URL: http://www.allapi.net/

Dim FileName as string ' Walking filename variable...
Dim DirName as string ' SubDirectory Name
Dim dirNames() as string ' Buffer for directory name entries
Dim nDir as Integer ' Number of directories in this path
Dim i as Integer ' for-loop counter...
Dim hSearch as Long ' Search Handle
Dim WFD as WIN32_FIND_DATA
Dim Cont as Integer
If Right(path, 1) <> "\" then path = path & "\"
' Search for subdirectories.
nDir = 0
ReDim dirNames(nDir)
Cont = true
hSearch = FindFirstFile(path & "*", WFD)
If hSearch <> INVALID_HANDLE_VALUE then
Do While Cont
DirName = StripNulls(WFD.cFileName)
' Ignore the current and encompassing directories.
If (DirName <> ".") And (DirName <> "..") then
' Check for directory with bitwise comparison.
If GetFileAttributes(path & DirName) And FILE_ATTRIBUTE_DIRECTORY then
dirNames(nDir) = DirName
DirCount = DirCount + 1
nDir = nDir + 1
ReDim Preserve dirNames(nDir)
End If
End If
Cont = FindNextFile(hSearch, WFD) 'get next subdirectory.
Loop
Cont = FindClose(hSearch)
End If
' Walk through this directory and sum file sizes.
hSearch = FindFirstFile(path & SearchStr, WFD)
Cont = true
If hSearch <> INVALID_HANDLE_VALUE then
While Cont
FileName = StripNulls(WFD.cFileName)
If (FileName <> ".") And (FileName <> "..") then
FindFilesAPI = FindFilesAPI + (WFD.nFileSizeHigh * MAXDWORD) + WFD.nFileSizeLow
FileCount = FileCount + 1
List1.AddItem path & FileName
End If
Cont = FindNextFile(hSearch, WFD) ' get next file
Wend
Cont = FindClose(hSearch)
End If
' If there are sub-directories...
If nDir > 0 then
' Recursively walk into them...
for i = 0 to nDir - 1
FindFilesAPI = FindFilesAPI + FindFilesAPI(path & dirNames(i) & "\", SearchStr, FileCount, DirCount)
next i
End If
End Function
Sub Command1_Click()
Dim SearchPath as string, FindStr as string
Dim FileSize as Long
Dim NumFiles as Integer, NumDirs as Integer
Screen.MousePointer = vbHourglass
List1.Clear
SearchPath = Text1.Text
FindStr = Text2.Text
FileSize = FindFilesAPI(SearchPath, FindStr, NumFiles, NumDirs)
Text3.Text = NumFiles & " Files found in " & NumDirs + 1 & " Directories"
Text4.Text = "Size of files found under " & SearchPath & " = " & Format(FileSize, "#,###,###,##0") & " Bytes"
Screen.MousePointer = vbDefault
End Sub

michi
September 7th, 2001, 10:31 AM
Hi,
You can use FileSystemObject.
=========

Option Explicit
Dim fso As New FileSystemObject
Dim fld As Folder

Private Sub Command1_Click()
Dim nDirs As Integer, nFiles As Integer, lSize As Long
Dim sDir As String, sSrchString As String
sDir = InputBox("Please enter the directory to search", _
"FileSystemObjects example", "C:\")
sSrchString = InputBox("Please enter the file name to search", _
"FileSystemObjects example", "vb.ini")
MousePointer = vbHourglass
Label1.Caption = "Searching " & vbCrLf & UCase(sDir) & "..."
lSize = FindFile(sDir, sSrchString, nDirs, nFiles)
MousePointer = vbDefault
MsgBox Str(nFiles) & " files found in" & Str(nDirs) & _
" directories", vbInformation
MsgBox "Total Size = " & lSize & " bytes"
End Sub

Private Function FindFile(ByVal sFol As String, sFile As String, _
nDirs As Integer, nFiles As Integer) As Long
Dim tFld As Folder, tFil As File, FileName As String

Set fld = fso.GetFolder(sFol)
FileName = Dir(fso.BuildPath(fld.Path, sFile), vbNormal Or _
vbHidden Or vbSystem Or vbReadOnly)
While Len(FileName) <> 0
FindFile = FindFile + FileLen(fso.BuildPath(fld.Path, _
FileName))
nFiles = nFiles + 1
List1.AddItem fso.BuildPath(fld.Path, FileName) ' Load ListBox
FileName = Dir() ' Get next file
DoEvents
Wend
Label1 = "Searching " & vbCrLf & fld.Path & "..."
nDirs = nDirs + 1
If fld.SubFolders.Count > 0 Then
For Each tFld In fld.SubFolders
DoEvents
FindFile = FindFile + FindFile(tFld.Path, sFile, nDirs, _
nFiles)
Next
End If
End Function
==========



Regards,

Michi

Iouri
September 7th, 2001, 10:35 AM
If you want to use 'Find Files' standard dialog, in your programs you can choose between the following
four methods.

1. Using DDE: it's needed an label control, even invisible.
------------------------------------------------------
Private Sub Command1_Click()
With Label1
.LinkTopic = "Folders|AppProperties"
.LinkMode = vbLinkManual
.LinkExecute "[OpenFindFile(,)]"
End With
End Sub

Private Sub Form_Load()
Label1.Visible = False
Command1.Caption = "Find File (1)..."
Me.Caption = "Find File (1)"
End Sub

2. Using keybd_event API function to simulate Win + 'F':
------------------------------------------------------
Private Declare Sub keybd_event Lib "user32" _
(ByVal bVk As Byte, _
ByVal bScan As Byte, _
ByVal dwFlags As Long, _
ByVal dwExtraInfo As Long)
Private Const VK_LWIN = &H5B
Private Const KEYEVENTF_KEYUP = &H2
Private Const VK_APPS = &H5D

Private Sub Command1_Click()
Call keybd_event(VK_LWIN, 0, 0, 0)
Call keybd_event(&H46, 0, 0, 0) 'F
Call keybd_event(VK_LWIN, 0, KEYEVENTF_KEYUP, 0)
End Sub

Private Sub Form_Load()
Command1.Caption = "Find File (2)..."
Me.Caption = "Find File (2)"
End Sub

3. Using MS Q183903 (http://support.microsoft.com/support/kb/articles/q183/9/03.asp)
------------------------------------------------------
Private Declare Function ShellExecute Lib "shell32.dll" _
Alias "ShellExecuteA" _
(ByVal hwnd As Long, _
ByVal lpOperation As String, _
ByVal lpFile As String, _
ByVal lpParameters As String, _
ByVal lpDirectory As String, _
ByVal nShowCmd As Long) As Long

Private Const SW_SHOWNORMAL = 1
Private Const SW_SHOWMINIMIZED = 2
Private Const SW_SHOWMAXIMIZED = 3
Private Const SW_SHOW = 5
Private Const SW_MINIMIZE = 6
Private Const SW_SHOWMINNOACTIVE = 7
Private Const SW_SHOWNA = 8
Private Const SW_RESTORE = 9
Private Const SW_SHOWDEFAULT = 10

Private Sub Command1_Click()
Call ShellExecute(Me.hwnd, _
"find", _
Dir1.Path, _
vbNullString, _
vbNullString, _
SW_SHOWNORMAL)
End Sub

Private Sub Drive1_Change()
Dir1.Path = Drive1.Drive
End Sub

Private Sub Form_Load()
Command1.Caption = "Find File (3)..."
End Sub

4. Using undocumented function SHFindFiles and SHSimpleIDListFromPath from Shell32.dll:
------------------------------------------------------
Private Declare Function SHFindFiles Lib "Shell32" Alias "#90" _
(pidlRoot As Long, pidlSavedSearch As Long) As Long
Private Declare Function SHSimpleIDListFromPath Lib "Shell32" Alias "#162" _
(ByVal lpszPath As String) As Long

Private Sub Command1_Click()
Dim l As Long
l = SHSimpleIDListFromPath(Dir1.Path)
SHFindFiles ByVal l, ByVal 0
End Sub

Private Sub Drive1_Change()
Dir1.Path = Drive1.Drive
End Sub


Private Sub Form_Load()
Command1.Caption = "Find File (4)..."
Me.Caption = "Find File (4)"
End Sub

For the last two methods you need to add a DriveListBox and a DirListBox control. With this methods you
can give the start path for searching.


Iouri Boutchkine
iouri@hotsheet.com

Iouri
September 7th, 2001, 10:37 AM
To search in the folder - there is a simple method

set f = fso.GetFolder("c:\Projects\MyFolder")

set fc = f.Files
for Each f1 in fc
if instrrev(f1.name,".txt") > 0 then
'handle text file
end if
next

Iouri Boutchkine
iouri@hotsheet.com

Andrew R.
September 7th, 2001, 11:53 AM
Thank you all guys. This one was the perfect solution for my requirements.
The only one problem is left to solve...