如何编写一个检查openGL支持的安装程序?

时间:2020-03-06 14:38:57  来源:igfitidea点击:

我们有一个使用OpenGL的3D查看器,但是我们的客户有时会抱怨它"不起作用"。我们怀疑这些问题中的大多数是由他们试图在businiss便携式计算机上使用(实际上是现代3d实时游戏)造成的。

我们如何在我们使用的Windows MSI安装程序中检查对openGL的支持?

另外,如果我们可以回答" OpenGL支持的图形卡列表?",那也很棒。奇怪的是,谷歌在这里没有帮助。

解决方案

自Windows NT或者Win95以来,OpenGL是Windows的一部分。我们不太可能会发现未预安装OpenGL的Windows系统(例如Windows 3.1)

但是,与非常老版本的Windows附带的默认OpenGL 1.1相比,应用程序可能需要更新的OpenGL版本。我们可以从程序中检查。我不知道如何从msi中找到它。

请注意,OpenGL是通过图形驱动程序而不是通过安装Service Pack来更新的。

关于启用OpenGL的图形卡:全部都具有OpenGL。即使客户使用石器时代的ISA ET4000图形卡,他也至少可以通过软件渲染安装OpenGL 1.1.

我认为我们可能仅仅依靠检查对OpenGL的硬件支持可能会有问题,因为可以肯定地说,过去10年内制造的每台笔记本电脑都提供了OpenGL。 (尽管如果这些笔记本电脑确实年代久远,那么此维基可能会有所帮助吗?)
但是,如果仅仅是程序需要大量图形,那么我可能会建议我们使用一个小型基准程序来检查客户系统是否一开始就可以使用。我们可以在这里尝试,看看是否可以使用现有的基准测试工具之一来,或者我们可以尝试为程序专门编写一个工具,例如一个小的测试脚本,而不是模拟在重负载下运行程序并记录诸如FPS之类的信息。
对于前者,我们甚至可能会发现可以将测试运行集成到MSI安装程序中,但是我对这种事情没有任何经验。
希望我们发现这些有用。

取决于客户所说的"不工作"。可能是以下之一:

  • 由于缺少某些OpenGL支持,因此它根本不会安装/启动。
  • 它启动,但进一步崩溃。
  • 它启动,不会崩溃,但是渲染已损坏。
  • 它可以正确启动和渲染所有内容,但是性能却很差。

所有Windows版本(自95开始)都内置了OpenGL支持。因此,除非应用程序需要更高的OpenGL版本,否则不太可能导致上述情况1)。

但是,默认的OpenGL实现是带有软件渲染的OpenGL 1.1. 如果用户未手动安装具有OpenGL支持的驱动程序(从NVIDIA / AMD / Intel网站下载的任何驱动程序都将具有OpenGL),则它们将默认为该缓慢且较旧的实现。这很可能导致上述情况3)和4)。

温和地说,即使OpenGL可用,在Windows上OpenGL驱动程序也不是很健壮。驱动程序中的各种错误很可能导致情况2),在这种情况下,执行有效的操作会导致驱动程序崩溃。

这是一个C ++ / WinAPI代码片段,它创建一个虚拟OpenGL上下文并检索信息(GL版本,图形卡名称,扩展名等):

// setup minimal required GL
HWND wnd = CreateWindow(
    "STATIC",
    "GL",
    WS_OVERLAPPEDWINDOW | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,
    0, 0, 16, 16,
    NULL, NULL,
    AfxGetInstanceHandle(), NULL );
HDC dc = GetDC( wnd );

PIXELFORMATDESCRIPTOR pfd = {
    sizeof(PIXELFORMATDESCRIPTOR), 1,
    PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL,
    PFD_TYPE_RGBA, 32,
    0, 0, 0, 0, 0, 0,
    0, 0, 0, 0, 0, 0, 0,
    16, 0,
    0, PFD_MAIN_PLANE, 0, 0, 0, 0
};

int fmt = ChoosePixelFormat( dc, &pfd );
SetPixelFormat( dc, fmt, &pfd );

HGLRC rc = wglCreateContext( dc );
wglMakeCurrent( dc, rc );

// get information
const char* vendor = (const char*)glGetString(GL_VENDOR);
const char* renderer = (const char*)glGetString(GL_RENDERER);
const char* extensions = (const char*)glGetString(GL_EXTENSIONS);
const char* version = (const char*)glGetString(GL_VERSION);

// DO SOMETHING WITH THOSE STRINGS HERE!

// cleanup
wglDeleteContext( rc );
ReleaseDC( wnd, dc );
DestroyWindow( wnd );

我们可以以某种方式将该代码插入安装程序或者应用程序,并至少检查GL版本是否为1.1;否则,请执行以下步骤。这将检测到"未安装驱动程序"的情况。要解决实际的OpenGL驱动程序错误,我们必须弄清楚它们并加以解决。很多工作。

Windows附带了对OpenGL 1.1的支持(正如其他人在此处指出的那样)。因此,用户面临的问题是由于1.1以后已添加到OpenGL的扩展。如果我们使用的是GLEW库,则很容易检查对以编程方式使用的所有扩展的支持。以下是检查Occlusion Query支持的方法:

if (GLEW_OK != glewInit())
{
    // GLEW failed!
    exit(1);
}

// Check if required extensions are supported
if (!GLEW_ARB_occlusion_query)
    cout << "Occlusion query not supported" << endl;

有关使用GLEW的更多信息,请参见此处。