上一篇post里提到了QQ音乐的QRC歌词,不过其他播放器并不能识别出这个格式,于是只好自己写个转换器了。
稍微写了一下,感觉效果还不错~~如下图
代码在此~
#import <string>
#import <iostream>
#import <fstream>
#import <regex.h>
using namespace std;
/*!
* @brief 把微秒时间转为LRC中的时间
*
* @discussion 并未考虑超过99:59.99的时间
*
* @return [dd:dd.dd]
*/
const char * microseconds_to_LRC_time(long long microsecond)
{
double seconds = microsecond / 1000.0;
int min = seconds / 60;
double sec = seconds - 60 * min;
return [NSString stringWithFormat:@"%02d:%05.2lf",min,sec].UTF8String;
}
@interface QRC : NSObject
/*!
* @brief 解析QRC到LRC
*
* @param QRCPath QRC文件路径
* @param error 出错时返回错误码和原因
*/
+ (void)ParserQRCDoc:(NSString *)QRCPath Error:(NSError **)error;
@end
@implementation QRC
+ (void)ParserQRCDoc:(NSString *)QRCPath
Error:(NSError **)error
{
ifstream QRC_file(QRCPath.UTF8String);
if(!QRC_file)
{
*error = [[NSError alloc] initWithDomain:@"com.[data deleted].QRC" code:-1 userInfo:@{@"Error":@"No such file"}];
return;
}
string str;
int cflags = REG_EXTENDED;
regex_t reg;
const char * pattern = "^\[([0-9]+)";
// 匹配以'['开头, 并且后面跟着数字的就行了
// 因为是转为LRC, 故提取出每句开始的时间就行
int z = regcomp(®, pattern, cflags);
if (z != 0)
{
char ebuf[128];
regerror(z, ®, ebuf, sizeof(ebuf));
*error = [[NSError alloc] initWithDomain:@"com.[data deleted].QRC" code:-2 userInfo:@{@"Error":[NSString stringWithFormat:@"%s",ebuf]}];
regfree(®);
return;
}
regmatch_t pm[10];
const size_t nmatch = 10;
while(getline(QRC_file, str))
{
z = regexec(®, str.c_str(), nmatch, pm, 0);
if (z == REG_NOMATCH)
{
continue;
}
else if (z != 0)
{
char ebuf[128];
regerror(z, ®, ebuf, sizeof(ebuf));
*error = [[NSError alloc] initWithDomain:@"com.[data deleted].QRC" code:-3 userInfo:@{@"Error":[NSString stringWithFormat:@"%s",ebuf]}];
regfree(®);
return;
}
else
{
const char * line = str.c_str();
for (int x = 1; x < nmatch && pm[x].rm_so != -1; ++ x)
{
char *mstr = strndup(line + pm[x].rm_so, pm[x].rm_eo - pm[x].rm_so);
long long microseconds = atoll(mstr);
free(mstr);
printf("[%s]",microseconds_to_LRC_time(microseconds));
}
BOOL print = YES;
for(int i = 0; i < strlen(line); i++)
{
if (line[i] == '[' || line[i] == '(')
{
print = NO;
continue;
}
else if (line[i] == ']' || line[i] == ')')
{
print = YES;
continue;
}
else
{
if (print) printf("%c",line[i]);
}
}
printf("n");
}
fflush(stdout);
}
}
@end
int main(int argc, const char * argv[])
{
@autoreleasepool
{
for (int i = 1; i < argc; i++) {
NSError *error;
[QRC ParserQRCDoc:[NSString stringWithUTF8String:argv[i]] Error:&error];
}
}
return 0;
}
qrc格式的歌词文件不是已经加密了吗?