0

按照opengl-tutorial.org上的教程 ,意识到我不能直接使用 printf 打印着色器编译日志,因为我是在 Windows 桌面应用程序中进行的。我尝试使用此方法将其转换为 LPWSTR:

//compile the shader
glShaderSource(fShader, 1, &pFsCode, NULL);
glCompileShader(fShader);

//check shader compilation
glGetShaderiv(fShader, GL_COMPILE_STATUS, &result);
glGetShaderiv(fShader, GL_INFO_LOG_LENGTH, &logLen);
if (logLen > 0) {
    //get compile log
    vector<char> fErr(logLen + 1);
    glGetShaderInfoLog(fShader, logLen, NULL, &fErr[0]);

    //try to convert log to LPWSTR
    wchar_t msg[100];
    swprintf(msg, sizeof(msg) / sizeof(*msg), L"%s\n", &fErr[0]);

    //print it
    wprintf(msg);
}

出于某种原因,我得到了这个输出:

⤱㨠攠牲牯䌠㄰ㄲ›瘣牥楳湯㌠〰洠獵⁴敢映汯潬敷⁤祢攠ੳ⠰⤲㨠攠牲牯䌠㈰㄰›湵畳灰牯整⁤敶獲潩〳ਰ⠰⤲㨠攠牲牯䌠〰〰›祳瑮硡攠牲牯‬湵硥数瑣摥✠✨‬硥数瑣湩⁧㨢∺愠⁴潴敫⠢ਢ⠰⤴㨠攠牲牯䌠㔷㈳

有人可以告诉我为什么我得到这个损坏的输出吗?

感谢所有帮助。

4

2 回答 2

2

您没有将chars 转换为wchar_ts 使用swprintf(..., "%s\n", ...),因为根据https://msdn.microsoft.com/en-us/library/hf4y5e3w.aspx %s意味着以下内容:

与 printf 函数一起使用时,指定单字节或多字节字符串;当与 wprintf 函数一起使用时,指定一个宽字符串。字符显示到第一个空字符或达到精度值。

由于您确实*wprintf在这里使用了一个函数,因此%s已经需要一个宽字符串,但是您给它一个非宽字符串。所以 ascii 文本(在这种情况下1) : error C0121: #version 300 must be followed by ...)被解释为宽字符串,从而导致垃圾。

根据同一个网页,%S这可能是解决您的问题的最快方法(“与 wprintf 函数一起使用时,指定单字节或多字节字符串” -%s普通 printf 的含义)。

于 2018-06-30T18:23:19.603 回答
0

正如@genpfault 在他的SO 回答中解释的那样,OpenGL 规范谈到了*GetString返回 UFT-8 字符串的命令。什么都没说glGetShaderInfoLog,但它似乎也返回一个 UTF-8 编码的字符串是合理的。

即使是 ASCII 转换成 UTF-8 也是一样的,因为 UTF-8 的前 127 码和 ASCII 码是一样的。

您最好的选择是打印 UTF-8 字符串,如果这在 C++ 中是可能的,无需任何转换。但今天它不在 Windows 中,它在内部使用 UFT-16,或者在 Linux 及其 UTF-32 用法。

对于转换,请使用std::codecvt。例如,请参阅此 SO question

于 2018-06-30T18:57:16.460 回答