Version 3.6.0.4, tag libreoffice-3.6.0.4
[LibreOffice.git] / svx / source / engine3d / viewpt3d2.cxx
blobe91e2c1ea0abee98588f65ae6131e05cd90e882c
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*************************************************************************
4 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
6 * Copyright 2000, 2010 Oracle and/or its affiliates.
8 * OpenOffice.org - a multi-platform office productivity suite
10 * This file is part of OpenOffice.org.
12 * OpenOffice.org is free software: you can redistribute it and/or modify
13 * it under the terms of the GNU Lesser General Public License version 3
14 * only, as published by the Free Software Foundation.
16 * OpenOffice.org is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU Lesser General Public License version 3 for more details
20 * (a copy is included in the LICENSE file that accompanied this code).
22 * You should have received a copy of the GNU Lesser General Public License
23 * version 3 along with OpenOffice.org. If not, see
24 * <http://www.openoffice.org/license.html>
25 * for a copy of the LGPLv3 License.
27 ************************************************************************/
29 #include <svx/viewpt3d.hxx>
30 #include <svx/volume3d.hxx>
32 Viewport3D::Viewport3D() :
33 aVRP(0, 0, 5),
34 aVPN(0, 0, 1),
35 aVUV(0, 1, 1),
36 aPRP(0, 0, 2),
37 fVPD(-3),
38 fNearClipDist (0.0),
39 fFarClipDist (0.0),
40 eProjection(PR_PERSPECTIVE),
41 eAspectMapping(AS_NO_MAPPING),
42 aDeviceRect(Point(0,0), Size(-1,-1)),
43 aViewPoint (0, 0, 5000),
44 bTfValid(0),
45 fWRatio (1.0),
46 fHRatio (1.0)
48 aViewWin.X = -1; aViewWin.Y = -1;
49 aViewWin.W = 2; aViewWin.H = 2;
52 // Set ViewWindow (in View coordinates)
54 void Viewport3D::SetViewWindow(double fX, double fY, double fW, double fH)
56 aViewWin.X = fX;
57 aViewWin.Y = fY;
58 if ( fW > 0 ) aViewWin.W = fW;
59 else aViewWin.W = 1.0;
60 if ( fH > 0 ) aViewWin.H = fH;
61 else aViewWin.H = 1.0;
63 fWRatio = aDeviceRect.GetWidth() / aViewWin.W;
64 fHRatio = aDeviceRect.GetHeight() / aViewWin.H;
67 // Returns observer position (PRP) in world coordinates
69 const basegfx::B3DPoint& Viewport3D::GetViewPoint()
71 MakeTransform();
73 return aViewPoint;
76 // Calculate View transformations matrix
78 void Viewport3D::MakeTransform(void)
80 if ( !bTfValid )
82 double fV, fXupVp, fYupVp;
83 aViewPoint = aVRP + aVPN * aPRP.getZ();
85 // Reset to Identity matrix
86 aViewTf.identity();
88 // shift in the origin
89 aViewTf.translate(-aVRP.getX(), -aVRP.getY(), -aVRP.getZ());
91 // fV = Length of the projection of aVPN on the yz plane:
92 fV = aVPN.getYZLength();
94 if ( fV != 0 )
96 basegfx::B3DHomMatrix aTemp;
97 const double fSin(aVPN.getY() / fV);
98 const double fCos(aVPN.getZ() / fV);
99 aTemp.set(2, 2, fCos);
100 aTemp.set(1, 1, fCos);
101 aTemp.set(2, 1, fSin);
102 aTemp.set(1, 2, -fSin);
103 aViewTf *= aTemp;
107 basegfx::B3DHomMatrix aTemp;
108 const double fSin(-aVPN.getX());
109 const double fCos(fV);
110 aTemp.set(2, 2, fCos);
111 aTemp.set(0, 0, fCos);
112 aTemp.set(0, 2, fSin);
113 aTemp.set(2, 0, -fSin);
114 aViewTf *= aTemp;
117 // Convert X- and Y- coordinates of the view up vector to the
118 // (preliminary) view coordinate system.
119 fXupVp = aViewTf.get(0, 0) * aVUV.getX() + aViewTf.get(0, 1) * aVUV.getY() + aViewTf.get(0, 2) * aVUV.getZ();
120 fYupVp = aViewTf.get(1, 0) * aVUV.getX() + aViewTf.get(1, 1) * aVUV.getY() + aViewTf.get(1, 2) * aVUV.getZ();
121 fV = sqrt(fXupVp * fXupVp + fYupVp * fYupVp);
123 if ( fV != 0 )
125 basegfx::B3DHomMatrix aTemp;
126 const double fSin(fXupVp / fV);
127 const double fCos(fYupVp / fV);
128 aTemp.set(1, 1, fCos);
129 aTemp.set(0, 0, fCos);
130 aTemp.set(1, 0, fSin);
131 aTemp.set(0, 1, -fSin);
132 aViewTf *= aTemp;
135 bTfValid = sal_True;
139 void Viewport3D::SetDeviceWindow(const Rectangle& rRect)
141 long nNewW = rRect.GetWidth();
142 long nNewH = rRect.GetHeight();
143 long nOldW = aDeviceRect.GetWidth();
144 long nOldH = aDeviceRect.GetHeight();
146 switch ( eAspectMapping )
148 double fRatio, fTmp;
150 // Mapping, without changing the real size of the objects in the
151 // Device Window
152 case AS_HOLD_SIZE:
153 // When the Device is invalid (w, h = -1), adapt the View
154 // with AsHoldX
155 if ( nOldW > 0 && nOldH > 0 )
157 fRatio = (double) nNewW / nOldW;
158 aViewWin.X *= fRatio;
159 aViewWin.W *= fRatio;
160 fRatio = (double) nNewH / nOldH;
161 aViewWin.Y *= fRatio;
162 aViewWin.H *= fRatio;
163 break;
165 case AS_HOLD_X:
166 // Adapt view height to view width
167 fRatio = (double) nNewH / nNewW;
168 fTmp = aViewWin.H;
169 aViewWin.H = aViewWin.W * fRatio;
170 aViewWin.Y = aViewWin.Y * aViewWin.H / fTmp;
171 break;
173 case AS_HOLD_Y:
174 // Adapt view width to view height
175 fRatio = (double) nNewW / nNewH;
176 fTmp = aViewWin.W;
177 aViewWin.W = aViewWin.H * fRatio;
178 aViewWin.X = aViewWin.X * aViewWin.W / fTmp;
179 break;
180 default: break;
182 fWRatio = nNewW / aViewWin.W;
183 fHRatio = nNewH / aViewWin.H;
185 aDeviceRect = rRect;
188 // Set View Reference Point
190 void Viewport3D::SetVRP(const basegfx::B3DPoint& rNewVRP)
192 aVRP = rNewVRP;
193 bTfValid = sal_False;
196 // Set View Plane Normal
198 void Viewport3D::SetVPN(const basegfx::B3DVector& rNewVPN)
200 aVPN = rNewVPN;
201 aVPN.normalize();
202 bTfValid = sal_False;
205 // Set View Up Vector
207 void Viewport3D::SetVUV(const basegfx::B3DVector& rNewVUV)
209 aVUV = rNewVUV;
210 bTfValid = sal_False;
213 // Set Center Of Projection
215 void Viewport3D::SetPRP(const basegfx::B3DPoint& rNewPRP)
217 aPRP = rNewPRP;
218 aPRP.setX(0.0);
219 aPRP.setY(0.0);
220 bTfValid = sal_False;
223 // Set View Plane Distance
225 void Viewport3D::SetVPD(double fNewVPD)
227 fVPD = fNewVPD;
228 bTfValid = sal_False;
231 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */