На главную Наши проекты:
Журнал   ·   Discuz!ML   ·   Wiki   ·   DRKB   ·   Помощь проекту
ПРАВИЛА FAQ Помощь Участники Календарь Избранное RSS
msm.ru
! Правила раздела FAQ в группе разделов С++.
1. Раздел FAQ предназначен для публикации готовых статей.
2. Здесь нельзя задавать вопросы, для этого существуют соответствующие разделы:
Чистый С++
Visual C++ / MFC / WTL / WinApi
Borland C++ Builder
COM / DCOM / ActiveX / ATL
Сопутствующие вопросы
3. Внимание, все темы и сообщения в разделе премодерируются. Любое сообщение или тема будут видны остальным участникам только после одобрения модератора.
Модераторы: B.V., Qraizer
  
> Как скопировать или переместить каталог , Как скопировать или переместить каталог со всем со
    Статью лучше читать здесь

    Как-то мне потребовалось скопировать каталог со всем содержимым. Вначале я пытался сделать это используя функцию FindFirstFile, FindNextFile, но реализация была довольно сложна и неудобна, поэтому я выбрал другой способ: использовать функцию SHFileOperation. Это стандартная API функция описания в shellapi.h, которая позволяет копировать, перемещать и удалять объекты файловой системы.

    Синтаксис функции:
    ExpandedWrap disabled
       
      int SHFileOperation(      
          LPSHFILEOPSTRUCT lpFileOp );


    Параметры :

    lpFileOp

    Указатель на структуру SHFILEOPSTRUCT которая содержит информацию о выполнимой операции. Этот параметр должен содержать правильное значение и не должен быть равен NULL. Вы ответственны за значения этого параметра, если вы укажете его неправильно, то можете получить неверные результаты.
    Возвращаемое значение:

    Ноль в случае успешного завершения, иначе ненулевое значение.

    SHFILEOPSTRUCT Structure

    Синтаксис
    ExpandedWrap disabled
       
      typedef struct _SHFILEOPSTRUCT {
      HWND hwnd;
      UINT wFunc;
      LPCTSTR pFrom;
      LPCTSTR pTo;
      FILEOP_FLAGS fFlags;
      BOOL fAnyOperationsAborted;
      LPVOID hNameMappings;
      LPCTSTR lpszProgressTitle;
      } SHFILEOPSTRUCT, *LPSHFILEOPSTRUCT;

    Члены функции

    hwnd

    Указатель на диалоговое окно, отображающее информацию о статусе выполнения файловой операции.

    wFunc

    Значение указывающее какое действие необходимо выполнить. Это значение должно иметь одно из следующих значений:

    FO_COPY

    Копировать файлы описанные в pFrom члене в место определенное в pTo члене.

    FO_DELETE

    Удалить файлы описанные в pFrom.

    FO_MOVE

    Переместить файлы из пути описанного в pFrom в место описанное в pTo.

    FO_RENAME

    Переименовать фалы описанные в pFrom. Вы не можете использовать этот флаг чтобы переименовать много файлов при единичном вызове функции. Используйте вместо этого FO_MOVE .

    pFrom

    Адрес буфера определяющего одно или более имен файлов. Эти имена должны быть абсолютными путями. Разрешено использовать стандартные групповые символы MS- DOS, такие как, "*" в именах файловых путей. Хотя этот член объявлен как строка оканчивающаяся нулем его можно использовать как буфер содержащий много файловых имен. Каждое имя файла должно оканчиваться одним NULL символом . Добавочный NULL символ должен быть добавлен в конце указывающий на конец pFrom.

    pTo

    Адрес буфера содержащего имя куда будет скопирован или перемещен файл или каталог. Этот параметр должен быть установлен в NULL, если он не используется. Подобно pFrom , параметр pTo также оканчивается двумя NULL символами . Таким образом pTo должен отвечать следующей спецификации :

    Групповые символы не поддерживаются.
    Операции копирования и перемещения могут определить путь получатель, но если он не будет существовать, система попытается его создать. Система обычно отображает диалоговое окно, спрашивающее хочет ли пользователь создать новую директорию. Чтобы скрыть это окно и директории создавались автоматически, необходимо установить флаг FOF_ NOCONFIRMMKDIR в члене структуры fFlags.
    Если при копировании или перемещении буфер может содержать много имен файлов, то должен быть установлен флаг FOF_ MULTIDESTFILES в члене структуры fFlags.
    Содержать много имен файлов в строке, также как и в pFrom.
    Использовать только абсолютный путь. Использование относительных путей может дать непредсказуемые результаты.
    fFlags

    Флаг который контролирует файловые операции. Этот параметр может быть комбинацией из флагов:

    FOF_ALLOWUNDO

    Позволять выполнить команду Отмена, если возможно. Если pFrom не содержит абсолютного пути и имен файлов, то этот флаг игнорируется.

    FOF_CONFIRMMOUSE

    Не используется .

    FOF_FILESONLY

    Выполнение операции над файлами только если определении групповые символы в имени файлов (*.*).

    FOF_MULTIDESTFILES

    Член pTo определяет множественные имена файлов (один на каждый исходный файл) для одной директории где расположены все имена файлов.

    FOF_NOCONFIRMATION

    Выполняется подтверждение "Да для Всех", для всех диалоговых окон.

    FOF_NOCONFIRMMKDIR

    Не требуется подтверждения для создания новой директории если не обходимо ее создание.

    FOF_NO_CONNECTED_ELEMENTS

    Версия 5.0. Не перемещать группу файлов. Перемещать файлы только по одиночке.

    FOF_NOCOPYSECURITYATTRIBS

    Версия 4.71. Не копировать атрибуты безопасности для файлов.

    FOF_NOERRORUI

    Не отображать пользовательский интерфейс при возникновении ошибки.

    FOF_NORECURSION

    Работать только с локальными директориями. Не работать с поддиректориями .

    FOF_NORECURSEREPARSE

    Treat reparse points as objects, not containers. You must set _WIN32_WINNT to 5.01 or later to use this flag. See Shell and Common Controls Versions for further discussion of versioning.

    FOF_RENAMEONCOLLISION

    Give the file being operated on a new name in a move, copy, or rename operation if a file with the target name already exists.

    FOF_SILENT

    Не отображать диалоговое окно прогресса.

    FOF_SIMPLEPROGRESS

    Показать упрощенный диалог, но не показывать имена файлов.

    FOF_WANTMAPPINGHANDLE

    Если флаг FOF_ RENAMEONCOLLISION установлен и несколько файлов переименовано, связать карту имен содержащих новые и старые имена с членом hNameMappings.

    FOF_WANTNUKEWARNING

    Version 5.0. Send a warning if a file is being destroyed during a delete operation rather than recycled. This flag partially overrides FOF_NOCONFIRMATION.

    fAnyOperationsAborted

    Значение устанавливается в TRUE если пользователь прервал файловую операцию, прежде чем оно успела окончиться, или FALSE в случае если операция завершилась.

    hNameMappings

    Указатель на объект карты имен содержащий новые и старые имена переименованных файлов. Этот член используется только если флаг FOF_WANTMAPPINGHANDLE установлен .

    lpszProgressTitle

    Адрес строки которая используется в заголовке диалогового окна, отображающего прогресс выполнения операции. Этот член используется только если fFlags включает флаг FOF_ SIMPLEPROGRESS.


    При использовании в pFrom и pTo относительных путей получить текущую директорию можно, использую функцию GetCurrentDirectory, а установить директорию функцией SetCurrentDirectory.

    Если вы удаляете файлы или каталоги, используя FO_DELETE параметр, то даже если установлен флаг FOF_ALLOWUNDO, удаление в корзину не произойдет, если вы используете относительные пути, поэтому используйте абсолютные пути.

    Вы не можете использовать функцию SHFileOperation для перемещения папок с локального диска на удаленный компьютер, кроме двух случаев: это перемещение папки My Documents и My Pictures.

    Следует отметить одну особенность заполнения структуры, которая вызывает затруднения у начинающих программистов; особенность в том, что поля pFrom и pTo должны иметь два завершающих нуля.

    Т.к. сам я поклонник использования CString, и использую его везде где только нужно использовать строки, то я предлагаю реализацию функции которая копирует или перемещает файлы или каталоги, а параметры у нее CString.


    ExpandedWrap disabled
       
      int CMainFrame::fnFileOperation(CString strCurrentPath, CString strAnotherPath, CString strFileName, UINT wFunc)
       
      {
       
      SHFILEOPSTRUCT lpFileOp;
       
      char chFrom[MAX_PATH],
       
      chTo[MAX_PATH];
       
      ZeroMemory(&chFrom, sizeof(chFrom));
       
      ZeroMemory(&chTo, sizeof(chTo));
       
      CString strFrom = strCurrentPath+strFileName;
       
      CString strTo = strAnotherPath+strFileName;
       
      strcpy(chFrom,(LPCTSTR)strFrom);
       
      strcpy(chTo,(LPCTSTR)strTo);
       
      lpFileOp.pFrom = chFrom; // откуда копировать
       
      lpFileOp.pTo = chTo; // куда копировать
       
      lpFileOp.wFunc = wFunc; // операция
       
      lpFileOp.hwnd = m_hWnd; // указатель на главное окно приложения
       
      lpFileOp.fFlags = FOF_SIMPLEPROGRESS // показать упрощенный диалог
       
      |FOF_NOCONFIRMMKDIR; // не задавать вопрос если требуется создание директории
       
      lpFileOp.fAnyOperationsAborted = TRUE;
       
      lpFileOp.lpszProgressTitle = "";
       
      lpFileOp.hNameMappings = NULL;
       
      int nRes = SHFileOperation(&lpFileOp);
       
      return nRes;
       
      }

    Пример вызова функции:


    ExpandedWrap disabled
       
      CString strCurrentPath,
       
      fnFileOperation(strCurrentPath, strAnotherPath, strFileName, FO_COPY);



    Возможно использование дополнительных переменных вам покажется и излишним, но это необходимо для того чтобы в конце имени файлов были два нулевых символа.
    Сообщение отредактировано: shapovalov -
      Цитата
      shapovalov, 9.09.04, 23:49
      но это необходимо для того чтобы в конце имени файлов были два нулевых символа.

      CString корректно работает при добавлении нулевого символа:

      ExpandedWrap disabled
        CString szFileName = _T("C:\\SuperPuperFolder\\SuperPuperFile.ext");
        szFileName += _T('\0');


      Добавлено в :
      ExpandedWrap disabled
        //shapovalov, 9.09.04, 23:49
        lpFileOp.fFlags = FOF_SIMPLEPROGRESS // показать окно прогресса
         
        &FOF_NOCONFIRMMKDIR; // не задавать вопрос если требуется создание директории

      Здесь явно ошибочно:
      1) FOF_SIMPLEPROGRESS означает "показать упрощенный диалог". По дефолту выводится диалог, в котором отображаются имена файлов, над которыми осуществляется операция. При использовании флага FOF_SILENT диалога вообще не будет.
      2) FOF_SIMPLEPROGRESS&FOF_NOCONFIRMMKDIR как ни парадоксально, даст 0 :) Флаги объединять надо не по И(&), а по ИЛИ(|).

      Добавлено в :
      Цитата
      shapovalov, 9.09.04, 23:49
      Выполнение операции над файлами только если определении групповые символы в имени файлов (*.*).

      Выполнение операции только над файлами

      Цитата
      shapovalov, 9.09.04, 23:49
      FO_COPY
      Копировать файлы описанные в pFrom члене в место определенное в pTo члене.


      Я конечно понимаю, программы-переводчики вещь хорошая, но я бы исправил русский язык
        Uncle_Bob, я уже ему все это, кроме CString, по аське объяснил, только вот он исчез почему-то B)
          Leprecon, я не изчез, в статье на своем сайте, я & на | исправил , сейчас исправлю и в формуме.
          К тому же статья получилась явно неудачная, я уже пожалел что написал ее.

          Добавлено в :
          Цитата
          Uncle_Bob, 14.09.04, 18:49
          Я конечно понимаю, программы-переводчики вещь хорошая, но я бы исправил русский язык

          Я не использовал переводчик, просто русский заню плохо.
          Сообщение отредактировано: shapovalov -
          0 пользователей читают эту тему (0 гостей и 0 скрытых пользователей)
          0 пользователей:


          Рейтинг@Mail.ru
          [ Script execution time: 0,0373 ]   [ 15 queries used ]   [ Generated: 1.05.24, 04:06 GMT ]