Home > Software engineering >  Copying Files From One Directory to Another With Progress bar C# WPF
Copying Files From One Directory to Another With Progress bar C# WPF

Time:12-21

I am using the Following Code for Copying the Files from one directory to Another Directory

private void CopyFilesRecursively(string serverDirectorty, string localDirectory)
    {
        serverDirectorty = settings["baseDocPathSource"] as string;
        localDirectory = settings["baseDocPath"] as string;

        //Now Create all of the directories
        foreach (string dirPath in Directory.GetDirectories(serverDirectorty, "*", SearchOption.AllDirectories))
        {
            Directory.CreateDirectory(dirPath.Replace(serverDirectorty, localDirectory));
        }

        //Copy all the files & Replaces any files with the same name
        foreach (string newPath in Directory.GetFiles(serverDirectorty, "*.*", SearchOption.AllDirectories))
        {
            File.Copy(newPath, newPath.Replace(serverDirectorty, localDirectory), true);
        }
    }

I want to Integrate the Progress bar to my code i.e. when I click the copy button I want to show the progress bar moving from 0 to 100 and when copying of the files is done I want to hide the progress bar.

Below is my XML File

    <Grid>
    <ProgressBar Visibility="Hidden" Name="pbCopy" HorizontalAlignment="Left" Height="65" Margin="127,151,0,0" VerticalAlignment="Top" Width="485"/>
    <Button Content="Copy Files" HorizontalAlignment="Left" Margin="283,253,0,0" VerticalAlignment="Top" Width="164" Height="66"/>

</Grid>

I want to Hide the Progress Bar from my Form Initially and want to set the Visibility "Visible" after clicking on the Button.

CodePudding user response:

Try to use the Progress class. Pass it to your method.

private void CopyFilesRecursively(string serverDirectorty, string localDirectory, IProgress<double> progress)
{
    serverDirectorty = settings["baseDocPathSource"] as string;
    localDirectory = settings["baseDocPath"] as string;

    //Now Create all of the directories
    foreach (string dirPath in Directory.GetDirectories(serverDirectorty, "*", SearchOption.AllDirectories))
    {
       Directory.CreateDirectory(dirPath.Replace(serverDirectorty, localDirectory));
    }

    //Copy all the files & Replaces any files with the same name
    var files = Directory.GetFiles(serverDirectorty, "*.*", SearchOption.AllDirectories);

    double processed = 0;
    //Reset progress value to 0.
    progress?.Report(0);
            
    foreach (string newPath in files)
    {
        File.Copy(newPath, newPath.Replace(serverDirectorty, localDirectory), true);
        //Report in percentage 1-100%. If you have a ton of files, you should reduce the number of calling progress?.Report() e.g. using dividing by modulo.
        progress?.Report((  processed / files.Length) * 100);
    }
            
    //If files weren't found.
    progress?.Report(100);
}

CodePudding user response:

Give the ProgressBar a name in your XAML markup:

<ProgressBar x:Name="pb" ... />

...and set its properties in your method. Something like this:

private void CopyFilesRecursively(string serverDirectorty, string localDirectory)
{
    serverDirectorty = settings["baseDocPathSource"] as string;
    localDirectory = settings["baseDocPath"] as string;

    //Now Create all of the directories
    foreach (string dirPath in Directory.GetDirectories(serverDirectorty, "*", SearchOption.AllDirectories))
    {
        Directory.CreateDirectory(dirPath.Replace(serverDirectorty, localDirectory));
    }

    //Copy all the files & Replaces any files with the same name
    string[] files = Directory.GetFiles(serverDirectorty, "*.*", SearchOption.AllDirectories);
    pb.Dispatcher.Invoke(() =>
    {
        pb.Visibility = Visibility.Visible;
        pb.Maximum = files.Length;
        pb.Value = 0;
    });
    for (int i = 0; i < files.Length; i  )
    {
        string newPath = files[i];
        File.Copy(newPath, newPath.Replace(serverDirectorty, localDirectory), true);
        pb.Dispatcher.Invoke(() => pb.Value  = i   1);
    }
    pb.Dispatcher.Invoke(() => pb.Visibility = Visibility.Collapsed);
}

Also make sure that you are running your copy method on a background thread:

private void Button_Click(object sender, RoutedEventArgs e)
{
    Task.Run(() => CopyFilesRecursively("...", "..."));
}
  • Related