1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
20 #include "vbahyperlink.hxx"
21 #include <vbahelper/helperdecl.hxx>
22 #include <com/sun/star/container/XIndexAccess.hpp>
23 #include <com/sun/star/text/XText.hpp>
24 #include <com/sun/star/text/XTextFieldsSupplier.hpp>
25 #include <com/sun/star/container/XEnumerationAccess.hpp>
26 #include <ooo/vba/office/MsoHyperlinkType.hpp>
27 #include <ooo/vba/msforms/XShape.hpp>
28 #include "vbarange.hxx"
30 using namespace ::ooo::vba
;
31 using namespace ::com::sun::star
;
33 // ============================================================================
35 ScVbaHyperlink::ScVbaHyperlink( const uno::Sequence
< uno::Any
>& rArgs
,
36 const uno::Reference
< uno::XComponentContext
>& rxContext
) throw (lang::IllegalArgumentException
) :
37 HyperlinkImpl_BASE( getXSomethingFromArgs
< XHelperInterface
>( rArgs
, 0 ), rxContext
),
38 mxCell( getXSomethingFromArgs
< table::XCell
>( rArgs
, 1, false ) ),
39 mnType( office::MsoHyperlinkType::msoHyperlinkRange
)
41 uno::Reference
< text::XTextFieldsSupplier
> xTextFields( mxCell
, uno::UNO_QUERY_THROW
);
42 uno::Reference
< container::XIndexAccess
> xIndex( xTextFields
->getTextFields(), uno::UNO_QUERY_THROW
);
43 mxTextField
.set( xIndex
->getByIndex(0), uno::UNO_QUERY_THROW
);
46 ScVbaHyperlink::ScVbaHyperlink( const uno::Reference
< XHelperInterface
>& rxAnchor
,
47 const uno::Reference
< uno::XComponentContext
>& rxContext
,
48 const uno::Any
& rAddress
, const uno::Any
& rSubAddress
,
49 const uno::Any
& rScreenTip
, const uno::Any
& rTextToDisplay
) throw (uno::RuntimeException
) :
50 HyperlinkImpl_BASE( rxAnchor
, rxContext
) // parent of Hyperlink is the anchor object
52 // extract parameters, Address must not be empty
53 UrlComponents aUrlComp
;
54 OUString aTextToDisplay
;
55 if( !(rAddress
>>= aUrlComp
.first
) || aUrlComp
.first
.isEmpty() )
56 throw uno::RuntimeException( OUString( "Cannot get address" ), uno::Reference
< uno::XInterface
>() );
57 rSubAddress
>>= aUrlComp
.second
;
58 rScreenTip
>>= maScreenTip
;
59 rTextToDisplay
>>= aTextToDisplay
;
61 // get anchor range or anchor shape
62 uno::Reference
< excel::XRange
> xAnchorRange( rxAnchor
, uno::UNO_QUERY
);
63 if( xAnchorRange
.is() )
65 mnType
= office::MsoHyperlinkType::msoHyperlinkRange
;
66 // only single ranges are allowed
67 uno::Reference
< table::XCellRange
> xUnoRange( ScVbaRange::getCellRange( xAnchorRange
), uno::UNO_QUERY_THROW
);
68 // insert the hyperlink into the top-left cell only
69 mxCell
.set( xUnoRange
->getCellByPosition( 0, 0 ), uno::UNO_SET_THROW
);
70 uno::Reference
< text::XText
> xText( mxCell
, uno::UNO_QUERY_THROW
);
71 // use cell text or URL if no TextToDisplay has been passed
72 if( aTextToDisplay
.isEmpty() )
74 aTextToDisplay
= xText
->getString();
75 if( aTextToDisplay
.isEmpty() )
77 OUStringBuffer
aBuffer( aUrlComp
.first
);
78 if( !aUrlComp
.second
.isEmpty() )
79 aBuffer
.appendAscii( RTL_CONSTASCII_STRINGPARAM( " - " ) ).append( aUrlComp
.second
);
80 aTextToDisplay
= aBuffer
.makeStringAndClear();
83 // create and initialize a new URL text field
84 uno::Reference
< lang::XMultiServiceFactory
> xFactory( ScVbaRange::getUnoModel( xAnchorRange
), uno::UNO_QUERY_THROW
);
85 uno::Reference
< text::XTextContent
> xUrlField( xFactory
->createInstance( OUString( "com.sun.star.text.TextField.URL" ) ), uno::UNO_QUERY_THROW
);
86 mxTextField
.set( xUrlField
, uno::UNO_QUERY_THROW
);
87 setUrlComponents( aUrlComp
);
88 setTextToDisplay( aTextToDisplay
);
89 // insert the text field into the document
90 xText
->setString( OUString() );
91 uno::Reference
< text::XTextRange
> xRange( xText
->createTextCursor(), uno::UNO_QUERY_THROW
);
92 xText
->insertTextContent( xRange
, xUrlField
, false );
96 uno::Reference
< msforms::XShape
> xAnchorShape( rxAnchor
, uno::UNO_QUERY_THROW
);
97 mnType
= office::MsoHyperlinkType::msoHyperlinkShape
;
98 // FIXME: insert hyperlink into shape
99 throw uno::RuntimeException();
103 ScVbaHyperlink::~ScVbaHyperlink()
107 OUString
ScVbaHyperlink::getName() throw (uno::RuntimeException
)
109 // it seems this attribute is same as TextToDisplay
110 return getTextToDisplay();
113 void ScVbaHyperlink::setName( const OUString
& rName
) throw (uno::RuntimeException
)
115 setTextToDisplay( rName
);
118 OUString
ScVbaHyperlink::getAddress() throw (uno::RuntimeException
)
120 return getUrlComponents().first
;
123 void ScVbaHyperlink::setAddress( const OUString
& rAddress
) throw (uno::RuntimeException
)
125 UrlComponents aUrlComp
= getUrlComponents();
126 aUrlComp
.first
= rAddress
;
127 setUrlComponents( aUrlComp
);
130 OUString
ScVbaHyperlink::getSubAddress() throw (uno::RuntimeException
)
132 return getUrlComponents().second
;
135 void ScVbaHyperlink::setSubAddress( const OUString
& rSubAddress
) throw (uno::RuntimeException
)
137 UrlComponents aUrlComp
= getUrlComponents();
138 aUrlComp
.second
= rSubAddress
;
139 setUrlComponents( aUrlComp
);
142 OUString SAL_CALL
ScVbaHyperlink::getScreenTip() throw (uno::RuntimeException
)
147 void SAL_CALL
ScVbaHyperlink::setScreenTip( const OUString
& rScreenTip
) throw (uno::RuntimeException
)
149 maScreenTip
= rScreenTip
;
152 OUString
ScVbaHyperlink::getTextToDisplay() throw (uno::RuntimeException
)
155 OUString aTextToDisplay
;
156 mxTextField
->getPropertyValue( OUString( "Representation" ) ) >>= aTextToDisplay
;
157 return aTextToDisplay
;
160 void ScVbaHyperlink::setTextToDisplay( const OUString
& rTextToDisplay
) throw (uno::RuntimeException
)
163 mxTextField
->setPropertyValue( OUString( "Representation" ), uno::Any( rTextToDisplay
) );
166 sal_Int32 SAL_CALL
ScVbaHyperlink::getType() throw (uno::RuntimeException
)
171 uno::Reference
< excel::XRange
> SAL_CALL
ScVbaHyperlink::getRange() throw (uno::RuntimeException
)
173 if( mnType
== office::MsoHyperlinkType::msoHyperlinkRange
)
175 // if constructed from Hyperlinks object, range has been passed as parent
176 uno::Reference
< excel::XRange
> xAnchorRange( getParent(), uno::UNO_QUERY
);
177 if( !xAnchorRange
.is() )
179 // if constructed via service c'tor, create new range based on cell
180 uno::Reference
< table::XCellRange
> xRange( mxCell
, uno::UNO_QUERY_THROW
);
181 // FIXME: need to pass current worksheet as the parent of XRange.
182 xAnchorRange
.set( new ScVbaRange( uno::Reference
< XHelperInterface
>(), mxContext
, xRange
) );
186 // error if called at a shape Hyperlink object
187 throw uno::RuntimeException();
190 uno::Reference
< msforms::XShape
> SAL_CALL
ScVbaHyperlink::getShape() throw (uno::RuntimeException
)
192 // error if called at a range Hyperlink object
193 return uno::Reference
< msforms::XShape
>( getParent(), uno::UNO_QUERY_THROW
);
196 VBAHELPER_IMPL_XHELPERINTERFACE( ScVbaHyperlink
, "ooo.vba.excel.Hyperlink" )
198 // private --------------------------------------------------------------------
200 void ScVbaHyperlink::ensureTextField() throw (uno::RuntimeException
)
202 if( !mxTextField
.is() )
203 throw uno::RuntimeException();
206 ScVbaHyperlink::UrlComponents
ScVbaHyperlink::getUrlComponents() throw (uno::RuntimeException
)
210 mxTextField
->getPropertyValue( OUString( "URL" ) ) >>= aUrl
;
211 sal_Int32 nHashPos
= aUrl
.indexOf( '#' );
213 return UrlComponents( aUrl
, OUString() );
214 return UrlComponents( aUrl
.copy( 0, nHashPos
), aUrl
.copy( nHashPos
+ 1 ) );
217 void ScVbaHyperlink::setUrlComponents( const UrlComponents
& rUrlComp
) throw (uno::RuntimeException
)
220 OUStringBuffer
aUrl( rUrlComp
.first
);
221 if( !rUrlComp
.second
.isEmpty() )
222 aUrl
.append( sal_Unicode( '#' ) ).append( rUrlComp
.second
);
223 mxTextField
->setPropertyValue( OUString( "URL" ), uno::Any( aUrl
.makeStringAndClear() ) );
228 namespace sdecl
= comphelper::service_decl
;
229 sdecl::vba_service_class_
<ScVbaHyperlink
, sdecl::with_args
<true> > serviceImpl
;
230 extern sdecl::ServiceDecl
const serviceDecl(
233 "ooo.vba.excel.Hyperlink" );
236 // ============================================================================
238 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */