Jump to content

Recommended Posts

Posted (edited)

;Copies the Desktop and My Documents Folders to a timestamped folder on the E drive and gives a progress bar of the files copying

Local $RHD = _SelectRemovableDrive()
If @error = 0 Then MsgBox(4096, "Drive Selected:", "Selected removable drive is " & $RHD)

While 1
    DirCreate($RHD&"Test1") ;Creates a dummy temp file for the purpose of getting the time of creation
    $timeStamp = FileGetTime($RHD&"Test1",1,1) ; Sets $timestamp to the time of folder creation above
    DirRemove($RHD&"Test1") ;deletes the temp folder
    DirCreate($RHD&$timeStamp) ;Creates the folder in the time/date format mentioned above
    $DestinationPath = ($RHD&$timeStamp) ;names $Destination Path for use in next function
    DirCreate($DestinationPath&"\My Documents") ;Creates the my documents directory in the time stamp folder
    DirCreate($DestinationPath&"\Desktop") ;Creates the Desktop directory in the time stamp folder
    $DPMyDocs = ($DestinationPath&"\My Documents") ;Creates a clean directory path for the CopyDirWithProgress Function below
    $DPDesktop = ($DestinationPath&"\Desktop") ;Creates a clean directory path for the CopyDirWithProgress Function below
    _CopyDirWithProgress(@DesktopDir, $DPDesktop) ;Copies the data to timestamp\Desktop
    _CopyDirWithProgress(@MyDocumentsDir, $DPMyDocs) ;Copies the data to timestamp\my documents
Exit
wend

Func _SelectRemovableDrive()
    Local $var = DriveGetDrive("REMOVABLE")
    If @error Then Return SetError(1, 0, 0)
    If $var[0] = 1 Then Return SetError(0, 0, $var[1])
    If $var[0] > 1 Then
        Local $sText = "Select Drive letter of the required removable drive." & @CRLF & @CRLF
        For $i = 1 To $var[0]
            $sText &= "Enter " & StringLeft($var[$i], 1) & " for " & $var[$i] & " Removable Drive - " & @TAB & "Size: " & _
                    Int(DriveSpaceTotal($var[$i])) & " MB Label: " & DriveGetLabel($var[$i]) & @CRLF
        Next
        Do
            Local $sHD = InputBox("Select Removable Drive", $sText, StringLeft($var[1], 1), "", 400)
            If @error Then Return SetError(1, 0, 0)
            For $i = 1 To $var[0]
                If StringUpper(StringLeft($var[$i], 1)) == StringUpper(StringRegExpReplace($sHD, "(?i)[^a-z]", "")) Then Return SetError(0, 0, $var[$i])
            Next
        Until 0 ; loop InputBox() until existing removable drive letter is entered or Cancel button is pressed.
    EndIf
EndFunc   ;==>_SelectRemovableDrive

Func _CopyDirWithProgress($sOriginalDir, $sDestDir)
  ;$sOriginalDir and $sDestDir are quite selfexplanatory...
  ;This func returns:
  ; -1 in case of critical error, bad original or destination dir
  ;  0 if everything went all right
  ; >0 is the number of file not copied and it makes a log file
  ;  if in the log appear as error message '0 file copied' it is a bug of some windows' copy command that does not redirect output...

   If StringRight($sOriginalDir, 1) <> '\' Then $sOriginalDir = $sOriginalDir & '\'
   If StringRight($sDestDir, 1) <> '\' Then $sDestDir = $sDestDir & '\'
   If $sOriginalDir = $sDestDir Then Return -1

   ProgressOn('Copying...', 'Making list of files...' & @LF & @LF, '', -1, -1, 18)
   Local $aFileList = _FileSearch($sOriginalDir)
   If $aFileList[0] = 0 Then
      ProgressOff()
      SetError(1)
      Return -1
   EndIf

   If FileExists($sDestDir) Then
      If Not StringInStr(FileGetAttrib($sDestDir), 'd') Then
         ProgressOff()
         SetError(2)
         Return -1
      EndIf
   Else
      DirCreate($sDestDir)
      If Not FileExists($sDestDir) Then
         ProgressOff()
         SetError(2)
         Return -1
      EndIf
   EndIf

   Local $iDirSize, $iCopiedSize = 0, $fProgress = 0
   Local $c, $FileName, $iOutPut = 0, $sLost = '', $sError
   Local $Sl = StringLen($sOriginalDir)

   _Quick_Sort($aFileList, 1, $aFileList[0])

   $iDirSize = Int(DirGetSize($sOriginalDir) / 1024)

   ProgressSet(Int($fProgress * 100), $aFileList[$c], 'Coping file:')
   For $c = 1 To $aFileList[0]
      $FileName = StringTrimLeft($aFileList[$c], $Sl)
      ProgressSet(Int($fProgress * 100), $aFileList[$c] & ' -> '& $sDestDir & $FileName & @LF & 'Total KiB: ' & $iDirSize & @LF & 'Done KiB: ' & $iCopiedSize, 'Coping file:  ' & Round($fProgress * 100, 2) & ' %   ' & $c & '/' &$aFileList[0])

      If StringInStr(FileGetAttrib($aFileList[$c]), 'd') Then
         DirCreate($sDestDir & $FileName)
      Else
         If Not FileCopy($aFileList[$c], $sDestDir & $FileName, 1) Then
            If Not FileCopy($aFileList[$c], $sDestDir & $FileName, 1) Then;Tries a second time
               If RunWait(@ComSpec & ' /c copy /y "' & $aFileList[$c] & '" "' & $sDestDir & $FileName & '">' & @TempDir & '\o.tmp', '', @SW_HIDE)=1 Then;and a third time, but this time it takes the error message
                  $sError = FileReadLine(@TempDir & '\o.tmp',1)
                  $iOutPut = $iOutPut + 1
                  $sLost = $sLost & $aFileList[$c] & '  ' & $sError & @CRLF
               EndIf
               FileDelete(@TempDir & '\o.tmp')
            EndIf
         EndIf

         FileSetAttrib($sDestDir & $FileName, "+A-RSH");<- Comment this line if you do not want attribs reset.

         $iCopiedSize = $iCopiedSize + Int(FileGetSize($aFileList[$c]) / 1024)
         $fProgress = $iCopiedSize / $iDirSize
      EndIf
   Next

   ProgressOff()

   If $sLost <> '' Then;tries to write the log somewhere.
      If FileWrite($sDestDir & 'notcopied.txt',$sLost) = 0 Then
         If FileWrite($sOriginalDir & 'notcopied.txt',$sLost) = 0 Then
            FileWrite(@WorkingDir & '\notcopied.txt',$sLost)
         EndIf
      EndIf
   EndIf

   Return $iOutPut
EndFunc  ;==>_CopyDirWithProgress

Func _FileSearch($sIstr, $bSF = 1)
  ; $bSF = 1 means looking in subfolders
  ; $sSF = 0 means looking only in the current folder.
  ; An array is returned with the full path of all files found. The pos [0] keeps the number of elements.
   Local $sCriteria, $sBuffer, $iH, $iH2, $sCS, $sCF, $sCF2, $sCP, $sFP, $sOutPut = '', $aNull[1]
   $sCP = StringLeft($sIstr, StringInStr($sIstr, '\', 0, -1))
   If $sCP = '' Then $sCP = @WorkingDir & '\'
   $sCriteria = StringTrimLeft($sIstr, StringInStr($sIstr, '\', 0, -1))
   If $sCriteria = '' Then $sCriteria = '*.*'

  ;To begin we seek in the starting path.
   $sCS = FileFindFirstFile($sCP & $sCriteria)
   If $sCS <> - 1 Then
      Do
         $sCF = FileFindNextFile($sCS)
         If @error Then
            FileClose($sCS)
            ExitLoop
         EndIf
         If $sCF = '.' Or $sCF = '..' Then ContinueLoop
         $sOutPut = $sOutPut & $sCP & $sCF & @LF
      Until 0
   EndIf

  ;And after, if needed, in the rest of the folders.
   If $bSF = 1 Then
      $sBuffer = @CR & $sCP & '*' & @LF;The buffer is set for keeping the given path plus a *.
      Do
         $sCS = StringTrimLeft(StringLeft($sBuffer, StringInStr($sBuffer, @LF, 0, 1) - 1), 1);current search.
         $sCP = StringLeft($sCS, StringInStr($sCS, '\', 0, -1));Current search path.
         $iH = FileFindFirstFile($sCS)
         If $iH <> - 1 Then
            Do
               $sCF = FileFindNextFile($iH)
               If @error Then
                  FileClose($iH)
                  ExitLoop
               EndIf
               If $sCF = '.' Or $sCF = '..' Then ContinueLoop
               If StringInStr(FileGetAttrib($sCP & $sCF), 'd') Then
                  $sBuffer = @CR & $sCP & $sCF & '\*' & @LF & $sBuffer;Every folder found is added in the begin of buffer
                  $sFP = $sCP & $sCF & '\';                               for future searches
                  $iH2 = FileFindFirstFile($sFP & $sCriteria);         and checked with the criteria.
                  If $iH2 <> - 1 Then
                     Do
                        $sCF2 = FileFindNextFile($iH2)
                        If @error Then
                           FileClose($iH2)
                           ExitLoop
                        EndIf
                        If $sCF2 = '.' Or $sCF2 = '..' Then ContinueLoop
                        $sOutPut = $sOutPut & $sFP & $sCF2 & @LF;Found items are put in the Output.
                     Until 0
                  EndIf
               EndIf
            Until 0
         EndIf
         $sBuffer = StringReplace($sBuffer, @CR & $sCS & @LF, '')
      Until $sBuffer = ''
   EndIf

   If $sOutPut = '' Then
      $aNull[0] = 0
      Return $aNull
   Else
      Return StringSplit(StringTrimRight($sOutPut, 1), @LF)
   EndIf
EndFunc  ;==>_FileSearch

Func _Quick_Sort(ByRef $SortArray, $First, $Last);Larry's code
   Dim $Low, $High
   Dim $Temp, $List_Separator

   $Low = $First
   $High = $Last
   $List_Separator = StringLen($SortArray[ ($First + $Last) / 2])
   Do
      While (StringLen($SortArray[$Low]) < $List_Separator)
         $Low = $Low + 1
      WEnd
      While (StringLen($SortArray[$High]) > $List_Separator)
         $High = $High - 1
      WEnd
      If ($Low <= $High) Then
         $Temp = $SortArray[$Low]
         $SortArray[$Low] = $SortArray[$High]
         $SortArray[$High] = $Temp
         $Low = $Low + 1
         $High = $High - 1
      EndIf
   Until $Low > $High
   If ($First < $High) Then _Quick_Sort($SortArray, $First, $High)
   If ($Low < $Last) Then _Quick_Sort($SortArray, $Low, $Last)
EndFunc  ;==>_Quick_Sort

I tried this without a Removable drive and it started to create the folders on my desktop, can you advise what things i should search for in the help to make a drive selection box rather than just one type

So it checks for REMOVABLE and FIXED, then this would give me the ability to backup to other destinations.

Also is there an easy way to add other folders into the backup

Nice piece of work and thanks for the time you have spent doing it

Edited by Chimaera
Posted

I am trying to do somewhat the same thing, but I don't want the parent folder my documents copied.

I want the individual dirs IN my documents to be copied so I did FileListToArray, then found the drive letter of the flash drive.

Where the heck do i find _copydirwithprogress?? i looked through the help and could not find it.

Also, how do I tell the script to FORMAT the usb drive w/o having to do shellexecute with wait?

Posted

Format Drive

FormatDrive()

Func FormatDrive()
    Opt('MustDeclareVars', 1)
    Local $iMsgBoxAnswer, $Drive, $DriveType, $DriveLabel = 'Backup'
    Do
        $Drive = InputBox('Drive Letter', 'Enter Drive Letter to which Setup Files will be installed', '', ' M1')
        If @error = 1 Then Return
        $Drive &= ':'
        $DriveType = DriveGetDrive('Removeable')
        If Not StringInStr($DriveType, $Drive) Then ContinueLoop
        If Not DriveSpaceFree($Drive) <= 1000 Then ContinueLoop
    Until DriveStatus($Drive) = 'Ready'
    DriveSetLabel($Drive, $DriveLabel)
    FileDelete(@TempDir & '\formatdrive.txt')
    FileWrite(@TempDir & '\formatdrive.txt', $DriveLabel & @CRLF & 'Y' & @CRLF)
    $iMsgBoxAnswer = MsgBox(262467, 'Format ' & $Drive & '?', 'Would you like to format ' & $Drive & '?', 10)
    Select
        Case $iMsgBoxAnswer = 6 ;Yes
            RunWait(@ComSpec & ' /c format ' & $Drive & ' /q /v:' & $DriveLabel & ' <' & @TempDir & '\formatdrive.txt', @SystemDir)
            Do
                Sleep(10)
            Until DriveStatus($Drive) = 'Ready'
            Opt('MustDeclareVars', 0)
            Return $Drive
        Case $iMsgBoxAnswer = 7 ;No
            Opt('MustDeclareVars', 0)
            Return $Drive
        Case $iMsgBoxAnswer = 2 ;Cancel
            Opt('MustDeclareVars', 0)
            Return
        Case $iMsgBoxAnswer = -1 ;Timeout
            Opt('MustDeclareVars', 0)
            Return $Drive
    EndSelect
EndFunc   ;==>FormatDrive

Posted

Format Drive

FormatDrive()

Func FormatDrive()
    Opt('MustDeclareVars', 1)
    Local $iMsgBoxAnswer, $Drive, $DriveType, $DriveLabel = 'Backup'
    Do
        $Drive = InputBox('Drive Letter', 'Enter Drive Letter to which Setup Files will be installed', '', ' M1')
        If @error = 1 Then Return
        $Drive &= ':'
        $DriveType = DriveGetDrive('Removeable')
        If Not StringInStr($DriveType, $Drive) Then ContinueLoop
        If Not DriveSpaceFree($Drive) <= 1000 Then ContinueLoop
    Until DriveStatus($Drive) = 'Ready'
    DriveSetLabel($Drive, $DriveLabel)
    FileDelete(@TempDir & '\formatdrive.txt')
    FileWrite(@TempDir & '\formatdrive.txt', $DriveLabel & @CRLF & 'Y' & @CRLF)
    $iMsgBoxAnswer = MsgBox(262467, 'Format ' & $Drive & '?', 'Would you like to format ' & $Drive & '?', 10)
    Select
        Case $iMsgBoxAnswer = 6 ;Yes
            RunWait(@ComSpec & ' /c format ' & $Drive & ' /q /v:' & $DriveLabel & ' <' & @TempDir & '\formatdrive.txt', @SystemDir)
            Do
                Sleep(10)
            Until DriveStatus($Drive) = 'Ready'
            Opt('MustDeclareVars', 0)
            Return $Drive
        Case $iMsgBoxAnswer = 7 ;No
            Opt('MustDeclareVars', 0)
            Return $Drive
        Case $iMsgBoxAnswer = 2 ;Cancel
            Opt('MustDeclareVars', 0)
            Return
        Case $iMsgBoxAnswer = -1 ;Timeout
            Opt('MustDeclareVars', 0)
            Return $Drive
    EndSelect
EndFunc   ;==>FormatDrive

Posted

Thank You Awl, lol!! I see I have alot to learn from reading these statements. I have seen COMSPEC for years but never had an occasion to use it.

I will integrate this with what I have now and this should be really cool!

..bvnseven

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...