comparison OrthancStone/Sources/Scene2D/Internals/OpenGLInfoPanelRenderer.cpp @ 1512:244ad1e4e76a

reorganization of folders
author Sebastien Jodogne <s.jodogne@gmail.com>
date Tue, 07 Jul 2020 16:21:02 +0200
parents Framework/Scene2D/Internals/OpenGLInfoPanelRenderer.cpp@be17fed8c7c5
children 92fca2b3ba3d
comparison
equal deleted inserted replaced
1511:9dfeee74c1e6 1512:244ad1e4e76a
1 /**
2 * Stone of Orthanc
3 * Copyright (C) 2012-2016 Sebastien Jodogne, Medical Physics
4 * Department, University Hospital of Liege, Belgium
5 * Copyright (C) 2017-2020 Osimis S.A., Belgium
6 *
7 * This program is free software: you can redistribute it and/or
8 * modify it under the terms of the GNU Affero General Public License
9 * as published by the Free Software Foundation, either version 3 of
10 * the License, or (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Affero General Public License for more details.
16 *
17 * You should have received a copy of the GNU Affero General Public License
18 * along with this program. If not, see <http://www.gnu.org/licenses/>.
19 **/
20
21
22 #include "OpenGLInfoPanelRenderer.h"
23
24 namespace OrthancStone
25 {
26 namespace Internals
27 {
28 void OpenGLInfoPanelRenderer::LoadTexture(const InfoPanelSceneLayer& layer)
29 {
30 if (!context_.IsContextLost())
31 {
32 context_.MakeCurrent();
33 texture_.reset(new OpenGL::OpenGLTexture(context_));
34 texture_->Load(layer.GetTexture(), layer.IsLinearInterpolation());
35 applySceneRotation_ = layer.ShouldApplySceneRotation();
36 anchor_ = layer.GetAnchor();
37 }
38 }
39
40 OpenGLInfoPanelRenderer::OpenGLInfoPanelRenderer(OpenGL::IOpenGLContext& context,
41 OpenGLColorTextureProgram& program,
42 const InfoPanelSceneLayer& layer) :
43 context_(context),
44 program_(program),
45 anchor_(BitmapAnchor_TopLeft),
46 applySceneRotation_(false)
47 {
48 LoadTexture(layer);
49 }
50
51 void OpenGLInfoPanelRenderer::Render(const AffineTransform2D& transform,
52 unsigned int canvasWidth,
53 unsigned int canvasHeight)
54 {
55 if (!context_.IsContextLost() && texture_.get() != NULL)
56 {
57 int dx = 0, dy = 0;
58 InfoPanelSceneLayer::ComputeAnchorLocation(
59 dx, dy, anchor_, texture_->GetWidth(), texture_->GetHeight(),
60 canvasWidth, canvasHeight);
61
62 // The position of this type of layer is layer: Ignore the
63 // "transform" coming from the scene
64 AffineTransform2D actualTransform =
65 AffineTransform2D::CreateOffset(dx, dy);
66
67 if (applySceneRotation_)
68 {
69 // the transformation is as follows:
70 // - originally, the image is aligned so that its top left corner
71 // is at 0,0
72 // - first, we translate the image by -w/2,-h/2
73 // - then we rotate it, so that the next rotation will make the
74 // image rotate around its center.
75 // - then, we translate the image by +w/2,+h/2 to put it
76 // back in place
77 // - the fourth and last transform is the one that brings the
78 // image to its desired anchored location.
79
80 int32_t halfWidth =
81 static_cast<int32_t>(0.5 * texture_->GetWidth());
82
83 int32_t halfHeight=
84 static_cast<int32_t>(0.5 * texture_->GetHeight());
85
86 AffineTransform2D translation1 =
87 AffineTransform2D::CreateOffset(-halfWidth, -halfHeight);
88
89 const Matrix& sceneTransformM = transform.GetHomogeneousMatrix();
90 Matrix r;
91 Matrix q;
92 LinearAlgebra::RQDecomposition3x3(r, q, sceneTransformM);
93
94 // counterintuitively, q is the rotation and r is the upper
95 // triangular
96 AffineTransform2D rotation(q);
97
98 AffineTransform2D translation2 =
99 AffineTransform2D::CreateOffset(halfWidth, halfHeight);
100
101 // please note that the last argument is the 1st applied
102 // transformation (rationale: if arguments are a, b and c, then
103 // the resulting matrix is a*b*c:
104 // x2 = (a*b*c)*x1 = (a*(b*(c*x1))) (you can see that the result
105 // of c*x1 is transformed by b, and the result of b*c*x1 is trans-
106 // formed by a)
107 actualTransform = AffineTransform2D::Combine(actualTransform,
108 translation2,
109 rotation,
110 translation1);
111 }
112
113 program_.Apply(*texture_, actualTransform, true);
114 }
115 }
116 }
117 }