2012-06-12 32 views
9

Tôi đang cố gắng sử dụng QGLWidget trong Qt 4.8.2. Tôi nhận thấy rằng bối cảnh mặc định QGLWidget tạo ra không hiển thị bất kỳ đầu ra cho OpenGL trên 3.1. The Qt wiki has a tutorial thể hiện bằng cách sử dụng OpenGL 3.3 để vẽ một hình tam giác đơn giản. Khi tôi cố gắng chạy hướng dẫn, tôi nhận được một màn hình trống. Nếu tôi thay đổi phiên bản OpenGL thành 3.1, tôi nhận được kết quả mong đợi (một hình tam giác màu đỏ).Không thể đặt phiên bản OpenGL mong muốn trong QGLWidget

Thẻ video của tôi hỗ trợ OpenGL 4.2 và gọi QGLFormat::openGLVersionFlags() trước khi tạo chương trình QGLWidget cho biết Qt phát hiện OpenGL 4.2 và tất cả các phiên bản máy tính để bàn trước đó.

Dưới đây là một ví dụ nhỏ:

#include <QApplication> 
#include <QGLWidget> 
#include <QDebug> 
#include <QtDeclarative/qdeclarativeview.h> 

int main(int argc, char * argv[]) 
{ 
    QApplication app(argc, argv); 

    qDebug() << "OpenGL Versions Supported: " << QGLFormat::openGLVersionFlags(); 

    QGLFormat qglFormat; 
    qglFormat.setVersion(4,2); // get expected output with (3,1) and below, else blank window 
    qglFormat.setProfile(QGLFormat::CoreProfile); 
    qglFormat.setSampleBuffers(true); 

    QGLWidget* qglWidget = new QGLWidget(qglFormat); 

    QString versionString(QLatin1String(reinterpret_cast<const char*>(glGetString(GL_VERSION)))); 
    qDebug() << "Driver Version String:" << versionString; 
    qDebug() << "Current Context:" << qglWidget->format(); 

    QDeclarativeView mainView; 
    mainView.setViewport(qglWidget); 
    mainView.setSource(QString("helloworld.qml")); 
    mainView.show(); 

    return app.exec(); 
} 

Dưới đây là kết quả:

OpenGL Versions Supported: QFlags(0x1|0x2|0x4|0x8|0x10|0x20|0x40|0x1000|0x2000|0x4000|0x8000|0x10000) 
Driver Version String: "4.2.0 NVIDIA 295.53" 
Current Context: QGLFormat(options QFlags(0x1|0x2|0x4|0x10|0x20|0x80|0x200|0x400) , plane 0 , depthBufferSize 24 , accumBufferSize 16 , stencilBufferSize 8 , redBufferSize 8 , greenBufferSize 8 , blueBufferSize 8 , alphaBufferSize -1 , samples 4 , swapInterval 0 , majorVersion 4 , minorVersion 2 , profile 1) 

Các QFlags() enum danh sách trên dòng đầu tiên mô tả các phiên bản OpenGL hỗ trợ. Danh sách này cho thấy tôi hỗ trợ tất cả các biến thể ngoại trừ phiên bản OpenGL/ES. QFlags() trên dòng thứ ba mô tả các tùy chọn định dạng (kênh alpha, bộ đệm stencil, v.v.).

Bất kỳ ai biết tại sao QGLWidget sẽ không hoạt động với bất kỳ thứ gì> = 3.1? Tôi đang trên Linux, có một Nvidia GT440, và glxinfo cho thấy nó hỗ trợ OpenGL 4.2.0. Phiên bản trình điều khiển được in trong đầu ra mẫu ở trên. Tôi không quá chắc chắn những gì khác để thử.

Chỉnh sửa: Tôi đã thực hiện một số lỗi/giả định khá xấu với giải thích của mình về sự cố trước chỉnh sửa này. Vấn đề vẫn còn tương tự, nhưng hy vọng sẽ có ý nghĩa hơn một chút. Xin lỗi vì bất kỳ sự nhầm lẫn nào.

+0

Trình biên dịch của bạn có biên dịch/liên kết không? Nếu bạn đang sử dụng ngữ cảnh 4.2 và trình đổ bóng không tương thích/không chính xác, đó là một nguyên nhân cho một cửa sổ trống. –

+0

Tôi chưa đạt được điều đó (shaders). Tôi muốn sử dụng QGLWidget như là một khung nhìn cho một QDeclarativeView và sau đó thêm một số nội dung 3d sử dụng shaders. Nhưng ngay cả một tập tin đơn giản với các thành phần mặc định như một hình chữ nhật {} làm cho không có gì.Nó sẽ hiển thị như mong đợi nếu tôi không đặt phiên bản QGLFormat, nhưng toàn bộ vấn đề này là tìm ra lý do tại sao tôi không thể đặt nó ở vị trí đầu tiên. Thêm vào đó, tôi sẽ gặp lỗi nếu tôi (hoặc Qt nội bộ) đang sử dụng các trình đổ bóng không tương thích. Sản lượng duy nhất là những gì tôi dán trong câu hỏi của tôi. – Prismatic

+0

Hmm, lý do duy nhất tại sao tôi đề xuất xem nhật ký trình đổ bóng là OpenGL 3.0 + yêu cầu các trình tạo bóng của riêng bạn được biên dịch và tải, trong khi OpenGL 2.0 trở xuống thì không. Tôi không có kinh nghiệm với việc sử dụng OpenGL thông qua QT, vì vậy tôi không biết bao nhiêu được xử lý cho bạn. Tuy nhiên, trong ví dụ bạn đã liên kết, tác giả chuẩn bị các trình tạo bóng của riêng mình. Nếu bạn không cung cấp shaders cho card đồ họa bằng cách sử dụng hồ sơ cốt lõi, bạn sẽ không làm bất cứ điều gì. –

Trả lời

4

Bạn nên di chuyển truy vấn OpenGL xuống sau mainView.show();. Trước show() ngữ cảnh OpenGL chưa được khởi tạo.

2

Phiên bản ngắn: cập nhật lên Qt5, nó được sửa ở đó.

P.S Và nếu bạn có thể sử dụng 5.4, bạn nên sử dụng các lớp QtOpenGL ... thay vì các lớp QGL ....

Phiên bản dài: Vì vậy, trong trường hợp bất kỳ ai gặp phải vấn đề như thế này.

Tôi đã cố gắng tạo ngữ cảnh KHÔNG OpenGL 3.0 với Intel HD3000 trên ubuntu 14.04 và Qt 4.8.6. Tôi đã đưa ra mã kiểm tra này được cung cấp ở phần cuối của câu trả lời. Đã thử tạo 3.1, 1.2, 2.1 .. v.v. tương thích với Core Tương thích .. nhưng luôn kết thúc với context->format().majorVersion() hiển thị phiên bản được yêu cầu và glGetString(GL_VERSION) hiển thị 3.0.

Sau khoảng 3 giờ, tôi nhận thấy rằng theo mặc định, Người tạo Qt sử dụng Qt4 thay vì Qt 5 gần đây, được cài đặt trên hệ thống của tôi. Và sau khi tôi biên dịch lại dự án với Qt 5.2.1 chính xác cùng một mã đã bắt đầu hoạt động như mong đợi.

Hy vọng điều này có thể giúp ai đó.

int main(int argc, char *argv[]) 
{ 
    QApplication a(argc, argv); 

    MainWindow w; 
    w.show(); 

    QGLFormat glFormat; 
    glFormat.setVersion(3, 1); 
    glFormat.setProfile(QGLFormat::NoProfile); 
    glFormat.setSampleBuffers(true); 
    glFormat.setDefaultFormat(glFormat); 
    glFormat.setSwapInterval(1); 
    QGLWidget widget(glFormat); 
    widget.makeCurrent(); 

    const QGLContext *context = widget.context(); 

    glewExperimental = GL_TRUE; 
    if (glewInit() != GLEW_OK) { 
     qWarning("Failed to initialize GLEW\n"); 
    } 
    qDebug() << "Context valid: " << context->isValid(); 
    qDebug() << "Really used OpenGl: " << context->format().majorVersion() << "." << context->format().minorVersion(); 
    qDebug() << "OpenGl information: VENDOR:  " << (const char*)glGetString(GL_VENDOR); 
    qDebug() << "     RENDERDER: " << (const char*)glGetString(GL_RENDERER); 
    qDebug() << "     VERSION:  " << (const char*)glGetString(GL_VERSION); 
    qDebug() << "     GLSL VERSION: " << (const char*)glGetString(GL_SHADING_LANGUAGE_VERSION); 
    qDebug() << "endstuff\n"; 

    return a.exec(); 
} 
Các vấn đề liên quan