bool FractoriumEmberController<T>::SyncSizes() { bool changed = false; GLWidget* gl = m_Fractorium->ui.GLDisplay; RendererCL<T, float>* rendererCL = nullptr; if (!m_GLController->SizesMatch()) { m_GLController->ClearWindow(); gl->SetDimensions(m_Ember.m_FinalRasW, m_Ember.m_FinalRasH); gl->Allocate(); gl->SetViewport(); if (m_Renderer->RendererType() == OPENCL_RENDERER && (rendererCL = dynamic_cast<RendererCL<T, float>*>(m_Renderer.get()))) rendererCL->SetOutputTexture(gl->OutputTexID()); m_Fractorium->CenterScrollbars(); changed = true; } return changed; }
bool FractoriumEmberController<T>::CreateRenderer(eRendererType renderType, const vector<pair<size_t, size_t>>& devices, bool shared) { bool ok = true; FractoriumSettings* s = m_Fractorium->m_Settings; GLWidget* gl = m_Fractorium->ui.GLDisplay; if (!m_Renderer.get() || (m_Renderer->RendererType() != renderType) || !Equal(m_Devices, devices)) { EmberReport emberReport; vector<string> errorReport; DeleteRenderer();//Delete the renderer and refresh the textures. //Before starting, must take care of allocations. gl->Allocate(true);//Forcing a realloc of the texture is necessary on AMD, but not on nVidia. m_Renderer = unique_ptr<EmberNs::RendererBase>(::CreateRenderer<T>(renderType, devices, shared, gl->OutputTexID(), emberReport));//Always make bucket type float. errorReport = emberReport.ErrorReport(); if (errorReport.empty()) { m_Devices = devices; m_OutputTexID = gl->OutputTexID(); m_Shared = shared; } else { ok = false; m_Fractorium->ShowCritical("Renderer Creation Error", "Could not create requested renderer, fallback CPU renderer created. See info tab for details."); m_Fractorium->ErrorReportToQTextEdit(errorReport, m_Fractorium->ui.InfoRenderingTextEdit); } } if (m_Renderer.get()) { m_RenderType = m_Renderer->RendererType(); if (m_RenderType == OPENCL_RENDERER) { auto val = 30 * m_Fractorium->m_Settings->Devices().size(); m_Fractorium->m_QualitySpin->DoubleClickZero(val); m_Fractorium->m_QualitySpin->DoubleClickNonZero(val); if (m_Fractorium->m_QualitySpin->value() < val) m_Fractorium->m_QualitySpin->setValue(val); } else { m_Fractorium->m_QualitySpin->DoubleClickZero(10); m_Fractorium->m_QualitySpin->DoubleClickNonZero(10); if (m_Fractorium->m_QualitySpin->value() > 10) m_Fractorium->m_QualitySpin->setValue(10); } m_Renderer->Callback(this); m_Renderer->NumChannels(4);//Always using 4 since the GL texture is RGBA. m_Renderer->ReclaimOnResize(true); m_Renderer->SetEmber(m_Ember);//Give it an initial ember, will be updated many times later. m_Renderer->EarlyClip(s->EarlyClip()); m_Renderer->YAxisUp(s->YAxisUp()); m_Renderer->ThreadCount(s->ThreadCount()); m_Renderer->Transparency(s->Transparency()); if (m_Renderer->RendererType() == CPU_RENDERER) m_Renderer->InteractiveFilter(s->CpuDEFilter() ? FILTER_DE : FILTER_LOG); else m_Renderer->InteractiveFilter(s->OpenCLDEFilter() ? FILTER_DE : FILTER_LOG); if ((m_Renderer->EarlyClip() != m_PreviewRenderer->EarlyClip()) || (m_Renderer->YAxisUp() != m_PreviewRenderer->YAxisUp())) { StopPreviewRender(); m_PreviewRenderer->EarlyClip(m_Renderer->EarlyClip()); m_PreviewRenderer->YAxisUp(m_Renderer->YAxisUp()); RenderPreviews(); } m_FailedRenders = 0; m_RenderElapsedTimer.Tic(); //Leave rendering in a stopped state. The caller is responsible for restarting the render loop again. } else { ok = false; m_Fractorium->ShowCritical("Renderer Creation Error", "Creating a basic CPU renderer failed, something is catastrophically wrong. Exiting program."); QApplication::quit(); } return ok; }