Rad Studio中使用ReadDirectoryChanges调用BASS流加载文件失败问题
问题描述
我尝试用ReadDirectoryChanges监控目录,将新增文件加载到BASS音频库的流中。通过FileOpenDialog测试的功能完全正常,但用ReadDirectoryChanges(RDC)触发时总是失败。肯定是操作存在失误,但始终无法定位问题,求排查方向。
代码片段
ToWav函数(RDC触发时调用)
void __fastcall TForm9::ToWav(FILE_NOTIFY_INFORMATION* File) { String FullFileName = OpokaClient.ImportLocation + copyfname(File); int BassResult = 0; LogLine("File added to: " + FullFileName, apSYSTEM); HSTREAM convert = NULL; convert = MyBASS_StreamCreateFile(false, FullFileName.c_str(), 0, 0, BASS_STREAM_DECODE | BASS_UNICODE); BassResult = MyBASS_ErrorGetCode(); LogLine("Bass Result: " + IntToStr(BassResult), apSYSTEM); }
Button2Click函数(FileOpenDialog测试用)
void __fastcall TForm9::Button2Click(TObject *Sender) { String FileName; int BassResult = 0; if(FileOpenDialog1->Execute()) { FileName = FileOpenDialog1->FileName; } else { LogLine("No file selected. FileName empty", apWARNING); return; } HSTREAM convert = NULL; LogLine("ConverterMain: ToWav: FileName: " + FileName, apSYSTEM); convert = MyBASS_StreamCreateFile(false, FileName.c_str(), 0, 0, BASS_STREAM_DECODE | BASS_UNICODE); BassResult = MyBASS_ErrorGetCode(); LogLine("chan ErrorCode: " + IntToStr(BassResult), apSYSTEM); }
copyfname函数(获取文件名)
wchar_t* copyfname(FILE_NOTIFY_INFORMATION* pfi) { wchar_t* pfn; pfn = new wchar_t[pfi->FileNameLength+1]; ZeroMemory(pfn, sizeof(wchar_t)*(pfi->FileNameLength+1)); memcpy(pfn, pfi->FileName, pfi->FileNameLength); return pfn; }
排查方向
- 路径拼接错误:检查
OpokaClient.ImportLocation末尾是否包含路径分隔符(如\)。如果没有,拼接后的路径会变成ImportFolder文件名,而非ImportFolder\文件名,导致BASS找不到文件。FileOpenDialog返回的是完整正确路径,所以测试正常。 - 文件未完全写入:RDC触发
FILE_ACTION_ADDED时,文件可能还在被写入(比如复制过程中),此时文件处于占用状态或内容不完整,BASS无法正常打开。可以尝试循环尝试打开文件,直到成功或超时,再调用BASS的流创建函数。 - 文件名长度计算错误:
FILE_NOTIFY_INFORMATION::FileNameLength是字节数,而wchar_t占2字节,所以分配内存时应该用pfi->FileNameLength / sizeof(wchar_t) + 1,而非直接用pfi->FileNameLength+1。当前代码分配的内存是实际需要的2倍,可能导致字符串末尾出现多余字符,影响路径正确性。 - 明确BASS错误码含义:根据
BassResult的数值对应BASS错误码(比如BASS_ERROR_FILEOPEN是2,BASS_ERROR_FORMAT是3),针对性排查。如果是文件打开错误,优先检查路径或文件占用;如果是格式错误,大概率是文件未写完。 - 字符串转换问题:虽然
String能接收wchar_t*,但要确保copyfname返回的字符串是正确终止的。当前用ZeroMemory初始化了内存,这部分没问题,但长度计算错误可能导致潜在的乱码问题。
内容的提问来源于stack exchange,提问作者Richard Harreman
相关产品推荐
相关产品推荐

