Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > .NET для новичков > Background Worker


Автор: fromrus 7.5.2008, 19:44
пытаюсь настроить прогрессБар под копирование файлов.Для этого использую BW/вот код класса,где присутствует метод копирования :
Код

class CopyFiles
{
public CopyFiles(){}
public static void Copy(DirectoryInfo source, DirectoryInfo destination)
{
FileInfo[] files = source.GetFiles();
DirectoryInfo[] dirs = source.GetDirectories();
if (!destination.Exists)
{
destination.Create();
}
foreach (FileInfo file in files)
{
file.CopyTo(Path.Combine(destination.FullName,
file.Name), true);
}
// Process subdirectories.
foreach (DirectoryInfo dir in dirs)
{
// Get destination directory.
string destinationDir = Path.Combine(destination.FullName, dir.Name);
// Call CopyDirectory() recursively.
Copy(dir, new DirectoryInfo(destinationDir));
}
}
}

А вот кнопка по которой копируется папка(ну во обще-то она как раз и не копируется):
Код

private void copy_Click(object sender, RoutedEventArgs e)
{
bw = new BackgroundWorker();
CopyFiles cop = new CopyFiles();
bw.RunWorkerAsync(cop); /////////////exeption-с ним все понятно,нулл передаю
}

ну и соответственно события worker'a:
Код

private void bw_DoWork(object sender,DoWorkEventArgs args)
{

CopyFiles.Copy(....);
progBar.Cursor = Cursors.Wait;
bw.ReportProgress(3);
}
private void BackgroundWorker_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
progBar.Value = e.ProgressPercentage;
}
private void BackgroundWorker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
progBar.Value = 0;
}

никак не одупляю че передавать в аргумент RunWorkerAsync....Помощи прошу!

Добавлено через 2 минуты и 38 секунд
эт забыл написать..)))) 
Код
bw=sender as BackgroundWorker

Но проблема та же!

Автор: vponomarov 7.5.2008, 20:43
на сколько я понимаю тебе нужно передавать в RunWorkerAsync список файлов, которые необходимо скопировать.
или вообще ничего не передавай, если список получается каким-то другим образом.
проблема не совчем понятна...

Автор: fromrus 8.5.2008, 00:51
надо чтоб файлы копировались в рабочем потоке,а прогресс бар отображал бы этот прогресс.Я не понимаю что передавать в параметр RunWorkerAsync...Если ничего не передавать вылезет тот же ексепшн,что и сейчас

Автор: 1stain 8.5.2008, 09:31
Цитата(fromrus @  8.5.2008,  00:51 Найти цитируемый пост)
надо чтоб файлы копировались в рабочем потоке,а прогресс бар отображал бы этот прогресс.

Ты видимо не совсем понял назначение работы с потоками и с сабжем в частности. Дополнительный поток как раз нужен для того, чтобы вынести в него операции, требующие много времени, в данном случае - работу с файлами.
На мой взгляд, копирование надо перенести в БВ, передавать аргументом соответственно путь источника и назначения. После завершения копирования каждого файла пересчитывать проценты прогресса.

Автор: mr.DUDA 8.5.2008, 09:49
Туда передаётся любой произвольный объект, который потом примет твой метод bw_DoWork через e.Argument. Естесственно, что в bw_DoWork объект приводить нужно явно:
Код
CopyFiles cop = (CopyFiles)e.Argument;

Автор: Ram1reS 8.5.2008, 10:07
Код


        private void bw_DoWork( object sender , DoWorkEventArgs e )
        {
            // в e.Argument хранится то, что ты передал в RunWorkerAsync
            CopyInfo cInfo = e.Argument as CopyInfo;
            CopyFiles.Copy( cInfo );
        }

        // метод для обновления прогресс бара, написал для примера
        private void bw_ProgressChanged( object sender , ProgressChangedEventArgs e )
        {
            pbProgress.Invoke( (MethodInvoker)delegate()
            {
                pbProgress.Value = e.ProgressPercentage;
            }
            );
        }

        private void btnStart_Click( object sender , EventArgs e )
        {
            CopyInfo cInfo = new CopyInfo();
            cInfo.source = new DirectoryInfo( @"C:\testdir\1" );
            cInfo.dest = new DirectoryInfo( @"C:\testdir\2" );
            // передаем bw информацию о папках
            bw.RunWorkerAsync(cInfo);
        }

        class CopyFiles
        {
            public CopyFiles() { }
            // чуть измененный метод Copy, чтобы принимал 1 параметр
            public static void Copy(CopyInfo cInfo )
            {
                FileInfo[] files = cInfo.source.GetFiles();
                DirectoryInfo[] dirs = cInfo.source.GetDirectories();
                if ( !cInfo.dest.Exists )
                {
                    cInfo.dest.Create();
                }
                foreach ( FileInfo file in files )
                {
                    file.CopyTo( Path.Combine( cInfo.dest.FullName ,
                    file.Name ) , true );
                }
                // Process subdirectories.
                foreach ( DirectoryInfo dir in dirs )
                {
                    // Get destination directory.
                    string destinationDir = Path.Combine( cInfo.dest.FullName , dir.Name );
                    // Call CopyDirectory() recursively.
                    CopyInfo newCopyInfo = new CopyInfo();
                    newCopyInfo.source = dir;
                    newCopyInfo.dest = new DirectoryInfo( destinationDir );
                    Copy( newCopyInfo);
                }
            }
        }

        class CopyInfo
        {
            public CopyInfo()  { }
            public DirectoryInfo source { get; set; }
            public DirectoryInfo dest { get; set; }
        }


Таким образом можно организовать копирование файлов в BackgroundWorker.

Не совсем понятно как Вы собирались обновлять прогрессбар...
Вам надо сначало узнать сколько всего элементов будут копироваться, установить это число в progressBar.Maximum, вести счетчик уже скопированных элементов и этим числом обновлять progressBar.Value (вызовом BackgroundWorker.ReportProgress(FilesCopied)) + у BackgroundWorker должен стоять флажок WorkerReportsProgress.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)