Я пишу небольшую программу MFC, которая программно переименовывает все файлы с помощью Visual Studio 2019, и пока мой код работает, пока я не попытаюсь вызвать CFile::Rename для файла, содержащего символы Юникода, как показано в следующем фрагменте кода. Цель программы — переименовать имя файла с символами Юникода в имя файла без символов Юникода. Я не думал, что необходимо копировать сюда весь исходный код, но загрузил сообщение об ошибке, которое отображается при вызове статической функции CFile::Rename. введите сюда описание изображения
CString oldFileName (see uploaded error message)
CString newFileName (see uploaded error message)
CFile::Rename(oldFileName, newFileName, 0);
// FileRenamerDlg.cpp : implementation file
//
#include "pch.h"
#include "framework.h"
#include "FileRenamer.h"
#include "FileRenamerDlg.h"
#include "afxdialogex.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#endif
...
void CFileRenamerDlg::OnBnClickedButton1()
{
// TODO: Add your control notification handler code here
//MessageBox(L"Hello, World!", L"Unicode Message Box", 0);
//CFileDialog dlg(TRUE);
//dlg.DoModal();
CFolderPickerDialog fdlg;
if (IDOK == fdlg.DoModal())
{
sPath = fdlg.GetPathName();
userEnteredEditBox.GetWindowText(userEntererdTokens);
}
}
void CFileRenamerDlg::ParseChars()
{
int curPos = 0;
int subPos = 0;
CString resToken = userEntererdTokens.Tokenize(_T(";"), curPos);
while (!resToken.IsEmpty())
{
// check if token length is greater than a single character
if (resToken.GetLength() > 1)
{
for (int i = 0; i < resToken.GetLength(); i++)
{
CString tempStr(resToken.GetAt(i));
tokens.Add(tempStr);
}
}
else
{
tokens.Add(resToken);
}
// Obtain next token
resToken = userEntererdTokens.Tokenize(_T(";"), curPos);
}
}
// This function we need to modify so that we remove all characters
// from and including the '(' and everything between all the way to
// closing ')' Therefore everything in between the (..)
void CFileRenamerDlg::ParseFileName(CStringW oldFileNameW)
{
int closeBracketPos = -1;
wchar_t* str = L"Test";
wchar_t tempChar;
wchar_t closingRoundBracket = ')';
CStringW newFileNameW;
int length = oldFileNameW.GetLength();
for (int i = 0; i < length; i++)
{
// getAt the first char of the oldfilename
tempChar = oldFileNameW.GetAt(i);
// since it is a token now check if its opening bracket
// we need the position of the opening bracket then find
// if there is a closing bracket and get its position
switch (tempChar)
{
case '(':
// save the position of i and shift everything by 1 position
closeBracketPos = oldFileNameW.Find(')', i);
if (oldFileNameW.GetAt(closeBracketPos + 1) == ' ')
{
i = closeBracketPos + 1;
}
else
{
i = closeBracketPos;
}
break;
case '[':
closeBracketPos = oldFileNameW.Find(']', i);
i = closeBracketPos;
break;
case '{':
closeBracketPos = oldFileNameW.Find('}', i);
i = closeBracketPos;
break;
case 10084: // '❤️' // ♥
i = i + 1;
break;
default:
newFileNameW.AppendChar(tempChar);
break;
}
}
MessageBox(sPath + oldFileNameW, sPath + newFileNameW, NULL);
CFile::Rename(sPath + oldFileNameW, sPath + newFileNameW, NULL);
}
void CFileRenamerDlg::ExecRenameFiles()
{
CFileFind listFiles;
CString foundFileName;
// start working for files
BOOL bWorking = listFiles.FindFile(sPath2, 0);
while (bWorking)
{
bWorking = listFiles.FindNextFile();
if (!listFiles.IsDots())
{
ParseFileName(listFiles.GetFileName());
}
}
}
bool CFileRenamerDlg::IsToken(char AChar)
{
// so we have an array of string tokens
int size = tokens.GetSize();
CString tokenChar;
CString strChar(AChar);
for(int i = 0; i < size; i++)
{
// old working code
tokenChar = tokens.GetAt(i);
// incoming char is a token so return true
if (strChar == tokenChar)
{
return true;
}
else
{
return false;
}
}
return false;
}
void CFileRenamerDlg::OnBnClickedGo()
{
// TODO: Add your control notification handler code here
SetDirectory();
ParseChars();
ExecRenameFiles();
}
void CFileRenamerDlg::SetDirectory()
{
int n = sPath.Replace(_T("\\"), _T("\\\\"));
sPath = sPath + _T("\\");
sPath2 = sPath + _T("\\*.*");
}
Я попытался преобразовать переменные CString oldFileName и CString newFileName в CStringW, но функция-член CFile::Rename() выдала ошибку во время компиляции, вероятно, потому что нет перегруженной функции-члена Rename(), которая принимает широкий строки символов.
Я пишу небольшую программу MFC, которая программно переименовывает все файлы с помощью Visual Studio 2019, и пока мой код работает, пока я не попытаюсь вызвать CFile::Rename для файла, содержащего символы Юникода, как показано в следующем фрагменте кода. Цель программы — переименовать имя файла с символами Юникода в имя файла без символов Юникода. Я не думал, что необходимо копировать сюда весь исходный код, но загрузил сообщение об ошибке, которое отображается при вызове статической функции CFile::Rename. введите сюда описание изображения [code]CString oldFileName (see uploaded error message) CString newFileName (see uploaded error message)
while (!resToken.IsEmpty()) { // check if token length is greater than a single character if (resToken.GetLength() > 1) { for (int i = 0; i < resToken.GetLength(); i++) { CString tempStr(resToken.GetAt(i)); tokens.Add(tempStr); } } else { tokens.Add(resToken); } // Obtain next token resToken = userEntererdTokens.Tokenize(_T(";"), curPos); } }
// This function we need to modify so that we remove all characters // from and including the '(' and everything between all the way to // closing ')' Therefore everything in between the (..) void CFileRenamerDlg::ParseFileName(CStringW oldFileNameW) { int closeBracketPos = -1; wchar_t* str = L"Test"; wchar_t tempChar; wchar_t closingRoundBracket = ')'; CStringW newFileNameW;
int length = oldFileNameW.GetLength();
for (int i = 0; i < length; i++) { // getAt the first char of the oldfilename tempChar = oldFileNameW.GetAt(i);
// since it is a token now check if its opening bracket // we need the position of the opening bracket then find // if there is a closing bracket and get its position
switch (tempChar) { case '(': // save the position of i and shift everything by 1 position closeBracketPos = oldFileNameW.Find(')', i);
if (oldFileNameW.GetAt(closeBracketPos + 1) == ' ') { i = closeBracketPos + 1; } else { i = closeBracketPos; } break;
case '[':
closeBracketPos = oldFileNameW.Find(']', i); i = closeBracketPos; break;
case '{':
closeBracketPos = oldFileNameW.Find('}', i); i = closeBracketPos; break;
BOOL bWorking = listFiles.FindFile(sPath2, 0); while (bWorking) { bWorking = listFiles.FindNextFile(); if (!listFiles.IsDots()) { ParseFileName(listFiles.GetFileName()); } } }
bool CFileRenamerDlg::IsToken(char AChar) { // so we have an array of string tokens int size = tokens.GetSize();
CString tokenChar; CString strChar(AChar);
for(int i = 0; i < size; i++) { // old working code tokenChar = tokens.GetAt(i);
// incoming char is a token so return true if (strChar == tokenChar) { return true; } else { return false; } } return false; } void CFileRenamerDlg::OnBnClickedGo() { // TODO: Add your control notification handler code here SetDirectory(); ParseChars(); ExecRenameFiles(); } void CFileRenamerDlg::SetDirectory() { int n = sPath.Replace(_T("\\"), _T("\\\\")); sPath = sPath + _T("\\"); sPath2 = sPath + _T("\\*.*"); }
[/code] Я попытался преобразовать переменные CString oldFileName и CString newFileName в CStringW, но функция-член CFile::Rename() выдала ошибку во время компиляции, вероятно, потому что нет перегруженной функции-члена Rename(), которая принимает широкий строки символов.
Я пишу небольшую программу MFC, которая программно переименовывает все файлы с помощью Visual Studio 2019, и пока мой код работает, пока я не попытаюсь вызвать CFile::Rename для файла, содержащего символы Юникода, как показано в следующем фрагменте...
Я создаю форму загрузки, используя класс загрузки codeiginiter, чтобы облегчить пользователю загрузку файла (разрешены только файлы .csv). Я хочу заставить пользователей переименовывать свои имена файлов перед загрузкой CSV, отклоняя их, если имя...
Я использую VS 2022. У меня есть работающее многопоточное приложение MFC C++ A (модальное) и отдельное рабочее (модальное) однопоточное приложение MFC C++ B. Я хотел бы использовать B как средство как для диалога A, так и для его дочерний поток для...
Я использую VS 2022. У меня есть работающее многопоточное приложение MFC C++ A (модальное) и отдельное рабочее (модальное) однопоточное приложение MFC C++ B. Я хотел бы использовать B как средство как для диалога A, так и для его дочерний поток для...