xref: /aoo41x/main/cui/source/dialogs/hlmarkwn.cxx (revision cdf0e10c)
1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 
28 // MARKER(update_precomp.py): autogen include statement, do not remove
29 #include "precompiled_cui.hxx"
30 
31 #include <vcl/wrkwin.hxx>
32 #include <dialmgr.hxx>
33 #include <sfx2/docfile.hxx>
34 #include <vcl/svapp.hxx>
35 #include <vcl/settings.hxx>
36 
37 // UNO-Stuff
38 #include <comphelper/processfactory.hxx>
39 #include <com/sun/star/awt/XBitmap.hpp>
40 #include <com/sun/star/frame/XDesktop.hpp>
41 #include <com/sun/star/frame/XDesktop.hpp>
42 #include <com/sun/star/frame/XComponentLoader.hpp>
43 #include <com/sun/star/beans/PropertyValue.hpp>
44 #include <com/sun/star/document/XLinkTargetSupplier.hpp>
45 #include <com/sun/star/beans/XPropertySet.hpp>
46 
47 #include <toolkit/unohlp.hxx>
48 
49 #include <cuires.hrc>
50 #include "hlmarkwn.hrc"
51 #include "hlmarkwn.hxx"
52 #include "hltpbase.hxx"
53 
54 using namespace ::com::sun::star;
55 using namespace ::rtl;
56 
57 /*************************************************************************
58 |*
59 |* Userdata-struct for tree-entries
60 |*
61 |************************************************************************/
62 
63 struct TargetData
64 {
65 	OUString		aUStrLinkname;
66 	sal_Bool		bIsTarget;
67 
68 	TargetData ( OUString aUStrLName, sal_Bool bTarget )
69 		:	bIsTarget ( bTarget )
70 	{
71 		if ( bIsTarget )
72 			aUStrLinkname = aUStrLName;
73 	}
74 };
75 
76 
77 //########################################################################
78 //#                                                                      #
79 //# Tree-Window 														 #
80 //#                                                                      #
81 //########################################################################
82 
83 SvxHlmarkTreeLBox::SvxHlmarkTreeLBox( Window* pParent, const ResId& rResId )
84 : SvTreeListBox	( pParent, rResId ),
85   mpParentWnd	( (SvxHlinkDlgMarkWnd*) pParent )
86 {
87 	SetNodeDefaultImages();
88 }
89 
90 void SvxHlmarkTreeLBox::Paint( const Rectangle& rRect )
91 {
92 	if( mpParentWnd->mnError == LERR_NOERROR )
93 	{
94 		SvTreeListBox::Paint(rRect);
95 	}
96 	else
97 	{
98 		Erase();
99 
100 		Rectangle aDrawRect( Point( 0, 0 ), GetSizePixel() );
101 
102 		String aStrMessage;
103 
104 		switch( mpParentWnd->mnError )
105 		{
106 		case LERR_NOENTRIES :
107 			aStrMessage = CUI_RESSTR( RID_SVXSTR_HYPDLG_ERR_LERR_NOENTRIES );
108 			break;
109 		case LERR_DOCNOTOPEN :
110 			aStrMessage = CUI_RESSTR( RID_SVXSTR_HYPDLG_ERR_LERR_DOCNOTOPEN );
111 			break;
112 		}
113 
114 		DrawText( aDrawRect, aStrMessage, TEXT_DRAW_LEFT | TEXT_DRAW_MULTILINE | TEXT_DRAW_WORDBREAK );
115 	}
116 
117 }
118 
119 //########################################################################
120 //#                                                                      #
121 //# Window-Class														 #
122 //#                                                                      #
123 //########################################################################
124 
125 /*************************************************************************
126 |*
127 |* Contructor / Destructor
128 |*
129 |************************************************************************/
130 
131 SvxHlinkDlgMarkWnd::SvxHlinkDlgMarkWnd( SvxHyperlinkTabPageBase *pParent )
132 :	ModalDialog( (Window*)pParent, CUI_RES ( RID_SVXFLOAT_HYPERLINK_MARKWND ) ),
133 	maBtApply( this, CUI_RES (BT_APPLY) ),
134 	maBtClose( this, CUI_RES (BT_CLOSE) ),
135 	maLbTree ( this, CUI_RES (TLB_MARK) ),
136 	mbUserMoved ( sal_False ),
137 	mbFirst	    ( sal_True ),
138 	mpParent	( pParent ),
139 	mnError		( LERR_NOERROR )
140 {
141 	FreeResource();
142 
143 	maBtApply.SetClickHdl		( LINK ( this, SvxHlinkDlgMarkWnd, ClickApplyHdl_Impl ) );
144 	maBtClose.SetClickHdl		( LINK ( this, SvxHlinkDlgMarkWnd, ClickCloseHdl_Impl ) );
145 	maLbTree.SetDoubleClickHdl	( LINK ( this, SvxHlinkDlgMarkWnd, ClickApplyHdl_Impl ) );
146 
147 	// Tree-ListBox mit Linien versehen
148 	maLbTree.SetStyle( maLbTree.GetStyle() | WB_TABSTOP | WB_BORDER | WB_HASLINES |
149 							WB_HASBUTTONS |  //WB_HASLINESATROOT |
150 							WB_HSCROLL | WB_HASBUTTONSATROOT );
151 
152     maLbTree.SetAccessibleName(String(CUI_RES(STR_MARK_TREE)));
153 
154 }
155 
156 SvxHlinkDlgMarkWnd::~SvxHlinkDlgMarkWnd()
157 {
158 	ClearTree();
159 }
160 
161 /*************************************************************************
162 |*
163 |* Set an errorstatus
164 |*
165 |************************************************************************/
166 
167 sal_uInt16 SvxHlinkDlgMarkWnd::SetError( sal_uInt16 nError)
168 {
169 	sal_uInt16 nOldError = mnError;
170 	mnError = nError;
171 
172 	if( mnError != LERR_NOERROR )
173 		ClearTree();
174 
175 	maLbTree.Invalidate();
176 
177 	return nOldError;
178 }
179 
180 /*************************************************************************
181 |*
182 |* Move window
183 |*
184 |************************************************************************/
185 
186 sal_Bool SvxHlinkDlgMarkWnd::MoveTo ( Point aNewPos )
187 {
188 	if ( !mbUserMoved )
189 	{
190 		sal_Bool bOldStatus = mbUserMoved;
191 		SetPosPixel ( aNewPos );
192 		mbUserMoved = bOldStatus;
193 	}
194 
195 	return mbUserMoved;
196 }
197 
198 void SvxHlinkDlgMarkWnd::Move ()
199 {
200 	Window::Move();
201 
202 	if ( IsReallyVisible() )
203 		mbUserMoved = sal_True;
204 }
205 
206 sal_Bool SvxHlinkDlgMarkWnd::ConnectToDialog( sal_Bool bDoit )
207 {
208 	sal_Bool bOldStatus = mbUserMoved;
209 
210 	mbUserMoved = !bDoit;
211 
212 	return bOldStatus;
213 }
214 
215 /*************************************************************************
216 |*
217 |* Interface to refresh tree
218 |*
219 |************************************************************************/
220 
221 void SvxHlinkDlgMarkWnd::RefreshTree ( String aStrURL )
222 {
223     String aEmptyStr;
224 	OUString aUStrURL;
225 
226 	EnterWait();
227 
228 	ClearTree();
229 
230 	xub_StrLen nPos = aStrURL.Search ( sal_Unicode('#') );
231 
232 	if( nPos != 0 )
233 		aUStrURL = ::rtl::OUString( aStrURL );
234 
235 	if( !RefreshFromDoc ( aUStrURL ) )
236 		maLbTree.Invalidate();
237 
238 	if ( nPos != STRING_NOTFOUND )
239 	{
240 		String aStrMark = aStrURL.Copy ( nPos+1 );
241 		SelectEntry ( aStrMark );
242 	}
243 
244 	LeaveWait();
245 
246 	maStrLastURL = aStrURL;
247 }
248 
249 /*************************************************************************
250 |*
251 |* get links from document
252 |*
253 |************************************************************************/
254 
255 sal_Bool SvxHlinkDlgMarkWnd::RefreshFromDoc( OUString aURL )
256 {
257 	mnError = LERR_NOERROR;
258 
259 	uno::Reference< lang::XMultiServiceFactory > xFactory( ::comphelper::getProcessServiceFactory() );
260 	if( xFactory.is() )
261 	{
262 		uno::Reference< frame::XDesktop > xDesktop( xFactory->createInstance( OUString::createFromAscii( "com.sun.star.frame.Desktop" ) ),
263 					uno::UNO_QUERY );
264 		if( xDesktop.is() )
265 		{
266 			uno::Reference< lang::XComponent > xComp;
267 
268 			if( aURL.getLength() )
269 			{
270 				// load from url
271 				uno::Reference< frame::XComponentLoader > xLoader( xDesktop, uno::UNO_QUERY );
272 				if( xLoader.is() )
273 				{
274 					try
275 					{
276 						uno::Sequence< beans::PropertyValue > aArg(1);
277 						aArg.getArray()[0].Name = OUString::createFromAscii( "Hidden" );
278 						aArg.getArray()[0].Value <<= (sal_Bool) sal_True;
279 						xComp = xLoader->loadComponentFromURL( aURL, OUString::createFromAscii( "_blank" ), 0, aArg );
280 					}
281 					catch( const io::IOException& )
282 					{
283 
284 					}
285 					catch( const lang::IllegalArgumentException& )
286 					{
287 
288 					}
289 				}
290 			}
291 			else
292 			{
293 				// the component with user focus ( current document )
294 				xComp = xDesktop->getCurrentComponent();
295 			}
296 
297 			if( xComp.is() )
298 			{
299 				uno::Reference< document::XLinkTargetSupplier > xLTS( xComp, uno::UNO_QUERY );
300 
301 				if( xLTS.is() )
302 				{
303 					if( FillTree( xLTS->getLinks() ) == 0 )
304 						mnError = LERR_NOENTRIES;
305 				}
306 				else
307 					mnError = LERR_DOCNOTOPEN;
308 
309 				if ( aURL.getLength() )
310 					xComp->dispose();
311 			}
312 			else
313 			{
314 				if( aURL.getLength() )
315 					mnError=LERR_DOCNOTOPEN;
316 			}
317 		}
318 	}
319 	return (mnError==0);
320 }
321 /*
322 void SvxHlinkDlgMarkWnd::Error(int nNr)
323 {
324 	switch(nNr)
325 	{
326 		case 0:
327 		{
328 			Rectangle aDrawRect( Point( 0, 0 ), maLbTree.GetSizePixel() );
329 			//maLbTree.SetTextColor( Color(COL_BLACK) );
330 			//maLbTree.DrawText( aDrawRect, "Keine Ziele im Dokument vorhanden.", TEXT_DRAW_LEFT);// | TEXT_DRAW_MULTILINE | TEXT_DRAW_WORDBREAK );
331 			maLbTree.DrawText( Point(0,0), "Keine Ziele im Dokument vorhanden.");
332 			maLbTree.DrawLine(aDrawRect.TopLeft(), aDrawRect.BottomRight() );
333 		}
334 		break;
335 		case 1:
336 			Rectangle aDrawRect( Point( 0, 0 ), maLbTree.GetSizePixel() );
337 			maLbTree.DrawText( aDrawRect, "Das Dokument konnte nicht ge�ffnet werden.", TEXT_DRAW_LEFT | TEXT_DRAW_MULTILINE | TEXT_DRAW_WORDBREAK );
338 			break;
339 	}
340 }
341 */
342 /*************************************************************************
343 |*
344 |* Fill Tree-Control
345 |*
346 |************************************************************************/
347 
348 int SvxHlinkDlgMarkWnd::FillTree( uno::Reference< container::XNameAccess > xLinks, SvLBoxEntry* pParentEntry )
349 {
350 	int nEntries=0;
351 	const uno::Sequence< OUString > aNames( xLinks->getElementNames() );
352 	const sal_uLong nLinks = aNames.getLength();
353 	const OUString* pNames = aNames.getConstArray();
354 
355     Color aMaskColor( COL_LIGHTMAGENTA );
356 	const OUString aProp_LinkDisplayName( RTL_CONSTASCII_USTRINGPARAM( "LinkDisplayName" ) );
357 	const OUString aProp_LinkTarget( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.document.LinkTarget" ) );
358 	const OUString aProp_LinkDisplayBitmap( RTL_CONSTASCII_USTRINGPARAM( "LinkDisplayBitmap" ) );
359 	for( sal_uLong i = 0; i < nLinks; i++ )
360 	{
361 		uno::Any aAny;
362 		OUString aLink( *pNames++ );
363 
364 		sal_Bool bError = sal_False;
365 		try
366 		{
367 			aAny = xLinks->getByName( aLink );
368 		}
369 		catch(const uno::Exception&)
370 		{
371 			// if the name of the target was invalid (like empty headings)
372 			// no object can be provided
373 			bError = sal_True;
374 		}
375 		if(bError)
376 			continue;
377 
378 		uno::Reference< beans::XPropertySet > xTarget;
379 
380 		if( aAny >>= xTarget )
381 		{
382 			try
383 			{
384 				// get name to display
385 				aAny = xTarget->getPropertyValue( aProp_LinkDisplayName );
386 				OUString aDisplayName;
387 				aAny >>= aDisplayName;
388 				String aStrDisplayname ( aDisplayName );
389 
390 				// is it a target ?
391 				uno::Reference< lang::XServiceInfo > xSI( xTarget, uno::UNO_QUERY );
392 				sal_Bool bIsTarget = xSI->supportsService( aProp_LinkTarget );
393 
394 				// create userdata
395 				TargetData *pData = new TargetData ( aLink, bIsTarget );
396 
397 				SvLBoxEntry* pEntry;
398 
399 				try
400 				{
401 					// get bitmap for the tree-entry
402 					uno::Reference< awt::XBitmap > aXBitmap( xTarget->getPropertyValue( aProp_LinkDisplayBitmap ), uno::UNO_QUERY );
403 					if( aXBitmap.is() )
404 					{
405                         Image aBmp( VCLUnoHelper::GetBitmap( aXBitmap ).GetBitmap(), aMaskColor );
406                         // insert Displayname into treelist with bitmaps
407 						pEntry = maLbTree.InsertEntry ( aStrDisplayname,
408                                                         aBmp, aBmp,
409 														pParentEntry,
410 														sal_False, LIST_APPEND,
411 														(void*)pData );
412                         maLbTree.SetExpandedEntryBmp( pEntry, aBmp, BMP_COLOR_HIGHCONTRAST );
413                         maLbTree.SetCollapsedEntryBmp( pEntry, aBmp, BMP_COLOR_HIGHCONTRAST );
414                         nEntries++;
415 					}
416 					else
417 					{
418 						// insert Displayname into treelist without bitmaps
419 						pEntry = maLbTree.InsertEntry ( aStrDisplayname,
420 														pParentEntry,
421 														sal_False, LIST_APPEND,
422 														(void*)pData );
423 						nEntries++;
424 					}
425 				}
426 				catch(const com::sun::star::uno::Exception&)
427 				{
428 					// insert Displayname into treelist without bitmaps
429 					pEntry = maLbTree.InsertEntry ( aStrDisplayname,
430 													pParentEntry,
431 													sal_False, LIST_APPEND,
432 													(void*)pData );
433 					nEntries++;
434 				}
435 
436 				uno::Reference< document::XLinkTargetSupplier > xLTS( xTarget, uno::UNO_QUERY );
437 				if( xLTS.is() )
438 					nEntries += FillTree( xLTS->getLinks(), pEntry );
439 			}
440 			catch(const com::sun::star::uno::Exception&)
441 			{
442 			}
443 		}
444 	}
445 
446 	return nEntries;
447 }
448 
449 /*************************************************************************
450 |*
451 |* Clear Tree
452 |*
453 |************************************************************************/
454 
455 void SvxHlinkDlgMarkWnd::ClearTree()
456 {
457 	SvLBoxEntry* pEntry = maLbTree.First();
458 
459 	while ( pEntry )
460 	{
461 		TargetData* pUserData = ( TargetData * ) pEntry->GetUserData();
462 		delete pUserData;
463 
464 		pEntry = maLbTree.Next( pEntry );
465 	}
466 
467 	maLbTree.Clear();
468 }
469 
470 /*************************************************************************
471 |*
472 |* Find Entry for Strng
473 |*
474 |************************************************************************/
475 
476 SvLBoxEntry* SvxHlinkDlgMarkWnd::FindEntry ( String aStrName )
477 {
478 	sal_Bool bFound=sal_False;
479 	SvLBoxEntry* pEntry = maLbTree.First();
480 
481 	while ( pEntry && !bFound )
482 	{
483 		TargetData* pUserData = ( TargetData * ) pEntry->GetUserData ();
484 		if ( aStrName == String( pUserData->aUStrLinkname ) )
485 			bFound = sal_True;
486 		else
487 			pEntry = maLbTree.Next( pEntry );
488 	}
489 
490 	return pEntry;
491 }
492 
493 /*************************************************************************
494 |*
495 |* Select Entry
496 |*
497 |************************************************************************/
498 
499 void SvxHlinkDlgMarkWnd::SelectEntry ( String aStrMark )
500 {
501 	SvLBoxEntry* pEntry = FindEntry ( aStrMark );
502 	if ( pEntry )
503 	{
504 		maLbTree.Select ( pEntry );
505 		maLbTree.MakeVisible ( pEntry );
506 	}
507 }
508 
509 /*************************************************************************
510 |*
511 |* Click on Apply-Button / Doubleclick on item in tree
512 |*
513 |************************************************************************/
514 
515 IMPL_LINK ( SvxHlinkDlgMarkWnd, ClickApplyHdl_Impl, void *, EMPTYARG )
516 {
517 	SvLBoxEntry* pEntry = maLbTree.GetCurEntry();
518 
519 	if ( pEntry )
520 	{
521 		TargetData *pData = ( TargetData * )pEntry->GetUserData();
522 
523 		if ( pData->bIsTarget )
524 		{
525 			String aStrMark ( pData->aUStrLinkname );
526 			mpParent->SetMarkStr ( aStrMark );
527 		}
528 	}
529 
530 	return( 0L );
531 }
532 
533 /*************************************************************************
534 |*
535 |* Click on Close-Button
536 |*
537 |************************************************************************/
538 
539 IMPL_LINK ( SvxHlinkDlgMarkWnd, ClickCloseHdl_Impl, void *, EMPTYARG )
540 {
541     Close();
542 
543 	return( 0L );
544 }
545 
546 
547