1 /**************************************************************
2 *
3 * Licensed to the Apache Software Foundation (ASF) under one
4 * or more contributor license agreements. See the NOTICE file
5 * distributed with this work for additional information
6 * regarding copyright ownership. The ASF licenses this file
7 * to you under the Apache License, Version 2.0 (the
8 * "License"); you may not use this file except in compliance
9 * with the License. You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing,
14 * software distributed under the License is distributed on an
15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16 * KIND, either express or implied. See the License for the
17 * specific language governing permissions and limitations
18 * under the License.
19 *
20 *************************************************************/
21
22
23
24 #include "precompiled_sd.hxx"
25
26 #include "PresenterTextView.hxx"
27
28 #include <i18npool/mslangid.hxx>
29 #include <cppcanvas/vclfactory.hxx>
30 #include <svl/itempool.hxx>
31 #include <svl/itemset.hxx>
32 #include <unotools/linguprops.hxx>
33 #include <unotools/lingucfg.hxx>
34 #include <editeng/colritem.hxx>
35 #include <editeng/editeng.hxx>
36 #include <editeng/editstat.hxx>
37 #include <editeng/eeitem.hxx>
38 #include <editeng/fhgtitem.hxx>
39 #include <editeng/fontitem.hxx>
40 #include <svx/xflclit.hxx>
41 #include <vcl/bitmapex.hxx>
42 #include <vcl/svapp.hxx>
43 #include <vcl/virdev.hxx>
44 #include <com/sun/star/awt/FontDescriptor.hpp>
45 #include <com/sun/star/awt/Size.hpp>
46 #include <com/sun/star/rendering/XSpriteCanvas.hpp>
47 #include <com/sun/star/util/Color.hpp>
48 #include <com/sun/star/i18n/ScriptType.hpp>
49
50
51 using namespace ::com::sun::star;
52 using namespace ::com::sun::star::uno;
53 using namespace ::com::sun::star::lang;
54 using ::rtl::OUString;
55
56 namespace sd { namespace presenter {
57
58 //===== Service ===============================================================
59
PresenterTextViewService_createInstance(const Reference<XComponentContext> & rxContext)60 Reference<XInterface> SAL_CALL PresenterTextViewService_createInstance (
61 const Reference<XComponentContext>& rxContext)
62 {
63 return Reference<XInterface>(static_cast<XWeak*>(new PresenterTextView(rxContext)));
64 }
65
66
67
68
PresenterTextViewService_getImplementationName(void)69 ::rtl::OUString PresenterTextViewService_getImplementationName (void) throw(RuntimeException)
70 {
71 return OUString::createFromAscii("com.sun.star.comp.Draw.PresenterTextView");
72 }
73
74
75
76
PresenterTextViewService_getSupportedServiceNames(void)77 Sequence<rtl::OUString> SAL_CALL PresenterTextViewService_getSupportedServiceNames (void)
78 throw (RuntimeException)
79 {
80 static const ::rtl::OUString sServiceName(
81 ::rtl::OUString::createFromAscii("com.sun.star.drawing.PresenterTextView"));
82 return Sequence<rtl::OUString>(&sServiceName, 1);
83 }
84
85
86
87 //===== PresenterTextView::Implementation =====================================
88
89 class PresenterTextView::Implementation
90 {
91 public:
92 const OUString msTextPropertyName;
93 const OUString msBitmapPropertyName;
94 const OUString msSizePropertyName;
95 const OUString msBackgroundColorPropertyName;
96 const OUString msTextColorPropertyName;
97 const OUString msFontDescriptorPropertyName;
98 const OUString msTopPropertyName;
99 const OUString msTopRelativePropertyName;
100 const OUString msTotalHeightPropertyName;
101
102 Implementation (void);
103 ~Implementation (void);
104
105 void SetCanvas (const cppcanvas::CanvasSharedPtr& rCanvas);
106 void SetSize (const Size aSize);
107 void SetBackgroundColor (const Color aColor);
108 void SetTextColor (const Color aColor);
109 void SetFontDescriptor (const awt::FontDescriptor& rFontDescriptor);
110 sal_Int32 GetTop (void) const;
111 void SetTop (const sal_Int32 nTop);
112 void SetText (const OUString& Text);
113 sal_Int32 ParseDistance (const OUString& rsDistance) const;
114 Reference<rendering::XBitmap> GetBitmap (void);
115 sal_Int32 GetTotalHeight (void);
116
117 private:
118 Reference<rendering::XBitmap> mxBitmap;
119 cppcanvas::CanvasSharedPtr mpCanvas;
120 VirtualDevice* mpOutputDevice;
121 EditEngine* mpEditEngine;
122 SfxItemPool* mpEditEngineItemPool;
123 Size maSize;
124 Color maBackgroundColor;
125 Color maTextColor;
126 String msText;
127 sal_Int32 mnTop;
128 sal_Int32 mnTotalHeight;
129
130 EditEngine * GetEditEngine (void);
131 EditEngine* CreateEditEngine (void);
132 void CheckTop (void);
133 };
134
135
136
137
138 //===== PresenterTextView =====================================================
139
PresenterTextView(const Reference<XComponentContext> & rxContext)140 PresenterTextView::PresenterTextView (const Reference<XComponentContext>& rxContext)
141 : PresenterTextViewInterfaceBase(),
142 mpImplementation(new Implementation())
143 {
144 (void)rxContext;
145 }
146
147
148
149
~PresenterTextView(void)150 PresenterTextView::~PresenterTextView (void)
151 {
152 }
153
154
155
156
disposing(void)157 void SAL_CALL PresenterTextView::disposing (void)
158 {
159 mpImplementation.reset();
160 }
161
162
163
164
165 //----- XInitialization -------------------------------------------------------
166
initialize(const Sequence<Any> & rArguments)167 void SAL_CALL PresenterTextView::initialize (const Sequence<Any>& rArguments)
168 throw (Exception, RuntimeException)
169 {
170 ThrowIfDisposed();
171
172 if (rArguments.getLength() == 1)
173 {
174 try
175 {
176 Reference<rendering::XBitmapCanvas> xCanvas (rArguments[0], UNO_QUERY_THROW);
177 if (xCanvas.is())
178 {
179 mpImplementation->SetCanvas(
180 cppcanvas::VCLFactory::getInstance().createCanvas(xCanvas));
181 }
182 }
183 catch (RuntimeException&)
184 {
185 throw;
186 }
187 }
188 else
189 {
190 throw RuntimeException(
191 OUString::createFromAscii("PresenterTextView: invalid number of arguments"),
192 static_cast<XWeak*>(this));
193 }
194 }
195
196
197
198
199 //-----------------------------------------------------------------------------
200
GetPropertyValue(const OUString & rsPropertyName)201 Any PresenterTextView::GetPropertyValue (const OUString& rsPropertyName)
202 {
203 ThrowIfDisposed();
204
205 if (rsPropertyName == mpImplementation->msBitmapPropertyName)
206 {
207 return Any(mpImplementation->GetBitmap());
208 }
209 else if (rsPropertyName == mpImplementation->msTopPropertyName)
210 {
211 return Any(mpImplementation->GetTop());
212 }
213 else if (rsPropertyName == mpImplementation->msTotalHeightPropertyName)
214 {
215 return Any(mpImplementation->GetTotalHeight());
216 }
217
218 return Any();
219 }
220
221
222
223
SetPropertyValue(const::rtl::OUString & rsPropertyName,const css::uno::Any & rValue)224 Any PresenterTextView::SetPropertyValue (
225 const ::rtl::OUString& rsPropertyName,
226 const css::uno::Any& rValue)
227 {
228 ThrowIfDisposed();
229
230 Any aOldValue;
231 if (rsPropertyName == mpImplementation->msTextPropertyName)
232 {
233 OUString sText;
234 if (rValue >>= sText)
235 mpImplementation->SetText(sText);
236 }
237 else if (rsPropertyName == mpImplementation->msSizePropertyName)
238 {
239 awt::Size aSize;
240 if (rValue >>= aSize)
241 mpImplementation->SetSize(Size(aSize.Width,aSize.Height));
242 }
243 else if (rsPropertyName == mpImplementation->msBackgroundColorPropertyName)
244 {
245 util::Color aColor = util::Color();
246 if (rValue >>= aColor)
247 mpImplementation->SetBackgroundColor(Color(aColor));
248 }
249 else if (rsPropertyName == mpImplementation->msTextColorPropertyName)
250 {
251 util::Color aColor = util::Color();
252 if (rValue >>= aColor)
253 mpImplementation->SetTextColor(Color(aColor));
254 }
255 else if (rsPropertyName == mpImplementation->msFontDescriptorPropertyName)
256 {
257 awt::FontDescriptor aFontDescriptor;
258 if (rValue >>= aFontDescriptor)
259 mpImplementation->SetFontDescriptor(aFontDescriptor);
260 }
261 else if (rsPropertyName == mpImplementation->msTopPropertyName)
262 {
263 sal_Int32 nTop = 0;
264 if (rValue >>= nTop)
265 mpImplementation->SetTop(nTop);
266 }
267 else if (rsPropertyName == mpImplementation->msTopRelativePropertyName)
268 {
269 OUString sDistance;
270 if (rValue >>= sDistance)
271 mpImplementation->SetTop(
272 mpImplementation->GetTop()
273 + mpImplementation->ParseDistance(sDistance));
274 }
275 return aOldValue;
276 }
277
278
279
280
ThrowIfDisposed(void)281 void PresenterTextView::ThrowIfDisposed (void)
282 throw (::com::sun::star::lang::DisposedException)
283 {
284 if (PresenterTextViewInterfaceBase::rBHelper.bDisposed
285 || PresenterTextViewInterfaceBase::rBHelper.bInDispose
286 || mpImplementation.get()==NULL)
287 {
288 throw lang::DisposedException (
289 ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(
290 "PresenterTextView object has already been disposed")),
291 static_cast<uno::XWeak*>(this));
292 }
293 }
294
295
296
297
298 //===== PresenterTextView::Implementation =====================================
299
Implementation(void)300 PresenterTextView::Implementation::Implementation (void)
301 : msTextPropertyName(OUString::createFromAscii("Text")),
302 msBitmapPropertyName(OUString::createFromAscii("Bitmap")),
303 msSizePropertyName(OUString::createFromAscii("Size")),
304 msBackgroundColorPropertyName(OUString::createFromAscii("BackgroundColor")),
305 msTextColorPropertyName(OUString::createFromAscii("TextColor")),
306 msFontDescriptorPropertyName(OUString::createFromAscii("FontDescriptor")),
307 msTopPropertyName(OUString::createFromAscii("Top")),
308 msTopRelativePropertyName(OUString::createFromAscii("RelativeTop")),
309 msTotalHeightPropertyName(OUString::createFromAscii("TotalHeight")),
310 mxBitmap(),
311 mpCanvas(),
312 mpOutputDevice(new VirtualDevice(*Application::GetDefaultDevice(), 0, 0)),
313 mpEditEngine(NULL),
314 mpEditEngineItemPool(EditEngine::CreatePool()),
315 maSize(100,100),
316 maBackgroundColor(0xffffffff),
317 maTextColor(0x00000000),
318 msText(),
319 mnTop(0),
320 mnTotalHeight(-1)
321 {
322 mpOutputDevice->SetMapMode(MAP_PIXEL);
323
324 GetEditEngine();
325 }
326
327
328
329
~Implementation(void)330 PresenterTextView::Implementation::~Implementation (void)
331 {
332 delete mpEditEngine;
333 SfxItemPool::Free(mpEditEngineItemPool);
334 delete mpOutputDevice;
335 }
336
337
338
339
GetEditEngine(void)340 EditEngine * PresenterTextView::Implementation::GetEditEngine (void)
341 {
342 if (mpEditEngine == NULL)
343 mpEditEngine = CreateEditEngine ();
344 return mpEditEngine;
345 }
346
347
348
349
CreateEditEngine(void)350 EditEngine* PresenterTextView::Implementation::CreateEditEngine (void)
351 {
352 EditEngine* pEditEngine = mpEditEngine;
353 if (pEditEngine == NULL)
354 {
355 //
356 // set fonts to be used
357 //
358 SvtLinguOptions aOpt;
359 SvtLinguConfig().GetOptions( aOpt );
360 //
361 struct FontDta {
362 sal_Int16 nFallbackLang;
363 sal_Int16 nLang;
364 sal_uInt16 nFontType;
365 sal_uInt16 nFontInfoId;
366 } aTable[3] =
367 {
368 // info to get western font to be used
369 { LANGUAGE_ENGLISH_US, LANGUAGE_NONE,
370 DEFAULTFONT_SERIF, EE_CHAR_FONTINFO },
371 // info to get CJK font to be used
372 { LANGUAGE_JAPANESE, LANGUAGE_NONE,
373 DEFAULTFONT_CJK_TEXT, EE_CHAR_FONTINFO_CJK },
374 // info to get CTL font to be used
375 { LANGUAGE_ARABIC_SAUDI_ARABIA, LANGUAGE_NONE,
376 DEFAULTFONT_CTL_TEXT, EE_CHAR_FONTINFO_CTL }
377 };
378 aTable[0].nLang = MsLangId::resolveSystemLanguageByScriptType(aOpt.nDefaultLanguage, ::com::sun::star::i18n::ScriptType::LATIN);
379 aTable[1].nLang = MsLangId::resolveSystemLanguageByScriptType(aOpt.nDefaultLanguage_CJK, ::com::sun::star::i18n::ScriptType::ASIAN);
380 aTable[2].nLang = MsLangId::resolveSystemLanguageByScriptType(aOpt.nDefaultLanguage_CTL, ::com::sun::star::i18n::ScriptType::COMPLEX);
381 //
382 for (int i = 0; i < 3; ++i)
383 {
384 const FontDta &rFntDta = aTable[i];
385 LanguageType nLang = (LANGUAGE_NONE == rFntDta.nLang) ?
386 rFntDta.nFallbackLang : rFntDta.nLang;
387 Font aFont = Application::GetDefaultDevice()->GetDefaultFont(
388 rFntDta.nFontType, nLang, DEFAULTFONT_FLAGS_ONLYONE);
389 mpEditEngineItemPool->SetPoolDefaultItem(
390 SvxFontItem(
391 aFont.GetFamily(),
392 aFont.GetName(),
393 aFont.GetStyleName(),
394 aFont.GetPitch(),
395 aFont.GetCharSet(),
396 rFntDta.nFontInfoId));
397 }
398
399
400 pEditEngine = new EditEngine (mpEditEngineItemPool);
401
402 pEditEngine->EnableUndo (sal_True);
403 pEditEngine->SetDefTab (sal_uInt16(
404 Application::GetDefaultDevice()->GetTextWidth(
405 UniString::CreateFromAscii("XXXX"))));
406
407 pEditEngine->SetControlWord(
408 (pEditEngine->GetControlWord()
409 | EE_CNTRL_AUTOINDENTING) &
410 (~EE_CNTRL_UNDOATTRIBS) &
411 (~EE_CNTRL_PASTESPECIAL));
412
413 pEditEngine->SetWordDelimiters (
414 UniString::CreateFromAscii(" .=+-*/(){}[];\""));
415 pEditEngine->SetRefMapMode (MAP_PIXEL);
416 pEditEngine->SetPaperSize (Size(800, 0));
417 pEditEngine->EraseVirtualDevice();
418 pEditEngine->ClearModifyFlag();
419 }
420
421 return pEditEngine;
422 }
423
424
425
426
SetCanvas(const cppcanvas::CanvasSharedPtr & rpCanvas)427 void PresenterTextView::Implementation::SetCanvas (const cppcanvas::CanvasSharedPtr& rpCanvas)
428 {
429 mpCanvas = rpCanvas;
430 mxBitmap = NULL;
431 }
432
433
434
435
SetSize(const Size aSize)436 void PresenterTextView::Implementation::SetSize (const Size aSize)
437 {
438 DBG_ASSERT(mpEditEngine!=NULL, "EditEngine missing");
439
440 maSize = aSize;
441 mpEditEngine->SetPaperSize(maSize);
442 mnTotalHeight = -1;
443 mxBitmap = NULL;
444 }
445
446
447
448
SetBackgroundColor(const Color aColor)449 void PresenterTextView::Implementation::SetBackgroundColor (const Color aColor)
450 {
451 maBackgroundColor = aColor;
452 mxBitmap = NULL;
453
454 DBG_ASSERT(mpEditEngine!=NULL, "EditEngine missing");
455 DBG_ASSERT(mpEditEngineItemPool!=NULL, "EditEngineItemPool missing");
456 mpEditEngine->SetBackgroundColor(aColor);
457 mpEditEngine->EnableAutoColor(sal_False);
458 mpEditEngine->ForceAutoColor(sal_False);
459 }
460
461
462
463
SetTextColor(const Color aColor)464 void PresenterTextView::Implementation::SetTextColor (const Color aColor)
465 {
466 maTextColor = aColor;
467 mxBitmap = NULL;
468
469 DBG_ASSERT(mpEditEngineItemPool!=NULL, "EditEngineItemPool missing");
470 mpEditEngineItemPool->SetPoolDefaultItem(SvxColorItem(aColor, EE_CHAR_COLOR));
471 }
472
473
474
475
SetFontDescriptor(const awt::FontDescriptor & rFontDescriptor)476 void PresenterTextView::Implementation::SetFontDescriptor (
477 const awt::FontDescriptor& rFontDescriptor)
478 {
479 mxBitmap = NULL;
480
481 DBG_ASSERT(mpEditEngineItemPool!=NULL, "EditEngineItemPool missing");
482
483 const sal_Int32 nFontHeight = rFontDescriptor.Height;
484
485 SvxFontHeightItem aFontHeight(
486 Application::GetDefaultDevice()->LogicToPixel(
487 Size(0, nFontHeight), MapMode (MAP_POINT)).Height(),
488 100,
489 EE_CHAR_FONTHEIGHT);
490 mpEditEngineItemPool->SetPoolDefaultItem( aFontHeight);
491 aFontHeight.SetWhich (EE_CHAR_FONTHEIGHT_CJK);
492 mpEditEngineItemPool->SetPoolDefaultItem( aFontHeight);
493 aFontHeight.SetWhich (EE_CHAR_FONTHEIGHT_CTL);
494 mpEditEngineItemPool->SetPoolDefaultItem( aFontHeight);
495
496 SvxFontItem aSvxFontItem (EE_CHAR_FONTINFO);
497 aSvxFontItem.SetFamilyName( rFontDescriptor.Name );
498 mpEditEngineItemPool->SetPoolDefaultItem(aSvxFontItem);
499
500 mnTotalHeight = -1;
501 mxBitmap = NULL;
502
503 CheckTop();
504 mnTotalHeight = -1;
505 }
506
507
508
509
GetTop(void) const510 sal_Int32 PresenterTextView::Implementation::GetTop (void) const
511 {
512 return mnTop;
513 }
514
515
516
517
SetTop(const sal_Int32 nTop)518 void PresenterTextView::Implementation::SetTop (const sal_Int32 nTop)
519 {
520 if (nTop == mnTop)
521 return;
522
523 mnTop = nTop;
524 mxBitmap = NULL;
525 CheckTop();
526 }
527
528
529
530
SetText(const OUString & rText)531 void PresenterTextView::Implementation::SetText (const OUString& rText)
532 {
533 DBG_ASSERT(mpEditEngine!=NULL, "EditEngine missing");
534 msText = rText;
535 mpEditEngine->SetPaperSize(maSize);
536 mnTotalHeight = -1;
537 mxBitmap = NULL;
538 }
539
540
541
542
ParseDistance(const OUString & rsDistance) const543 sal_Int32 PresenterTextView::Implementation::ParseDistance (const OUString& rsDistance) const
544 {
545 DBG_ASSERT(mpEditEngine!=NULL, "EditEngine missing");
546 sal_Int32 nDistance (0);
547 if (rsDistance.endsWithAsciiL("px", 2))
548 {
549 nDistance = rsDistance.copy(0,rsDistance.getLength()-2).toInt32();
550 }
551 else if (rsDistance.endsWithAsciiL("l", 1))
552 {
553 const sal_Int32 nLines (rsDistance.copy(0,rsDistance.getLength()-1).toInt32());
554 // Take the height of the first line as the height of every line.
555 const sal_uInt32 nFirstLineHeight (mpEditEngine->GetLineHeight(0,0));
556 nDistance = nFirstLineHeight * nLines;
557 }
558
559 return nDistance;
560 }
561
562
563
564
GetBitmap(void)565 Reference<rendering::XBitmap> PresenterTextView::Implementation::GetBitmap (void)
566 {
567 DBG_ASSERT(mpEditEngine!=NULL, "EditEngine missing");
568
569 if ( ! mxBitmap.is())
570 {
571 if (mpOutputDevice != NULL)
572 delete mpOutputDevice;
573 mpOutputDevice = new VirtualDevice(*Application::GetDefaultDevice(), 0, 0);
574 mpOutputDevice->SetMapMode(MAP_PIXEL);
575 mpOutputDevice->SetOutputSizePixel(maSize, sal_True);
576 mpOutputDevice->SetLineColor();
577 mpOutputDevice->SetFillColor();
578 mpOutputDevice->SetBackground(Wallpaper());
579 mpOutputDevice->Erase();
580
581 MapMode aMapMode (mpOutputDevice->GetMapMode());
582 aMapMode.SetOrigin(Point(0,0));
583 mpOutputDevice->SetMapMode(aMapMode);
584 const Rectangle aWindowBox (Point(0,0), maSize);
585 mpOutputDevice->DrawRect(aWindowBox);
586
587 mpEditEngine->Clear();
588 mpEditEngine->SetText(msText);
589 mpEditEngine->SetPaperSize(maSize);
590
591 mpEditEngine->Draw(mpOutputDevice, aWindowBox, Point(0,mnTop));
592
593 const BitmapEx aBitmap (mpOutputDevice->GetBitmapEx(Point(0,0), maSize));
594 mxBitmap = cppcanvas::VCLFactory::getInstance().createBitmap(
595 mpCanvas,
596 aBitmap
597 )->getUNOBitmap();
598 }
599 return mxBitmap;
600 }
601
602
603
604
GetTotalHeight(void)605 sal_Int32 PresenterTextView::Implementation::GetTotalHeight (void)
606 {
607 DBG_ASSERT(mpEditEngine!=NULL, "EditEngine missing");
608
609 if (mnTotalHeight < 0)
610 {
611 if ( ! mxBitmap.is())
612 GetBitmap();
613 mnTotalHeight = mpEditEngine->GetTextHeight();
614 }
615 return mnTotalHeight;
616 }
617
618
619
620
CheckTop(void)621 void PresenterTextView::Implementation::CheckTop (void)
622 {
623 DBG_ASSERT(mpEditEngine!=NULL, "EditEngine missing");
624
625 if (mnTotalHeight < 0)
626 mnTotalHeight = mpEditEngine->GetTextHeight();
627 if (mpEditEngine!=NULL && mnTop >= mnTotalHeight)
628 mnTop = mnTotalHeight - mpEditEngine->GetLineHeight(0,0);
629
630 if (mnTotalHeight < maSize.Height())
631 mnTop = 0;
632
633 if (mnTotalHeight - mnTop < maSize.Height())
634 mnTop = mnTotalHeight - maSize.Height();
635
636 if (mnTop < 0)
637 mnTop = 0;
638 }
639
640
641 } } // end of namespace ::sd::presenter
642