OpenGL 2.1でwin32スレッドを使用します。私が達成しようとしているのは、「ロード中」という単純なイメージをレンダリングし、バックグラウンド全体で3Dシーンがロードされていることです。今は動作しますが、時には私のキューブマップのテクスチャの一部がMozilla Firefox Browserからデータを取得する問題があります(これはどのように起こりますか?)、その小さなボックスはテクスチャで無視します。それはそれがあるはずです。: 2番目のスレッドでのOpenGLリソースのロード
私はプログラムをロードしようとします。 は、これは私のスレッドがどのように見えるかです:
WindowsThread::WindowsThread(HGLRC graphicsContext, HDC deviceContext) :
graphicsContext_(graphicsContext),
deviceContext_(deviceContext),
running_(false),
task_(0),
mode_(WT_NORMAL)
{
handle_ = CreateThread(0, 0,
(unsigned long (__stdcall *)(void *)) this->staticRun,
(void*) this, CREATE_SUSPENDED, &id_);
if (handle_ == 0) {
LOGE("Unable to create thread.");
return;
}
if (!SetThreadPriority(handle_, THREAD_PRIORITY_NORMAL)) {
LOGE("Unable to set thread priority for thread.");
return;
}
}
WindowsThread::~WindowsThread() {
finishTask();
running_ = false;
WaitForSingleObject(handle_, INFINITE);
CloseHandle(handle_);
wglDeleteContext(graphicsContext_);
}
void WindowsThread::start() {
running_ = true;
if (!ResumeThread(handle_)) {
LOGW("Unable to resume thread.");
}
}
bool WindowsThread::isRunning() {
return running_;
}
void WindowsThread::setTask(Task* task, Mode mode) {
finishTask();
task_ = task;
mode_ = mode;
}
bool WindowsThread::hasTask() {
return task_ != 0;
}
void WindowsThread::finishTask() {
while (task_ != 0) {
Sleep(1);
}
}
void WindowsThread::stop() {
running_ = false;
}
int WindowsThread::staticRun(void* thread) {
return ((WindowsThread*) thread)->run();
}
int WindowsThread::run() {
wglMakeCurrent(deviceContext_, graphicsContext_);
while (running_) {
if (task_ != 0) {
task_->run();
task_ = 0;
}
Sleep(10);
}
wglMakeCurrent(0, 0);
return 1;
}
ThreadManager:
WindowsThreadManager::WindowsThreadManager(
System* system, UINT threadPoolSize)
{
if (threadPoolSize == 0) {
SYSTEM_INFO info;
GetSystemInfo(&info);
threadPoolSize = info.dwNumberOfProcessors;
if (threadPoolSize == 0) {
threadPoolSize = 1;
}
}
LOGI("Number of threads used: %d", threadPoolSize);
masterContext_ = wglGetCurrentContext();
HDC hdc = wglGetCurrentDC();
for (UINT i = 0; i < threadPoolSize; i++) {
HGLRC threadContext = wglCreateContext(hdc);
wglShareLists(masterContext_, threadContext);
WindowsThread* thread = new WindowsThread(threadContext, hdc);
thread->start();
threads_.push_back(thread);
}
}
WindowsThreadManager::~WindowsThreadManager() {
for (UINT i = 0; i < threads_.size(); i++) {
delete threads_[i];
}
for (UINT i = 0; i < tasks_.size(); i++) {
delete tasks_[i];
}
}
void WindowsThreadManager::execute(Task* task, Mode mode) {
WindowsThread::Mode wtMode = WindowsThread::WT_NORMAL;
if (mode == TM_GRAPHICS_CONTEXT) {
wtMode = WindowsThread::WT_GRPAHICS_CONTEXT;
}
tasks_.push_back(task);
for (UINT i = 0; i < threads_.size(); i++) {
if (!threads_[i]->hasTask()) {
threads_[i]->setTask(task, wtMode);
return;
}
}
threads_[0]->setTask(task, wtMode);
}
void WindowsThreadManager::joinAll() {
for (UINT i = 0; i < threads_.size(); i++) {
if (threads_[i]->hasTask()) {
threads_[i]->finishTask();
}
}
}
私はWinodws 8 上の最新のドライバに問題があるかもしれない任意のアイデアとNvidiaの670GTXを使うのか?
[編集]ローダースレッドの最後にglFinish()を追加しました。これですべて正常にロードされます。私はどこかで赤く、OpenGLはすぐにそのすべての作業を終了しないので、これは事実だと思います。コンテキストがNULLに設定されて作業を完了することができました。
openglとスレッドは通常通りません。 –
はい、私はそれについてかなり赤いです。実際には、前に2つのコンテキストを実装していました.1つはレンダリングしたものに、もう1つはリソースをロードしました。リソースがロードされたときに、私はそのコンテキストを取り、それをメインコンテキストとし、最後のメインコンテキストを削除しました。これは問題なく動作しました。 – SMart
@BЈовић:OpenGLとマルチスレッドができますが、それは正しいことが簡単ではありません。 – datenwolf