mirror of
https://github.com/OPM/ResInsight.git
synced 2025-01-21 22:13:25 -06:00
#279 Use frame buffer objects for snapshots when available, otherwise use grabFrameBuffer()
This commit is contained in:
parent
457c3c732b
commit
0128baddff
@ -108,6 +108,8 @@
|
||||
#ifdef WIN32
|
||||
#include <fcntl.h>
|
||||
#endif
|
||||
#include "RiuSummaryQwtPlot.h"
|
||||
#include "RiuWellLogPlot.h"
|
||||
|
||||
namespace caf
|
||||
{
|
||||
@ -1392,6 +1394,43 @@ RiuMainPlotWindow* RiaApplication::mainPlotWindow()
|
||||
return m_mainPlotWindow;
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
///
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
RimViewWindow* RiaApplication::activeViewWindow()
|
||||
{
|
||||
RimViewWindow* viewWindow = NULL;
|
||||
|
||||
QWidget* topLevelWidget = RiaApplication::activeWindow();
|
||||
|
||||
if (dynamic_cast<RiuMainWindow*>(topLevelWidget))
|
||||
{
|
||||
viewWindow = RiaApplication::instance()->activeReservoirView();
|
||||
}
|
||||
|
||||
if (dynamic_cast<RiuMainPlotWindow*>(topLevelWidget))
|
||||
{
|
||||
RiuMainPlotWindow* mainPlotWindow = dynamic_cast<RiuMainPlotWindow*>(topLevelWidget);
|
||||
QList<QMdiSubWindow*> subwindows = mainPlotWindow->subWindowList(QMdiArea::StackingOrder);
|
||||
if (subwindows.size() > 0)
|
||||
{
|
||||
RiuSummaryQwtPlot* summaryQwtPlot = dynamic_cast<RiuSummaryQwtPlot*>(subwindows.back()->widget());
|
||||
if (summaryQwtPlot)
|
||||
{
|
||||
viewWindow = summaryQwtPlot->ownerPlotDefinition();
|
||||
}
|
||||
|
||||
RiuWellLogPlot* wellLogPlot = dynamic_cast<RiuWellLogPlot*>(subwindows.back()->widget());
|
||||
if (wellLogPlot)
|
||||
{
|
||||
viewWindow = wellLogPlot->ownerPlotDefinition();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return viewWindow;
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
///
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
@ -1777,9 +1816,9 @@ void RiaApplication::saveSnapshotAs(const QString& fileName)
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
void RiaApplication::copySnapshotToClipboard()
|
||||
{
|
||||
QClipboard* clipboard = QApplication::clipboard();
|
||||
if (clipboard)
|
||||
{
|
||||
QClipboard* clipboard = QApplication::clipboard();
|
||||
if (clipboard)
|
||||
{
|
||||
QImage image = grabFrameBufferImage();
|
||||
if (!image.isNull())
|
||||
{
|
||||
@ -2160,21 +2199,26 @@ cvf::Font* RiaApplication::customFont()
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
QImage RiaApplication::grabFrameBufferImage()
|
||||
{
|
||||
// TODO: Create a general solution that also works with well log plots and summary plots
|
||||
// For now, only reservoir views are supported by this solution
|
||||
/*
|
||||
RimViewWindow* viewWindow = RiaApplication::activeViewWindow();
|
||||
if (viewWindow)
|
||||
{
|
||||
return viewWindow->snapshotWindowContent();
|
||||
}
|
||||
|
||||
return QImage();
|
||||
*/
|
||||
|
||||
QImage image;
|
||||
if (m_activeReservoirView && m_activeReservoirView->viewer())
|
||||
{
|
||||
m_activeReservoirView->viewer()->repaint();
|
||||
|
||||
GLint currentReadBuffer;
|
||||
glGetIntegerv(GL_READ_BUFFER, ¤tReadBuffer);
|
||||
|
||||
glReadBuffer(GL_FRONT);
|
||||
image = m_activeReservoirView->viewer()->grabFrameBuffer();
|
||||
|
||||
glReadBuffer(currentReadBuffer);
|
||||
return m_activeReservoirView->snapshotWindowContent();
|
||||
}
|
||||
|
||||
return image;
|
||||
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
|
@ -48,6 +48,7 @@ class RimEclipseView;
|
||||
class RimProject;
|
||||
class RimSummaryPlot;
|
||||
class RimView;
|
||||
class RimViewWindow;
|
||||
class RimWellLogPlot;
|
||||
|
||||
class RiuMainPlotWindow;
|
||||
@ -178,6 +179,8 @@ public:
|
||||
RiuMainPlotWindow* getOrCreateAndShowMainPlotWindow();
|
||||
RiuMainPlotWindow* mainPlotWindow();
|
||||
|
||||
static RimViewWindow* activeViewWindow();
|
||||
|
||||
private:
|
||||
enum ProjectLoadAction
|
||||
{
|
||||
|
@ -20,15 +20,7 @@
|
||||
|
||||
#include "RiaApplication.h"
|
||||
|
||||
#include "RimSummaryPlot.h"
|
||||
#include "RimView.h"
|
||||
#include "RimViewWindow.h"
|
||||
#include "RimWellLogPlot.h"
|
||||
|
||||
#include "RiuMainPlotWindow.h"
|
||||
#include "RiuMainWindow.h"
|
||||
#include "RiuSummaryQwtPlot.h"
|
||||
#include "RiuWellLogPlot.h"
|
||||
|
||||
#include <QAction>
|
||||
#include <QClipboard>
|
||||
@ -49,34 +41,7 @@ bool RicSnapshotViewToClipboardFeature::isCommandEnabled()
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
void RicSnapshotViewToClipboardFeature::onActionTriggered(bool isChecked)
|
||||
{
|
||||
RimViewWindow* viewWindow = NULL;
|
||||
|
||||
QWidget* topLevelWidget = RiaApplication::activeWindow();
|
||||
|
||||
if (dynamic_cast<RiuMainWindow*>(topLevelWidget))
|
||||
{
|
||||
viewWindow = RiaApplication::instance()->activeReservoirView();
|
||||
}
|
||||
|
||||
if (dynamic_cast<RiuMainPlotWindow*>(topLevelWidget))
|
||||
{
|
||||
RiuMainPlotWindow* mainPlotWindow = dynamic_cast<RiuMainPlotWindow*>(topLevelWidget);
|
||||
QList<QMdiSubWindow*> subwindows = mainPlotWindow->subWindowList(QMdiArea::StackingOrder);
|
||||
if (subwindows.size() > 0)
|
||||
{
|
||||
RiuSummaryQwtPlot* summaryQwtPlot = dynamic_cast<RiuSummaryQwtPlot*>(subwindows.back()->widget());
|
||||
if (summaryQwtPlot)
|
||||
{
|
||||
viewWindow = summaryQwtPlot->ownerPlotDefinition();
|
||||
}
|
||||
|
||||
RiuWellLogPlot* wellLogPlot = dynamic_cast<RiuWellLogPlot*>(subwindows.back()->widget());
|
||||
if (wellLogPlot)
|
||||
{
|
||||
viewWindow = wellLogPlot->ownerPlotDefinition();
|
||||
}
|
||||
}
|
||||
}
|
||||
RimViewWindow* viewWindow = RiaApplication::activeViewWindow();
|
||||
|
||||
if (viewWindow)
|
||||
{
|
||||
|
@ -255,21 +255,14 @@ void RimView::updateViewerWidget()
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
QImage RimView::snapshotWindowContent()
|
||||
{
|
||||
QImage image;
|
||||
if (m_viewer)
|
||||
{
|
||||
m_viewer->repaint();
|
||||
|
||||
GLint currentReadBuffer;
|
||||
glGetIntegerv(GL_READ_BUFFER, ¤tReadBuffer);
|
||||
|
||||
glReadBuffer(GL_FRONT);
|
||||
image = m_viewer->grabFrameBuffer();
|
||||
|
||||
glReadBuffer(currentReadBuffer);
|
||||
return m_viewer->snapshotImage();
|
||||
}
|
||||
|
||||
return image;
|
||||
return QImage();
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
|
@ -154,6 +154,7 @@ public:
|
||||
|
||||
void selectOverlayInfoConfig();
|
||||
|
||||
virtual QImage snapshotWindowContent() override;
|
||||
|
||||
virtual void zoomAll() override;
|
||||
|
||||
@ -197,9 +198,6 @@ protected:
|
||||
virtual void resetLegendsInViewer() = 0;
|
||||
virtual void calculateCurrentTotalCellVisibility(cvf::UByteArray* totalVisibility) = 0;
|
||||
|
||||
virtual QImage snapshotWindowContent() override;
|
||||
|
||||
|
||||
QPointer<RiuViewer> m_viewer;
|
||||
|
||||
caf::PdmField<int> m_currentTimeStep;
|
||||
|
@ -46,9 +46,11 @@
|
||||
#include "cvfDrawable.h"
|
||||
#include "cvfDrawableGeo.h"
|
||||
#include "cvfDynamicUniformSet.h"
|
||||
#include "cvfFramebufferObject.h"
|
||||
#include "cvfHitItemCollection.h"
|
||||
#include "cvfManipulatorTrackball.h"
|
||||
#include "cvfModel.h"
|
||||
#include "cvfOpenGLCapabilities.h"
|
||||
#include "cvfOpenGLResourceManager.h"
|
||||
#include "cvfOverlayImage.h"
|
||||
#include "cvfPart.h"
|
||||
@ -56,8 +58,11 @@
|
||||
#include "cvfRayIntersectSpec.h"
|
||||
#include "cvfRenderQueueSorter.h"
|
||||
#include "cvfRenderSequence.h"
|
||||
#include "cvfRenderbufferObject.h"
|
||||
#include "cvfRendering.h"
|
||||
#include "cvfScene.h"
|
||||
#include "cvfShaderSourceProvider.h"
|
||||
#include "cvfSingleQuadRenderingGenerator.h"
|
||||
#include "cvfTextureImage.h"
|
||||
#include "cvfTransform.h"
|
||||
#include "cvfUniform.h"
|
||||
@ -184,6 +189,20 @@ void caf::Viewer::setupMainRendering()
|
||||
m_mainRendering->renderEngine()->enableForcedImmediateMode(true);
|
||||
}
|
||||
|
||||
if (contextGroup()->capabilities() &&
|
||||
contextGroup()->capabilities()->hasCapability(cvf::OpenGLCapabilities::FRAMEBUFFER_OBJECT))
|
||||
{
|
||||
m_offscreenFbo = new cvf::FramebufferObject;
|
||||
m_mainRendering->setTargetFramebuffer(m_offscreenFbo.p());
|
||||
|
||||
cvf::ref<cvf::RenderbufferObject> rbo = new cvf::RenderbufferObject(cvf::RenderbufferObject::DEPTH_COMPONENT24, 1, 1);
|
||||
m_offscreenFbo->attachDepthRenderbuffer(rbo.p());
|
||||
|
||||
m_offscreenTexture = new cvf::Texture(cvf::Texture::TEXTURE_2D, cvf::Texture::RGBA);
|
||||
m_offscreenTexture->setSize(1, 1);
|
||||
m_offscreenFbo->attachColorTexture2d(0, m_offscreenTexture.p());
|
||||
}
|
||||
|
||||
updateOverlayImagePresence();
|
||||
}
|
||||
|
||||
@ -192,7 +211,25 @@ void caf::Viewer::setupMainRendering()
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
void caf::Viewer::setupRenderingSequence()
|
||||
{
|
||||
m_renderingSequence->addRendering(m_mainRendering.p());
|
||||
m_renderingSequence->addRendering(m_mainRendering.p());
|
||||
|
||||
if (m_offscreenFbo.notNull())
|
||||
{
|
||||
// Setup second rendering drawing the texture on the screen
|
||||
// -------------------------------------------------------------------------
|
||||
cvf::SingleQuadRenderingGenerator quadRenderGen;
|
||||
cvf::ref<cvf::Sampler> sampler = new cvf::Sampler;
|
||||
sampler->setWrapMode(cvf::Sampler::CLAMP_TO_EDGE);
|
||||
sampler->setMinFilter(cvf::Sampler::NEAREST);
|
||||
sampler->setMagFilter(cvf::Sampler::NEAREST);
|
||||
|
||||
quadRenderGen.addTexture(m_offscreenTexture.p(), sampler.p(), "u_texture2D");
|
||||
quadRenderGen.addFragmentShaderCode(cvf::ShaderSourceProvider::instance()->getSourceFromRepository(cvf::ShaderSourceRepository::fs_Unlit));
|
||||
quadRenderGen.addFragmentShaderCode(cvf::ShaderSourceProvider::instance()->getSourceFromRepository(cvf::ShaderSourceRepository::src_Texture));
|
||||
|
||||
cvf::ref<cvf::Rendering> quadRendering = quadRenderGen.generate();
|
||||
m_renderingSequence->addRendering(quadRendering.p());
|
||||
}
|
||||
|
||||
updateCamera(width(), height());
|
||||
}
|
||||
@ -277,7 +314,6 @@ void caf::Viewer::updateCamera(int width, int height)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
///
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
@ -464,6 +500,16 @@ void caf::Viewer::resizeGL(int width, int height)
|
||||
{
|
||||
if (width < 1 || height < 1) return;
|
||||
|
||||
if (m_offscreenFbo.notNull())
|
||||
{
|
||||
m_offscreenFbo->resizeAttachedBuffers(width, height);
|
||||
|
||||
CVF_ASSERT(m_renderingSequence->renderingCount() > 1);
|
||||
|
||||
cvf::ref<cvf::Rendering> quadRendering = m_renderingSequence->rendering(1);
|
||||
quadRendering->camera()->viewport()->set(0, 0, width, height);
|
||||
}
|
||||
|
||||
updateCamera(width, height);
|
||||
}
|
||||
|
||||
@ -476,7 +522,6 @@ void caf::Viewer::enablePerfInfoHud(bool enable)
|
||||
updateOverlayImagePresence();
|
||||
}
|
||||
|
||||
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
///
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
@ -485,8 +530,6 @@ bool caf::Viewer::isPerfInfoHudEnabled()
|
||||
return m_showPerfInfoHud;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
///
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
@ -772,6 +815,32 @@ bool caf::Viewer::isShadersSupported()
|
||||
return false;
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
///
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
QImage caf::Viewer::snapshotImage()
|
||||
{
|
||||
QImage image;
|
||||
if (m_offscreenTexture.notNull() && m_offscreenTexture->image())
|
||||
{
|
||||
image = cvfqt::Utils::toQImage(*(m_offscreenTexture->image()));
|
||||
}
|
||||
else
|
||||
{
|
||||
// Code moved from RimView::snapshotWindowContent()
|
||||
|
||||
GLint currentReadBuffer;
|
||||
glGetIntegerv(GL_READ_BUFFER, ¤tReadBuffer);
|
||||
|
||||
glReadBuffer(GL_FRONT);
|
||||
image = this->grabFrameBuffer();
|
||||
|
||||
glReadBuffer(currentReadBuffer);
|
||||
}
|
||||
|
||||
return image;
|
||||
}
|
||||
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
///
|
||||
//--------------------------------------------------------------------------------------------------
|
||||
|
@ -49,15 +49,17 @@
|
||||
|
||||
namespace cvf {
|
||||
class Camera;
|
||||
class FramebufferObject;
|
||||
class HitItemCollection;
|
||||
class Model;
|
||||
class OverlayImage;
|
||||
class OverlayItem;
|
||||
class OverlayScalarMapperLegend;
|
||||
class RenderSequence;
|
||||
class Rendering;
|
||||
class Scene;
|
||||
class Texture;
|
||||
class TextureImage;
|
||||
class OverlayItem;
|
||||
}
|
||||
|
||||
namespace caf {
|
||||
@ -150,6 +152,7 @@ public:
|
||||
// Find out whether the system supports shaders
|
||||
static bool isShadersSupported();
|
||||
|
||||
QImage snapshotImage();
|
||||
|
||||
public slots:
|
||||
virtual void slotSetCurrentFrame(int frameIndex);
|
||||
@ -224,6 +227,10 @@ private:
|
||||
// Parallel projection light modification
|
||||
|
||||
cvf::ref<GlobalViewerDynUniformSet> m_globalUniformSet;
|
||||
|
||||
// Offscreen render objects
|
||||
cvf::ref<cvf::FramebufferObject> m_offscreenFbo;
|
||||
cvf::ref<cvf::Texture> m_offscreenTexture;
|
||||
};
|
||||
|
||||
} // End namespace caf
|
||||
|
Loading…
Reference in New Issue
Block a user