Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 :
21 : #include <svx/dlgctl3d.hxx>
22 : #include <svx/dialogs.hrc>
23 : #include <svx/view3d.hxx>
24 : #include <svx/fmmodel.hxx>
25 : #include <svl/itempool.hxx>
26 : #include <svx/fmpage.hxx>
27 : #include <svx/polysc3d.hxx>
28 : #include <svx/sphere3d.hxx>
29 : #include <svx/cube3d.hxx>
30 : #include <vcl/svapp.hxx>
31 : #include <vcl/builderfactory.hxx>
32 : #include <svx/helperhittest3d.hxx>
33 : #include <basegfx/polygon/b2dpolygontools.hxx>
34 : #include <svx/polygn3d.hxx>
35 : #include <svx/xlnclit.hxx>
36 : #include <svx/xlnwtit.hxx>
37 : #include "helpid.hrc"
38 : #include <algorithm>
39 : #include <svx/dialmgr.hxx>
40 : #include <vcl/settings.hxx>
41 :
42 : using namespace com::sun::star;
43 :
44 0 : Svx3DPreviewControl::Svx3DPreviewControl(vcl::Window* pParent, WinBits nStyle)
45 : : Control(pParent, nStyle),
46 : mpModel(0),
47 : mpFmPage(0),
48 : mp3DView(0),
49 : mpScene(0),
50 : mp3DObj(0),
51 0 : mnObjectType(SvxPreviewObjectType::SPHERE)
52 : {
53 0 : Construct();
54 :
55 : // do not paint background self, DrawingLayer paints this buffered and as page
56 0 : SetControlBackground();
57 0 : SetBackground();
58 0 : }
59 :
60 0 : Size Svx3DPreviewControl::GetOptimalSize() const
61 : {
62 0 : return LogicToPixel(Size(80, 100), MAP_APPFONT);
63 : }
64 :
65 0 : VCL_BUILDER_FACTORY(Svx3DPreviewControl)
66 :
67 0 : Svx3DPreviewControl::~Svx3DPreviewControl()
68 : {
69 0 : disposeOnce();
70 0 : }
71 :
72 0 : void Svx3DPreviewControl::dispose()
73 : {
74 0 : delete mp3DView;
75 0 : delete mpModel;
76 0 : Control::dispose();
77 0 : }
78 :
79 0 : void Svx3DPreviewControl::Construct()
80 : {
81 : // Do never mirror the preview window. This explicitly includes right
82 : // to left writing environments.
83 0 : EnableRTL (false);
84 0 : SetMapMode( MAP_100TH_MM );
85 :
86 : // Model
87 0 : mpModel = new FmFormModel();
88 0 : mpModel->GetItemPool().FreezeIdRanges();
89 :
90 : // Page
91 0 : mpFmPage = new FmFormPage( *mpModel );
92 0 : mpModel->InsertPage( mpFmPage, 0 );
93 :
94 : // 3D View
95 0 : mp3DView = new E3dView( mpModel, this );
96 0 : mp3DView->SetBufferedOutputAllowed(true);
97 0 : mp3DView->SetBufferedOverlayAllowed(true);
98 :
99 : // 3D Scene
100 0 : mpScene = new E3dPolyScene(mp3DView->Get3DDefaultAttributes());
101 :
102 : // initially create object
103 0 : SetObjectType(SvxPreviewObjectType::SPHERE);
104 :
105 : // camera and perspective
106 0 : Camera3D& rCamera = (Camera3D&) mpScene->GetCamera();
107 0 : const basegfx::B3DRange& rVolume = mpScene->GetBoundVolume();
108 0 : double fW = rVolume.getWidth();
109 0 : double fH = rVolume.getHeight();
110 0 : double fCamZ = rVolume.getMaxZ() + ((fW + fH) / 2.0);
111 :
112 0 : rCamera.SetAutoAdjustProjection(false);
113 0 : rCamera.SetViewWindow(- fW / 2, - fH / 2, fW, fH);
114 0 : basegfx::B3DPoint aLookAt;
115 0 : double fDefaultCamPosZ = mp3DView->GetDefaultCamPosZ();
116 0 : basegfx::B3DPoint aCamPos(0.0, 0.0, fCamZ < fDefaultCamPosZ ? fDefaultCamPosZ : fCamZ);
117 0 : rCamera.SetPosAndLookAt(aCamPos, aLookAt);
118 0 : double fDefaultCamFocal = mp3DView->GetDefaultCamFocal();
119 0 : rCamera.SetFocalLength(fDefaultCamFocal);
120 0 : rCamera.SetDefaults(basegfx::B3DPoint(0.0, 0.0, fDefaultCamPosZ), aLookAt, fDefaultCamFocal);
121 :
122 0 : mpScene->SetCamera( rCamera );
123 0 : mpFmPage->InsertObject( mpScene );
124 :
125 0 : basegfx::B3DHomMatrix aRotation;
126 0 : aRotation.rotate(DEG2RAD( 25 ), 0.0, 0.0);
127 0 : aRotation.rotate(0.0, DEG2RAD( 40 ), 0.0);
128 0 : mpScene->SetTransform(aRotation * mpScene->GetTransform());
129 :
130 : // invalidate SnapRects of objects
131 0 : mpScene->SetRectsDirty();
132 :
133 0 : SfxItemSet aSet( mpModel->GetItemPool(),
134 : XATTR_LINESTYLE, XATTR_LINESTYLE,
135 : XATTR_FILL_FIRST, XATTR_FILLBITMAP,
136 0 : 0, 0 );
137 0 : aSet.Put( XLineStyleItem( drawing::LineStyle_NONE ) );
138 0 : aSet.Put( XFillStyleItem( drawing::FillStyle_SOLID ) );
139 0 : aSet.Put( XFillColorItem( "", Color( COL_WHITE ) ) );
140 :
141 0 : mpScene->SetMergedItemSet(aSet);
142 :
143 : // PageView
144 0 : SdrPageView* pPageView = mp3DView->ShowSdrPage( mpFmPage );
145 0 : mp3DView->hideMarkHandles();
146 :
147 : // mark scene
148 0 : mp3DView->MarkObj( mpScene, pPageView );
149 0 : }
150 :
151 0 : void Svx3DPreviewControl::Resize()
152 : {
153 : // size of page
154 0 : Size aSize( GetSizePixel() );
155 0 : aSize = PixelToLogic( aSize );
156 0 : mpFmPage->SetSize( aSize );
157 :
158 : // set size
159 0 : Size aObjSize( aSize.Width()*5/6, aSize.Height()*5/6 );
160 0 : Point aObjPoint( (aSize.Width() - aObjSize.Width()) / 2,
161 0 : (aSize.Height() - aObjSize.Height()) / 2);
162 0 : Rectangle aRect( aObjPoint, aObjSize);
163 0 : mpScene->SetSnapRect( aRect );
164 0 : }
165 :
166 0 : void Svx3DPreviewControl::Paint(vcl::RenderContext& rRenderContext, const Rectangle& rRect)
167 : {
168 0 : mp3DView->CompleteRedraw(&rRenderContext, vcl::Region(rRect));
169 0 : }
170 :
171 0 : void Svx3DPreviewControl::MouseButtonDown(const MouseEvent& rMEvt)
172 : {
173 0 : Control::MouseButtonDown(rMEvt);
174 :
175 0 : if( rMEvt.IsShift() && rMEvt.IsMod1() )
176 : {
177 0 : if(SvxPreviewObjectType::SPHERE == GetObjectType())
178 : {
179 0 : SetObjectType(SvxPreviewObjectType::CUBE);
180 : }
181 : else
182 : {
183 0 : SetObjectType(SvxPreviewObjectType::SPHERE);
184 : }
185 : }
186 0 : }
187 :
188 0 : void Svx3DPreviewControl::SetObjectType(SvxPreviewObjectType nType)
189 : {
190 0 : if( mnObjectType != nType || !mp3DObj)
191 : {
192 0 : SfxItemSet aSet(mpModel->GetItemPool(), SDRATTR_START, SDRATTR_END, 0, 0);
193 0 : mnObjectType = nType;
194 :
195 0 : if( mp3DObj )
196 : {
197 0 : aSet.Put(mp3DObj->GetMergedItemSet());
198 0 : mpScene->Remove3DObj( mp3DObj );
199 0 : delete mp3DObj;
200 0 : mp3DObj = NULL;
201 : }
202 :
203 0 : switch( nType )
204 : {
205 : case SvxPreviewObjectType::SPHERE:
206 : {
207 : mp3DObj = new E3dSphereObj(
208 0 : mp3DView->Get3DDefaultAttributes(),
209 : basegfx::B3DPoint( 0, 0, 0 ),
210 0 : basegfx::B3DVector( 5000, 5000, 5000 ));
211 : }
212 0 : break;
213 :
214 : case SvxPreviewObjectType::CUBE:
215 : {
216 : mp3DObj = new E3dCubeObj(
217 0 : mp3DView->Get3DDefaultAttributes(),
218 : basegfx::B3DPoint( -2500, -2500, -2500 ),
219 0 : basegfx::B3DVector( 5000, 5000, 5000 ));
220 : }
221 0 : break;
222 : }
223 :
224 0 : if (mp3DObj)
225 : {
226 0 : mpScene->Insert3DObj( mp3DObj );
227 0 : mp3DObj->SetMergedItemSet(aSet);
228 : }
229 :
230 0 : Resize();
231 : }
232 0 : }
233 :
234 0 : SfxItemSet Svx3DPreviewControl::Get3DAttributes() const
235 : {
236 0 : return mp3DObj->GetMergedItemSet();
237 : }
238 :
239 0 : void Svx3DPreviewControl::Set3DAttributes( const SfxItemSet& rAttr )
240 : {
241 0 : mp3DObj->SetMergedItemSet(rAttr, true);
242 0 : Resize();
243 0 : }
244 :
245 :
246 :
247 : #define RADIUS_LAMP_PREVIEW_SIZE (4500.0)
248 : #define RADIUS_LAMP_SMALL (600.0)
249 : #define RADIUS_LAMP_BIG (1000.0)
250 : #define NO_LIGHT_SELECTED (0xffffffff)
251 : #define MAX_NUMBER_LIGHTS (8)
252 :
253 0 : Svx3DLightControl::Svx3DLightControl(vcl::Window* pParent, WinBits nStyle)
254 : : Svx3DPreviewControl(pParent, nStyle),
255 : maUserInteractiveChangeCallback(),
256 : maUserSelectionChangeCallback(),
257 : maChangeCallback(),
258 : maSelectionChangeCallback(),
259 : maSelectedLight(NO_LIGHT_SELECTED),
260 : mpExpansionObject(0),
261 : mpLampBottomObject(0),
262 : mpLampShaftObject(0),
263 : maLightObjects(MAX_NUMBER_LIGHTS, nullptr),
264 : mfRotateX(-20.0),
265 : mfRotateY(45.0),
266 : mfRotateZ(0.0),
267 : maActionStartPoint(),
268 : mnInteractionStartDistance(5 * 5 * 2),
269 : mfSaveActionStartHor(0.0),
270 : mfSaveActionStartVer(0.0),
271 : mfSaveActionStartRotZ(0.0),
272 : mbMouseMoved(false),
273 0 : mbGeometrySelected(false)
274 : {
275 0 : Construct2();
276 0 : }
277 :
278 0 : void Svx3DLightControl::Construct2()
279 : {
280 : {
281 : // hide all page stuff, use control background (normally gray)
282 0 : const Color aDialogColor(Application::GetSettings().GetStyleSettings().GetDialogColor());
283 0 : mp3DView->SetPageVisible(false);
284 0 : mp3DView->SetApplicationBackgroundColor(aDialogColor);
285 0 : mp3DView->SetApplicationDocumentColor(aDialogColor);
286 : }
287 :
288 : {
289 : // create invisible expansion object
290 0 : const double fMaxExpansion(RADIUS_LAMP_BIG + RADIUS_LAMP_PREVIEW_SIZE);
291 : mpExpansionObject = new E3dCubeObj(
292 0 : mp3DView->Get3DDefaultAttributes(),
293 : basegfx::B3DPoint(-fMaxExpansion, -fMaxExpansion, -fMaxExpansion),
294 0 : basegfx::B3DVector(2.0 * fMaxExpansion, 2.0 * fMaxExpansion, 2.0 * fMaxExpansion));
295 0 : mpScene->Insert3DObj( mpExpansionObject );
296 0 : SfxItemSet aSet(mpModel->GetItemPool());
297 0 : aSet.Put( XLineStyleItem( drawing::LineStyle_NONE ) );
298 0 : aSet.Put( XFillStyleItem( drawing::FillStyle_NONE ) );
299 0 : mpExpansionObject->SetMergedItemSet(aSet);
300 : }
301 :
302 : {
303 : // create lamp control object (Yellow lined object)
304 : // base circle
305 0 : const basegfx::B2DPolygon a2DCircle(basegfx::tools::createPolygonFromCircle(basegfx::B2DPoint(0.0, 0.0), RADIUS_LAMP_PREVIEW_SIZE));
306 0 : basegfx::B3DPolygon a3DCircle(basegfx::tools::createB3DPolygonFromB2DPolygon(a2DCircle));
307 0 : basegfx::B3DHomMatrix aTransform;
308 :
309 0 : aTransform.rotate(F_PI2, 0.0, 0.0);
310 0 : aTransform.translate(0.0, -RADIUS_LAMP_PREVIEW_SIZE, 0.0);
311 0 : a3DCircle.transform(aTransform);
312 :
313 : // create object for it
314 : mpLampBottomObject = new E3dPolygonObj(
315 0 : mp3DView->Get3DDefaultAttributes(),
316 : basegfx::B3DPolyPolygon(a3DCircle),
317 0 : true);
318 0 : mpScene->Insert3DObj( mpLampBottomObject );
319 :
320 : // half circle with stand
321 0 : basegfx::B2DPolygon a2DHalfCircle;
322 0 : a2DHalfCircle.append(basegfx::B2DPoint(RADIUS_LAMP_PREVIEW_SIZE, 0.0));
323 0 : a2DHalfCircle.append(basegfx::B2DPoint(RADIUS_LAMP_PREVIEW_SIZE, -RADIUS_LAMP_PREVIEW_SIZE));
324 : a2DHalfCircle.append(basegfx::tools::createPolygonFromEllipseSegment(
325 0 : basegfx::B2DPoint(0.0, 0.0), RADIUS_LAMP_PREVIEW_SIZE, RADIUS_LAMP_PREVIEW_SIZE, F_2PI - F_PI2, F_PI2));
326 0 : basegfx::B3DPolygon a3DHalfCircle(basegfx::tools::createB3DPolygonFromB2DPolygon(a2DHalfCircle));
327 :
328 : // create object for it
329 : mpLampShaftObject = new E3dPolygonObj(
330 0 : mp3DView->Get3DDefaultAttributes(),
331 : basegfx::B3DPolyPolygon(a3DHalfCircle),
332 0 : true);
333 0 : mpScene->Insert3DObj( mpLampShaftObject );
334 :
335 : // initially invisible
336 0 : SfxItemSet aSet(mpModel->GetItemPool());
337 0 : aSet.Put( XLineStyleItem( drawing::LineStyle_NONE ) );
338 0 : aSet.Put( XFillStyleItem( drawing::FillStyle_NONE ) );
339 :
340 0 : mpLampBottomObject->SetMergedItemSet(aSet);
341 0 : mpLampShaftObject->SetMergedItemSet(aSet);
342 : }
343 :
344 : {
345 : // change camera settings
346 0 : Camera3D& rCamera = (Camera3D&) mpScene->GetCamera();
347 0 : const basegfx::B3DRange& rVolume = mpScene->GetBoundVolume();
348 0 : double fW = rVolume.getWidth();
349 0 : double fH = rVolume.getHeight();
350 0 : double fCamZ = rVolume.getMaxZ() + ((fW + fH) / 2.0);
351 :
352 0 : rCamera.SetAutoAdjustProjection(false);
353 0 : rCamera.SetViewWindow(- fW / 2, - fH / 2, fW, fH);
354 0 : basegfx::B3DPoint aLookAt;
355 0 : double fDefaultCamPosZ = mp3DView->GetDefaultCamPosZ();
356 0 : basegfx::B3DPoint aCamPos(0.0, 0.0, fCamZ < fDefaultCamPosZ ? fDefaultCamPosZ : fCamZ);
357 0 : rCamera.SetPosAndLookAt(aCamPos, aLookAt);
358 0 : double fDefaultCamFocal = mp3DView->GetDefaultCamFocal();
359 0 : rCamera.SetFocalLength(fDefaultCamFocal);
360 0 : rCamera.SetDefaults(basegfx::B3DPoint(0.0, 0.0, fDefaultCamPosZ), aLookAt, fDefaultCamFocal);
361 :
362 0 : mpScene->SetCamera( rCamera );
363 :
364 0 : basegfx::B3DHomMatrix aNeutral;
365 0 : mpScene->SetTransform(aNeutral);
366 : }
367 :
368 : // invalidate SnapRects of objects
369 0 : mpScene->SetRectsDirty();
370 0 : }
371 :
372 0 : void Svx3DLightControl::ConstructLightObjects()
373 : {
374 0 : for(sal_uInt32 a(0); a < MAX_NUMBER_LIGHTS; a++)
375 : {
376 : // get rid of possible existing light object
377 0 : if(maLightObjects[a])
378 : {
379 0 : mpScene->Remove3DObj(maLightObjects[a]);
380 0 : delete maLightObjects[a];
381 0 : maLightObjects[a] = 0;
382 : }
383 :
384 0 : if(GetLightOnOff(a))
385 : {
386 0 : const bool bIsSelectedLight(a == maSelectedLight);
387 0 : basegfx::B3DVector aDirection(GetLightDirection(a));
388 0 : aDirection.normalize();
389 0 : aDirection *= RADIUS_LAMP_PREVIEW_SIZE;
390 :
391 0 : const double fLampSize(bIsSelectedLight ? RADIUS_LAMP_BIG : RADIUS_LAMP_SMALL);
392 : E3dObject* pNewLight = new E3dSphereObj(
393 0 : mp3DView->Get3DDefaultAttributes(),
394 : basegfx::B3DPoint( 0, 0, 0 ),
395 0 : basegfx::B3DVector( fLampSize, fLampSize, fLampSize));
396 0 : mpScene->Insert3DObj(pNewLight);
397 :
398 0 : basegfx::B3DHomMatrix aTransform;
399 0 : aTransform.translate(aDirection.getX(), aDirection.getY(), aDirection.getZ());
400 0 : pNewLight->SetTransform(aTransform);
401 :
402 0 : SfxItemSet aSet(mpModel->GetItemPool());
403 0 : aSet.Put( XLineStyleItem( drawing::LineStyle_NONE ) );
404 0 : aSet.Put( XFillStyleItem( drawing::FillStyle_SOLID ) );
405 0 : aSet.Put( XFillColorItem(OUString(), GetLightColor(a)));
406 0 : pNewLight->SetMergedItemSet(aSet);
407 :
408 0 : maLightObjects[a] = pNewLight;
409 : }
410 : }
411 0 : }
412 :
413 0 : void Svx3DLightControl::AdaptToSelectedLight()
414 : {
415 0 : if(NO_LIGHT_SELECTED == maSelectedLight)
416 : {
417 : // make mpLampBottomObject/mpLampShaftObject invisible
418 0 : SfxItemSet aSet(mpModel->GetItemPool());
419 0 : aSet.Put( XLineStyleItem( drawing::LineStyle_NONE ) );
420 0 : aSet.Put( XFillStyleItem( drawing::FillStyle_NONE ) );
421 0 : mpLampBottomObject->SetMergedItemSet(aSet);
422 0 : mpLampShaftObject->SetMergedItemSet(aSet);
423 : }
424 : else
425 : {
426 0 : basegfx::B3DVector aDirection(GetLightDirection(maSelectedLight));
427 0 : aDirection.normalize();
428 :
429 : // make mpLampBottomObject/mpLampShaftObject visible (yellow hairline)
430 0 : SfxItemSet aSet(mpModel->GetItemPool());
431 0 : aSet.Put( XLineStyleItem( drawing::LineStyle_SOLID ) );
432 0 : aSet.Put( XLineColorItem(OUString(), COL_YELLOW));
433 0 : aSet.Put( XLineWidthItem(0));
434 0 : aSet.Put( XFillStyleItem( drawing::FillStyle_NONE ) );
435 0 : mpLampBottomObject->SetMergedItemSet(aSet);
436 0 : mpLampShaftObject->SetMergedItemSet(aSet);
437 :
438 : // adapt transformation of mpLampShaftObject
439 0 : basegfx::B3DHomMatrix aTransform;
440 0 : double fRotateY(0.0);
441 :
442 0 : if(!basegfx::fTools::equalZero(aDirection.getZ()) || !basegfx::fTools::equalZero(aDirection.getX()))
443 : {
444 0 : fRotateY = atan2(-aDirection.getZ(), aDirection.getX());
445 : }
446 :
447 0 : aTransform.rotate(0.0, fRotateY, 0.0);
448 0 : mpLampShaftObject->SetTransform(aTransform);
449 :
450 : // adapt transformation of selected light
451 0 : E3dObject* pSelectedLight = maLightObjects[sal_Int32(maSelectedLight)];
452 :
453 0 : if(pSelectedLight)
454 : {
455 0 : aTransform.identity();
456 : aTransform.translate(
457 0 : aDirection.getX() * RADIUS_LAMP_PREVIEW_SIZE,
458 0 : aDirection.getY() * RADIUS_LAMP_PREVIEW_SIZE,
459 0 : aDirection.getZ() * RADIUS_LAMP_PREVIEW_SIZE);
460 0 : pSelectedLight->SetTransform(aTransform);
461 0 : }
462 : }
463 0 : }
464 :
465 0 : void Svx3DLightControl::TrySelection(Point aPosPixel)
466 : {
467 0 : if(mpScene)
468 : {
469 0 : const Point aPosLogic(PixelToLogic(aPosPixel));
470 0 : const basegfx::B2DPoint aPoint(aPosLogic.X(), aPosLogic.Y());
471 0 : std::vector< const E3dCompoundObject* > aResult;
472 0 : getAllHit3DObjectsSortedFrontToBack(aPoint, *mpScene, aResult);
473 :
474 0 : if(!aResult.empty())
475 : {
476 : // exclude expansion object which will be part of
477 : // the hits. It's invisible, but for HitTest, it's included
478 0 : const E3dCompoundObject* pResult = 0;
479 :
480 0 : for(sal_uInt32 b(0); !pResult && b < aResult.size(); b++)
481 : {
482 0 : if(aResult[b] && aResult[b] != mpExpansionObject)
483 : {
484 0 : pResult = aResult[b];
485 : }
486 : }
487 :
488 0 : if(pResult == mp3DObj)
489 : {
490 0 : if(!mbGeometrySelected)
491 : {
492 0 : mbGeometrySelected = true;
493 0 : maSelectedLight = NO_LIGHT_SELECTED;
494 0 : ConstructLightObjects();
495 0 : AdaptToSelectedLight();
496 0 : Invalidate();
497 :
498 0 : if(maSelectionChangeCallback.IsSet())
499 : {
500 0 : maSelectionChangeCallback.Call(this);
501 : }
502 : }
503 : }
504 : else
505 : {
506 0 : sal_uInt32 aNewSelectedLight(NO_LIGHT_SELECTED);
507 :
508 0 : for(sal_uInt32 a(0); a < MAX_NUMBER_LIGHTS; a++)
509 : {
510 0 : if(maLightObjects[a] && maLightObjects[a] == pResult)
511 : {
512 0 : aNewSelectedLight = a;
513 : }
514 : }
515 :
516 0 : if(aNewSelectedLight != maSelectedLight)
517 : {
518 0 : SelectLight(aNewSelectedLight);
519 :
520 0 : if(maSelectionChangeCallback.IsSet())
521 : {
522 0 : maSelectionChangeCallback.Call(this);
523 : }
524 : }
525 : }
526 0 : }
527 : }
528 0 : }
529 :
530 0 : void Svx3DLightControl::Paint(vcl::RenderContext& rRenderContext, const Rectangle& rRect)
531 : {
532 0 : Svx3DPreviewControl::Paint(rRenderContext, rRect);
533 0 : }
534 :
535 0 : void Svx3DLightControl::MouseButtonDown( const MouseEvent& rMEvt )
536 : {
537 0 : bool bCallParent(true);
538 :
539 : // switch state
540 0 : if(rMEvt.IsLeft())
541 : {
542 0 : if(IsSelectionValid() || mbGeometrySelected)
543 : {
544 0 : mbMouseMoved = false;
545 0 : bCallParent = false;
546 0 : maActionStartPoint = rMEvt.GetPosPixel();
547 0 : StartTracking();
548 : }
549 : else
550 : {
551 : // Single click without moving much trying to do a selection
552 0 : TrySelection(rMEvt.GetPosPixel());
553 0 : bCallParent = false;
554 : }
555 : }
556 :
557 : // call parent
558 0 : if(bCallParent)
559 : {
560 0 : Svx3DPreviewControl::MouseButtonDown(rMEvt);
561 : }
562 0 : }
563 :
564 0 : void Svx3DLightControl::Tracking( const TrackingEvent& rTEvt )
565 : {
566 0 : if(rTEvt.IsTrackingEnded())
567 : {
568 0 : if(rTEvt.IsTrackingCanceled())
569 : {
570 0 : if(mbMouseMoved)
571 : {
572 : // interrupt tracking
573 0 : mbMouseMoved = false;
574 :
575 0 : if(mbGeometrySelected)
576 : {
577 0 : SetRotation(mfSaveActionStartVer, mfSaveActionStartHor, mfSaveActionStartRotZ);
578 : }
579 : else
580 : {
581 0 : SetPosition(mfSaveActionStartHor, mfSaveActionStartVer);
582 : }
583 :
584 0 : if(maChangeCallback.IsSet())
585 : {
586 0 : maChangeCallback.Call(this);
587 : }
588 : }
589 : }
590 : else
591 : {
592 0 : const MouseEvent& rMEvt = rTEvt.GetMouseEvent();
593 :
594 0 : if(mbMouseMoved)
595 : {
596 : // was change dinteractively
597 : }
598 : else
599 : {
600 : // simple click without much movement, try selection
601 0 : TrySelection(rMEvt.GetPosPixel());
602 : }
603 : }
604 : }
605 : else
606 : {
607 0 : const MouseEvent& rMEvt = rTEvt.GetMouseEvent();
608 0 : Point aDeltaPos = rMEvt.GetPosPixel() - maActionStartPoint;
609 :
610 0 : if(!mbMouseMoved)
611 : {
612 0 : if(sal_Int32(aDeltaPos.X() * aDeltaPos.X() + aDeltaPos.Y() * aDeltaPos.Y()) > mnInteractionStartDistance)
613 : {
614 0 : if(mbGeometrySelected)
615 : {
616 0 : GetRotation(mfSaveActionStartVer, mfSaveActionStartHor, mfSaveActionStartRotZ);
617 : }
618 : else
619 : {
620 : // intercation start, save values
621 0 : GetPosition(mfSaveActionStartHor, mfSaveActionStartVer);
622 : }
623 :
624 0 : mbMouseMoved = true;
625 : }
626 : }
627 :
628 0 : if(mbMouseMoved)
629 : {
630 0 : if(mbGeometrySelected)
631 : {
632 0 : double fNewRotX = mfSaveActionStartVer - ((double)aDeltaPos.Y() * F_PI180);
633 0 : double fNewRotY = mfSaveActionStartHor + ((double)aDeltaPos.X() * F_PI180);
634 :
635 : // cut horizontal
636 0 : while(fNewRotY < 0.0)
637 : {
638 0 : fNewRotY += F_2PI;
639 : }
640 :
641 0 : while(fNewRotY >= F_2PI)
642 : {
643 0 : fNewRotY -= F_2PI;
644 : }
645 :
646 : // cut vertical
647 0 : if(fNewRotX < -F_PI2)
648 : {
649 0 : fNewRotX = -F_PI2;
650 : }
651 :
652 0 : if(fNewRotX > F_PI2)
653 : {
654 0 : fNewRotX = F_PI2;
655 : }
656 :
657 0 : SetRotation(fNewRotX, fNewRotY, mfSaveActionStartRotZ);
658 :
659 0 : if(maChangeCallback.IsSet())
660 : {
661 0 : maChangeCallback.Call(this);
662 : }
663 : }
664 : else
665 : {
666 : // interaction in progress
667 0 : double fNewPosHor = mfSaveActionStartHor + ((double)aDeltaPos.X());
668 0 : double fNewPosVer = mfSaveActionStartVer - ((double)aDeltaPos.Y());
669 :
670 : // cut horizontal
671 0 : while(fNewPosHor < 0.0)
672 : {
673 0 : fNewPosHor += 360.0;
674 : }
675 :
676 0 : while(fNewPosHor >= 360.0)
677 : {
678 0 : fNewPosHor -= 360.0;
679 : }
680 :
681 : // cut vertical
682 0 : if(fNewPosVer < -90.0)
683 : {
684 0 : fNewPosVer = -90.0;
685 : }
686 :
687 0 : if(fNewPosVer > 90.0)
688 : {
689 0 : fNewPosVer = 90.0;
690 : }
691 :
692 0 : SetPosition(fNewPosHor, fNewPosVer);
693 :
694 0 : if(maChangeCallback.IsSet())
695 : {
696 0 : maChangeCallback.Call(this);
697 : }
698 : }
699 : }
700 : }
701 0 : }
702 :
703 0 : void Svx3DLightControl::Resize()
704 : {
705 : // set size of page
706 0 : const Size aSize(PixelToLogic(GetSizePixel()));
707 0 : mpFmPage->SetSize(aSize);
708 :
709 : // set position and size of scene
710 0 : mpScene->SetSnapRect(Rectangle(Point(0, 0), aSize));
711 0 : }
712 :
713 0 : void Svx3DLightControl::SetObjectType(SvxPreviewObjectType nType)
714 : {
715 : // call parent
716 0 : Svx3DPreviewControl::SetObjectType(nType);
717 :
718 : // apply object rotation
719 0 : if(mp3DObj)
720 : {
721 0 : basegfx::B3DHomMatrix aObjectRotation;
722 0 : aObjectRotation.rotate(mfRotateX, mfRotateY, mfRotateZ);
723 0 : mp3DObj->SetTransform(aObjectRotation);
724 : }
725 0 : }
726 :
727 0 : bool Svx3DLightControl::IsSelectionValid()
728 : {
729 0 : if((NO_LIGHT_SELECTED != maSelectedLight) && (GetLightOnOff(maSelectedLight)))
730 : {
731 0 : return true;
732 : }
733 :
734 0 : return false;
735 : }
736 :
737 0 : void Svx3DLightControl::GetPosition(double& rHor, double& rVer)
738 : {
739 0 : if(IsSelectionValid())
740 : {
741 0 : basegfx::B3DVector aDirection(GetLightDirection(maSelectedLight));
742 0 : aDirection.normalize();
743 0 : rHor = atan2(-aDirection.getX(), -aDirection.getZ()) + F_PI; // 0..2PI
744 0 : rVer = atan2(aDirection.getY(), aDirection.getXZLength()); // -PI2..PI2
745 0 : rHor /= F_PI180; // 0..360.0
746 0 : rVer /= F_PI180; // -90.0..90.0
747 : }
748 0 : if(IsGeometrySelected())
749 : {
750 0 : rHor = mfRotateY / F_PI180; // 0..360.0
751 0 : rVer = mfRotateX / F_PI180; // -90.0..90.0
752 : }
753 0 : }
754 :
755 0 : void Svx3DLightControl::SetPosition(double fHor, double fVer)
756 : {
757 0 : if(IsSelectionValid())
758 : {
759 : // set selected light's direction
760 0 : fHor = (fHor * F_PI180) - F_PI; // -PI..PI
761 0 : fVer *= F_PI180; // -PI2..PI2
762 0 : basegfx::B3DVector aDirection(cos(fVer) * -sin(fHor), sin(fVer), cos(fVer) * -cos(fHor));
763 0 : aDirection.normalize();
764 :
765 0 : if(!aDirection.equal(GetLightDirection(maSelectedLight)))
766 : {
767 : // set changed light direction at SdrScene
768 0 : SfxItemSet aSet(mpModel->GetItemPool());
769 :
770 0 : switch(maSelectedLight)
771 : {
772 0 : case 0: aSet.Put(makeSvx3DLightDirection1Item(aDirection)); break;
773 0 : case 1: aSet.Put(makeSvx3DLightDirection2Item(aDirection)); break;
774 0 : case 2: aSet.Put(makeSvx3DLightDirection3Item(aDirection)); break;
775 0 : case 3: aSet.Put(makeSvx3DLightDirection4Item(aDirection)); break;
776 0 : case 4: aSet.Put(makeSvx3DLightDirection5Item(aDirection)); break;
777 0 : case 5: aSet.Put(makeSvx3DLightDirection6Item(aDirection)); break;
778 0 : case 6: aSet.Put(makeSvx3DLightDirection7Item(aDirection)); break;
779 : default:
780 0 : case 7: aSet.Put(makeSvx3DLightDirection8Item(aDirection)); break;
781 : }
782 :
783 0 : mpScene->SetMergedItemSet(aSet);
784 :
785 : // correct 3D light's and LampFrame's geometries
786 0 : AdaptToSelectedLight();
787 0 : Invalidate();
788 0 : }
789 : }
790 0 : if(IsGeometrySelected())
791 : {
792 0 : if(mfRotateX != fVer || mfRotateY != fHor)
793 : {
794 0 : mfRotateX = fVer * F_PI180;
795 0 : mfRotateY = fHor * F_PI180;
796 :
797 0 : if(mp3DObj)
798 : {
799 0 : basegfx::B3DHomMatrix aObjectRotation;
800 0 : aObjectRotation.rotate(mfRotateX, mfRotateY, mfRotateZ);
801 0 : mp3DObj->SetTransform(aObjectRotation);
802 :
803 0 : Invalidate();
804 : }
805 : }
806 : }
807 0 : }
808 :
809 0 : void Svx3DLightControl::SetRotation(double fRotX, double fRotY, double fRotZ)
810 : {
811 0 : if(IsGeometrySelected())
812 : {
813 0 : if(fRotX != mfRotateX || fRotY != mfRotateY || fRotZ != mfRotateZ)
814 : {
815 0 : mfRotateX = fRotX;
816 0 : mfRotateY = fRotY;
817 0 : mfRotateZ = fRotZ;
818 :
819 0 : if(mp3DObj)
820 : {
821 0 : basegfx::B3DHomMatrix aObjectRotation;
822 0 : aObjectRotation.rotate(mfRotateX, mfRotateY, mfRotateZ);
823 0 : mp3DObj->SetTransform(aObjectRotation);
824 :
825 0 : Invalidate();
826 : }
827 : }
828 : }
829 0 : }
830 :
831 0 : void Svx3DLightControl::GetRotation(double& rRotX, double& rRotY, double& rRotZ)
832 : {
833 0 : rRotX = mfRotateX;
834 0 : rRotY = mfRotateY;
835 0 : rRotZ = mfRotateZ;
836 0 : }
837 :
838 0 : void Svx3DLightControl::Set3DAttributes( const SfxItemSet& rAttr )
839 : {
840 : // call parent
841 0 : Svx3DPreviewControl::Set3DAttributes(rAttr);
842 :
843 0 : if(maSelectedLight != NO_LIGHT_SELECTED && !GetLightOnOff(maSelectedLight))
844 : {
845 : // selected light is no more active, select new one
846 0 : maSelectedLight = NO_LIGHT_SELECTED;
847 : }
848 :
849 : // local updates
850 0 : ConstructLightObjects();
851 0 : AdaptToSelectedLight();
852 0 : Invalidate();
853 0 : }
854 :
855 0 : void Svx3DLightControl::SelectLight(sal_uInt32 nLightNumber)
856 : {
857 0 : if(nLightNumber > 7)
858 : {
859 0 : nLightNumber = NO_LIGHT_SELECTED;
860 : }
861 :
862 0 : if(NO_LIGHT_SELECTED != nLightNumber)
863 : {
864 0 : if(!GetLightOnOff(nLightNumber))
865 : {
866 0 : nLightNumber = NO_LIGHT_SELECTED;
867 : }
868 : }
869 :
870 0 : if(nLightNumber != maSelectedLight)
871 : {
872 0 : maSelectedLight = nLightNumber;
873 0 : mbGeometrySelected = false;
874 0 : ConstructLightObjects();
875 0 : AdaptToSelectedLight();
876 0 : Invalidate();
877 : }
878 0 : }
879 :
880 0 : bool Svx3DLightControl::GetLightOnOff(sal_uInt32 nNum) const
881 : {
882 0 : if(nNum <= 7)
883 : {
884 0 : const SfxItemSet aLightItemSet(Get3DAttributes());
885 :
886 0 : switch(nNum)
887 : {
888 0 : case 0 : return static_cast<const SfxBoolItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTON_1)).GetValue();
889 0 : case 1 : return static_cast<const SfxBoolItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTON_2)).GetValue();
890 0 : case 2 : return static_cast<const SfxBoolItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTON_3)).GetValue();
891 0 : case 3 : return static_cast<const SfxBoolItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTON_4)).GetValue();
892 0 : case 4 : return static_cast<const SfxBoolItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTON_5)).GetValue();
893 0 : case 5 : return static_cast<const SfxBoolItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTON_6)).GetValue();
894 0 : case 6 : return static_cast<const SfxBoolItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTON_7)).GetValue();
895 0 : case 7 : return static_cast<const SfxBoolItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTON_8)).GetValue();
896 0 : }
897 : }
898 :
899 0 : return false;
900 : }
901 :
902 0 : Color Svx3DLightControl::GetLightColor(sal_uInt32 nNum) const
903 : {
904 0 : if(nNum <= 7)
905 : {
906 0 : const SfxItemSet aLightItemSet(Get3DAttributes());
907 :
908 0 : switch(nNum)
909 : {
910 0 : case 0 : return static_cast<const SvxColorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTCOLOR_1)).GetValue();
911 0 : case 1 : return static_cast<const SvxColorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTCOLOR_2)).GetValue();
912 0 : case 2 : return static_cast<const SvxColorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTCOLOR_3)).GetValue();
913 0 : case 3 : return static_cast<const SvxColorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTCOLOR_4)).GetValue();
914 0 : case 4 : return static_cast<const SvxColorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTCOLOR_5)).GetValue();
915 0 : case 5 : return static_cast<const SvxColorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTCOLOR_6)).GetValue();
916 0 : case 6 : return static_cast<const SvxColorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTCOLOR_7)).GetValue();
917 0 : case 7 : return static_cast<const SvxColorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTCOLOR_8)).GetValue();
918 0 : }
919 : }
920 :
921 0 : return Color(COL_BLACK);
922 : }
923 :
924 0 : basegfx::B3DVector Svx3DLightControl::GetLightDirection(sal_uInt32 nNum) const
925 : {
926 0 : if(nNum <= 7)
927 : {
928 0 : const SfxItemSet aLightItemSet(Get3DAttributes());
929 :
930 0 : switch(nNum)
931 : {
932 0 : case 0 : return static_cast<const SvxB3DVectorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTDIRECTION_1)).GetValue();
933 0 : case 1 : return static_cast<const SvxB3DVectorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTDIRECTION_2)).GetValue();
934 0 : case 2 : return static_cast<const SvxB3DVectorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTDIRECTION_3)).GetValue();
935 0 : case 3 : return static_cast<const SvxB3DVectorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTDIRECTION_4)).GetValue();
936 0 : case 4 : return static_cast<const SvxB3DVectorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTDIRECTION_5)).GetValue();
937 0 : case 5 : return static_cast<const SvxB3DVectorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTDIRECTION_6)).GetValue();
938 0 : case 6 : return static_cast<const SvxB3DVectorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTDIRECTION_7)).GetValue();
939 0 : case 7 : return static_cast<const SvxB3DVectorItem&>(aLightItemSet.Get(SDRATTR_3DSCENE_LIGHTDIRECTION_8)).GetValue();
940 0 : }
941 : }
942 :
943 0 : return basegfx::B3DVector();
944 : }
945 :
946 0 : SvxLightCtl3D::SvxLightCtl3D( vcl::Window* pParent)
947 : : Control(pParent, WB_BORDER | WB_TABSTOP),
948 : maLightControl(VclPtr<Svx3DLightControl>::Create(this, 0)),
949 : maHorScroller(VclPtr<ScrollBar>::Create(this, WB_HORZ | WB_DRAG)),
950 : maVerScroller(VclPtr<ScrollBar>::Create(this, WB_VERT | WB_DRAG)),
951 0 : maSwitcher(VclPtr<PushButton>::Create(this, 0))
952 : {
953 : // init members
954 0 : Init();
955 0 : }
956 :
957 0 : Size SvxLightCtl3D::GetOptimalSize() const
958 : {
959 0 : return LogicToPixel(Size(80, 100), MAP_APPFONT);
960 : }
961 :
962 0 : VCL_BUILDER_FACTORY(SvxLightCtl3D)
963 :
964 0 : void SvxLightCtl3D::Init()
965 : {
966 : // #i58240# set HelpIDs for scrollbars and switcher
967 0 : maHorScroller->SetHelpId(HID_CTRL3D_HSCROLL);
968 0 : maVerScroller->SetHelpId(HID_CTRL3D_VSCROLL);
969 0 : maSwitcher->SetHelpId(HID_CTRL3D_SWITCHER);
970 0 : maSwitcher->SetAccessibleName(SVX_RESSTR(STR_SWITCH));
971 :
972 : // Light preview
973 0 : maLightControl->Show();
974 0 : maLightControl->SetChangeCallback( LINK(this, SvxLightCtl3D, InternalInteractiveChange) );
975 0 : maLightControl->SetSelectionChangeCallback( LINK(this, SvxLightCtl3D, InternalSelectionChange) );
976 :
977 : // Horiz Scrollbar
978 0 : maHorScroller->Show();
979 0 : maHorScroller->SetRange(Range(0, 36000));
980 0 : maHorScroller->SetLineSize(100);
981 0 : maHorScroller->SetPageSize(1000);
982 0 : maHorScroller->SetScrollHdl( LINK(this, SvxLightCtl3D, ScrollBarMove) );
983 :
984 : // Vert Scrollbar
985 0 : maVerScroller->Show();
986 0 : maVerScroller->SetRange(Range(0, 18000));
987 0 : maVerScroller->SetLineSize(100);
988 0 : maVerScroller->SetPageSize(1000);
989 0 : maVerScroller->SetScrollHdl( LINK(this, SvxLightCtl3D, ScrollBarMove) );
990 :
991 : // Switch Button
992 0 : maSwitcher->Show();
993 0 : maSwitcher->SetClickHdl( LINK(this, SvxLightCtl3D, ButtonPress) );
994 :
995 : // check selection
996 0 : CheckSelection();
997 :
998 : // new layout
999 0 : NewLayout();
1000 0 : }
1001 :
1002 0 : SvxLightCtl3D::~SvxLightCtl3D()
1003 : {
1004 0 : disposeOnce();
1005 0 : }
1006 :
1007 0 : void SvxLightCtl3D::dispose()
1008 : {
1009 0 : maLightControl.disposeAndClear();
1010 0 : maHorScroller.disposeAndClear();
1011 0 : maVerScroller.disposeAndClear();
1012 0 : maSwitcher.disposeAndClear();
1013 0 : Control::dispose();
1014 0 : }
1015 :
1016 0 : void SvxLightCtl3D::Resize()
1017 : {
1018 : // call parent
1019 0 : Control::Resize();
1020 :
1021 : // new layout
1022 0 : NewLayout();
1023 0 : }
1024 :
1025 0 : void SvxLightCtl3D::NewLayout()
1026 : {
1027 : // Layout members
1028 0 : const Size aSize(GetOutputSizePixel());
1029 0 : const sal_Int32 nScrollSize(maHorScroller->GetSizePixel().Height());
1030 :
1031 : // Preview control
1032 0 : Point aPoint(0, 0);
1033 0 : Size aDestSize(aSize.Width() - nScrollSize, aSize.Height() - nScrollSize);
1034 0 : maLightControl->SetPosSizePixel(aPoint, aDestSize);
1035 :
1036 : // hor scrollbar
1037 0 : aPoint.Y() = aSize.Height() - nScrollSize;
1038 0 : aDestSize.Height() = nScrollSize;
1039 0 : maHorScroller->SetPosSizePixel(aPoint, aDestSize);
1040 :
1041 : // vert scrollbar
1042 0 : aPoint.X() = aSize.Width() - nScrollSize;
1043 0 : aPoint.Y() = 0;
1044 0 : aDestSize.Width() = nScrollSize;
1045 0 : aDestSize.Height() = aSize.Height() - nScrollSize;
1046 0 : maVerScroller->SetPosSizePixel(aPoint, aDestSize);
1047 :
1048 : // button
1049 0 : aPoint.Y() = aSize.Height() - nScrollSize;
1050 0 : aDestSize.Height() = nScrollSize;
1051 0 : maSwitcher->SetPosSizePixel(aPoint, aDestSize);
1052 0 : }
1053 :
1054 0 : void SvxLightCtl3D::CheckSelection()
1055 : {
1056 0 : const bool bSelectionValid(maLightControl->IsSelectionValid() || maLightControl->IsGeometrySelected());
1057 0 : maHorScroller->Enable(bSelectionValid);
1058 0 : maVerScroller->Enable(bSelectionValid);
1059 :
1060 0 : if(bSelectionValid)
1061 : {
1062 0 : double fHor(0.0), fVer(0.0);
1063 0 : maLightControl->GetPosition(fHor, fVer);
1064 0 : maHorScroller->SetThumbPos( sal_Int32(fHor * 100.0) );
1065 0 : maVerScroller->SetThumbPos( 18000 - sal_Int32((fVer + 90.0) * 100.0) );
1066 : }
1067 0 : }
1068 :
1069 0 : void SvxLightCtl3D::move( double fDeltaHor, double fDeltaVer )
1070 : {
1071 0 : double fHor(0.0), fVer(0.0);
1072 :
1073 0 : maLightControl->GetPosition(fHor, fVer);
1074 0 : fHor += fDeltaHor;
1075 0 : fVer += fDeltaVer;
1076 :
1077 0 : if( fVer > 90.0 )
1078 0 : return;
1079 :
1080 0 : if ( fVer < -90.0 )
1081 0 : return;
1082 :
1083 0 : maLightControl->SetPosition(fHor, fVer);
1084 0 : maHorScroller->SetThumbPos( sal_Int32(fHor * 100.0) );
1085 0 : maVerScroller->SetThumbPos( 18000 - sal_Int32((fVer + 90.0) * 100.0) );
1086 :
1087 0 : if(maUserInteractiveChangeCallback.IsSet())
1088 : {
1089 0 : maUserInteractiveChangeCallback.Call(this);
1090 : }
1091 : }
1092 :
1093 0 : void SvxLightCtl3D::KeyInput( const KeyEvent& rKEvt )
1094 : {
1095 0 : const vcl::KeyCode aCode(rKEvt.GetKeyCode());
1096 :
1097 0 : if( aCode.GetModifier() )
1098 : {
1099 0 : Control::KeyInput( rKEvt );
1100 0 : return;
1101 : }
1102 :
1103 0 : switch ( aCode.GetCode() )
1104 : {
1105 : case KEY_SPACE:
1106 : {
1107 0 : break;
1108 : }
1109 : case KEY_LEFT:
1110 : {
1111 0 : move( -4.0, 0.0 ); // #i58242# changed move direction in X
1112 0 : break;
1113 : }
1114 : case KEY_RIGHT:
1115 : {
1116 0 : move( 4.0, 0.0 ); // #i58242# changed move direction in X
1117 0 : break;
1118 : }
1119 : case KEY_UP:
1120 : {
1121 0 : move( 0.0, 4.0 );
1122 0 : break;
1123 : }
1124 : case KEY_DOWN:
1125 : {
1126 0 : move( 0.0, -4.0 );
1127 0 : break;
1128 : }
1129 : case KEY_PAGEUP:
1130 : {
1131 0 : sal_Int32 nLight(maLightControl->GetSelectedLight() - 1);
1132 :
1133 0 : while((nLight >= 0) && !maLightControl->GetLightOnOff(nLight))
1134 : {
1135 0 : nLight--;
1136 : }
1137 :
1138 0 : if(nLight < 0)
1139 : {
1140 0 : nLight = 7;
1141 :
1142 0 : while((nLight >= 0) && !maLightControl->GetLightOnOff(nLight))
1143 : {
1144 0 : nLight--;
1145 : }
1146 : }
1147 :
1148 0 : if(nLight >= 0)
1149 : {
1150 0 : maLightControl->SelectLight(nLight);
1151 0 : CheckSelection();
1152 :
1153 0 : if(maUserSelectionChangeCallback.IsSet())
1154 : {
1155 0 : maUserSelectionChangeCallback.Call(this);
1156 : }
1157 : }
1158 :
1159 0 : break;
1160 : }
1161 : case KEY_PAGEDOWN:
1162 : {
1163 0 : sal_Int32 nLight(maLightControl->GetSelectedLight() - 1);
1164 :
1165 0 : while(nLight <= 7 && !maLightControl->GetLightOnOff(nLight))
1166 : {
1167 0 : nLight++;
1168 : }
1169 :
1170 0 : if(nLight > 7)
1171 : {
1172 0 : nLight = 0;
1173 :
1174 0 : while(nLight <= 7 && !maLightControl->GetLightOnOff(nLight))
1175 : {
1176 0 : nLight++;
1177 : }
1178 : }
1179 :
1180 0 : if(nLight <= 7)
1181 : {
1182 0 : maLightControl->SelectLight(nLight);
1183 0 : CheckSelection();
1184 :
1185 0 : if(maUserSelectionChangeCallback.IsSet())
1186 : {
1187 0 : maUserSelectionChangeCallback.Call(this);
1188 : }
1189 : }
1190 :
1191 0 : break;
1192 : }
1193 : default:
1194 : {
1195 0 : Control::KeyInput( rKEvt );
1196 0 : break;
1197 : }
1198 : }
1199 : }
1200 :
1201 0 : void SvxLightCtl3D::GetFocus()
1202 : {
1203 0 : Control::GetFocus();
1204 :
1205 0 : if(HasFocus() && IsEnabled())
1206 : {
1207 0 : CheckSelection();
1208 :
1209 0 : Size aFocusSize = maLightControl->GetOutputSizePixel();
1210 :
1211 0 : aFocusSize.Width() -= 4;
1212 0 : aFocusSize.Height() -= 4;
1213 :
1214 0 : Rectangle aFocusRect( Point( 2, 2 ), aFocusSize );
1215 :
1216 0 : aFocusRect = maLightControl->PixelToLogic( aFocusRect );
1217 :
1218 0 : maLightControl->ShowFocus( aFocusRect );
1219 : }
1220 0 : }
1221 :
1222 0 : void SvxLightCtl3D::LoseFocus()
1223 : {
1224 0 : Control::LoseFocus();
1225 :
1226 0 : maLightControl->HideFocus();
1227 0 : }
1228 :
1229 0 : IMPL_LINK_NOARG(SvxLightCtl3D, ScrollBarMove)
1230 : {
1231 0 : const sal_Int32 nHor(maHorScroller->GetThumbPos());
1232 0 : const sal_Int32 nVer(maVerScroller->GetThumbPos());
1233 :
1234 : maLightControl->SetPosition(
1235 : ((double)nHor) / 100.0,
1236 0 : ((double)((18000 - nVer) - 9000)) / 100.0);
1237 :
1238 0 : if(maUserInteractiveChangeCallback.IsSet())
1239 : {
1240 0 : maUserInteractiveChangeCallback.Call(this);
1241 : }
1242 :
1243 0 : return 0;
1244 : }
1245 :
1246 0 : IMPL_LINK_NOARG(SvxLightCtl3D, ButtonPress)
1247 : {
1248 0 : if(SvxPreviewObjectType::SPHERE == GetSvx3DLightControl().GetObjectType())
1249 : {
1250 0 : GetSvx3DLightControl().SetObjectType(SvxPreviewObjectType::CUBE);
1251 : }
1252 : else
1253 : {
1254 0 : GetSvx3DLightControl().SetObjectType(SvxPreviewObjectType::SPHERE);
1255 : }
1256 :
1257 0 : return 0;
1258 : }
1259 :
1260 0 : IMPL_LINK_NOARG(SvxLightCtl3D, InternalInteractiveChange)
1261 : {
1262 0 : double fHor(0.0), fVer(0.0);
1263 :
1264 0 : maLightControl->GetPosition(fHor, fVer);
1265 0 : maHorScroller->SetThumbPos( sal_Int32(fHor * 100.0) );
1266 0 : maVerScroller->SetThumbPos( 18000 - sal_Int32((fVer + 90.0) * 100.0) );
1267 :
1268 0 : if(maUserInteractiveChangeCallback.IsSet())
1269 : {
1270 0 : maUserInteractiveChangeCallback.Call(this);
1271 : }
1272 :
1273 0 : return 0;
1274 : }
1275 :
1276 0 : IMPL_LINK_NOARG(SvxLightCtl3D, InternalSelectionChange)
1277 : {
1278 0 : CheckSelection();
1279 :
1280 0 : if(maUserSelectionChangeCallback.IsSet())
1281 : {
1282 0 : maUserSelectionChangeCallback.Call(this);
1283 : }
1284 :
1285 0 : return 0;
1286 390 : }
1287 :
1288 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|