diff options
Diffstat (limited to 'fpicker/source/office')
25 files changed, 10143 insertions, 0 deletions
diff --git a/fpicker/source/office/OfficeControlAccess.cxx b/fpicker/source/office/OfficeControlAccess.cxx new file mode 100644 index 000000000000..50e99f2b590b --- /dev/null +++ b/fpicker/source/office/OfficeControlAccess.cxx @@ -0,0 +1,789 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_fpicker.hxx" + +#include "OfficeControlAccess.hxx" +#include <com/sun/star/ui/dialogs/ExtendedFilePickerElementIds.hpp> +#include <com/sun/star/ui/dialogs/CommonFilePickerElementIds.hpp> +#include <com/sun/star/ui/dialogs/ControlActions.hpp> +#include <vcl/lstbox.hxx> +#include <com/sun/star/uno/Sequence.hxx> +#include <tools/urlobj.hxx> + +#include <algorithm> +#include <functional> + +//......................................................................... +namespace svt +{ +//......................................................................... + + // helper ------------------------------------------------------------- + + using namespace ::com::sun::star::uno; + using namespace ::com::sun::star::lang; + using namespace ::com::sun::star::ui::dialogs; + + using namespace ExtendedFilePickerElementIds; + using namespace CommonFilePickerElementIds; + using namespace InternalFilePickerElementIds; + + // -------------------------------------------------------------------- + namespace + { + // ---------------------------------------------------------------- + #define PROPERTY_FLAG_TEXT 0x00000001 + #define PROPERTY_FLAG_ENDBALED 0x00000002 + #define PROPERTY_FLAG_VISIBLE 0x00000004 + #define PROPERTY_FLAG_HELPURL 0x00000008 + #define PROPERTY_FLAG_LISTITEMS 0x00000010 + #define PROPERTY_FLAG_SELECTEDITEM 0x00000020 + #define PROPERTY_FLAG_SELECTEDITEMINDEX 0x00000040 + #define PROPERTY_FLAG_CHECKED 0x00000080 + + // ---------------------------------------------------------------- + // ................................................................ + struct ControlDescription + { + const sal_Char* pControlName; + sal_Int16 nControlId; + sal_Int32 nPropertyFlags; + }; + + // ................................................................ + typedef const ControlDescription* ControlDescIterator; + typedef ::std::pair< ControlDescIterator, ControlDescIterator > ControlDescRange; + + // ...................................................................... + #define PROPERTY_FLAGS_COMMON ( PROPERTY_FLAG_ENDBALED | PROPERTY_FLAG_VISIBLE | PROPERTY_FLAG_HELPURL ) + #define PROPERTY_FLAGS_LISTBOX ( PROPERTY_FLAG_LISTITEMS | PROPERTY_FLAG_SELECTEDITEM | PROPERTY_FLAG_SELECTEDITEMINDEX ) + #define PROPERTY_FLAGS_CHECKBOX ( PROPERTY_FLAG_CHECKED | PROPERTY_FLAG_TEXT ) + + // Note: this array MUST be sorted by name! + static const ControlDescription aDescriptions[] = { + { "AutoExtensionBox", CHECKBOX_AUTOEXTENSION, PROPERTY_FLAGS_COMMON | PROPERTY_FLAGS_CHECKBOX }, + { "CancelButton", PUSHBUTTON_CANCEL, PROPERTY_FLAGS_COMMON | PROPERTY_FLAG_TEXT }, + { "CurrentFolderText", FIXEDTEXT_CURRENTFOLDER, PROPERTY_FLAGS_COMMON | PROPERTY_FLAG_TEXT }, + { "DefaultLocationButton", TOOLBOXBUTOON_DEFAULT_LOCATION, PROPERTY_FLAGS_COMMON }, + { "FileURLEdit", EDIT_FILEURL, PROPERTY_FLAGS_COMMON | PROPERTY_FLAG_TEXT }, + { "FileURLEditLabel", EDIT_FILEURL_LABEL, PROPERTY_FLAGS_COMMON | PROPERTY_FLAG_TEXT }, + { "FileView", CONTROL_FILEVIEW, PROPERTY_FLAGS_COMMON }, + { "FilterList", LISTBOX_FILTER, PROPERTY_FLAGS_COMMON }, + { "FilterListLabel", LISTBOX_FILTER_LABEL, PROPERTY_FLAGS_COMMON | PROPERTY_FLAG_TEXT }, + { "FilterOptionsBox", CHECKBOX_FILTEROPTIONS, PROPERTY_FLAGS_COMMON | PROPERTY_FLAGS_CHECKBOX }, + { "HelpButton", PUSHBUTTON_HELP, PROPERTY_FLAGS_COMMON | PROPERTY_FLAG_TEXT }, + { "ImageTemplateList", LISTBOX_IMAGE_TEMPLATE, PROPERTY_FLAGS_COMMON | PROPERTY_FLAGS_LISTBOX }, + { "ImageTemplateListLabel", LISTBOX_IMAGE_TEMPLATE_LABEL, PROPERTY_FLAGS_COMMON | PROPERTY_FLAG_TEXT }, + { "LevelUpButton", TOOLBOXBUTOON_LEVEL_UP, PROPERTY_FLAGS_COMMON }, + { "LinkBox", CHECKBOX_LINK, PROPERTY_FLAGS_COMMON | PROPERTY_FLAGS_CHECKBOX }, + { "NewFolderButton", TOOLBOXBUTOON_NEW_FOLDER, PROPERTY_FLAGS_COMMON }, + { "OkButton", PUSHBUTTON_OK , PROPERTY_FLAGS_COMMON | PROPERTY_FLAG_TEXT }, + { "PasswordBox", CHECKBOX_PASSWORD, PROPERTY_FLAGS_COMMON | PROPERTY_FLAGS_CHECKBOX }, + { "PlayButton", PUSHBUTTON_PLAY, PROPERTY_FLAGS_COMMON | PROPERTY_FLAG_TEXT }, + { "PreviewBox", CHECKBOX_PREVIEW, PROPERTY_FLAGS_COMMON | PROPERTY_FLAGS_CHECKBOX }, + { "ReadOnlyBox", CHECKBOX_READONLY, PROPERTY_FLAGS_COMMON | PROPERTY_FLAGS_CHECKBOX }, + { "SelectionBox", CHECKBOX_SELECTION, PROPERTY_FLAGS_COMMON | PROPERTY_FLAGS_CHECKBOX }, + { "TemplateList", LISTBOX_TEMPLATE, PROPERTY_FLAGS_COMMON | PROPERTY_FLAGS_LISTBOX }, + { "TemplateListLabel", LISTBOX_TEMPLATE_LABEL, PROPERTY_FLAGS_COMMON | PROPERTY_FLAG_TEXT }, + { "VersionList", LISTBOX_VERSION, PROPERTY_FLAGS_COMMON | PROPERTY_FLAGS_LISTBOX }, + { "VersionListLabel", LISTBOX_VERSION_LABEL, PROPERTY_FLAGS_COMMON | PROPERTY_FLAG_TEXT } + }; + + // ................................................................ + static const sal_Int32 s_nControlCount = sizeof( aDescriptions ) / sizeof( aDescriptions[0] ); + + static ControlDescIterator s_pControls = aDescriptions; + static ControlDescIterator s_pControlsEnd = aDescriptions + s_nControlCount; + + // ................................................................ + struct ControlDescriptionLookup + { + bool operator()( const ::rtl::OUString& _rLookup, const ControlDescription& _rDesc ) + { + return _rLookup.compareToAscii( _rDesc.pControlName ) < 0; + } + bool operator()( const ControlDescription& _rDesc, const ::rtl::OUString& _rLookup ) + { + return _rLookup.compareToAscii( _rDesc.pControlName ) > 0; + } + }; + + // ................................................................ + struct ExtractControlName : public ::std::unary_function< ControlDescription, ::rtl::OUString > + { + ::rtl::OUString operator()( const ControlDescription& _rDesc ) + { + return ::rtl::OUString::createFromAscii( _rDesc.pControlName ); + } + }; + + // ---------------------------------------------------------------- + // ................................................................ + struct ControlProperty + { + const sal_Char* pPropertyName; + sal_Int16 nPropertyId; + }; + + typedef const ControlProperty* ControlPropertyIterator; + + // ................................................................ + static const ControlProperty aProperties[] = { + { "Text", PROPERTY_FLAG_TEXT }, + { "Enabled", PROPERTY_FLAG_ENDBALED }, + { "Visible", PROPERTY_FLAG_VISIBLE }, + { "HelpURL", PROPERTY_FLAG_HELPURL }, + { "ListItems", PROPERTY_FLAG_LISTITEMS }, + { "SelectedItem", PROPERTY_FLAG_SELECTEDITEM }, + { "SelectedItemIndex", PROPERTY_FLAG_SELECTEDITEMINDEX }, + { "Checked", PROPERTY_FLAG_CHECKED } + }; + + // ................................................................ + static const int s_nPropertyCount = sizeof( aProperties ) / sizeof( aProperties[0] ); + + static ControlPropertyIterator s_pProperties = aProperties; + static ControlPropertyIterator s_pPropertiesEnd = aProperties + s_nPropertyCount; + + // ................................................................ + struct ControlPropertyLookup + { + ::rtl::OUString m_sLookup; + ControlPropertyLookup( const ::rtl::OUString& _rLookup ) : m_sLookup( _rLookup ) { } + + sal_Bool operator()( const ControlProperty& _rProp ) + { + return m_sLookup.equalsAscii( _rProp.pPropertyName ); + } + }; + + //----------------------------------------------------------------- + void lcl_throwIllegalArgumentException( ) SAL_THROW( (IllegalArgumentException) ) + { + throw IllegalArgumentException(); + // TODO: error message in the exception + } + } + + //--------------------------------------------------------------------- + OControlAccess::OControlAccess( IFilePickerController* _pController, SvtFileView* _pFileView ) + :m_pFilePickerController( _pController ) + ,m_pFileView( _pFileView ) + { + DBG_ASSERT( m_pFilePickerController, "OControlAccess::OControlAccess: invalid control locator!" ); + } + + //--------------------------------------------------------------------- + void OControlAccess::setHelpURL( Window* _pControl, const ::rtl::OUString& sHelpURL, sal_Bool _bFileView ) + { + rtl::OUString sHelpID( sHelpURL ); + INetURLObject aHID( sHelpURL ); + if ( aHID.GetProtocol() == INET_PROT_HID ) + sHelpID = aHID.GetURLPath(); + + // URLs should always be UTF8 encoded and escaped + rtl::OString sID( rtl::OUStringToOString( sHelpID, RTL_TEXTENCODING_UTF8 ) ); + if ( _bFileView ) + // the file view "overloaded" the SetHelpId + static_cast< SvtFileView* >( _pControl )->SetHelpId( sID ); + else + _pControl->SetHelpId( sID ); + } + + //--------------------------------------------------------------------- + ::rtl::OUString OControlAccess::getHelpURL( Window* _pControl, sal_Bool _bFileView ) + { + rtl::OString aHelpId = _pControl->GetHelpId(); + if ( _bFileView ) + // the file view "overloaded" the SetHelpId + aHelpId = static_cast< SvtFileView* >( _pControl )->GetHelpId( ); + + ::rtl::OUString sHelpURL; + ::rtl::OUString aTmp( rtl::OStringToOUString( aHelpId, RTL_TEXTENCODING_UTF8 ) ); + INetURLObject aHID( aTmp ); + if ( aHID.GetProtocol() == INET_PROT_NOT_VALID ) + sHelpURL = rtl::OUString::createFromAscii( INET_HID_SCHEME ); + sHelpURL += aTmp; + return sHelpURL; + } + + // -------------------------------------------------------------------------- + Any OControlAccess::getControlProperty( const ::rtl::OUString& _rControlName, const ::rtl::OUString& _rControlProperty ) + { + // look up the control + sal_Int16 nControlId = -1; + sal_Int32 nPropertyMask = 0; + Control* pControl = implGetControl( _rControlName, &nControlId, &nPropertyMask ); + // will throw an IllegalArgumentException if the name is not valid + + // look up the property + ControlPropertyIterator aPropDesc = ::std::find_if( s_pProperties, s_pPropertiesEnd, ControlPropertyLookup( _rControlProperty ) ); + if ( aPropDesc == s_pPropertiesEnd ) + // it's a completely unknown property + lcl_throwIllegalArgumentException(); + + if ( 0 == ( nPropertyMask & aPropDesc->nPropertyId ) ) + // it's a property which is known, but not allowed for this control + lcl_throwIllegalArgumentException(); + + return implGetControlProperty( pControl, aPropDesc->nPropertyId ); + } + + //--------------------------------------------------------------------- + Control* OControlAccess::implGetControl( const ::rtl::OUString& _rControlName, sal_Int16* _pId, sal_Int32* _pPropertyMask ) const SAL_THROW( (IllegalArgumentException) ) + { + Control* pControl = NULL; + + // translate the name into an id + ControlDescRange aFoundRange = ::std::equal_range( s_pControls, s_pControlsEnd, _rControlName, ControlDescriptionLookup() ); + if ( aFoundRange.first != aFoundRange.second ) + { + // get the VCL control determined by this id + pControl = m_pFilePickerController->getControl( aFoundRange.first->nControlId ); + } + + // if not found 'til here, the name is invalid, or we do not have the control in the current mode + if ( !pControl ) + lcl_throwIllegalArgumentException(); + + // out parameters and outta here + if ( _pId ) + *_pId = aFoundRange.first->nControlId; + if ( _pPropertyMask ) + *_pPropertyMask = aFoundRange.first->nPropertyFlags; + + return pControl; + } + + //--------------------------------------------------------------------- + void OControlAccess::setControlProperty( const ::rtl::OUString& _rControlName, const ::rtl::OUString& _rControlProperty, const ::com::sun::star::uno::Any& _rValue ) + { + // look up the control + sal_Int16 nControlId = -1; + Control* pControl = implGetControl( _rControlName, &nControlId ); + // will throw an IllegalArgumentException if the name is not valid + + // look up the property + ControlPropertyIterator aPropDesc = ::std::find_if( s_pProperties, s_pPropertiesEnd, ControlPropertyLookup( _rControlProperty ) ); + if ( aPropDesc == s_pPropertiesEnd ) + lcl_throwIllegalArgumentException(); + + // set the property + implSetControlProperty( nControlId, pControl, aPropDesc->nPropertyId, _rValue, sal_False ); + } + + // -------------------------------------------------------------------------- + Sequence< ::rtl::OUString > OControlAccess::getSupportedControls( ) + { + Sequence< ::rtl::OUString > aControls( s_nControlCount ); + ::rtl::OUString* pControls = aControls.getArray(); + + // collect the names of all _actually_existent_ controls + for ( ControlDescIterator aControl = s_pControls; aControl != s_pControlsEnd; ++aControl ) + { + if ( m_pFilePickerController->getControl( aControl->nControlId ) ) + *pControls++ = ::rtl::OUString::createFromAscii( aControl->pControlName ); + } + + aControls.realloc( pControls - aControls.getArray() ); + return aControls; + } + + // -------------------------------------------------------------------------- + Sequence< ::rtl::OUString > OControlAccess::getSupportedControlProperties( const ::rtl::OUString& _rControlName ) + { + sal_Int16 nControlId = -1; + sal_Int32 nPropertyMask = 0; + implGetControl( _rControlName, &nControlId, &nPropertyMask ); + // will throw an IllegalArgumentException if the name is not valid + + // fill in the property names + Sequence< ::rtl::OUString > aProps( s_nPropertyCount ); + ::rtl::OUString* pProperty = aProps.getArray(); + + for ( ControlPropertyIterator aProp = s_pProperties; aProp != s_pPropertiesEnd; ++aProp ) + if ( 0 != ( nPropertyMask & aProp->nPropertyId ) ) + *pProperty++ = ::rtl::OUString::createFromAscii( aProp->pPropertyName ); + + aProps.realloc( pProperty - aProps.getArray() ); + return aProps; + } + + // -------------------------------------------------------------------------- + sal_Bool OControlAccess::isControlSupported( const ::rtl::OUString& _rControlName ) + { + return ::std::binary_search( s_pControls, s_pControlsEnd, _rControlName, ControlDescriptionLookup() ); + } + + // -------------------------------------------------------------------------- + sal_Bool OControlAccess::isControlPropertySupported( const ::rtl::OUString& _rControlName, const ::rtl::OUString& _rControlProperty ) + { + // look up the control + sal_Int16 nControlId = -1; + sal_Int32 nPropertyMask = 0; + implGetControl( _rControlName, &nControlId, &nPropertyMask ); + // will throw an IllegalArgumentException if the name is not valid + + // look up the property + ControlPropertyIterator aPropDesc = ::std::find_if( s_pProperties, s_pPropertiesEnd, ControlPropertyLookup( _rControlProperty ) ); + if ( aPropDesc == s_pPropertiesEnd ) + // it's a property which is completely unknown + return sal_False; + + return 0 != ( aPropDesc->nPropertyId & nPropertyMask ); + } + + //----------------------------------------------------------------------------- + void OControlAccess::setValue( sal_Int16 _nControlId, sal_Int16 _nControlAction, const Any& _rValue ) + { + Control* pControl = m_pFilePickerController->getControl( _nControlId ); + DBG_ASSERT( pControl, "OControlAccess::SetValue: don't have this control in the current mode!" ); + if ( pControl ) + { + sal_Int16 nPropertyId = -1; + if ( ControlActions::SET_HELP_URL == _nControlAction ) + { + nPropertyId = PROPERTY_FLAG_HELPURL; + } + else + { + switch ( _nControlId ) + { + case CHECKBOX_AUTOEXTENSION: + case CHECKBOX_PASSWORD: + case CHECKBOX_FILTEROPTIONS: + case CHECKBOX_READONLY: + case CHECKBOX_LINK: + case CHECKBOX_PREVIEW: + case CHECKBOX_SELECTION: + nPropertyId = PROPERTY_FLAG_CHECKED; + break; + + case LISTBOX_FILTER: + DBG_ERRORFILE( "Use the XFilterManager to access the filter listbox" ); + break; + + case LISTBOX_VERSION: + case LISTBOX_TEMPLATE: + case LISTBOX_IMAGE_TEMPLATE: + if ( ControlActions::SET_SELECT_ITEM == _nControlAction ) + { + nPropertyId = PROPERTY_FLAG_SELECTEDITEMINDEX; + } + else + { + DBG_ASSERT( WINDOW_LISTBOX == pControl->GetType(), "OControlAccess::SetValue: implGetControl returned nonsense!" ); + implDoListboxAction( static_cast< ListBox* >( pControl ), _nControlAction, _rValue ); + } + break; + } + } + + if ( -1 != nPropertyId ) + implSetControlProperty( _nControlId, pControl, nPropertyId, _rValue ); + } + } + + //----------------------------------------------------------------------------- + Any OControlAccess::getValue( sal_Int16 _nControlId, sal_Int16 _nControlAction ) const + { + Any aRet; + + Control* pControl = m_pFilePickerController->getControl( _nControlId, sal_False ); + DBG_ASSERT( pControl, "OControlAccess::GetValue: don't have this control in the current mode!" ); + if ( pControl ) + { + sal_Int16 nPropertyId = -1; + if ( ControlActions::SET_HELP_URL == _nControlAction ) + { + nPropertyId = PROPERTY_FLAG_HELPURL; + } + else + { + switch ( _nControlId ) + { + case CHECKBOX_AUTOEXTENSION: + case CHECKBOX_PASSWORD: + case CHECKBOX_FILTEROPTIONS: + case CHECKBOX_READONLY: + case CHECKBOX_LINK: + case CHECKBOX_PREVIEW: + case CHECKBOX_SELECTION: + nPropertyId = PROPERTY_FLAG_CHECKED; + break; + + case LISTBOX_FILTER: + if ( ControlActions::GET_SELECTED_ITEM == _nControlAction ) + { + aRet <<= ::rtl::OUString( m_pFilePickerController->getCurFilter() );; + } + else + { + DBG_ERRORFILE( "Use the XFilterManager to access the filter listbox" ); + } + break; + + case LISTBOX_VERSION: + case LISTBOX_TEMPLATE: + case LISTBOX_IMAGE_TEMPLATE: + switch ( _nControlAction ) + { + case ControlActions::GET_SELECTED_ITEM: + nPropertyId = PROPERTY_FLAG_SELECTEDITEM; + break; + case ControlActions::GET_SELECTED_ITEM_INDEX: + nPropertyId = PROPERTY_FLAG_SELECTEDITEMINDEX; + break; + case ControlActions::GET_ITEMS: + nPropertyId = PROPERTY_FLAG_LISTITEMS; + break; + default: + DBG_ERRORFILE( "OControlAccess::GetValue: invalid control action for the listbox!" ); + break; + } + break; + } + } + + if ( -1 != nPropertyId ) + aRet = implGetControlProperty( pControl, nPropertyId ); + } + + return aRet; + } + + //----------------------------------------------------------------------------- + void OControlAccess::setLabel( sal_Int16 nId, const ::rtl::OUString &rLabel ) + { + Control* pControl = m_pFilePickerController->getControl( nId, sal_True ); + DBG_ASSERT( pControl, "OControlAccess::GetValue: don't have this control in the current mode!" ); + if ( pControl ) + pControl->SetText( rLabel ); + } + + //----------------------------------------------------------------------------- + ::rtl::OUString OControlAccess::getLabel( sal_Int16 nId ) const + { + ::rtl::OUString sLabel; + + Control* pControl = m_pFilePickerController->getControl( nId, sal_True ); + DBG_ASSERT( pControl, "OControlAccess::GetValue: don't have this control in the current mode!" ); + if ( pControl ) + sLabel = pControl->GetText(); + + return sLabel; + } + + //----------------------------------------------------------------------------- + void OControlAccess::enableControl( sal_Int16 _nId, sal_Bool _bEnable ) + { + m_pFilePickerController->enableControl( _nId, _bEnable ); + } + + // ----------------------------------------------------------------------- + void OControlAccess::implDoListboxAction( ListBox* _pListbox, sal_Int16 _nControlAction, const Any& _rValue ) + { + switch ( _nControlAction ) + { + case ControlActions::ADD_ITEM: + { + ::rtl::OUString aEntry; + _rValue >>= aEntry; + if ( aEntry.getLength() ) + _pListbox->InsertEntry( aEntry ); + } + break; + + case ControlActions::ADD_ITEMS: + { + Sequence < ::rtl::OUString > aTemplateList; + _rValue >>= aTemplateList; + + if ( aTemplateList.getLength() ) + { + for ( long i=0; i < aTemplateList.getLength(); i++ ) + _pListbox->InsertEntry( aTemplateList[i] ); + } + } + break; + + case ControlActions::DELETE_ITEM: + { + sal_Int32 nPos = 0; + if ( _rValue >>= nPos ) + _pListbox->RemoveEntry( (USHORT) nPos ); + } + break; + + case ControlActions::DELETE_ITEMS: + _pListbox->Clear(); + break; + + default: + DBG_ERRORFILE( "Wrong ControlAction for implDoListboxAction()" ); + } + } + + //----------------------------------------------------------------------------- + void OControlAccess::implSetControlProperty( sal_Int16 _nControlId, Control* _pControl, sal_Int16 _nProperty, const Any& _rValue, sal_Bool _bIgnoreIllegalArgument ) + { + if ( !_pControl ) + _pControl = m_pFilePickerController->getControl( _nControlId ); + DBG_ASSERT( _pControl, "OControlAccess::implSetControlProperty: invalid argument, this will crash!" ); + if ( !_pControl ) + return; + + DBG_ASSERT( _pControl == m_pFilePickerController->getControl( _nControlId ), + "OControlAccess::implSetControlProperty: inconsistent parameters!" ); + + switch ( _nProperty ) + { + case PROPERTY_FLAG_TEXT: + { + ::rtl::OUString sText; + if ( _rValue >>= sText ) + { + _pControl->SetText( sText ); + } + else if ( !_bIgnoreIllegalArgument ) + { + lcl_throwIllegalArgumentException(); + } + } + break; + + case PROPERTY_FLAG_ENDBALED: + { + sal_Bool bEnabled = sal_False; + if ( _rValue >>= bEnabled ) + { + m_pFilePickerController->enableControl( _nControlId, bEnabled ); + } + else if ( !_bIgnoreIllegalArgument ) + { + lcl_throwIllegalArgumentException(); + } + } + break; + + case PROPERTY_FLAG_VISIBLE: + { + sal_Bool bVisible = sal_False; + if ( _rValue >>= bVisible ) + { + _pControl->Show( bVisible ); + } + else if ( !_bIgnoreIllegalArgument ) + { + lcl_throwIllegalArgumentException(); + } + } + break; + + case PROPERTY_FLAG_HELPURL: + { + ::rtl::OUString sHelpURL; + if ( _rValue >>= sHelpURL ) + { + setHelpURL( _pControl, sHelpURL, m_pFileView == _pControl ); + } + else if ( !_bIgnoreIllegalArgument ) + { + lcl_throwIllegalArgumentException(); + } + } + break; + + case PROPERTY_FLAG_LISTITEMS: + { + DBG_ASSERT( WINDOW_LISTBOX == _pControl->GetType(), + "OControlAccess::implSetControlProperty: invalid control/property combination!" ); + + Sequence< ::rtl::OUString > aItems; + if ( _rValue >>= aItems ) + { + // remove all previous items + static_cast< ListBox* >( _pControl )->Clear(); + + // add the new ones + const ::rtl::OUString* pItems = aItems.getConstArray(); + const ::rtl::OUString* pItemsEnd = aItems.getConstArray() + aItems.getLength(); + for ( const ::rtl::OUString* pItem = pItems; + pItem != pItemsEnd; + ++pItem + ) + { + static_cast< ListBox* >( _pControl )->InsertEntry( *pItem ); + } + + } + else if ( !_bIgnoreIllegalArgument ) + { + lcl_throwIllegalArgumentException(); + } + } + break; + + case PROPERTY_FLAG_SELECTEDITEM: + { + DBG_ASSERT( WINDOW_LISTBOX == _pControl->GetType(), + "OControlAccess::implSetControlProperty: invalid control/property combination!" ); + + ::rtl::OUString sSelected; + if ( _rValue >>= sSelected ) + { + static_cast< ListBox* >( _pControl )->SelectEntry( sSelected ); + } + else if ( !_bIgnoreIllegalArgument ) + { + lcl_throwIllegalArgumentException(); + } + } + break; + + case PROPERTY_FLAG_SELECTEDITEMINDEX: + { + DBG_ASSERT( WINDOW_LISTBOX == _pControl->GetType(), + "OControlAccess::implSetControlProperty: invalid control/property combination!" ); + + sal_Int32 nPos = 0; + if ( _rValue >>= nPos ) + { + static_cast< ListBox* >( _pControl )->SelectEntryPos( (USHORT) nPos ); + } + else if ( !_bIgnoreIllegalArgument ) + { + lcl_throwIllegalArgumentException(); + } + } + break; + + case PROPERTY_FLAG_CHECKED: + { + DBG_ASSERT( WINDOW_CHECKBOX == _pControl->GetType(), + "OControlAccess::implSetControlProperty: invalid control/property combination!" ); + + sal_Bool bChecked = sal_False; + if ( _rValue >>= bChecked ) + { + static_cast< CheckBox* >( _pControl )->Check( bChecked ); + } + else if ( !_bIgnoreIllegalArgument ) + { + lcl_throwIllegalArgumentException(); + } + } + break; + + default: + DBG_ERROR( "OControlAccess::implSetControlProperty: invalid property id!" ); + } + } + + //----------------------------------------------------------------------------- + Any OControlAccess::implGetControlProperty( Control* _pControl, sal_Int16 _nProperty ) const + { + DBG_ASSERT( _pControl, "OControlAccess::implGetControlProperty: invalid argument, this will crash!" ); + + Any aReturn; + switch ( _nProperty ) + { + case PROPERTY_FLAG_TEXT: + aReturn <<= ::rtl::OUString( _pControl->GetText() ); + break; + + case PROPERTY_FLAG_ENDBALED: + aReturn <<= (sal_Bool)_pControl->IsEnabled(); + break; + + case PROPERTY_FLAG_VISIBLE: + aReturn <<= (sal_Bool)_pControl->IsVisible(); + break; + + case PROPERTY_FLAG_HELPURL: + aReturn <<= getHelpURL( _pControl, m_pFileView == _pControl ); + break; + + case PROPERTY_FLAG_LISTITEMS: + { + DBG_ASSERT( WINDOW_LISTBOX == _pControl->GetType(), + "OControlAccess::implGetControlProperty: invalid control/property combination!" ); + + Sequence< ::rtl::OUString > aItems( static_cast< ListBox* >( _pControl )->GetEntryCount() ); + ::rtl::OUString* pItems = aItems.getArray(); + for ( USHORT i=0; i<static_cast< ListBox* >( _pControl )->GetEntryCount(); ++i ) + *pItems++ = static_cast< ListBox* >( _pControl )->GetEntry( i ); + + aReturn <<= aItems; + } + break; + + case PROPERTY_FLAG_SELECTEDITEM: + { + DBG_ASSERT( WINDOW_LISTBOX == _pControl->GetType(), + "OControlAccess::implGetControlProperty: invalid control/property combination!" ); + + USHORT nSelected = static_cast< ListBox* >( _pControl )->GetSelectEntryPos(); + ::rtl::OUString sSelected; + if ( LISTBOX_ENTRY_NOTFOUND != nSelected ) + sSelected = static_cast< ListBox* >( _pControl )->GetSelectEntry(); + aReturn <<= sSelected; + } + break; + + case PROPERTY_FLAG_SELECTEDITEMINDEX: + { + DBG_ASSERT( WINDOW_LISTBOX == _pControl->GetType(), + "OControlAccess::implGetControlProperty: invalid control/property combination!" ); + + USHORT nSelected = static_cast< ListBox* >( _pControl )->GetSelectEntryPos(); + if ( LISTBOX_ENTRY_NOTFOUND != nSelected ) + aReturn <<= (sal_Int32)static_cast< ListBox* >( _pControl )->GetSelectEntryPos(); + else + aReturn <<= (sal_Int32)-1; + } + break; + + case PROPERTY_FLAG_CHECKED: + DBG_ASSERT( WINDOW_CHECKBOX == _pControl->GetType(), + "OControlAccess::implGetControlProperty: invalid control/property combination!" ); + + aReturn <<= (sal_Bool)static_cast< CheckBox* >( _pControl )->IsChecked( ); + break; + + default: + DBG_ERROR( "OControlAccess::implGetControlProperty: invalid property id!" ); + } + return aReturn; + } + +//......................................................................... +} // namespace svt +//......................................................................... + diff --git a/fpicker/source/office/OfficeControlAccess.hxx b/fpicker/source/office/OfficeControlAccess.hxx new file mode 100644 index 000000000000..35196907f900 --- /dev/null +++ b/fpicker/source/office/OfficeControlAccess.hxx @@ -0,0 +1,125 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +#ifndef SVTOOLS_CONTROLACCESS_HXX +#define SVTOOLS_CONTROLACCESS_HXX + +#include <svtools/fileview.hxx> +#include <vcl/lstbox.hxx> +#include <com/sun/star/lang/IllegalArgumentException.hpp> +#include "pickercallbacks.hxx" + +//......................................................................... +namespace svt +{ +//......................................................................... + + // -------------------------------------------------------------------- + namespace InternalFilePickerElementIds + { + static const sal_Int16 PUSHBUTTON_HELP = (sal_Int16)0x1000; + static const sal_Int16 TOOLBOXBUTOON_DEFAULT_LOCATION = (sal_Int16)0x1001; + static const sal_Int16 TOOLBOXBUTOON_LEVEL_UP = (sal_Int16)0x1002; + static const sal_Int16 TOOLBOXBUTOON_NEW_FOLDER = (sal_Int16)0x1003; + static const sal_Int16 FIXEDTEXT_CURRENTFOLDER = (sal_Int16)0x1004; + } + + // -------------------------------------------------------------------- + /** implements the XControlAccess, XControlInformation and XFilePickerControlAccess for the file picker + */ + class OControlAccess + { + IFilePickerController* m_pFilePickerController; + SvtFileView* m_pFileView; + + public: + OControlAccess( IFilePickerController* _pController, SvtFileView* _pFileView ); + + // XControlAccess implementation + void setControlProperty( const ::rtl::OUString& _rControlName, const ::rtl::OUString& _rControlProperty, const ::com::sun::star::uno::Any& _rValue ); + ::com::sun::star::uno::Any getControlProperty( const ::rtl::OUString& _rControlName, const ::rtl::OUString& _rControlProperty ); + + // XControlInformation implementation + ::com::sun::star::uno::Sequence< ::rtl::OUString > getSupportedControls( ); + ::com::sun::star::uno::Sequence< ::rtl::OUString > getSupportedControlProperties( const ::rtl::OUString& _rControlName ); + sal_Bool isControlSupported( const ::rtl::OUString& _rControlName ); + sal_Bool isControlPropertySupported( const ::rtl::OUString& _rControlName, const ::rtl::OUString& _rControlProperty ); + + // XFilePickerControlAccess + void setValue( sal_Int16 _nId, sal_Int16 _nCtrlAction, const ::com::sun::star::uno::Any& _rValue ); + ::com::sun::star::uno::Any getValue( sal_Int16 _nId, sal_Int16 _nCtrlAction ) const; + void setLabel( sal_Int16 _nId, const ::rtl::OUString& _rValue ); + ::rtl::OUString getLabel( sal_Int16 _nId ) const; + void enableControl( sal_Int16 _nId, sal_Bool _bEnable ); + + static void setHelpURL( Window* _pControl, const ::rtl::OUString& _rURL, sal_Bool _bFileView ); + static ::rtl::OUString getHelpURL( Window* _pControl, sal_Bool _bFileView ); + + private: + /** implements the various methods for setting properties on controls + + @param _nControlId + the id of the control + @param _pControl + the affected control. Must be the same as referred by <arg>_nControlId</arg>, or NULL. + @param _nProperty + the property to set + See PROPERTY_FLAG_* + @param _rValue + the value to set + @param _bIgnoreIllegalArgument + if <FALSE/>, an exception will be thrown if the given value is of improper type + */ + void implSetControlProperty( + sal_Int16 _nControlId, + Control* _pControl, sal_Int16 _nProperty, const ::com::sun::star::uno::Any& _rValue, + sal_Bool _bIgnoreIllegalArgument = sal_True ); + + Control* implGetControl( const ::rtl::OUString& _rControlName, sal_Int16* _pId = NULL, sal_Int32* _pPropertyMask = NULL ) const SAL_THROW( (::com::sun::star::lang::IllegalArgumentException) ); + + /** implements the various methods for retrieving properties from controls + + @param _pControl + the affected control + @PRECOND not <NULL/> + @param _nProperty + the property to retrieve + See PROPERTY_FLAG_* + @return + */ + ::com::sun::star::uno::Any implGetControlProperty( Control* _pControl, sal_Int16 _nProperty ) const; + + void implDoListboxAction( ListBox* _pListbox, sal_Int16 _nCtrlAction, const ::com::sun::star::uno::Any& _rValue ); + + }; + +//......................................................................... +} // namespace svt +//......................................................................... + +#endif // SVTOOLS_CONTROLACCESS_HXX + diff --git a/fpicker/source/office/OfficeFilePicker.cxx b/fpicker/source/office/OfficeFilePicker.cxx new file mode 100644 index 000000000000..516c62fe7580 --- /dev/null +++ b/fpicker/source/office/OfficeFilePicker.cxx @@ -0,0 +1,1186 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_fpicker.hxx" + +#include "OfficeFilePicker.hxx" +#include "iodlg.hxx" + +#ifndef _LIST_ +#include <list> +#endif +#ifndef _FUNCTIONAL_ +#include <functional> +#endif +#ifndef _ALGORITHM_ +#include <algorithm> +#endif +#include <tools/urlobj.hxx> +#include <tools/debug.hxx> +#define _SVSTDARR_STRINGSDTOR +#include "svl/svstdarr.hxx" +#include <com/sun/star/uno/Any.hxx> +#include <com/sun/star/ui/dialogs/FilePickerEvent.hpp> +#include <com/sun/star/ui/dialogs/FilePreviewImageFormats.hpp> +#include <com/sun/star/ui/dialogs/TemplateDescription.hpp> +#include <com/sun/star/beans/PropertyValue.hpp> +#include <com/sun/star/beans/XPropertySet.hpp> +#include <com/sun/star/awt/XWindow.hpp> +#include <com/sun/star/beans/StringPair.hpp> +#include <com/sun/star/uno/Sequence.hxx> +#include <com/sun/star/beans/NamedValue.hpp> +#include <unotools/ucbhelper.hxx> +#include <unotools/pathoptions.hxx> +#include <comphelper/sequence.hxx> +#include <cppuhelper/typeprovider.hxx> +#include "vos/mutex.hxx" +#ifndef _SV_APP_HXX +#include "vcl/svapp.hxx" +#endif + +// define ---------------------------------------------------------------- + +#define MAKE_ANY ::com::sun::star::uno::makeAny + +// using ---------------------------------------------------------------- + +using namespace ::com::sun::star::container; +using namespace ::com::sun::star::lang; +using namespace ::com::sun::star::ui::dialogs; +using namespace ::com::sun::star::uno; +using namespace ::com::sun::star::beans; +using namespace ::com::sun::star::awt; +using namespace ::utl; + +//===================================================================== + +//===================================================================== + +struct FilterEntry +{ +protected: + ::rtl::OUString m_sTitle; + ::rtl::OUString m_sFilter; + + UnoFilterList m_aSubFilters; + +public: + FilterEntry( const ::rtl::OUString& _rTitle, const ::rtl::OUString& _rFilter ) + :m_sTitle( _rTitle ) + ,m_sFilter( _rFilter ) + { + } + + FilterEntry( const ::rtl::OUString& _rTitle, const UnoFilterList& _rSubFilters ); + + ::rtl::OUString getTitle() const { return m_sTitle; } + ::rtl::OUString getFilter() const { return m_sFilter; } + + /// determines if the filter has sub filter (i.e., the filter is a filter group in real) + sal_Bool hasSubFilters( ) const; + + /** retrieves the filters belonging to the entry + @return + the number of sub filters + */ + sal_Int32 getSubFilters( UnoFilterList& _rSubFilterList ); + + // helpers for iterating the sub filters + const UnoFilterEntry* beginSubFilters() const { return m_aSubFilters.getConstArray(); } + const UnoFilterEntry* endSubFilters() const { return m_aSubFilters.getConstArray() + m_aSubFilters.getLength(); } +}; + +//===================================================================== + +//--------------------------------------------------------------------- +FilterEntry::FilterEntry( const ::rtl::OUString& _rTitle, const UnoFilterList& _rSubFilters ) + :m_sTitle( _rTitle ) + ,m_aSubFilters( _rSubFilters ) +{ +} + +//--------------------------------------------------------------------- +sal_Bool FilterEntry::hasSubFilters( ) const +{ + return ( 0 < m_aSubFilters.getLength() ); +} + +//--------------------------------------------------------------------- +sal_Int32 FilterEntry::getSubFilters( UnoFilterList& _rSubFilterList ) +{ + _rSubFilterList = m_aSubFilters; + return m_aSubFilters.getLength(); +} + +// struct ElementEntry_Impl ---------------------------------------------- + +struct ElementEntry_Impl +{ + sal_Int16 m_nElementID; + sal_Int16 m_nControlAction; + Any m_aValue; + rtl::OUString m_aLabel; + sal_Bool m_bEnabled : 1; + + sal_Bool m_bHasValue : 1; + sal_Bool m_bHasLabel : 1; + sal_Bool m_bHasEnabled : 1; + + ElementEntry_Impl( sal_Int16 nId ); + + void setValue( const Any& rVal ) { m_aValue = rVal; m_bHasValue = sal_True; } + void setAction( sal_Int16 nAction ) { m_nControlAction = nAction; } + void setLabel( const rtl::OUString& rVal ) { m_aLabel = rVal; m_bHasLabel = sal_True; } + void setEnabled( sal_Bool bEnabled ) { m_bEnabled = bEnabled; m_bHasEnabled = sal_True; } +}; + +ElementEntry_Impl::ElementEntry_Impl( sal_Int16 nId ) + : m_nElementID( nId ) + , m_nControlAction( 0 ) + , m_bEnabled( sal_False ) + , m_bHasValue( sal_False ) + , m_bHasLabel( sal_False ) + , m_bHasEnabled( sal_False ) +{} + +//------------------------------------------------------------------------------------ +void SvtFilePicker::prepareExecute() +{ + // set the default directory + // --**-- doesn't match the spec yet + if ( m_aDisplayDirectory.getLength() > 0 || m_aDefaultName.getLength() > 0 ) + { + if ( m_aDisplayDirectory.getLength() > 0 ) + { + + INetURLObject aPath( m_aDisplayDirectory ); + if ( m_aDefaultName.getLength() > 0 ) + { + aPath.insertName( m_aDefaultName ); + getDialog()->SetHasFilename( true ); + } + String sPath = aPath.GetMainURL( INetURLObject::NO_DECODE ); + getDialog()->SetPath( aPath.GetMainURL( INetURLObject::NO_DECODE ) ); + } + else if ( m_aDefaultName.getLength() > 0 ) + { + getDialog()->SetPath( m_aDefaultName ); + getDialog()->SetHasFilename( true ); + } + } + else + { + // Default-Standard-Dir setzen + INetURLObject aStdDirObj( SvtPathOptions().GetWorkPath() ); + getDialog()->SetPath( aStdDirObj.GetMainURL( INetURLObject::NO_DECODE ) ); + } + + // set the control values and set the control labels, too + if ( m_pElemList && !m_pElemList->empty() ) + { + ::svt::OControlAccess aAccess( getDialog(), getDialog()->GetView() ); + + ElementList::iterator aListIter; + for ( aListIter = m_pElemList->begin(); + aListIter != m_pElemList->end(); ++aListIter ) + { + ElementEntry_Impl& rEntry = *aListIter; + if ( rEntry.m_bHasValue ) + aAccess.setValue( rEntry.m_nElementID, rEntry.m_nControlAction, rEntry.m_aValue ); + if ( rEntry.m_bHasLabel ) + aAccess.setLabel( rEntry.m_nElementID, rEntry.m_aLabel ); + if ( rEntry.m_bHasEnabled ) + aAccess.enableControl( rEntry.m_nElementID, rEntry.m_bEnabled ); + } + + getDialog()->updateListboxLabelSizes(); + } + + if ( m_pFilterList && !m_pFilterList->empty() ) + { + for ( FilterList::iterator aListIter = m_pFilterList->begin(); + aListIter != m_pFilterList->end(); + ++aListIter + ) + { + if ( aListIter->hasSubFilters() ) + { // it's a filter group + UnoFilterList aSubFilters; + aListIter->getSubFilters( aSubFilters ); + + getDialog()->AddFilterGroup( aListIter->getTitle(), aSubFilters ); + } + else + // it's a single filter + getDialog()->AddFilter( aListIter->getTitle(), aListIter->getFilter() ); + } + } + + // set the default filter + if ( m_aCurrentFilter.getLength() > 0 ) + getDialog()->SetCurFilter( m_aCurrentFilter ); + +} + +//----------------------------------------------------------------------------- +IMPL_LINK( SvtFilePicker, DialogClosedHdl, Dialog*, pDlg ) +{ + if ( m_xDlgClosedListener.is() ) + { + sal_Int16 nRet = static_cast< sal_Int16 >( pDlg->GetResult() ); + ::com::sun::star::ui::dialogs::DialogClosedEvent aEvent( *this, nRet ); + m_xDlgClosedListener->dialogClosed( aEvent ); + m_xDlgClosedListener.clear(); + } + return 0; +} + +//------------------------------------------------------------------------------------ +// SvtFilePicker +//------------------------------------------------------------------------------------ + +//------------------------------------------------------------------------------------ +WinBits SvtFilePicker::getWinBits( WinBits& rExtraBits ) +{ + // set the winbits for creating the filedialog + WinBits nBits = 0L; + rExtraBits = 0L; + + // set the standard bits acording to the service name + if ( m_nServiceType == TemplateDescription::FILEOPEN_SIMPLE ) + { + nBits = WB_OPEN; + } + else if ( m_nServiceType == TemplateDescription::FILESAVE_SIMPLE ) + { + nBits = WB_SAVEAS; + } + else if ( m_nServiceType == TemplateDescription::FILESAVE_AUTOEXTENSION ) + { + nBits = WB_SAVEAS; + rExtraBits = SFX_EXTRA_AUTOEXTENSION; + } + else if ( m_nServiceType == TemplateDescription::FILESAVE_AUTOEXTENSION_PASSWORD ) + { + nBits = WB_SAVEAS | SFXWB_PASSWORD; + rExtraBits = SFX_EXTRA_AUTOEXTENSION; + } + else if ( m_nServiceType == TemplateDescription::FILESAVE_AUTOEXTENSION_PASSWORD_FILTEROPTIONS ) + { + nBits = WB_SAVEAS | SFXWB_PASSWORD; + rExtraBits = SFX_EXTRA_AUTOEXTENSION | SFX_EXTRA_FILTEROPTIONS; + } + else if ( m_nServiceType == TemplateDescription::FILESAVE_AUTOEXTENSION_TEMPLATE ) + { + nBits = WB_SAVEAS; + rExtraBits = SFX_EXTRA_AUTOEXTENSION | SFX_EXTRA_TEMPLATES; + } + else if ( m_nServiceType == TemplateDescription::FILESAVE_AUTOEXTENSION_SELECTION ) + { + nBits = WB_SAVEAS; + rExtraBits = SFX_EXTRA_AUTOEXTENSION | SFX_EXTRA_SELECTION; + } + + else if ( m_nServiceType == TemplateDescription::FILEOPEN_LINK_PREVIEW_IMAGE_TEMPLATE ) + { + nBits = WB_OPEN; + rExtraBits = SFX_EXTRA_INSERTASLINK | SFX_EXTRA_SHOWPREVIEW | SFX_EXTRA_IMAGE_TEMPLATE; + } + else if ( m_nServiceType == TemplateDescription::FILEOPEN_PLAY ) + { + nBits = WB_OPEN; + rExtraBits = SFX_EXTRA_PLAYBUTTON; + } + else if ( m_nServiceType == TemplateDescription::FILEOPEN_READONLY_VERSION ) + { + nBits = WB_OPEN | SFXWB_READONLY; + rExtraBits = SFX_EXTRA_SHOWVERSIONS; + } + else if ( m_nServiceType == TemplateDescription::FILEOPEN_LINK_PREVIEW ) + { + nBits = WB_OPEN; + rExtraBits = SFX_EXTRA_INSERTASLINK | SFX_EXTRA_SHOWPREVIEW; + } + if ( m_bMultiSelection && ( ( nBits & WB_OPEN ) == WB_OPEN ) ) + nBits |= SFXWB_MULTISELECTION; + + return nBits; +} + +//------------------------------------------------------------------------------------ +void SvtFilePicker::notify( sal_Int16 _nEventId, sal_Int16 _nControlId ) +{ + if ( !m_xListener.is() ) + return; + + FilePickerEvent aEvent( *this, _nControlId ); + + switch ( _nEventId ) + { + case FILE_SELECTION_CHANGED: + m_xListener->fileSelectionChanged( aEvent ); + break; + case DIRECTORY_CHANGED: + m_xListener->directoryChanged( aEvent ); + break; + case HELP_REQUESTED: + m_xListener->helpRequested( aEvent ); + break; + case CTRL_STATE_CHANGED: + m_xListener->controlStateChanged( aEvent ); + break; + case DIALOG_SIZE_CHANGED: + m_xListener->dialogSizeChanged(); + break; + default: + DBG_ERRORFILE( "SvtFilePicker::notify(): Unknown event id!" ); + break; + } +} + +//------------------------------------------------------------------------------------ +namespace { + //................................................................................ + struct FilterTitleMatch : public ::std::unary_function< FilterEntry, bool > + { + protected: + const ::rtl::OUString& rTitle; + + public: + FilterTitleMatch( const ::rtl::OUString& _rTitle ) : rTitle( _rTitle ) { } + + //............................................................................ + bool operator () ( const FilterEntry& _rEntry ) + { + sal_Bool bMatch; + if ( !_rEntry.hasSubFilters() ) + // a real filter + bMatch = ( _rEntry.getTitle() == rTitle ); + else + // a filter group -> search the sub filters + bMatch = + _rEntry.endSubFilters() != ::std::find_if( + _rEntry.beginSubFilters(), + _rEntry.endSubFilters(), + *this + ); + + return bMatch ? true : false; + } + bool operator () ( const UnoFilterEntry& _rEntry ) + { + return _rEntry.First == rTitle ? true : false; + } + }; +} + +//------------------------------------------------------------------------------------ +sal_Bool SvtFilePicker::FilterNameExists( const ::rtl::OUString& rTitle ) +{ + sal_Bool bRet = sal_False; + + if ( m_pFilterList ) + bRet = + m_pFilterList->end() != ::std::find_if( + m_pFilterList->begin(), + m_pFilterList->end(), + FilterTitleMatch( rTitle ) + ); + + return bRet; +} + +//------------------------------------------------------------------------------------ +sal_Bool SvtFilePicker::FilterNameExists( const UnoFilterList& _rGroupedFilters ) +{ + sal_Bool bRet = sal_False; + + if ( m_pFilterList ) + { + const UnoFilterEntry* pStart = _rGroupedFilters.getConstArray(); + const UnoFilterEntry* pEnd = pStart + _rGroupedFilters.getLength(); + for ( ; pStart != pEnd; ++pStart ) + if ( m_pFilterList->end() != ::std::find_if( m_pFilterList->begin(), m_pFilterList->end(), FilterTitleMatch( pStart->First ) ) ) + break; + + bRet = pStart != pEnd; + } + + return bRet; +} + +//------------------------------------------------------------------------------------ +void SvtFilePicker::ensureFilterList( const ::rtl::OUString& _rInitialCurrentFilter ) +{ + if ( !m_pFilterList ) + { + m_pFilterList = new FilterList; + + // set the first filter to the current filter + if ( ! m_aCurrentFilter.getLength() ) + m_aCurrentFilter = _rInitialCurrentFilter; + } +} + +//------------------------------------------------------------------------------------ +// class SvtFilePicker +//------------------------------------------------------------------------------------ +SvtFilePicker::SvtFilePicker( const Reference < XMultiServiceFactory >& xFactory ) + :OCommonPicker( xFactory ) + ,m_pFilterList ( NULL ) + ,m_pElemList ( NULL ) + ,m_bMultiSelection ( sal_False ) + ,m_nServiceType ( TemplateDescription::FILEOPEN_SIMPLE ) +{ +} + +SvtFilePicker::~SvtFilePicker() +{ + if ( m_pFilterList && !m_pFilterList->empty() ) + m_pFilterList->erase( m_pFilterList->begin(), m_pFilterList->end() ); + delete m_pFilterList; + + if ( m_pElemList && !m_pElemList->empty() ) + m_pElemList->erase( m_pElemList->begin(), m_pElemList->end() ); + delete m_pElemList; +} + +//------------------------------------------------------------------------------------ +sal_Int16 SvtFilePicker::implExecutePicker( ) +{ + getDialog()->SetFileCallback( this ); + + prepareExecute(); + + getDialog()->EnableAutocompletion( TRUE ); + // now we are ready to execute the dialog + sal_Int16 nRet = getDialog()->Execute(); + + // the execution of the dialog yields, so it is possible the at this point the window or the dialog is closed + if ( getDialog() ) + getDialog()->SetFileCallback( NULL ); + + return nRet; +} + +//------------------------------------------------------------------------------------ +SvtFileDialog* SvtFilePicker::implCreateDialog( Window* _pParent ) +{ + WinBits nExtraBits; + WinBits nBits = getWinBits( nExtraBits ); + + SvtFileDialog* dialog = new SvtFileDialog( _pParent, nBits, nExtraBits ); + + // Set StandardDir if present + if ( m_aStandardDir.getLength() > 0) + { + String sStandardDir = String( m_aStandardDir ); + dialog->SetStandardDir( sStandardDir ); + dialog->SetBlackList( m_aBlackList ); + } + + return dialog; +} + +//------------------------------------------------------------------------------------ +// disambiguate XInterface +//------------------------------------------------------------------------------------ +IMPLEMENT_FORWARD_XINTERFACE2( SvtFilePicker, OCommonPicker, SvtFilePicker_Base ) + +//------------------------------------------------------------------------------------ +// disambiguate XTypeProvider +//------------------------------------------------------------------------------------ +IMPLEMENT_FORWARD_XTYPEPROVIDER2( SvtFilePicker, OCommonPicker, SvtFilePicker_Base ) + +//------------------------------------------------------------------------------------ +// XExecutableDialog functions +//------------------------------------------------------------------------------------ + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFilePicker::setTitle( const ::rtl::OUString& _rTitle ) throw (RuntimeException) +{ + OCommonPicker::setTitle( _rTitle ); +} + +//------------------------------------------------------------------------------------ +sal_Int16 SAL_CALL SvtFilePicker::execute( ) throw (RuntimeException) +{ + return OCommonPicker::execute(); +} + +//------------------------------------------------------------------------------------ +// XAsynchronousExecutableDialog functions +//------------------------------------------------------------------------------------ + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFilePicker::setDialogTitle( const ::rtl::OUString& _rTitle ) throw (RuntimeException) +{ + setTitle( _rTitle ); +} + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFilePicker::startExecuteModal( const Reference< ::com::sun::star::ui::dialogs::XDialogClosedListener >& xListener ) throw (RuntimeException) +{ + m_xDlgClosedListener = xListener; + prepareDialog(); + prepareExecute(); + getDialog()->EnableAutocompletion( TRUE ); + getDialog()->StartExecuteModal( LINK( this, SvtFilePicker, DialogClosedHdl ) ); +} + +//------------------------------------------------------------------------------------ +// XFilePicker functions +//------------------------------------------------------------------------------------ + +void SAL_CALL SvtFilePicker::setMultiSelectionMode( sal_Bool bMode ) throw( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + m_bMultiSelection = bMode; +} + +void SAL_CALL SvtFilePicker::setDefaultName( const rtl::OUString& aName ) throw( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + m_aDefaultName = aName; +} + +void SAL_CALL SvtFilePicker::setDisplayDirectory( const rtl::OUString& aDirectory ) + throw( IllegalArgumentException, RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + m_aDisplayDirectory = aDirectory; +} + +rtl::OUString SAL_CALL SvtFilePicker::getDisplayDirectory() throw( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( getDialog() ) + { + rtl::OUString aPath = getDialog()->GetPath(); + + // #97148# ---- + if( m_aOldHideDirectory == aPath ) + return m_aOldDisplayDirectory; + m_aOldHideDirectory = aPath; + + // #102204# ----- + if( !getDialog()->ContentIsFolder( aPath ) ) + { + INetURLObject aFolder( aPath ); + aFolder.CutLastName(); + aPath = aFolder.GetMainURL( INetURLObject::NO_DECODE ); + } + m_aOldDisplayDirectory = aPath; + return aPath; + } + else + return m_aDisplayDirectory; +} + +Sequence< rtl::OUString > SAL_CALL SvtFilePicker::getFiles() throw( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( ! getDialog() ) + { + Sequence< rtl::OUString > aEmpty; + return aEmpty; + } + + // if there is more than one path we have to return the path to the + // files first and then the list of the selected entries + + SvStringsDtor* pPathList = getDialog()->GetPathList(); + USHORT i, nCount = pPathList->Count(); + USHORT nTotal = nCount > 1 ? nCount+1: nCount; + + Sequence< rtl::OUString > aPath( nTotal ); + + if ( nCount == 1 ) + aPath[0] = rtl::OUString( *pPathList->GetObject( 0 ) ); + else if ( nCount > 1 ) + { + INetURLObject aObj( *pPathList->GetObject( 0 ) ); + aObj.removeSegment(); + aPath[0] = aObj.GetMainURL( INetURLObject::NO_DECODE ); + + for ( i = 0; i < nCount; /* i++ is done below */ ) + { + aObj.SetURL( *pPathList->GetObject(i++) ); + aPath[i] = aObj.getName(); + } + } + + delete pPathList; + return aPath; +} + +//------------------------------------------------------------------------------------ +// XFilePickerControlAccess functions +//------------------------------------------------------------------------------------ + +void SAL_CALL SvtFilePicker::setValue( sal_Int16 nElementID, + sal_Int16 nControlAction, + const Any& rValue ) + throw( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( getDialog() ) + { + ::svt::OControlAccess aAccess( getDialog(), getDialog()->GetView() ); + aAccess.setValue( nElementID, nControlAction, rValue ); + } + else + { + if ( !m_pElemList ) + m_pElemList = new ElementList; + + sal_Bool bFound = sal_False; + ElementList::iterator aListIter; + + for ( aListIter = m_pElemList->begin(); + aListIter != m_pElemList->end(); ++aListIter ) + { + ElementEntry_Impl& rEntry = *aListIter; + if ( ( rEntry.m_nElementID == nElementID ) && + ( !rEntry.m_bHasValue || ( rEntry.m_nControlAction == nControlAction ) ) ) + { + rEntry.setAction( nControlAction ); + rEntry.setValue( rValue ); + bFound = sal_True; + } + } + + if ( !bFound ) + { + ElementEntry_Impl aNew( nElementID ); + aNew.setAction( nControlAction ); + aNew.setValue( rValue ); + m_pElemList->insert( m_pElemList->end(), aNew ); + } + } +} + +//------------------------------------------------------------------------------------ + +Any SAL_CALL SvtFilePicker::getValue( sal_Int16 nElementID, sal_Int16 nControlAction ) + throw( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + Any aAny; + + // execute() called? + if ( getDialog() ) + { + ::svt::OControlAccess aAccess( getDialog(), getDialog()->GetView() ); + aAny = aAccess.getValue( nElementID, nControlAction ); + } + else if ( m_pElemList && !m_pElemList->empty() ) + { + ElementList::iterator aListIter; + for ( aListIter = m_pElemList->begin(); + aListIter != m_pElemList->end(); ++aListIter ) + { + ElementEntry_Impl& rEntry = *aListIter; + if ( ( rEntry.m_nElementID == nElementID ) && + ( rEntry.m_bHasValue ) && + ( rEntry.m_nControlAction == nControlAction ) ) + { + aAny = rEntry.m_aValue; + break; + } + } + } + + return aAny; +} + + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFilePicker::setLabel( sal_Int16 nLabelID, const rtl::OUString& rValue ) + throw ( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( getDialog() ) + { + ::svt::OControlAccess aAccess( getDialog(), getDialog()->GetView() ); + aAccess.setLabel( nLabelID, rValue ); + } + else + { + if ( !m_pElemList ) + m_pElemList = new ElementList; + + sal_Bool bFound = sal_False; + ElementList::iterator aListIter; + + for ( aListIter = m_pElemList->begin(); + aListIter != m_pElemList->end(); ++aListIter ) + { + ElementEntry_Impl& rEntry = *aListIter; + if ( rEntry.m_nElementID == nLabelID ) + { + rEntry.setLabel( rValue ); + bFound = sal_True; + } + } + + if ( !bFound ) + { + ElementEntry_Impl aNew( nLabelID ); + aNew.setLabel( rValue ); + m_pElemList->insert( m_pElemList->end(), aNew ); + } + } +} + +//------------------------------------------------------------------------------------ +rtl::OUString SAL_CALL SvtFilePicker::getLabel( sal_Int16 nLabelID ) + throw ( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + rtl::OUString aLabel; + + if ( getDialog() ) + { + ::svt::OControlAccess aAccess( getDialog(), getDialog()->GetView() ); + aLabel = aAccess.getLabel( nLabelID ); + } + else if ( m_pElemList && !m_pElemList->empty() ) + { + ElementList::iterator aListIter; + for ( aListIter = m_pElemList->begin(); + aListIter != m_pElemList->end(); ++aListIter ) + { + ElementEntry_Impl& rEntry = *aListIter; + if ( rEntry.m_nElementID == nLabelID ) + { + if ( rEntry.m_bHasLabel ) + aLabel = rEntry.m_aLabel; + break; + } + } + } + + return aLabel; +} + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFilePicker::enableControl( sal_Int16 nElementID, sal_Bool bEnable ) + throw( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( getDialog() ) + { + ::svt::OControlAccess aAccess( getDialog(), getDialog()->GetView() ); + aAccess.enableControl( nElementID, bEnable ); + } + else + { + if ( !m_pElemList ) + m_pElemList = new ElementList; + + sal_Bool bFound = sal_False; + ElementList::iterator aListIter; + + for ( aListIter = m_pElemList->begin(); + aListIter != m_pElemList->end(); ++aListIter ) + { + ElementEntry_Impl& rEntry = *aListIter; + if ( rEntry.m_nElementID == nElementID ) + { + rEntry.setEnabled( bEnable ); + bFound = sal_True; + } + } + + if ( !bFound ) + { + ElementEntry_Impl aNew( nElementID ); + aNew.setEnabled( bEnable ); + m_pElemList->insert( m_pElemList->end(), aNew ); + } + } +} + +//------------------------------------------------------------------------------------ +// XFilePickerNotifier functions +//------------------------------------------------------------------------------------ + +void SAL_CALL SvtFilePicker::addFilePickerListener( const Reference< XFilePickerListener >& xListener ) throw ( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + m_xListener = xListener; +} + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFilePicker::removeFilePickerListener( const Reference< XFilePickerListener >& ) throw ( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + m_xListener.clear(); +} + +//------------------------------------------------------------------------------------ +// XFilePreview functions +//------------------------------------------------------------------------------------ + +Sequence< sal_Int16 > SAL_CALL SvtFilePicker::getSupportedImageFormats() + throw ( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + Sequence< sal_Int16 > aFormats( 1 ); + + aFormats[0] = FilePreviewImageFormats::BITMAP; + + return aFormats; +} + +//------------------------------------------------------------------------------------ +sal_Int32 SAL_CALL SvtFilePicker::getTargetColorDepth() throw ( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + sal_Int32 nDepth = 0; + + if ( getDialog() ) + nDepth = getDialog()->getTargetColorDepth(); + + return nDepth; +} + +//------------------------------------------------------------------------------------ +sal_Int32 SAL_CALL SvtFilePicker::getAvailableWidth() throw ( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + sal_Int32 nWidth = 0; + + if ( getDialog() ) + nWidth = getDialog()->getAvailableWidth(); + + return nWidth; +} + +//------------------------------------------------------------------------------------ +sal_Int32 SAL_CALL SvtFilePicker::getAvailableHeight() throw ( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + sal_Int32 nHeigth = 0; + + if ( getDialog() ) + nHeigth = getDialog()->getAvailableHeight(); + + return nHeigth; +} + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFilePicker::setImage( sal_Int16 aImageFormat, const Any& rImage ) + throw ( IllegalArgumentException, RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( getDialog() ) + getDialog()->setImage( aImageFormat, rImage ); +} + +//------------------------------------------------------------------------------------ +sal_Bool SAL_CALL SvtFilePicker::setShowState( sal_Bool bShowState ) + throw ( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + sal_Bool bRet = sal_False; + + if ( getDialog() ) + bRet = getDialog()->setShowState( bShowState ); + + return bRet; +} + +//------------------------------------------------------------------------------------ +sal_Bool SAL_CALL SvtFilePicker::getShowState() throw ( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + sal_Bool bRet = sal_False; + + if ( getDialog() ) + bRet = getDialog()->getShowState(); + + return bRet; +} + +//------------------------------------------------------------------------------------ +// XFilterGroupManager functions +//------------------------------------------------------------------------------------ + +void SAL_CALL SvtFilePicker::appendFilterGroup( const ::rtl::OUString& sGroupTitle, + const Sequence< StringPair >& aFilters ) + throw ( IllegalArgumentException, RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + + // check the names + if ( FilterNameExists( aFilters ) ) + throw IllegalArgumentException( + rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("filter name exists")), + static_cast< OWeakObject * >(this), 1); + + // ensure that we have a filter list + ::rtl::OUString sInitialCurrentFilter; + if ( aFilters.getLength() ) + sInitialCurrentFilter = aFilters[0].First; + ensureFilterList( sInitialCurrentFilter ); + + // append the filter + m_pFilterList->insert( m_pFilterList->end(), FilterEntry( sGroupTitle, aFilters ) ); +} + +//------------------------------------------------------------------------------------ +// XFilterManager functions +//------------------------------------------------------------------------------------ + +void SAL_CALL SvtFilePicker::appendFilter( const rtl::OUString& aTitle, + const rtl::OUString& aFilter ) + throw( IllegalArgumentException, RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + // check the name + if ( FilterNameExists( aTitle ) ) + // TODO: a more precise exception message + throw IllegalArgumentException(); + + // ensure that we have a filter list + ensureFilterList( aTitle ); + + // append the filter + m_pFilterList->insert( m_pFilterList->end(), FilterEntry( aTitle, aFilter ) ); +} + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFilePicker::setCurrentFilter( const rtl::OUString& aTitle ) + throw( IllegalArgumentException, RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( ! FilterNameExists( aTitle ) ) + throw IllegalArgumentException(); + + m_aCurrentFilter = aTitle; + + if ( getDialog() ) + getDialog()->SetCurFilter( aTitle ); +} + +//------------------------------------------------------------------------------------ +rtl::OUString SAL_CALL SvtFilePicker::getCurrentFilter() + throw( RuntimeException ) +{ + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + rtl::OUString aFilter = getDialog() ? rtl::OUString( getDialog()->GetCurFilter() ) : + rtl::OUString( m_aCurrentFilter ); + return aFilter; +} + + +//------------------------------------------------------------------------------------ +// XInitialization functions +//------------------------------------------------------------------------------------ + +void SAL_CALL SvtFilePicker::initialize( const Sequence< Any >& _rArguments ) + throw ( Exception, RuntimeException ) +{ + checkAlive(); + + Sequence< Any > aArguments( _rArguments.getLength()); + + m_nServiceType = TemplateDescription::FILEOPEN_SIMPLE; + + if ( _rArguments.getLength() >= 1 ) + { + // compatibility: one argument, type sal_Int16 , specifies the service type + int index = 0; + + if (_rArguments[0] >>= m_nServiceType) + { + // skip the first entry if it was the ServiceType, because it's not needed in OCommonPicker::initialize and it's not a NamedValue + NamedValue emptyNamedValue; + aArguments[0] <<= emptyNamedValue; + index = 1; + + } + for ( int i = index; i < _rArguments.getLength(); i++) + { + NamedValue namedValue; + aArguments[i] <<= _rArguments[i]; + + if (aArguments[i] >>= namedValue ) + { + + if ( namedValue.Name.equals( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "StandardDir" ) ) ) ) + { + ::rtl::OUString sStandardDir; + + namedValue.Value >>= sStandardDir; + + // Set the directory for the "back to the default dir" button + if ( sStandardDir.getLength() > 0 ) + { + m_aStandardDir = sStandardDir; + } + } + else if ( namedValue.Name.equals( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "BlackList" ) ) ) ) + { + namedValue.Value >>= m_aBlackList; + } + } + } + } + + // let the base class analyze the sequence (will call into implHandleInitializationArgument) + OCommonPicker::initialize( aArguments ); +} + +//------------------------------------------------------------------------- +sal_Bool SvtFilePicker::implHandleInitializationArgument( const ::rtl::OUString& _rName, const Any& _rValue ) SAL_THROW( ( Exception, RuntimeException ) ) +{ + if ( _rName.equalsAscii( "TemplateDescription" ) ) + { + m_nServiceType = TemplateDescription::FILEOPEN_SIMPLE; + OSL_VERIFY( _rValue >>= m_nServiceType ); + return sal_True; + } + if ( _rName.equalsAscii( "StandardDir" ) ) + { + OSL_VERIFY( _rValue >>= m_aStandardDir ); + return sal_True; + } + + if ( _rName.equalsAscii( "BlackList" ) ) + { + OSL_VERIFY( _rValue >>= m_aBlackList ); + return sal_True; + } + + + + return OCommonPicker::implHandleInitializationArgument( _rName, _rValue ); +} + +//------------------------------------------------------------------------------------ +// XServiceInfo +//------------------------------------------------------------------------------------ + +/* XServiceInfo */ +rtl::OUString SAL_CALL SvtFilePicker::getImplementationName() throw( RuntimeException ) +{ + return impl_getStaticImplementationName(); +} + +/* XServiceInfo */ +sal_Bool SAL_CALL SvtFilePicker::supportsService( const rtl::OUString& sServiceName ) throw( RuntimeException ) +{ + Sequence< rtl::OUString > seqServiceNames = getSupportedServiceNames(); + const rtl::OUString* pArray = seqServiceNames.getConstArray(); + for ( sal_Int32 i = 0; i < seqServiceNames.getLength(); i++ ) + { + if ( sServiceName == pArray[i] ) + { + return sal_True ; + } + } + return sal_False ; +} + +/* XServiceInfo */ +Sequence< rtl::OUString > SAL_CALL SvtFilePicker::getSupportedServiceNames() throw( RuntimeException ) +{ + return impl_getStaticSupportedServiceNames(); +} + +/* Helper for XServiceInfo */ +Sequence< rtl::OUString > SvtFilePicker::impl_getStaticSupportedServiceNames() +{ + Sequence< rtl::OUString > seqServiceNames( 1 ); + rtl::OUString* pArray = seqServiceNames.getArray(); + pArray[0] = rtl::OUString::createFromAscii( "com.sun.star.ui.dialogs.OfficeFilePicker" ); + return seqServiceNames ; +} + +/* Helper for XServiceInfo */ +rtl::OUString SvtFilePicker::impl_getStaticImplementationName() +{ + return rtl::OUString::createFromAscii( "com.sun.star.svtools.OfficeFilePicker" ); +} + +/* Helper for registry */ +Reference< XInterface > SAL_CALL SvtFilePicker::impl_createInstance( + const Reference< XComponentContext >& rxContext) throw( Exception ) +{ + Reference< XMultiServiceFactory > xServiceManager (rxContext->getServiceManager(), UNO_QUERY_THROW); + return Reference< XInterface >( *new SvtFilePicker( xServiceManager ) ); +} diff --git a/fpicker/source/office/OfficeFilePicker.hxx b/fpicker/source/office/OfficeFilePicker.hxx new file mode 100644 index 000000000000..c203924f6e51 --- /dev/null +++ b/fpicker/source/office/OfficeFilePicker.hxx @@ -0,0 +1,230 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ +#ifndef INCLUDED_SVT_FILEPICKER_HXX +#define INCLUDED_SVT_FILEPICKER_HXX + +#include <cppuhelper/implbase7.hxx> +#include <com/sun/star/ui/dialogs/XFilePickerControlAccess.hpp> +#include <com/sun/star/ui/dialogs/XFilePickerNotifier.hpp> +#include <com/sun/star/ui/dialogs/XFilePreview.hpp> +#include <com/sun/star/ui/dialogs/XFilterManager.hpp> +#include <com/sun/star/ui/dialogs/XFilterGroupManager.hpp> +#include <com/sun/star/ui/dialogs/XFilePickerListener.hpp> +#include <com/sun/star/ui/dialogs/XAsynchronousExecutableDialog.hpp> +#include <com/sun/star/lang/XServiceInfo.hpp> +#include <com/sun/star/lang/XEventListener.hpp> +#ifndef _COM_SUN_STAR_UNO_XCOMPONENT_CONTEXT_HPP_ +#include <com/sun/star/uno/XComponentContext.hpp> +#endif + + +#include <tools/wintypes.hxx> +#include "commonpicker.hxx" +#include "pickercallbacks.hxx" + +#include <list> + +class Dialog; + +struct FilterEntry; +struct ElementEntry_Impl; + +typedef ::std::list< FilterEntry > FilterList; // can be maintained more effectively +typedef ::std::list < ElementEntry_Impl > ElementList; + +typedef ::com::sun::star::beans::StringPair UnoFilterEntry; +typedef ::com::sun::star::uno::Sequence< UnoFilterEntry > UnoFilterList; // can be transported more effectively +typedef ::com::sun::star::uno::Sequence< ::rtl::OUString > OUStringList; // can be transported more effectively + +// class SvtFilePicker --------------------------------------------------- + +typedef ::cppu::ImplHelper7 < ::com::sun::star::ui::dialogs::XFilePickerControlAccess + , ::com::sun::star::ui::dialogs::XFilePickerNotifier + , ::com::sun::star::ui::dialogs::XFilePreview + , ::com::sun::star::ui::dialogs::XFilterManager + , ::com::sun::star::ui::dialogs::XFilterGroupManager + , ::com::sun::star::lang::XServiceInfo + , ::com::sun::star::ui::dialogs::XAsynchronousExecutableDialog + > SvtFilePicker_Base; + +class SvtFilePicker :public SvtFilePicker_Base + ,public ::svt::OCommonPicker + ,public ::svt::IFilePickerListener +{ +private: + FilterList* m_pFilterList; + ElementList* m_pElemList; + + sal_Bool m_bMultiSelection; + sal_Int16 m_nServiceType; + ::rtl::OUString m_aDefaultName; + ::rtl::OUString m_aCurrentFilter; + + // #97148# -------------- + ::rtl::OUString m_aOldDisplayDirectory; + ::rtl::OUString m_aOldHideDirectory; + + ::rtl::OUString m_aStandardDir; + OUStringList m_aBlackList; + + ::com::sun::star::uno::Reference< ::com::sun::star::ui::dialogs::XFilePickerListener > + m_xListener; + ::com::sun::star::uno::Reference< ::com::sun::star::ui::dialogs::XDialogClosedListener > + m_xDlgClosedListener; + +public: + SvtFilePicker( const ::com::sun::star::uno::Reference < ::com::sun::star::lang::XMultiServiceFactory >& xFactory ); + virtual ~SvtFilePicker(); + + //------------------------------------------------------------------------------------ + // disambiguate XInterface + //------------------------------------------------------------------------------------ + DECLARE_XINTERFACE( ) + + //------------------------------------------------------------------------------------ + // disambiguate XTypeProvider + //------------------------------------------------------------------------------------ + DECLARE_XTYPEPROVIDER( ) + + //------------------------------------------------------------------------------------ + // XExecutableDialog functions + //------------------------------------------------------------------------------------ + virtual void SAL_CALL setTitle( const ::rtl::OUString& _rTitle ) throw (::com::sun::star::uno::RuntimeException); + virtual sal_Int16 SAL_CALL execute( ) throw (::com::sun::star::uno::RuntimeException); + + //------------------------------------------------------------------------------------ + // XAsynchronousExecutableDialog functions + //------------------------------------------------------------------------------------ + virtual void SAL_CALL setDialogTitle( const ::rtl::OUString& _rTitle ) throw (::com::sun::star::uno::RuntimeException); + virtual void SAL_CALL startExecuteModal( const ::com::sun::star::uno::Reference< ::com::sun::star::ui::dialogs::XDialogClosedListener >& xListener ) throw (::com::sun::star::uno::RuntimeException); + + //------------------------------------------------------------------------------------ + // XFilePicker functions + //------------------------------------------------------------------------------------ + + virtual void SAL_CALL setMultiSelectionMode( sal_Bool bMode ) throw( ::com::sun::star::uno::RuntimeException ); + virtual void SAL_CALL setDefaultName( const ::rtl::OUString& aName ) throw( ::com::sun::star::uno::RuntimeException ); + virtual void SAL_CALL setDisplayDirectory( const ::rtl::OUString& aDirectory ) throw( ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException ); + virtual ::rtl::OUString SAL_CALL getDisplayDirectory() throw( ::com::sun::star::uno::RuntimeException ); + virtual com::sun::star::uno::Sequence< ::rtl::OUString > SAL_CALL getFiles() throw( ::com::sun::star::uno::RuntimeException ); + + //------------------------------------------------------------------------------------ + // XFilePickerControlAccess functions + //------------------------------------------------------------------------------------ + + virtual void SAL_CALL setValue( sal_Int16 ElementID, sal_Int16 ControlAction, const com::sun::star::uno::Any& value ) throw( ::com::sun::star::uno::RuntimeException ); + virtual com::sun::star::uno::Any SAL_CALL getValue( sal_Int16 ElementID, sal_Int16 ControlAction ) throw( ::com::sun::star::uno::RuntimeException ); + virtual void SAL_CALL setLabel( sal_Int16 ElementID, const ::rtl::OUString& aValue ) throw ( ::com::sun::star::uno::RuntimeException ); + virtual ::rtl::OUString SAL_CALL getLabel( sal_Int16 ElementID ) throw ( ::com::sun::star::uno::RuntimeException ); + virtual void SAL_CALL enableControl( sal_Int16 ElementID, sal_Bool bEnable ) throw( ::com::sun::star::uno::RuntimeException ); + + //------------------------------------------------------------------------------------ + // XFilePickerNotifier functions + //------------------------------------------------------------------------------------ + + virtual void SAL_CALL addFilePickerListener( const ::com::sun::star::uno::Reference< ::com::sun::star::ui::dialogs::XFilePickerListener >& xListener ) throw ( ::com::sun::star::uno::RuntimeException ); + virtual void SAL_CALL removeFilePickerListener( const ::com::sun::star::uno::Reference< ::com::sun::star::ui::dialogs::XFilePickerListener >& xListener ) throw ( ::com::sun::star::uno::RuntimeException ); + + //------------------------------------------------------------------------------------ + // XFilePreview functions + //------------------------------------------------------------------------------------ + + virtual com::sun::star::uno::Sequence< sal_Int16 > SAL_CALL getSupportedImageFormats() throw ( ::com::sun::star::uno::RuntimeException ); + virtual sal_Int32 SAL_CALL getTargetColorDepth() throw ( ::com::sun::star::uno::RuntimeException ); + virtual sal_Int32 SAL_CALL getAvailableWidth() throw ( ::com::sun::star::uno::RuntimeException ); + virtual sal_Int32 SAL_CALL getAvailableHeight() throw ( ::com::sun::star::uno::RuntimeException ); + virtual void SAL_CALL setImage( sal_Int16 aImageFormat, const com::sun::star::uno::Any& aImage ) throw ( ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException ); + virtual sal_Bool SAL_CALL setShowState( sal_Bool bShowState ) throw ( ::com::sun::star::uno::RuntimeException ); + virtual sal_Bool SAL_CALL getShowState() throw ( ::com::sun::star::uno::RuntimeException ); + + //------------------------------------------------------------------------------------ + // XFilterManager functions + //------------------------------------------------------------------------------------ + + virtual void SAL_CALL appendFilter( const ::rtl::OUString& aTitle, const ::rtl::OUString& aFilter ) throw( ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException ); + virtual void SAL_CALL setCurrentFilter( const ::rtl::OUString& aTitle ) throw( ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException ); + virtual ::rtl::OUString SAL_CALL getCurrentFilter() throw( ::com::sun::star::uno::RuntimeException ); + + //------------------------------------------------------------------------------------ + // XFilterGroupManager functions + //------------------------------------------------------------------------------------ + virtual void SAL_CALL appendFilterGroup( const ::rtl::OUString& sGroupTitle, const com::sun::star::uno::Sequence< com::sun::star::beans::StringPair >& aFilters ) throw (::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException); + + //------------------------------------------------------------------------------------ + // XInitialization functions + //------------------------------------------------------------------------------------ + + virtual void SAL_CALL initialize( const com::sun::star::uno::Sequence< com::sun::star::uno::Any >& aArguments ) throw ( com::sun::star::uno::Exception, ::com::sun::star::uno::RuntimeException ); + + //------------------------------------------------------------------------------------ + // XServiceInfo functions + //------------------------------------------------------------------------------------ + + /* XServiceInfo */ + virtual ::rtl::OUString SAL_CALL getImplementationName() throw( ::com::sun::star::uno::RuntimeException ); + virtual sal_Bool SAL_CALL supportsService( const ::rtl::OUString& sServiceName ) throw( ::com::sun::star::uno::RuntimeException ); + virtual com::sun::star::uno::Sequence< ::rtl::OUString > SAL_CALL + getSupportedServiceNames() throw( ::com::sun::star::uno::RuntimeException ); + + /* Helper for XServiceInfo */ + static com::sun::star::uno::Sequence< ::rtl::OUString > + impl_getStaticSupportedServiceNames(); + static ::rtl::OUString impl_getStaticImplementationName(); + + /* Helper for registry */ + static ::com::sun::star::uno::Reference< com::sun::star::uno::XInterface > SAL_CALL impl_createInstance ( + const ::com::sun::star::uno::Reference< com::sun::star::uno::XComponentContext >& rxContext ) + throw( com::sun::star::uno::Exception ); + +protected: + //------------------------------------------------------------------------------------ + // OCommonPicker overridables + //------------------------------------------------------------------------------------ + virtual SvtFileDialog* implCreateDialog( Window* _pParent ); + virtual sal_Int16 implExecutePicker( ); + virtual sal_Bool implHandleInitializationArgument( + const ::rtl::OUString& _rName, + const ::com::sun::star::uno::Any& _rValue + ) + SAL_THROW( ( ::com::sun::star::uno::Exception, ::com::sun::star::uno::RuntimeException ) ); + +private: + WinBits getWinBits( WinBits& rExtraBits ); + virtual void notify( sal_Int16 _nEventId, sal_Int16 _nControlId ); + + sal_Bool FilterNameExists( const ::rtl::OUString& rTitle ); + sal_Bool FilterNameExists( const UnoFilterList& _rGroupedFilters ); + + void ensureFilterList( const ::rtl::OUString& _rInitialCurrentFilter ); + + void prepareExecute( ); + + DECL_LINK( DialogClosedHdl, Dialog* ); +}; + +#endif // INCLUDED_SVT_FILEPICKER_HXX + diff --git a/fpicker/source/office/OfficeFilePicker.src b/fpicker/source/office/OfficeFilePicker.src new file mode 100644 index 000000000000..8fbbc35a40e5 --- /dev/null +++ b/fpicker/source/office/OfficeFilePicker.src @@ -0,0 +1,99 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +#include "svtools/svtools.hrc" + +String STR_SVT_FILEPICKER_AUTO_EXTENSION +{ + Text [ en-US ] = "~Automatic file name extension" ; +}; + +String STR_SVT_FILEPICKER_PASSWORD +{ + Text [ en-US ] = "Save with pass~word" ; +}; + +String STR_SVT_FILEPICKER_FILTER_OPTIONS +{ + Text [ en-US ] = "~Edit filter settings"; +}; + +String STR_SVT_FILEPICKER_READONLY +{ + Text [ en-US ] = "~Read-only" ; +}; + +String STR_SVT_FILEPICKER_INSERT_AS_LINK +{ + Text [ en-US ] = "~Link" ; +}; + +String STR_SVT_FILEPICKER_SHOW_PREVIEW +{ + Text [ en-US ] = "Pr~eview" ; +}; + +String STR_SVT_FILEPICKER_PLAY +{ + Text [ en-US ] = "~Play" ; +}; + +String STR_SVT_FILEPICKER_VERSION +{ + Text [ en-US ] = "~Version:"; +}; + +String STR_SVT_FILEPICKER_TEMPLATES +{ + Text [ en-US ] = "S~tyles:" ; +}; + +String STR_SVT_FILEPICKER_IMAGE_TEMPLATE +{ + Text [ en-US ] = "Style:"; +}; + +String STR_SVT_FILEPICKER_SELECTION +{ + Text [ en-US ] = "~Selection" ; +}; + +String STR_SVT_FILEPICKER_FILTER_TITLE +{ + Text [ en-US ] = "File ~type:" ; +}; + +String STR_SVT_FOLDERPICKER_DEFAULT_TITLE +{ + Text [ en-US ] = "Select Path" ; +}; + +String STR_SVT_FOLDERPICKER_DEFAULT_DESCRIPTION +{ + Text [ en-US ] = "Please select a folder."; +}; + diff --git a/fpicker/source/office/OfficeFolderPicker.cxx b/fpicker/source/office/OfficeFolderPicker.cxx new file mode 100644 index 000000000000..48d3a2b43bad --- /dev/null +++ b/fpicker/source/office/OfficeFolderPicker.cxx @@ -0,0 +1,265 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_fpicker.hxx" + +#include "OfficeFolderPicker.hxx" + +#include "iodlg.hxx" + +#include <list> +#include <tools/urlobj.hxx> + +#define _SVSTDARR_STRINGSDTOR +#include "svl/svstdarr.hxx" +#include <com/sun/star/container/XContentEnumerationAccess.hpp> +#include <com/sun/star/container/XSet.hpp> +#include <com/sun/star/uno/Any.hxx> +#include <cppuhelper/factory.hxx> +#include <com/sun/star/beans/XPropertySet.hpp> +#include <unotools/pathoptions.hxx> + +// using ---------------------------------------------------------------- + +using namespace ::com::sun::star::container; +using namespace ::com::sun::star::lang; +using namespace ::com::sun::star::uno; +using namespace ::com::sun::star::beans; + +//------------------------------------------------------------------------------------ +// class SvtFolderPicker +//------------------------------------------------------------------------------------ + +//------------------------------------------------------------------------------------ +SvtFolderPicker::SvtFolderPicker( const Reference < XMultiServiceFactory >& _rxFactory ) + :OCommonPicker( _rxFactory ) +{ +} + +//------------------------------------------------------------------------------------ +SvtFolderPicker::~SvtFolderPicker() +{ +} + +//------------------------------------------------------------------------------------ +// disambiguate XInterface +//------------------------------------------------------------------------------------ +IMPLEMENT_FORWARD_XINTERFACE2( SvtFolderPicker, OCommonPicker, SvtFolderPicker_Base ) + +//------------------------------------------------------------------------------------ +// disambiguate XTypeProvider +//------------------------------------------------------------------------------------ +IMPLEMENT_FORWARD_XTYPEPROVIDER2( SvtFolderPicker, OCommonPicker, SvtFolderPicker_Base ) + +//------------------------------------------------------------------------------------ +// XExecutableDialog functions +//------------------------------------------------------------------------------------ + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFolderPicker::setTitle( const ::rtl::OUString& _rTitle ) throw (RuntimeException) +{ + OCommonPicker::setTitle( _rTitle ); +} + +//------------------------------------------------------------------------------------ +sal_Int16 SAL_CALL SvtFolderPicker::execute( ) throw (RuntimeException) +{ + return OCommonPicker::execute(); +} + +//------------------------------------------------------------------------------------ +// XAsynchronousExecutableDialog functions +//------------------------------------------------------------------------------------ + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFolderPicker::setDialogTitle( const ::rtl::OUString& _rTitle) throw (RuntimeException) +{ + setTitle( _rTitle ); +} + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFolderPicker::startExecuteModal( const Reference< ::com::sun::star::ui::dialogs::XDialogClosedListener >& xListener ) throw (RuntimeException) +{ + m_xListener = xListener; + prepareDialog(); + prepareExecute(); + getDialog()->EnableAutocompletion( TRUE ); + getDialog()->StartExecuteModal( LINK( this, SvtFolderPicker, DialogClosedHdl ) ); +} + +//------------------------------------------------------------------------------------ +SvtFileDialog* SvtFolderPicker::implCreateDialog( Window* _pParent ) +{ + return new SvtFileDialog( _pParent, SFXWB_PATHDIALOG ); +} + +//------------------------------------------------------------------------------------ +sal_Int16 SvtFolderPicker::implExecutePicker( ) +{ + prepareExecute(); + + // now we are ready to execute the dialog + getDialog()->EnableAutocompletion( FALSE ); + sal_Int16 nRet = getDialog()->Execute(); + + return nRet; +} + +//------------------------------------------------------------------------------------ +void SvtFolderPicker::prepareExecute() +{ + // set the default directory + if ( m_aDisplayDirectory.getLength() > 0 ) + getDialog()->SetPath( m_aDisplayDirectory ); + else + { + // Default-Standard-Dir setzen + INetURLObject aStdDirObj( SvtPathOptions().GetWorkPath() ); + getDialog()->SetPath( aStdDirObj.GetMainURL( INetURLObject::NO_DECODE) ); + } +} + +//----------------------------------------------------------------------------- +IMPL_LINK( SvtFolderPicker, DialogClosedHdl, Dialog*, pDlg ) +{ + if ( m_xListener.is() ) + { + sal_Int16 nRet = static_cast< sal_Int16 >( pDlg->GetResult() ); + ::com::sun::star::ui::dialogs::DialogClosedEvent aEvent( *this, nRet ); + m_xListener->dialogClosed( aEvent ); + m_xListener.clear(); + } + return 0; + } + +//------------------------------------------------------------------------------------ +// XFolderPicker functions +//------------------------------------------------------------------------------------ + +void SAL_CALL SvtFolderPicker::setDisplayDirectory( const ::rtl::OUString& aDirectory ) + throw( IllegalArgumentException, RuntimeException ) +{ + m_aDisplayDirectory = aDirectory; +} + +//------------------------------------------------------------------------------------ +::rtl::OUString SAL_CALL SvtFolderPicker::getDisplayDirectory() throw( RuntimeException ) +{ + ::rtl::OUString aResult; + + if ( ! getDialog() ) + return m_aDisplayDirectory; + + SvStringsDtor* pPathList = getDialog()->GetPathList(); + + if ( pPathList->Count() ) + aResult = ::rtl::OUString( *pPathList->GetObject( 0 ) ); + + delete pPathList; + + return aResult; +} + +//------------------------------------------------------------------------------------ +::rtl::OUString SAL_CALL SvtFolderPicker::getDirectory() throw( RuntimeException ) +{ + ::rtl::OUString aResult; + + if ( ! getDialog() ) + return m_aDisplayDirectory; + + SvStringsDtor* pPathList = getDialog()->GetPathList(); + + if ( pPathList->Count() ) + aResult = ::rtl::OUString( *pPathList->GetObject( 0 ) ); + + delete pPathList; + + return aResult; +} + +//------------------------------------------------------------------------------------ +void SAL_CALL SvtFolderPicker::setDescription( const ::rtl::OUString& aDescription ) + throw( RuntimeException ) +{ + m_aDescription = aDescription; +} + +//------------------------------------------------------------------------------------ +// XServiceInfo +//------------------------------------------------------------------------------------ + +/* XServiceInfo */ +::rtl::OUString SAL_CALL SvtFolderPicker::getImplementationName() throw( RuntimeException ) +{ + return impl_getStaticImplementationName(); +} + +/* XServiceInfo */ +sal_Bool SAL_CALL SvtFolderPicker::supportsService( const ::rtl::OUString& sServiceName ) throw( RuntimeException ) +{ + Sequence< ::rtl::OUString > seqServiceNames = getSupportedServiceNames(); + const ::rtl::OUString* pArray = seqServiceNames.getConstArray(); + for ( sal_Int32 i = 0; i < seqServiceNames.getLength(); i++ ) + { + if ( sServiceName == pArray[i] ) + { + return sal_True ; + } + } + return sal_False ; +} + +/* XServiceInfo */ +Sequence< ::rtl::OUString > SAL_CALL SvtFolderPicker::getSupportedServiceNames() throw( RuntimeException ) +{ + return impl_getStaticSupportedServiceNames(); +} + +/* Helper for XServiceInfo */ +Sequence< ::rtl::OUString > SvtFolderPicker::impl_getStaticSupportedServiceNames() +{ + Sequence< ::rtl::OUString > seqServiceNames(1); + seqServiceNames[0] = ::rtl::OUString::createFromAscii( "com.sun.star.ui.dialogs.OfficeFolderPicker" ); + return seqServiceNames ; +} + +/* Helper for XServiceInfo */ +::rtl::OUString SvtFolderPicker::impl_getStaticImplementationName() +{ + return ::rtl::OUString::createFromAscii( "com.sun.star.svtools.OfficeFolderPicker" ); +} + +/* Helper for registry */ +Reference< XInterface > SAL_CALL SvtFolderPicker::impl_createInstance( const Reference< XComponentContext >& rxContext ) + throw( Exception ) +{ + Reference< XMultiServiceFactory > xServiceManager (rxContext->getServiceManager(), UNO_QUERY_THROW); + return Reference< XInterface >( *new SvtFolderPicker( xServiceManager ) ); +} + diff --git a/fpicker/source/office/OfficeFolderPicker.hxx b/fpicker/source/office/OfficeFolderPicker.hxx new file mode 100644 index 000000000000..1cba8a122063 --- /dev/null +++ b/fpicker/source/office/OfficeFolderPicker.hxx @@ -0,0 +1,122 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ +#ifndef INCLUDED_SVT_FOLDERPICKER_HXX +#define INCLUDED_SVT_FOLDERPICKER_HXX + +#include <cppuhelper/implbase3.hxx> +#include <com/sun/star/ui/dialogs/XFolderPicker.hpp> +#include <com/sun/star/ui/dialogs/XAsynchronousExecutableDialog.hpp> +#include <com/sun/star/lang/XServiceInfo.hpp> +#include <com/sun/star/lang/XSingleServiceFactory.hpp> +#include <com/sun/star/lang/DisposedException.hpp> +#include <com/sun/star/uno/XComponentContext.hpp> +#include "commonpicker.hxx" + +class Dialog; + +// class SvtFolderPicker --------------------------------------------------- + +typedef ::cppu::ImplHelper3 < ::com::sun::star::ui::dialogs::XFolderPicker + , ::com::sun::star::ui::dialogs::XAsynchronousExecutableDialog + , ::com::sun::star::lang::XServiceInfo + > SvtFolderPicker_Base; + +class SvtFolderPicker :public SvtFolderPicker_Base + ,public ::svt::OCommonPicker +{ +private: + ::rtl::OUString m_aDescription; + + ::com::sun::star::uno::Reference< ::com::sun::star::ui::dialogs::XDialogClosedListener > + m_xListener; + + void prepareExecute( ); + DECL_LINK( DialogClosedHdl, Dialog* ); + +public: + SvtFolderPicker( const ::com::sun::star::uno::Reference < ::com::sun::star::lang::XMultiServiceFactory >& xFactory ); + virtual ~SvtFolderPicker(); + + //------------------------------------------------------------------------------------ + // disambiguate XInterface + //------------------------------------------------------------------------------------ + DECLARE_XINTERFACE( ) + + //------------------------------------------------------------------------------------ + // disambiguate XTypeProvider + //------------------------------------------------------------------------------------ + DECLARE_XTYPEPROVIDER( ) + + //------------------------------------------------------------------------------------ + // XFolderPicker functions + //------------------------------------------------------------------------------------ + + virtual void SAL_CALL setDisplayDirectory( const ::rtl::OUString& aDirectory ) throw( ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException ); + virtual ::rtl::OUString SAL_CALL getDisplayDirectory() throw( ::com::sun::star::uno::RuntimeException ); + virtual ::rtl::OUString SAL_CALL getDirectory() throw( ::com::sun::star::uno::RuntimeException ); + virtual void SAL_CALL setDescription( const ::rtl::OUString& aDescription ) throw ( ::com::sun::star::uno::RuntimeException ); + + //------------------------------------------------------------------------------------ + // XExecutableDialog functions + //------------------------------------------------------------------------------------ + virtual void SAL_CALL setTitle( const ::rtl::OUString& _rTitle ) throw (::com::sun::star::uno::RuntimeException); + virtual sal_Int16 SAL_CALL execute( ) throw (::com::sun::star::uno::RuntimeException); + + //------------------------------------------------------------------------------------ + // XAsynchronousExecutableDialog functions + //------------------------------------------------------------------------------------ + virtual void SAL_CALL setDialogTitle( const ::rtl::OUString& _rTitle ) throw (::com::sun::star::uno::RuntimeException); + virtual void SAL_CALL startExecuteModal( const ::com::sun::star::uno::Reference< ::com::sun::star::ui::dialogs::XDialogClosedListener >& xListener ) throw (::com::sun::star::uno::RuntimeException); + + //------------------------------------------------------------------------------------ + // XServiceInfo functions + //------------------------------------------------------------------------------------ + + /* XServiceInfo */ + virtual ::rtl::OUString SAL_CALL getImplementationName() throw( ::com::sun::star::uno::RuntimeException ); + virtual sal_Bool SAL_CALL supportsService( const ::rtl::OUString& sServiceName ) throw( ::com::sun::star::uno::RuntimeException ); + virtual com::sun::star::uno::Sequence< ::rtl::OUString > SAL_CALL + getSupportedServiceNames() throw( ::com::sun::star::uno::RuntimeException ); + + /* Helper for XServiceInfo */ + static com::sun::star::uno::Sequence< ::rtl::OUString > impl_getStaticSupportedServiceNames(); + static ::rtl::OUString impl_getStaticImplementationName(); + + /* Helper for registry */ + static ::com::sun::star::uno::Reference< com::sun::star::uno::XInterface > SAL_CALL impl_createInstance ( + const ::com::sun::star::uno::Reference< com::sun::star::uno::XComponentContext >& rxContext ) + throw( com::sun::star::uno::Exception ); + +protected: + //------------------------------------------------------------------------------------ + // OCommonPicker overridables + //------------------------------------------------------------------------------------ + virtual SvtFileDialog* implCreateDialog( Window* _pParent ); + virtual sal_Int16 implExecutePicker( ); +}; + +#endif // INCLUDED_SVT_FOLDERPICKER_HXX diff --git a/fpicker/source/office/asyncfilepicker.cxx b/fpicker/source/office/asyncfilepicker.cxx new file mode 100644 index 000000000000..4d08805999f4 --- /dev/null +++ b/fpicker/source/office/asyncfilepicker.cxx @@ -0,0 +1,220 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_fpicker.hxx" + +#include "asyncfilepicker.hxx" +#include "iodlg.hxx" +#include "svtools/fileview.hxx" +#include <tools/debug.hxx> + +#include <memory> + +//........................................................................ +namespace svt +{ +//........................................................................ + + //==================================================================== + //= AsyncPickerAction + //==================================================================== + DBG_NAME( AsyncPickerAction ) + //-------------------------------------------------------------------- + AsyncPickerAction::AsyncPickerAction( SvtFileDialog* _pDialog, SvtFileView* _pView, const Action _eAction ) + :m_refCount ( 0 ) + ,m_eAction ( _eAction ) + ,m_pView ( _pView ) + ,m_pDialog ( _pDialog ) + ,m_bRunning ( false ) + { + DBG_CTOR( AsyncPickerAction, NULL ); + DBG_ASSERT( m_pDialog, "AsyncPickerAction::AsyncPickerAction: invalid dialog!" ); + DBG_ASSERT( m_pView, "AsyncPickerAction::AsyncPickerAction: invalid view!" ); + } + + //-------------------------------------------------------------------- + AsyncPickerAction::~AsyncPickerAction() + { + DBG_DTOR( AsyncPickerAction, NULL ); + } + + //-------------------------------------------------------------------- + oslInterlockedCount SAL_CALL AsyncPickerAction::acquire() + { + return osl_incrementInterlockedCount( &m_refCount ); + } + + //-------------------------------------------------------------------- + oslInterlockedCount SAL_CALL AsyncPickerAction::release() + { + if ( 0 == osl_decrementInterlockedCount( &m_refCount ) ) + { + delete this; + return 0; + } + return m_refCount; + } + + //-------------------------------------------------------------------- + void AsyncPickerAction::cancel() + { + DBG_TESTSOLARMUTEX(); + // if this asserts, we'd need to have an own mutex per instance + + OSL_ENSURE( m_bRunning, "AsyncPickerAction::cancel: not running" ); + if ( m_pView ) + m_pView->CancelRunningAsyncAction(); + } + + //-------------------------------------------------------------------- + void AsyncPickerAction::execute( + const String& _rURL, + const String& _rFilter, + sal_Int32 _nMinTimeout, + sal_Int32 _nMaxTimeout, + const OUStringList& rBlackList ) + { + DBG_TESTSOLARMUTEX(); + // if this asserts, we'd need to have an own mutex per instance + + sal_Int32 nMinTimeout = _nMinTimeout; + sal_Int32 nMaxTimeout = _nMaxTimeout; + // normalizations + if ( nMinTimeout < 0 ) + // if negative, this is considered as "do it synchronously" + nMinTimeout = 0; + else if ( nMinTimeout < 1000 ) + nMinTimeout = 1000; + if ( nMaxTimeout <= nMinTimeout ) + nMaxTimeout = nMinTimeout + 30000; + + ::std::auto_ptr< FileViewAsyncAction > pActionDescriptor; + if ( nMinTimeout ) + { + pActionDescriptor.reset( new FileViewAsyncAction ); + pActionDescriptor->nMinTimeout = nMinTimeout; + pActionDescriptor->nMaxTimeout = nMaxTimeout; + pActionDescriptor->aFinishHandler = LINK( this, AsyncPickerAction, OnActionDone ); + } + + FileViewResult eResult = eFailure; + m_sURL = _rURL; + switch ( m_eAction ) + { + case ePrevLevel: + eResult = m_pView->PreviousLevel( pActionDescriptor.get() ); + break; + + case eOpenURL: + eResult = m_pView->Initialize( _rURL, _rFilter, pActionDescriptor.get(), rBlackList ); + break; + + case eExecuteFilter: + // preserve the filename (FS: why?) + m_sFileName = m_pDialog->getCurrentFileText(); + // execute the new filter + eResult = m_pView->ExecuteFilter( _rFilter, pActionDescriptor.get() ); + break; + + default: + DBG_ERROR( "AsyncPickerAction::execute: unknown action!" ); + break; + } + + acquire(); + if ( ( eResult == eSuccess ) || ( eResult == eFailure ) ) + { + // the handler is only called if the action could not be finished within + // the given minimum time period. In case of success, we need to call it + // explicitly + OnActionDone( reinterpret_cast< void* >( eResult ) ); + } + else if ( eResult == eStillRunning ) + { + m_bRunning = true; + m_pDialog->onAsyncOperationStarted(); + } + } + + //-------------------------------------------------------------------- + IMPL_LINK( AsyncPickerAction, OnActionDone, void*, pEmptyArg ) + { + DBG_TESTSOLARMUTEX(); + // if this asserts, we'd need to have an own mutex per instance + + FileViewResult eResult = static_cast< FileViewResult >( reinterpret_cast< sal_IntPtr >( pEmptyArg ) ); + OSL_ENSURE( eStillRunning != eResult, "AsyncPickerAction::OnActionDone: invalid result!" ); + + // release once (since we acquired in |execute|), but keep alive until the + // end of the method + ::rtl::Reference< AsyncPickerAction > xKeepAlive( this ); + release(); + + m_pDialog->onAsyncOperationFinished(); + m_bRunning = true; + + if ( eFailure == eResult ) + // TODO: do we need some kind of cleanup here? + return 0L; + + if ( eTimeout == eResult ) + { + m_pDialog->displayIOException( m_sURL, ::com::sun::star::ucb::IOErrorCode_CANT_READ ); + return 0L; + } + + OSL_ENSURE( eSuccess == eResult, "AsyncPickerAction::OnActionDone: what else valid results are there?" ); + + switch ( m_eAction ) + { + case ePrevLevel: + case eOpenURL: + m_pDialog->UpdateControls( m_pView->GetViewURL() ); + break; + + case eExecuteFilter: + // restore the filename + m_pView->SetNoSelection(); + m_pDialog->setCurrentFileText( m_sFileName, true ); + + // notify listeners + m_pDialog->FilterSelect(); + break; + + default: + DBG_ERROR( "AsyncPickerAction::OnActionDone: unknown action!" ); + break; + } + + return 1L; + } + +//........................................................................ +} // namespace svt +//........................................................................ + diff --git a/fpicker/source/office/asyncfilepicker.hxx b/fpicker/source/office/asyncfilepicker.hxx new file mode 100644 index 000000000000..d489a075b9ff --- /dev/null +++ b/fpicker/source/office/asyncfilepicker.hxx @@ -0,0 +1,118 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +#ifndef SVTOOLS_SOURCE_FILEPICKER_ASYNCFILEPICKER_HXX +#define SVTOOLS_SOURCE_FILEPICKER_ASYNCFILEPICKER_HXX + +/** === begin UNO includes === **/ +/** === end UNO includes === **/ + +#include <tools/link.hxx> +#include <tools/string.hxx> +#include <rtl/ref.hxx> +#include <rtl/ustring.hxx> +#include <com/sun/star/uno/Sequence.h> + +class SvtFileView; +class SvtFileDialog; + +typedef ::com::sun::star::uno::Sequence< ::rtl::OUString > OUStringList; + +//........................................................................ +namespace svt +{ +//........................................................................ + + + //==================================================================== + //= AsyncPickerAction + //==================================================================== + class AsyncPickerAction : public ::rtl::IReference + { + public: + enum Action + { + ePrevLevel, + eOpenURL, + eExecuteFilter + }; + + private: + mutable oslInterlockedCount m_refCount; + Action m_eAction; + SvtFileView* m_pView; + SvtFileDialog* m_pDialog; + String m_sURL; + String m_sFileName; + bool m_bRunning; + + public: + AsyncPickerAction( SvtFileDialog* _pDialog, SvtFileView* _pView, const Action _eAction ); + + /** executes the action + + @param _nMinTimeout + the minimum timeout to wait, in milliseconds. If negative, the action will we done + synchronously. If between 0 and 999, it will be corrected to 1000, means the + smallest valid value is 1000 (which equals one second). + @param _nMaxTimeout + The maximum time to wait for a result, in milliseconds. If there's no result of + the action within the given time frame, the action will be cancelled. + If smaller than or equal to <arg>_nMinTimeout</arg>, it will be corrected to + <arg>_nMinTimeout</arg> + 30000. + */ + void execute( + const String& _rURL, + const String& _rFilter, + sal_Int32 _nMinTimeout, + sal_Int32 _nMaxTimeout, + const OUStringList& rBlackList = OUStringList() ); + + /// cancels the running action + void cancel(); + + // IReference overridables + virtual oslInterlockedCount SAL_CALL acquire(); + virtual oslInterlockedCount SAL_CALL release(); + + protected: + virtual ~AsyncPickerAction(); + + private: + DECL_LINK( OnActionDone, void* ); + + AsyncPickerAction(); // never implemented + AsyncPickerAction( const AsyncPickerAction& ); // never implemented + AsyncPickerAction& operator=( const AsyncPickerAction& ); // never implemented + }; + +//........................................................................ +} // namespace svt +//........................................................................ + +#endif // SVTOOLS_SOURCE_FILEPICKER_ASYNCFILEPICKER_HXX + diff --git a/fpicker/source/office/commonpicker.cxx b/fpicker/source/office/commonpicker.cxx new file mode 100644 index 000000000000..7fcab23e7657 --- /dev/null +++ b/fpicker/source/office/commonpicker.cxx @@ -0,0 +1,506 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_fpicker.hxx" + +#include "commonpicker.hxx" +#include <com/sun/star/beans/PropertyAttribute.hpp> +#include <com/sun/star/beans/NamedValue.hpp> +#include <vcl/svapp.hxx> +#include <vos/mutex.hxx> +#include <toolkit/helper/vclunohelper.hxx> +#include <comphelper/weakeventlistener.hxx> +#include <comphelper/types.hxx> +#include <vcl/msgbox.hxx> +#include "iodlg.hxx" + +//......................................................................... +namespace svt +{ +//......................................................................... + +#define PROPERTY_ID_HELPURL 1 +#define PROPERTY_ID_WINDOW 2 + + // using -------------------------------------------------------------- + + using namespace ::com::sun::star::lang; + using namespace ::com::sun::star::ui::dialogs; + using namespace ::com::sun::star::uno; + using namespace ::com::sun::star::beans; + using namespace ::comphelper; + + //--------------------------------------------------------------------- + OCommonPicker::OCommonPicker( const ::com::sun::star::uno::Reference< ::com::sun::star::lang::XMultiServiceFactory >& _rxFactory ) + :OCommonPicker_Base( m_aMutex ) + ,OPropertyContainer( GetBroadcastHelper() ) + ,m_xORB( _rxFactory ) + ,m_pDlg( NULL ) + ,m_nCancelEvent( 0 ) + ,m_bExecuting( sal_False ) + { + // the two properties we have + registerProperty( + ::rtl::OUString::createFromAscii( "HelpURL" ), PROPERTY_ID_HELPURL, + PropertyAttribute::TRANSIENT, + &m_sHelpURL, ::getCppuType( &m_sHelpURL ) + ); + + registerProperty( + ::rtl::OUString::createFromAscii( "Window" ), PROPERTY_ID_WINDOW, + PropertyAttribute::TRANSIENT | PropertyAttribute::READONLY, + &m_xWindow, ::getCppuType( &m_xWindow ) + ); + } + + //--------------------------------------------------------------------- + OCommonPicker::~OCommonPicker() + { + if ( !GetBroadcastHelper().bDisposed ) + { + acquire(); + dispose(); + } + } + + //--------------------------------------------------------------------- + // disambiguate XInterface + //--------------------------------------------------------------------- + IMPLEMENT_FORWARD_XINTERFACE2( OCommonPicker, OCommonPicker_Base, OPropertyContainer ) + + //--------------------------------------------------------------------- + // disambiguate XTypeProvider + //--------------------------------------------------------------------- + IMPLEMENT_FORWARD_XTYPEPROVIDER2( OCommonPicker, OCommonPicker_Base, OPropertyContainer ) + + //--------------------------------------------------------------------- + // XComponent related methods + //--------------------------------------------------------------------- + void OCommonPicker::checkAlive() const SAL_THROW( (DisposedException) ) + { + if ( GetBroadcastHelper().bInDispose || GetBroadcastHelper().bDisposed ) + throw DisposedException(); + } + + void OCommonPicker::prepareDialog() + { + if ( !getDialog() ) + createPicker(); + + // set the title + if ( m_aTitle.getLength() > 0 ) + getDialog()->SetText( m_aTitle ); + } + + //--------------------------------------------------------------------- + void SAL_CALL OCommonPicker::disposing() + { + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + + stopWindowListening(); + + if ( m_nCancelEvent ) + Application::RemoveUserEvent( m_nCancelEvent ); + + { + ::osl::MutexGuard aOwnGuard( m_aMutex ); + if ( m_bExecuting && m_pDlg ) + m_pDlg->EndDialog( RET_CANCEL ); + } + + delete m_pDlg; + m_pDlg = NULL; + m_xWindow = NULL; + m_xDialogParent = NULL; + } + + //--------------------------------------------------------------------- + void OCommonPicker::stopWindowListening() + { + disposeComponent( m_xWindowListenerAdapter ); + disposeComponent( m_xParentListenerAdapter ); + } + + //--------------------------------------------------------------------- + // XEventListener + //--------------------------------------------------------------------- + void SAL_CALL OCommonPicker::disposing( const EventObject& _rSource ) throw (RuntimeException) + { + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + sal_Bool bDialogDying = _rSource.Source == m_xWindow; + sal_Bool bParentDying = _rSource.Source == m_xDialogParent; + + if ( bDialogDying || bParentDying ) + { + stopWindowListening(); + + if ( !bDialogDying ) // it's the parent which is dying -> delete the dialog + delete m_pDlg; + + m_pDlg = NULL; + m_xWindow = NULL; + m_xDialogParent = NULL; + } + else + { + DBG_ERROR( "OCommonPicker::disposing: where did this come from?" ); + } + } + + //--------------------------------------------------------------------- + // property set related methods + //--------------------------------------------------------------------- + ::cppu::IPropertyArrayHelper* OCommonPicker::createArrayHelper( ) const + { + Sequence< Property > aProps; + describeProperties( aProps ); + return new cppu::OPropertyArrayHelper( aProps ); + } + + //--------------------------------------------------------------------- + ::cppu::IPropertyArrayHelper& SAL_CALL OCommonPicker::getInfoHelper() + { + return *const_cast< OCommonPicker* >( this )->getArrayHelper(); + } + + //--------------------------------------------------------------------- + Reference< XPropertySetInfo > SAL_CALL OCommonPicker::getPropertySetInfo( ) throw(RuntimeException) + { + return ::cppu::OPropertySetHelper::createPropertySetInfo( getInfoHelper() ); + } + + //--------------------------------------------------------------------- + void SAL_CALL OCommonPicker::setFastPropertyValue_NoBroadcast( sal_Int32 _nHandle, const Any& _rValue ) throw (Exception) + { + OPropertyContainer::setFastPropertyValue_NoBroadcast( _nHandle, _rValue ); + + // if the HelpURL changed, forward this to the dialog + if ( PROPERTY_ID_HELPURL == _nHandle ) + if ( m_pDlg ) + OControlAccess::setHelpURL( m_pDlg, m_sHelpURL, sal_False ); + } + + + //--------------------------------------------------------------------- + sal_Bool OCommonPicker::createPicker() + { + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + + if ( !m_pDlg ) + { + m_pDlg = implCreateDialog( VCLUnoHelper::GetWindow( m_xDialogParent ) ); + DBG_ASSERT( m_pDlg, "OCommonPicker::createPicker: invalid dialog returned!" ); + + if ( m_pDlg ) + { + // synchronize the help id of the dialog with out help URL property + if ( m_sHelpURL.getLength() ) + { // somebody already set the help URL while we had no dialog yet + OControlAccess::setHelpURL( m_pDlg, m_sHelpURL, sal_False ); + } + else + { + m_sHelpURL = OControlAccess::getHelpURL( m_pDlg, sal_False ); + } + + m_xWindow = VCLUnoHelper::GetInterface( m_pDlg ); + + // add as event listener to the window + Reference< XComponent > xWindowComp( m_xWindow, UNO_QUERY ); + OSL_ENSURE( xWindowComp.is(), "OCommonPicker::createFileDialog: invalid window component!" ); + if ( xWindowComp.is() ) + { + m_xWindowListenerAdapter = new OWeakEventListenerAdapter( this, xWindowComp ); + // the adapter will add itself as listener, and forward notifications + } + + // _and_ add as event listener to the parent - in case the parent is destroyed + // before we are disposed, our disposal would access dead VCL windows then .... + m_xDialogParent = VCLUnoHelper::GetInterface( m_pDlg->GetParent() ); + xWindowComp = xWindowComp.query( m_xDialogParent ); + OSL_ENSURE( xWindowComp.is() || !m_pDlg->GetParent(), "OCommonPicker::createFileDialog: invalid window component (the parent this time)!" ); + if ( xWindowComp.is() ) + { + m_xParentListenerAdapter = new OWeakEventListenerAdapter( this, xWindowComp ); + // the adapter will add itself as listener, and forward notifications + } + } + } + + return NULL != m_pDlg; + } + + //--------------------------------------------------------------------- + // XControlAccess functions + //--------------------------------------------------------------------- + void SAL_CALL OCommonPicker::setControlProperty( const ::rtl::OUString& aControlName, const ::rtl::OUString& aControlProperty, const Any& aValue ) throw (IllegalArgumentException, RuntimeException) + { + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( createPicker() ) + { + ::svt::OControlAccess aAccess( m_pDlg, m_pDlg->GetView() ); + aAccess.setControlProperty( aControlName, aControlProperty, aValue ); + } + } + + //--------------------------------------------------------------------- + Any SAL_CALL OCommonPicker::getControlProperty( const ::rtl::OUString& aControlName, const ::rtl::OUString& aControlProperty ) throw (IllegalArgumentException, RuntimeException) + { + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( createPicker() ) + { + ::svt::OControlAccess aAccess( m_pDlg, m_pDlg->GetView() ); + return aAccess.getControlProperty( aControlName, aControlProperty ); + } + + return Any(); + } + + //--------------------------------------------------------------------- + // XControlInformation functions + //--------------------------------------------------------------------- + Sequence< ::rtl::OUString > SAL_CALL OCommonPicker::getSupportedControls( ) throw (RuntimeException) + { + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( createPicker() ) + { + ::svt::OControlAccess aAccess( m_pDlg, m_pDlg->GetView() ); + return aAccess.getSupportedControls( ); + } + + return Sequence< ::rtl::OUString >(); + } + + //--------------------------------------------------------------------- + sal_Bool SAL_CALL OCommonPicker::isControlSupported( const ::rtl::OUString& aControlName ) throw (RuntimeException) + { + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( createPicker() ) + { + ::svt::OControlAccess aAccess( m_pDlg, m_pDlg->GetView() ); + return aAccess.isControlSupported( aControlName ); + } + + return sal_False; + } + + //--------------------------------------------------------------------- + Sequence< ::rtl::OUString > SAL_CALL OCommonPicker::getSupportedControlProperties( const ::rtl::OUString& aControlName ) throw (IllegalArgumentException, RuntimeException) + { + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( createPicker() ) + { + ::svt::OControlAccess aAccess( m_pDlg, m_pDlg->GetView() ); + return aAccess.getSupportedControlProperties( aControlName ); + } + + return Sequence< ::rtl::OUString >(); + } + + //--------------------------------------------------------------------- + sal_Bool SAL_CALL OCommonPicker::isControlPropertySupported( const ::rtl::OUString& aControlName, const ::rtl::OUString& aControlProperty ) throw (IllegalArgumentException, RuntimeException) + { + checkAlive(); + + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + if ( createPicker() ) + { + ::svt::OControlAccess aAccess( m_pDlg, m_pDlg->GetView() ); + return aAccess.isControlPropertySupported( aControlName, aControlProperty ); + } + + return sal_False; + } + + //--------------------------------------------------------------------- + // XExecutableDialog functions + //--------------------------------------------------------------------- + void SAL_CALL OCommonPicker::setTitle( const rtl::OUString& _rTitle ) throw( RuntimeException ) + { + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + m_aTitle = _rTitle; + } + + //--------------------------------------------------------------------- + sal_Int16 OCommonPicker::execute() throw (RuntimeException) + { + ::vos::OGuard aGuard( Application::GetSolarMutex() ); + + prepareDialog(); + + { + ::osl::MutexGuard aOwnGuard( m_aMutex ); + m_bExecuting = sal_True; + } + sal_Int16 nResult = implExecutePicker(); + { + ::osl::MutexGuard aOwnGuard( m_aMutex ); + m_bExecuting = sal_False; + } + + return nResult; + } + + //--------------------------------------------------------------------- + // XCancellable functions + //--------------------------------------------------------------------- + void SAL_CALL OCommonPicker::cancel( ) throw (RuntimeException) + { + { + ::osl::MutexGuard aGuard( m_aMutex ); + if ( m_nCancelEvent ) + // nothing to do - the event for cancelling the dialog is already on the way + return; + } + + // The thread which executes our dialog has locked the solar mutex for + // sure. Cancelling the dialog should be done with a locked solar mutex, too. + // Thus we post ourself a message for cancelling the dialog. This way, the message + // is either handled in the thread which opened the dialog (which may even be + // this thread here), or, if no dialog is open, in the thread doing scheduling + // currently. Both is okay for us .... + // + // Note that we could do check if we are really executing the dialog currently. + // but the information would be potentially obsolete at the moment our event + // arrives, so we need to check it there, anyway ... + m_nCancelEvent = Application::PostUserEvent( LINK( this, OCommonPicker, OnCancelPicker ) ); + } + + //--------------------------------------------------------------------- + IMPL_LINK( OCommonPicker, OnCancelPicker, void*, EMPTYARG ) + { + // By definition, the solar mutex is locked when we arrive here. Note that this + // is important, as for instance the consistency of m_pDlg depends on this mutex. + ::osl::MutexGuard aGuard( m_aMutex ); + m_nCancelEvent = 0; + + if ( !m_bExecuting ) + // nothing to do. This may be because the dialog was cancelled after our cancel method + // posted this async event, or because somebody called cancel without the dialog + // being executed at this time. + return 0; + + OSL_ENSURE( getDialog(), "OCommonPicker::OnCancelPicker: executing, but no dialog!" ); + if ( getDialog() ) + getDialog()->EndDialog( RET_CANCEL ); + + return 0L; + } + + //------------------------------------------------------------------------------------ + // XInitialization functions + //------------------------------------------------------------------------------------ + void SAL_CALL OCommonPicker::initialize( const Sequence< Any >& _rArguments ) + throw ( Exception, RuntimeException ) + { + checkAlive(); + + ::rtl::OUString sSettingName; + Any aSettingValue; + + PropertyValue aPropArg; + NamedValue aPairArg; + + + const Any* pArguments = _rArguments.getConstArray(); + const Any* pArgumentsEnd = _rArguments.getConstArray() + _rArguments.getLength(); + for ( const Any* pArgument = pArguments; + pArgument != pArgumentsEnd; + ++pArgument + ) + { + if ( *pArgument >>= aPropArg ) + { + if ( aPropArg.Name.getLength() <= 0) + continue; + + sSettingName = aPropArg.Name; + aSettingValue = aPropArg.Value; + } + else if ( *pArgument >>= aPairArg ) + { + if ( aPairArg.Name.getLength() <= 0) + continue; + + sSettingName = aPairArg.Name; + aSettingValue = aPairArg.Value; + + + } + else + { + DBG_ERROR( + ( ::rtl::OString( "OCommonPicker::initialize: unknown argument type at position " ) + += ::rtl::OString::valueOf( (sal_Int32)( pArguments - _rArguments.getConstArray() ) ) + ).getStr() + ); + continue; + } + +#ifdef DBG_UTIL + sal_Bool bKnownSetting = +#endif + implHandleInitializationArgument( sSettingName, aSettingValue ); + DBG_ASSERT( bKnownSetting, + ( ::rtl::OString( "OCommonPicker::initialize: unknown argument \"" ) + += ::rtl::OString( sSettingName.getStr(), sSettingName.getLength(), osl_getThreadTextEncoding() ) + += ::rtl::OString( "\"!" ) + ).getStr() + ); + } + } + + //--------------------------------------------------------------------- + sal_Bool OCommonPicker::implHandleInitializationArgument( const ::rtl::OUString& _rName, const Any& _rValue ) SAL_THROW( ( Exception, RuntimeException ) ) + { + sal_Bool bKnown = sal_True; + if ( _rName.equalsAscii( "ParentWindow" ) ) + { + m_xDialogParent.clear(); + OSL_VERIFY( _rValue >>= m_xDialogParent ); + OSL_ENSURE( VCLUnoHelper::GetWindow( m_xDialogParent ), "OCommonPicker::implHandleInitializationArgument: invalid parent window given!" ); + } + else + bKnown = sal_False; + return bKnown; + } + +//......................................................................... +} // namespace svt +//......................................................................... + diff --git a/fpicker/source/office/commonpicker.hxx b/fpicker/source/office/commonpicker.hxx new file mode 100644 index 000000000000..2531f5e7f4c5 --- /dev/null +++ b/fpicker/source/office/commonpicker.hxx @@ -0,0 +1,209 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +#ifndef SVTOOLS_COMMONPICKER_HXX +#define SVTOOLS_COMMONPICKER_HXX + +#include <cppuhelper/compbase5.hxx> +#include <com/sun/star/ui/dialogs/XControlInformation.hpp> +#include <com/sun/star/ui/dialogs/XControlAccess.hpp> +#include <com/sun/star/lang/XMultiServiceFactory.hpp> +#include <com/sun/star/lang/DisposedException.hpp> +#include <com/sun/star/awt/XWindow.hpp> +#include <com/sun/star/util/XCancellable.hpp> +#include <com/sun/star/lang/XInitialization.hpp> +#include <comphelper/broadcasthelper.hxx> +#include <comphelper/propertycontainer.hxx> +#include <comphelper/proparrhlp.hxx> +#include <comphelper/uno3.hxx> +#include <tools/link.hxx> + +class SvtFileDialog; +class Window; + +namespace comphelper +{ + class OWeakEventListenerAdapter; +} + +//......................................................................... +namespace svt +{ +//......................................................................... + + typedef ::cppu::WeakComponentImplHelper5 < ::com::sun::star::ui::dialogs::XControlAccess + , ::com::sun::star::ui::dialogs::XControlInformation + , ::com::sun::star::lang::XEventListener + , ::com::sun::star::util::XCancellable + , ::com::sun::star::lang::XInitialization + > OCommonPicker_Base; + /** implements common functionality for the 2 UNO picker components + */ + class OCommonPicker + :public ::comphelper::OBaseMutex + ,public OCommonPicker_Base + ,public ::comphelper::OPropertyContainer + ,public ::comphelper::OPropertyArrayUsageHelper< OCommonPicker > + { + private: + ::com::sun::star::uno::Reference< ::com::sun::star::lang::XMultiServiceFactory > m_xORB; + + // <properties> + ::rtl::OUString m_sHelpURL; + ::com::sun::star::uno::Reference< ::com::sun::star::awt::XWindow > m_xWindow; + // </properties> + + SvtFileDialog* m_pDlg; + sal_uInt32 m_nCancelEvent; + sal_Bool m_bExecuting; + + ::com::sun::star::uno::Reference< ::com::sun::star::awt::XWindow > m_xDialogParent; + + ::com::sun::star::uno::Reference< ::com::sun::star::lang::XComponent > m_xWindowListenerAdapter; + ::com::sun::star::uno::Reference< ::com::sun::star::lang::XComponent > m_xParentListenerAdapter; + + protected: + ::rtl::OUString m_aTitle; + ::rtl::OUString m_aDisplayDirectory; + + protected: + inline SvtFileDialog* getDialog() { return m_pDlg; } + + inline const ::cppu::OBroadcastHelper& GetBroadcastHelper() const { return OCommonPicker_Base::rBHelper; } + inline ::cppu::OBroadcastHelper& GetBroadcastHelper() { return OCommonPicker_Base::rBHelper; } + + public: + OCommonPicker( const ::com::sun::star::uno::Reference< ::com::sun::star::lang::XMultiServiceFactory >& _rxFactory ); + + protected: + virtual ~OCommonPicker(); + + // overridables + + // will be called with locked SolarMutex + virtual SvtFileDialog* implCreateDialog( Window* _pParent ) = 0; + virtual sal_Int16 implExecutePicker( ) = 0; + // do NOT override XExecutableDialog::execute! We need to do some stuff there ourself ... + + protected: + //------------------------------------------------------------------------------------ + // disambiguate XInterface + //------------------------------------------------------------------------------------ + DECLARE_XINTERFACE( ) + + //------------------------------------------------------------------------------------ + // disambiguate XTypeProvider + //------------------------------------------------------------------------------------ + DECLARE_XTYPEPROVIDER( ) + + //------------------------------------------------------------------------------------ + // ComponentHelper/XComponent + //------------------------------------------------------------------------------------ + virtual void SAL_CALL disposing(); + + //------------------------------------------------------------------------------------ + // XEventListner + //------------------------------------------------------------------------------------ + virtual void SAL_CALL disposing( const ::com::sun::star::lang::EventObject& Source ) throw (::com::sun::star::uno::RuntimeException); + + //------------------------------------------------------------------------------------ + // property set related methods + //------------------------------------------------------------------------------------ + + // XPropertySet pure methods + virtual ::com::sun::star::uno::Reference< ::com::sun::star::beans::XPropertySetInfo > SAL_CALL getPropertySetInfo( ) throw(::com::sun::star::uno::RuntimeException); + // OPropertySetHelper pure methods + virtual ::cppu::IPropertyArrayHelper& SAL_CALL getInfoHelper(); + // OPropertyArrayUsageHelper pure methods + virtual ::cppu::IPropertyArrayHelper* createArrayHelper( ) const; + + // OPropertySetHelper overridden methods + virtual void SAL_CALL setFastPropertyValue_NoBroadcast( + sal_Int32 _nHandle, const ::com::sun::star::uno::Any& _rValue ) throw (::com::sun::star::uno::Exception); + + //------------------------------------------------------------------------------------ + // XExecutableDialog functions + //------------------------------------------------------------------------------------ + virtual void SAL_CALL setTitle( const ::rtl::OUString& _rTitle ) throw( ::com::sun::star::uno::RuntimeException ); + virtual sal_Int16 SAL_CALL execute() throw( ::com::sun::star::uno::RuntimeException ); + + //------------------------------------------------------------------------------------ + // XControlAccess functions + //------------------------------------------------------------------------------------ + virtual void SAL_CALL setControlProperty( const ::rtl::OUString& aControlName, const ::rtl::OUString& aControlProperty, const ::com::sun::star::uno::Any& aValue ) throw (::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException); + virtual ::com::sun::star::uno::Any SAL_CALL getControlProperty( const ::rtl::OUString& aControlName, const ::rtl::OUString& aControlProperty ) throw (::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException); + + //------------------------------------------------------------------------------------ + // XControlInformation functions + //------------------------------------------------------------------------------------ + virtual ::com::sun::star::uno::Sequence< ::rtl::OUString > SAL_CALL getSupportedControls( ) throw (::com::sun::star::uno::RuntimeException); + virtual sal_Bool SAL_CALL isControlSupported( const ::rtl::OUString& aControlName ) throw (::com::sun::star::uno::RuntimeException); + virtual ::com::sun::star::uno::Sequence< ::rtl::OUString > SAL_CALL getSupportedControlProperties( const ::rtl::OUString& aControlName ) throw (::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException); + virtual sal_Bool SAL_CALL isControlPropertySupported( const ::rtl::OUString& aControlName, const ::rtl::OUString& aControlProperty ) throw (::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException); + + //------------------------------------------------------------------------------------ + // XCancellable functions + //------------------------------------------------------------------------------------ + virtual void SAL_CALL cancel( ) throw (::com::sun::star::uno::RuntimeException); + + //------------------------------------------------------------------------------------ + // XInitialization functions + //------------------------------------------------------------------------------------ + + virtual void SAL_CALL initialize( const ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Any >& aArguments ) throw ( ::com::sun::star::uno::Exception, ::com::sun::star::uno::RuntimeException ); + + //------------------------------------------------------------------------------------ + // misc + //------------------------------------------------------------------------------------ + void checkAlive() const SAL_THROW( (::com::sun::star::lang::DisposedException) ); + + void prepareDialog(); + + protected: + sal_Bool createPicker(); + + /** handle a single argument from the XInitialization::initialize method + + @return <TRUE/> if the argument could be handled + */ + virtual sal_Bool implHandleInitializationArgument( + const ::rtl::OUString& _rName, + const ::com::sun::star::uno::Any& _rValue + ) + SAL_THROW( ( ::com::sun::star::uno::Exception, ::com::sun::star::uno::RuntimeException ) ); + + private: + void stopWindowListening(); + + DECL_LINK( OnCancelPicker, void* ); + }; +//......................................................................... +} // namespace svt +//......................................................................... + +#endif // SVTOOLS_COMMONPICKER_HXX + diff --git a/fpicker/source/office/fpinteraction.cxx b/fpicker/source/office/fpinteraction.cxx new file mode 100644 index 000000000000..72529bad04d6 --- /dev/null +++ b/fpicker/source/office/fpinteraction.cxx @@ -0,0 +1,169 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_fpicker.hxx" +#include "fpinteraction.hxx" +#include <tools/debug.hxx> +#include <com/sun/star/ucb/InteractiveIOException.hpp> +#include <com/sun/star/task/XInteractionAbort.hpp> +#include <com/sun/star/task/XInteractionApprove.hpp> +#include <com/sun/star/task/XInteractionDisapprove.hpp> +#include <com/sun/star/task/XInteractionRetry.hpp> + +//........................................................................ +namespace svt +{ +//........................................................................ + using namespace ::com::sun::star::uno; + using namespace ::com::sun::star::task; + using namespace ::com::sun::star::ucb; + + //==================================================================== + //= OFilePickerInteractionHandler + //==================================================================== + DBG_NAME( OFilePickerInteractionHandler ) + //-------------------------------------------------------------------- + OFilePickerInteractionHandler::OFilePickerInteractionHandler( const ::com::sun::star::uno::Reference< ::com::sun::star::task::XInteractionHandler >& _rxMaster ) + :m_xMaster( _rxMaster ) + ,m_bUsed( sal_False ) + ,m_eInterceptions( OFilePickerInteractionHandler::E_NOINTERCEPTION ) + { + DBG_CTOR( OFilePickerInteractionHandler, NULL ); + DBG_ASSERT( m_xMaster.is(), "OFilePickerInteractionHandler::OFilePickerInteractionHandler: invalid master handler!" ); + } + + //-------------------------------------------------------------------- + OFilePickerInteractionHandler::~OFilePickerInteractionHandler( ) + { + DBG_DTOR( OFilePickerInteractionHandler, NULL ); + } + + //-------------------------------------------------------------------- + void SAL_CALL OFilePickerInteractionHandler::handle( const Reference< XInteractionRequest >& _rxRequest ) throw (RuntimeException) + { + if (!_rxRequest.is()) + return; + + m_bUsed = sal_True; + + // extract some generic continuations ... might we need it later + // if something goes wrong. + Reference< XInteractionAbort > xAbort; + Reference< XInteractionApprove > xApprove; + Reference< XInteractionDisapprove > xDisapprove; + Reference< XInteractionRetry > xRetry; + + const Sequence< Reference< XInteractionContinuation > > lConts = _rxRequest->getContinuations(); + const Reference< XInteractionContinuation >* pConts = lConts.getConstArray(); + for (sal_Int32 i=0; i<lConts.getLength(); ++i) + { + if (!xAbort.is()) + xAbort = Reference< XInteractionAbort >(pConts[i], UNO_QUERY); + if (!xApprove.is()) + xApprove = Reference< XInteractionApprove >(pConts[i], UNO_QUERY); + if (!xDisapprove.is()) + xDisapprove = Reference< XInteractionDisapprove >(pConts[i], UNO_QUERY); + if (!xRetry.is()) + xRetry = Reference< XInteractionRetry >(pConts[i], UNO_QUERY); + } + + // safe the original request for later analyzing! + m_aException = _rxRequest->getRequest(); + + // intercept some interesting interactions + + // The "does not exist" interaction will be supressed here completly. + if (m_eInterceptions & OFilePickerInteractionHandler::E_DOESNOTEXIST) + { + InteractiveIOException aIoException; + if ( + (m_aException >>= aIoException ) && + (IOErrorCode_NOT_EXISTING == aIoException.Code) + ) + { + if (xAbort.is()) + xAbort->select(); + return; + } + } + + // no master => abort this operation ... + if (!m_xMaster.is()) + { + if (xAbort.is()) + xAbort->select(); + return; + } + + // forward it to our master - so he can handle all + // not interesting interactions :-) + m_xMaster->handle(_rxRequest); + } + + //-------------------------------------------------------------------- + void OFilePickerInteractionHandler::enableInterceptions( EInterceptedInteractions eInterceptions ) + { + m_eInterceptions = eInterceptions; + } + + //-------------------------------------------------------------------- + sal_Bool OFilePickerInteractionHandler::wasUsed() const + { + return m_bUsed; + } + + //-------------------------------------------------------------------- + void OFilePickerInteractionHandler::resetUseState() + { + m_bUsed = sal_False; + } + + //-------------------------------------------------------------------- + void OFilePickerInteractionHandler::forgetRequest() + { + m_aException = Any(); + } + + //-------------------------------------------------------------------- + sal_Bool OFilePickerInteractionHandler::wasAccessDenied() const + { + InteractiveIOException aIoException; + if ( + (m_aException >>= aIoException ) && + (IOErrorCode_ACCESS_DENIED == aIoException.Code) + ) + { + return sal_True; + } + return sal_False; + } + +//........................................................................ +} // namespace svt +//........................................................................ + diff --git a/fpicker/source/office/fpinteraction.hxx b/fpicker/source/office/fpinteraction.hxx new file mode 100644 index 000000000000..9b1b4e2c27a4 --- /dev/null +++ b/fpicker/source/office/fpinteraction.hxx @@ -0,0 +1,92 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +#ifndef SVTOOLS_FILEPICKER_INTERACTION_HXX +#define SVTOOLS_FILEPICKER_INTERACTION_HXX + +#include <cppuhelper/implbase1.hxx> +#include <com/sun/star/task/XInteractionHandler.hpp> + +//........................................................................ +namespace svt +{ +//........................................................................ + + //==================================================================== + //= OFilePickerInteractionHandler + //==================================================================== + typedef ::cppu::WeakImplHelper1 < ::com::sun::star::task::XInteractionHandler + > OFilePickerInteractionHandler_Base; + + /** a InteractionHandler implementation which extends another handler with some customizability + */ + class OFilePickerInteractionHandler : public OFilePickerInteractionHandler_Base + { + public: + /** flags, which indicates special handled interactions + These values will be used combained as flags - so they must + in range [2^n]! + */ + enum EInterceptedInteractions + { + E_NOINTERCEPTION = 0, + E_DOESNOTEXIST = 1 + // next values [2,4,8,16 ...]! + }; + + protected: + ::com::sun::star::uno::Reference< ::com::sun::star::task::XInteractionHandler > m_xMaster ; // our master handler + ::com::sun::star::uno::Any m_aException ; // the last handled request + sal_Bool m_bUsed ; // indicates using of this interaction handler instance + EInterceptedInteractions m_eInterceptions ; // enable/disable interception of some special interactions + + public: + OFilePickerInteractionHandler( const ::com::sun::star::uno::Reference< ::com::sun::star::task::XInteractionHandler >& _rxMaster ); + + // some generic functions + void enableInterceptions( EInterceptedInteractions eInterceptions ); + sal_Bool wasUsed () const; + void resetUseState (); + void forgetRequest (); + + // functions to analyze last cached request + sal_Bool wasAccessDenied() const; + + protected: + // XInteractionHandler + virtual void SAL_CALL handle( const ::com::sun::star::uno::Reference< ::com::sun::star::task::XInteractionRequest >& _rxRequest ) throw (::com::sun::star::uno::RuntimeException); + + private: + ~OFilePickerInteractionHandler(); + }; + +//........................................................................ +} // namespace svt +//........................................................................ + +#endif // SVTOOLS_FILEPICKER_INTERACTION_HXX + diff --git a/fpicker/source/office/fps_office.component b/fpicker/source/office/fps_office.component new file mode 100644 index 000000000000..3e49f68a49db --- /dev/null +++ b/fpicker/source/office/fps_office.component @@ -0,0 +1,37 @@ +<?xml version="1.0" encoding="UTF-8"?> +<!--********************************************************************** +* +* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. +* +* Copyright 2000, 2010 Oracle and/or its affiliates. +* +* OpenOffice.org - a multi-platform office productivity suite +* +* This file is part of OpenOffice.org. +* +* OpenOffice.org is free software: you can redistribute it and/or modify +* it under the terms of the GNU Lesser General Public License version 3 +* only, as published by the Free Software Foundation. +* +* OpenOffice.org is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU Lesser General Public License version 3 for more details +* (a copy is included in the LICENSE file that accompanied this code). +* +* You should have received a copy of the GNU Lesser General Public License +* version 3 along with OpenOffice.org. If not, see +* <http://www.openoffice.org/license.html> +* for a copy of the LGPLv3 License. +* +**********************************************************************--> + +<component loader="com.sun.star.loader.SharedLibrary" + xmlns="http://openoffice.org/2010/uno-components"> + <implementation name="com.sun.star.svtools.OfficeFilePicker"> + <service name="com.sun.star.ui.dialogs.OfficeFilePicker"/> + </implementation> + <implementation name="com.sun.star.svtools.OfficeFolderPicker"> + <service name="com.sun.star.ui.dialogs.OfficeFolderPicker"/> + </implementation> +</component> diff --git a/fpicker/source/office/fps_office.cxx b/fpicker/source/office/fps_office.cxx new file mode 100644 index 000000000000..3d06873338de --- /dev/null +++ b/fpicker/source/office/fps_office.cxx @@ -0,0 +1,73 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_fpicker.hxx" +#include "sal/types.h" + +#ifndef _CPPUHELPER_IMPLEMENTATIONENTRY_HXX_ +#include "cppuhelper/implementationentry.hxx" +#endif + +#include "OfficeFilePicker.hxx" +#include "OfficeFolderPicker.hxx" + +static cppu::ImplementationEntry g_entries[] = +{ + { + SvtFilePicker::impl_createInstance, + SvtFilePicker::impl_getStaticImplementationName, + SvtFilePicker::impl_getStaticSupportedServiceNames, + cppu::createSingleComponentFactory, 0, 0 + }, + { + SvtFolderPicker::impl_createInstance, + SvtFolderPicker::impl_getStaticImplementationName, + SvtFolderPicker::impl_getStaticSupportedServiceNames, + cppu::createSingleComponentFactory, 0, 0 + }, + { 0, 0, 0, 0, 0, 0 } +}; + +extern "C" +{ +SAL_DLLPUBLIC_EXPORT void SAL_CALL +component_getImplementationEnvironment( + const sal_Char ** ppEnvTypeName, uno_Environment ** /* ppEnv */) +{ + *ppEnvTypeName = CPPU_CURRENT_LANGUAGE_BINDING_NAME; +} + +SAL_DLLPUBLIC_EXPORT void * SAL_CALL component_getFactory( + const sal_Char * pImplementationName, void * pServiceManager, void * pRegistryKey) +{ + return cppu::component_getFactoryHelper ( + pImplementationName, pServiceManager, pRegistryKey, g_entries); +} + +} // extern "C" diff --git a/fpicker/source/office/fpsmartcontent.cxx b/fpicker/source/office/fpsmartcontent.cxx new file mode 100644 index 000000000000..a7842a5a2e58 --- /dev/null +++ b/fpicker/source/office/fpsmartcontent.cxx @@ -0,0 +1,308 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_fpicker.hxx" +#include "fpsmartcontent.hxx" + +/** === begin UNO includes === **/ +#include <com/sun/star/container/XChild.hpp> +#include <com/sun/star/ucb/ContentInfo.hpp> +#include <com/sun/star/ucb/ContentInfoAttribute.hpp> +#include <com/sun/star/ucb/XContent.hpp> +/** === end UNO includes === **/ + +#include <comphelper/processfactory.hxx> +#include <ucbhelper/commandenvironment.hxx> +#include <tools/solar.h> +#include <tools/debug.hxx> +#include <tools/string.hxx> + +//........................................................................ +namespace svt +{ +//........................................................................ + + using namespace ::com::sun::star::uno; + using namespace ::com::sun::star::task; + using namespace ::com::sun::star::ucb; + using namespace ::com::sun::star::lang; + using namespace ::com::sun::star::container; + + //==================================================================== + //= SmartContent + //==================================================================== + //-------------------------------------------------------------------- + SmartContent::SmartContent() + :m_pContent( NULL ) + ,m_eState( NOT_BOUND ) + ,m_pOwnInteraction( NULL ) + { + } + + //-------------------------------------------------------------------- + SmartContent::SmartContent( const ::rtl::OUString& _rInitialURL ) + :m_pContent( NULL ) + ,m_eState( NOT_BOUND ) + { + bindTo( _rInitialURL ); + } + + //-------------------------------------------------------------------- + SmartContent::~SmartContent() + { + //Do not delete the content. Because the content will be used by the cache. + //DELETEZ( m_pContent ); + } + + //-------------------------------------------------------------------- + void SmartContent::enableOwnInteractionHandler(::svt::OFilePickerInteractionHandler::EInterceptedInteractions eInterceptions) + { + Reference< XMultiServiceFactory > xFactory = ::comphelper::getProcessServiceFactory(); + Reference< XInteractionHandler > xGlobalInteractionHandler = Reference< XInteractionHandler >( + xFactory->createInstance( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("com.sun.star.task.InteractionHandler") ) ), UNO_QUERY ); + + m_pOwnInteraction = new ::svt::OFilePickerInteractionHandler(xGlobalInteractionHandler); + m_pOwnInteraction->enableInterceptions(eInterceptions); + m_xOwnInteraction = m_pOwnInteraction; + + m_xCmdEnv = new ::ucbhelper::CommandEnvironment( m_xOwnInteraction, Reference< XProgressHandler >() ); + } + + //-------------------------------------------------------------------- + void SmartContent::enableDefaultInteractionHandler() + { + // Don't free the memory here! It will be done by the next + // call automaticly - releasing of the uno reference ... + m_pOwnInteraction = NULL; + m_xOwnInteraction = Reference< XInteractionHandler >(); + + Reference< XMultiServiceFactory > xFactory = ::comphelper::getProcessServiceFactory(); + Reference< XInteractionHandler > xGlobalInteractionHandler = Reference< XInteractionHandler >( + xFactory->createInstance( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("com.sun.star.task.InteractionHandler") ) ), UNO_QUERY ); + m_xCmdEnv = new ucbhelper::CommandEnvironment( xGlobalInteractionHandler, Reference< XProgressHandler >() ); + } + + //-------------------------------------------------------------------- + ::svt::OFilePickerInteractionHandler* SmartContent::getOwnInteractionHandler() const + { + if (!m_xOwnInteraction.is()) + return NULL; + return m_pOwnInteraction; + } + + //-------------------------------------------------------------------- + SmartContent::InteractionHandlerType SmartContent::queryCurrentInteractionHandler() const + { + if (m_xOwnInteraction.is()) + return IHT_OWN; + + if (!m_xCmdEnv.is()) + return IHT_NONE; + + return IHT_DEFAULT; + } + + //-------------------------------------------------------------------- + void SmartContent::disableInteractionHandler() + { + // Don't free the memory here! It will be done by the next + // call automaticly - releasing of the uno reference ... + m_pOwnInteraction = NULL; + m_xOwnInteraction.clear(); + + m_xCmdEnv.clear(); + } + + //-------------------------------------------------------------------- + void SmartContent::bindTo( const ::rtl::OUString& _rURL ) + { + if ( getURL() == _rURL ) + // nothing to do, regardless of the state + return; + + DELETEZ( m_pContent ); + m_eState = INVALID; // default to INVALID + m_sURL = _rURL; + + if ( m_sURL.getLength() ) + { + try + { + m_pContent = new ::ucbhelper::Content( _rURL, m_xCmdEnv ); + m_eState = UNKNOWN; + // from now on, the state is unknown -> we cannot know for sure if the content + // is really valid (some UCP's only tell this when asking for properties, not upon + // creation) + } + catch( ContentCreationException& ) + { + } + catch( Exception& ) + { + DBG_ERROR( "SmartContent::bindTo: unexpected exception caught!" ); + } + } + else + { + m_eState = NOT_BOUND; + } + + + // don't forget to reset the may internal used interaction handler ... + // But do it only for our own specialized interaction helper! + ::svt::OFilePickerInteractionHandler* pHandler = getOwnInteractionHandler(); + if (pHandler) + { + pHandler->resetUseState(); + pHandler->forgetRequest(); + } + } + + //-------------------------------------------------------------------- + sal_Bool SmartContent::implIs( const ::rtl::OUString& _rURL, Type _eType ) + { + // bind to this content + bindTo( _rURL ); + + // did we survive this? + if ( isInvalid() || !isBound() ) + return sal_False; + + DBG_ASSERT( m_pContent, "SmartContent::implIs: inconsistence!" ); + // if, after an bindTo, we don't have a content, then we should be INVALID, or at least + // NOT_BOUND (the latter happens, for example, if somebody tries to ask for an empty URL) + + sal_Bool bIs = sal_False; + try + { + if ( Folder == _eType ) + bIs = m_pContent->isFolder(); + else + bIs = m_pContent->isDocument(); + + // from here on, we definately know that the content is valid + m_eState = VALID; + } + catch( Exception& ) + { + // now we're definately invalid + m_eState = INVALID; + } + return bIs; + } + + //-------------------------------------------------------------------- + void SmartContent::getTitle( ::rtl::OUString& /* [out] */ _rTitle ) + { + if ( !isBound() || isInvalid() ) + return; + + try + { + ::rtl::OUString sTitle; + m_pContent->getPropertyValue( ::rtl::OUString::createFromAscii( "Title" ) ) >>= sTitle; + _rTitle = sTitle; + + // from here on, we definately know that the content is valid + m_eState = VALID; + } + catch( ::com::sun::star::uno::Exception& ) + { + // now we're definately invalid + m_eState = INVALID; + } + } + + //-------------------------------------------------------------------- + sal_Bool SmartContent::hasParentFolder( ) + { + if ( !isBound() || isInvalid() ) + return sal_False; + + sal_Bool bRet = sal_False; + try + { + Reference< XChild > xChild( m_pContent->get(), UNO_QUERY ); + if ( xChild.is() ) + { + Reference< XContent > xParent( xChild->getParent(), UNO_QUERY ); + if ( xParent.is() ) + { + String aParentURL = String( xParent->getIdentifier()->getContentIdentifier() ); + bRet = ( aParentURL.Len() > 0 && aParentURL != (String)(m_pContent->getURL()) ); + + // now we're definately valid + m_eState = VALID; + } + } + } + catch( const Exception& ) + { + // now we're definately invalid + m_eState = INVALID; + } + return bRet; + } + + //-------------------------------------------------------------------- + sal_Bool SmartContent::canCreateFolder( ) + { + if ( !isBound() || isInvalid() ) + return sal_False; + + sal_Bool bRet = sal_False; + try + { + Sequence< ContentInfo > aInfo = m_pContent->queryCreatableContentsInfo(); + const ContentInfo* pInfo = aInfo.getConstArray(); + sal_Int32 nCount = aInfo.getLength(); + for ( sal_Int32 i = 0; i < nCount; ++i, ++pInfo ) + { + // Simply look for the first KIND_FOLDER... + if ( pInfo->Attributes & ContentInfoAttribute::KIND_FOLDER ) + { + bRet = sal_True; + break; + } + } + + // now we're definately valid + m_eState = VALID; + } + catch( Exception& ) + { + // now we're definately invalid + m_eState = INVALID; + } + return bRet; + } + +//........................................................................ +} // namespace svt +//........................................................................ + diff --git a/fpicker/source/office/fpsmartcontent.hxx b/fpicker/source/office/fpsmartcontent.hxx new file mode 100644 index 000000000000..d5474ae3fd5f --- /dev/null +++ b/fpicker/source/office/fpsmartcontent.hxx @@ -0,0 +1,212 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +#ifndef SVTOOLS_SOURCE_FILEPICKER_FPSMARTCONTENT_HXX +#define SVTOOLS_SOURCE_FILEPICKER_FPSMARTCONTENT_HXX + +#include "fpinteraction.hxx" + +/** === begin UNO includes === **/ +#include <com/sun/star/ucb/XCommandEnvironment.hpp> +#include <com/sun/star/task/XInteractionHandler.hpp> +/** === end UNO includes === **/ +#include <ucbhelper/content.hxx> + +//........................................................................ +namespace svt +{ +//........................................................................ + + //==================================================================== + //= SmartContent + //==================================================================== + /** a "smart content" which basically wraps an UCB content, but caches some informations + so that repeatedly recreating it may be faster + */ + class SmartContent + { + public: + enum State + { + NOT_BOUND, // never bound + UNKNOWN, // bound, but validity is unknown + VALID, // bound to an URL, and valid + INVALID // bound to an URL, and invalid + }; + + private: + ::rtl::OUString m_sURL; + ::ucbhelper::Content* m_pContent; + State m_eState; + ::com::sun::star::uno::Reference < ::com::sun::star::ucb::XCommandEnvironment > m_xCmdEnv; + ::com::sun::star::uno::Reference < ::com::sun::star::task::XInteractionHandler > m_xOwnInteraction; + ::svt::OFilePickerInteractionHandler* m_pOwnInteraction; + + private: + enum Type { Folder, Document }; + /// checks if the currently bound content is a folder or document + sal_Bool implIs( const ::rtl::OUString& _rURL, Type _eType ); + + SmartContent( const SmartContent& _rSource ); // never implemented + SmartContent& operator=( const SmartContent& _rSource ); // never implemented + + public: + SmartContent(); + SmartContent( const ::rtl::OUString& _rInitialURL ); + ~SmartContent(); + + public: + + /** create and set a specialized interaction handler at the internal used command environment. + + @param eInterceptions + will be directly forwarded to OFilePickerInteractionHandler::enableInterceptions() + */ + void enableOwnInteractionHandler(::svt::OFilePickerInteractionHandler::EInterceptedInteractions eInterceptions); + + /** disable the specialized interaction handler and use the global UI interaction handler only. + */ + void enableDefaultInteractionHandler(); + + /** return the internal used interaction handler object ... + Because this pointer will be valid only, if the uno object is hold + alive by it's uno reference (and this reference is set on the + command environment) we must return NULL, in case this environment does + not exist! + */ + ::svt::OFilePickerInteractionHandler* getOwnInteractionHandler() const; + + /** describes different types of interaction handlers + */ + enum InteractionHandlerType + { + IHT_NONE, + IHT_OWN, + IHT_DEFAULT + }; + + /** return the type of the internal used interaction handler object ... + + @seealso InteractionHandlerType + */ + InteractionHandlerType queryCurrentInteractionHandler() const; + + /** disable internal used interaction handler object ... + */ + void disableInteractionHandler(); + + /** returns the current state of the content + + @seealso State + */ + inline State getState( ) const { return m_eState; } + + /** checks if the content is valid + <p>Note that "not (is valid)" is not the same as "is invalid"</p> + */ + inline sal_Bool isValid( ) const { return VALID == getState(); } + + /** checks if the content is valid + <p>Note that "not (is invalid)" is not the same as "is valid"</p> + */ + inline sal_Bool isInvalid( ) const { return INVALID == getState(); } + + /** checks if the content is bound + */ + inline sal_Bool isBound( ) const { return NOT_BOUND != getState(); } + + /** returns the URL of the content + */ + inline ::rtl::OUString getURL() const { return m_pContent ? m_pContent->getURL() : m_sURL; } + + /** (re)creates the content for the given URL + + <p>Note that getState will return either UNKNOWN or INVALID after the call returns, + but never VALID. The reason is that there are content providers which allow to construct + content objects, even if the respective contents are not accessible. They tell about this + only upon working with the content object (e.g. when asking for the IsFolder).</p> + + @postcond + <member>getState</member> does not return NOT_BOUND after the call returns + */ + void bindTo( const ::rtl::OUString& _rURL ); + + /** retrieves the title of the content + @precond + the content is bound and not invalid + */ + void getTitle( ::rtl::OUString& /* [out] */ _rTitle ); + + /** checks if the content has a parent folder + @precond + the content is bound and not invalid + */ + sal_Bool hasParentFolder( ); + + /** checks if sub folders below the content can be created + @precond + the content is bound and not invalid + */ + sal_Bool canCreateFolder( ); + + /** binds to the given URL, checks whether or not it refers to a folder + + @postcond + the content is not in the state UNKNOWN + */ + inline sal_Bool isFolder( const ::rtl::OUString& _rURL ) + { + return implIs( _rURL, Folder ); + } + + /** binds to the given URL, checks whether or not it refers to a document + + @postcond + the content is not in the state UNKNOWN + */ + inline sal_Bool isDocument( const ::rtl::OUString& _rURL ) + { + return implIs( _rURL, Document ); + } + + /** checks if the content is existent (it is if and only if it is a document or a folder) + */ + inline sal_Bool is( const ::rtl::OUString& _rURL ) + { + return implIs( _rURL, Folder ) || implIs( _rURL, Document ); + } + + inline sal_Bool isFolder( ) { return isFolder( getURL() ); } + inline sal_Bool isDocument( ) { return isDocument( getURL() ); } + inline sal_Bool is( ) { return is( getURL() ); } + }; + +//........................................................................ +} // namespace svt +//........................................................................ + +#endif // SVTOOLS_SOURCE_FILEPICKER_FPSMARTCONTENT_HXX diff --git a/fpicker/source/office/iodlg.cxx b/fpicker/source/office/iodlg.cxx new file mode 100644 index 000000000000..b9d7fac3aa3b --- /dev/null +++ b/fpicker/source/office/iodlg.cxx @@ -0,0 +1,3482 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_fpicker.hxx" + +// includes -------------------------------------------------------------- + +#include "iodlg.hxx" +#include <tools/stream.hxx> +#include <tools/urlobj.hxx> +#include <vcl/fixed.hxx> +#include <vcl/lstbox.hxx> +#include <vcl/msgbox.hxx> +#include <vcl/svapp.hxx> +#include <vcl/timer.hxx> +#include <unotools/ucbhelper.hxx> +#include <ucbhelper/contentbroker.hxx> +#include "svtools/ehdl.hxx" +#include "svl/urihelper.hxx" +#include "unotools/pathoptions.hxx" +#include "unotools/viewoptions.hxx" +#include "svtools/fileview.hxx" +#include "unotools/inetoptions.hxx" +#include "svtools/sfxecode.hxx" +#include "svl/svarray.hxx" +#include "svtools/svtabbx.hxx" + +#define _SVSTDARR_USHORTS +#define _SVSTDARR_STRINGSDTOR +#include "svl/svstdarr.hxx" +#include <toolkit/helper/vclunohelper.hxx> +#include <unotools/localfilehelper.hxx> + +#ifndef _SVTOOLS_HRC +#include "svtools/svtools.hrc" +#endif +#ifndef _SVT_HELPID_HRC +#include "svtools/helpid.hrc" +#endif +#ifndef _SVTOOLS_IODLGIMPL_HRC +#include "iodlg.hrc" +#endif +#include "rtl/instance.hxx" +#include "asyncfilepicker.hxx" +#include "iodlgimp.hxx" +#include "svtools/inettbc.hxx" +#include "unotools/syslocale.hxx" +#include "svtools/QueryFolderName.hxx" +#ifndef _RTL_USTRING_HXX +#include <rtl/ustring.hxx> +#endif +#include <com/sun/star/lang/XMultiServiceFactory.hpp> +#include <com/sun/star/ucb/XContentProviderManager.hpp> +#include <com/sun/star/ui/dialogs/CommonFilePickerElementIds.hpp> +#include <com/sun/star/ui/dialogs/ExtendedFilePickerElementIds.hpp> +#include <com/sun/star/ui/dialogs/ControlActions.hpp> +#include <com/sun/star/beans/PropertyValue.hpp> +#include <com/sun/star/sdbc/XResultSet.hpp> +#include <com/sun/star/sdbc/XRow.hpp> +#include <com/sun/star/util/URL.hpp> +#include <com/sun/star/uno/Exception.hpp> +#include <com/sun/star/uno/Reference.hxx> +#include <com/sun/star/util/XURLTransformer.hpp> +#include <com/sun/star/uno/RuntimeException.hpp> +#include <com/sun/star/beans/XPropertySet.hpp> + +#ifndef _UNOTOOLS_PROCESSFACTORY_HXX +#include <comphelper/processfactory.hxx> +#endif +#include <osl/file.h> +#include <vcl/waitobj.hxx> + +// #97148# ------------------------------------ +#include <com/sun/star/task/XInteractionHandler.hpp> +#include "com/sun/star/ucb/InteractiveAugmentedIOException.hpp" +#include "fpinteraction.hxx" +#include <osl/process.h> +#include <comphelper/interaction.hxx> + +#include <algorithm> +#include <functional> + +//#define AUTOSELECT_USERFILTER + // define this for the experimental feature of user-filter auto selection + // means if the user enters e.g. *.doc<enter>, and there is a filter which is responsible for *.doc files (only), + // then this filter is selected automatically + +using namespace ::com::sun::star::beans; +using namespace ::com::sun::star::frame; +using namespace ::com::sun::star::ui::dialogs; +using namespace ::com::sun::star::uno; +using namespace ::com::sun::star::lang; +using namespace ::com::sun::star::ucb; +using namespace ::com::sun::star::container; +using namespace ::com::sun::star::task; +using namespace ::com::sun::star::sdbc; +using namespace ::utl; +using namespace ::svt; + +using namespace ExtendedFilePickerElementIds; +using namespace CommonFilePickerElementIds; +using namespace InternalFilePickerElementIds; + +#define IODLG_CONFIGNAME String(RTL_CONSTASCII_USTRINGPARAM("FileDialog")) +#define IMPGRF_CONFIGNAME String(RTL_CONSTASCII_USTRINGPARAM("ImportGraphicDialog")) + +#define GET_DECODED_NAME(aObj) \ + aObj.getName( INetURLObject::LAST_SEGMENT, true, INetURLObject::DECODE_WITH_CHARSET ) + +// Zeit die beim Traveln in der Filterbox gewartet wird, +// bis in der Browsebox gefiltert wird ( in ms ). +#define TRAVELFILTER_TIMEOUT 750 + +#define WIDTH_ADDITION 15 + +// functions ------------------------------------------------------------- + +namespace +{ + + //----------------------------------------------------------------------------- + String getMostCurrentFilter( SvtExpFileDlg_Impl* pImpl ) + { + DBG_ASSERT( pImpl, "invalid impl pointer" ); + const SvtFileDialogFilter_Impl* pFilter = pImpl->_pUserFilter; + + if ( !pFilter ) + pFilter = pImpl->GetCurFilter(); + + // Filtern. + if ( !pFilter ) + return String(); + + return pFilter->GetType(); + } + + //----------------------------------------------------------------------------- + sal_Bool restoreCurrentFilter( SvtExpFileDlg_Impl* _pImpl ) + { + DBG_ASSERT( _pImpl->GetCurFilter(), "restoreCurrentFilter: no current filter!" ); + DBG_ASSERT( _pImpl->GetCurFilterDisplayName().Len(), "restoreCurrentFilter: no current filter (no display name)!" ); + + _pImpl->SelectFilterListEntry( _pImpl->GetCurFilterDisplayName() ); + +#ifdef DBG_UTIL + String sSelectedDisplayName; + DBG_ASSERT( ( _pImpl->GetSelectedFilterEntry( sSelectedDisplayName ) == _pImpl->GetCurFilter() ) + && ( sSelectedDisplayName == _pImpl->GetCurFilterDisplayName() ), + "restoreCurrentFilter: inconsistence!" ); +#endif + return _pImpl->m_bNeedDelayedFilterExecute; + } + + //----------------------------------------------------------------------------- + String GetFsysExtension_Impl( const String& rFile, const String& rLastFilterExt ) + { + xub_StrLen nDotPos = rFile.SearchBackward( '.' ); + if ( nDotPos != STRING_NOTFOUND ) + { + if ( rLastFilterExt.Len() ) + { + if ( rFile.Copy( nDotPos + 1 ).EqualsIgnoreCaseAscii( rLastFilterExt ) ) + return String( rLastFilterExt ); + } + else + return String( rFile.Copy( nDotPos ) ); + } + return String(); + } + + //----------------------------------------------------------------------------- + void SetFsysExtension_Impl( String& rFile, const String& rExtension ) + { + const sal_Unicode* p0 = rFile.GetBuffer(); + const sal_Unicode* p1 = p0 + rFile.Len() - 1; + while ( p1 >= p0 && *p1 != sal_Unicode( '.' ) ) + p1--; + if ( p1 >= p0 ) + // remove old extension + rFile.Erase( + sal::static_int_cast< xub_StrLen >( + p1 - p0 + 1 - ( rExtension.Len() > 0 ? 0 : 1 ) ) ); + else if ( rExtension.Len() ) + // no old extension + rFile += sal_Unicode( '.' ); + rFile += rExtension; + } + + //----------------------------------------------------------------------------- + // move the control with the given offset + void lcl_MoveControl( Control* _pControl, sal_Int32 _nDeltaX, sal_Int32 _nDeltaY, sal_Int32* _pMaxY = NULL ) + { + if ( _pControl ) + { + Point aNewPos = _pControl->GetPosPixel(); + + // adjust the vertical position + aNewPos.Y() += _nDeltaY; + if ( _pMaxY && ( aNewPos.Y() > *_pMaxY ) ) + *_pMaxY = aNewPos.Y(); + + // adjust the horizontal position + aNewPos.X() += _nDeltaX; + + _pControl->SetPosPixel( aNewPos ); + } + } + + //------------------------------------------------------------------------- + void lcl_autoUpdateFileExtension( SvtFileDialog* _pDialog, const String& _rLastFilterExt ) + { + // if auto extension is enabled .... + if ( _pDialog->isAutoExtensionEnabled() ) + { + // automatically switch to the extension of the (maybe just newly selected) extension + String aNewFile = _pDialog->getCurrentFileText( ); + String aExt = GetFsysExtension_Impl( aNewFile, _rLastFilterExt ); + + // but only if there already is an extension + if ( aExt.Len() ) + { + // check if it is a real file extension, and not only the "post-dot" part in + // a directory name + // 28.03.2002 - 98337 - fs@openoffice.org + sal_Bool bRealExtensions = sal_True; + if ( STRING_NOTFOUND != aExt.Search( '/' ) ) + bRealExtensions = sal_False; + else if ( STRING_NOTFOUND != aExt.Search( '\\' ) ) + bRealExtensions = sal_False; + else + { + // no easy way to tell, because the part containing the dot already is the last + // segment of the complete file name + // So we have to check if the file name denotes a folder or a file. + // For performance reasons, we do this for file urls only + INetURLObject aURL( aNewFile ); + if ( INET_PROT_NOT_VALID == aURL.GetProtocol() ) + { + String sURL; + if ( ::utl::LocalFileHelper::ConvertPhysicalNameToURL( aNewFile, sURL ) ) + aURL = INetURLObject( sURL ); + } + if ( INET_PROT_FILE == aURL.GetProtocol() ) + { + // #97148# & #102204# ----- + try + { + bRealExtensions = !_pDialog->ContentIsFolder( aURL.GetMainURL( INetURLObject::NO_DECODE ) ); + } + catch( ::com::sun::star::uno::Exception& ) + { + DBG_WARNING( "Exception in lcl_autoUpdateFileExtension" ); + } + } + } + + if ( bRealExtensions ) + { + SetFsysExtension_Impl( aNewFile, _pDialog->GetDefaultExt() ); + _pDialog->setCurrentFileText( aNewFile ); + } + } + } + } + + //------------------------------------------------------------------------- + sal_Bool lcl_getHomeDirectory( const String& _rForURL, String& /* [out] */ _rHomeDir ) + { + _rHomeDir.Erase(); + + // now ask the content broker for a provider for this scheme + //================================================================= + try + { + // get the content provider manager + ::ucbhelper::ContentBroker* pBroker = ::ucbhelper::ContentBroker::get(); + Reference< XContentProviderManager > xProviderManager; + if ( pBroker ) + xProviderManager = pBroker->getContentProviderManagerInterface(); + + //================================================================= + // get the provider for the current scheme + Reference< XContentProvider > xProvider; + if ( xProviderManager.is() ) + xProvider = xProviderManager->queryContentProvider( _rForURL ); + + DBG_ASSERT( xProvider.is(), "lcl_getHomeDirectory: could not find a (valid) content provider for the current URL!" ); + Reference< XPropertySet > xProviderProps( xProvider, UNO_QUERY ); + if ( xProviderProps.is() ) + { + Reference< XPropertySetInfo > xPropInfo = xProviderProps->getPropertySetInfo(); + const ::rtl::OUString sHomeDirPropertyName( RTL_CONSTASCII_USTRINGPARAM( "HomeDirectory" ) ); + if ( !xPropInfo.is() || xPropInfo->hasPropertyByName( sHomeDirPropertyName ) ) + { + ::rtl::OUString sHomeDirectory; + xProviderProps->getPropertyValue( sHomeDirPropertyName ) >>= sHomeDirectory; + _rHomeDir = sHomeDirectory; + } + } + } + catch( const Exception& ) + { + DBG_ERROR( "lcl_getHomeDirectory: caught an exception!" ); + } + return 0 < _rHomeDir.Len(); + } + + //--------------------------------------------------------------------- + static String lcl_ensureFinalSlash( const String& _rDir ) + { + INetURLObject aWorkPathObj( _rDir, INET_PROT_FILE ); + aWorkPathObj.setFinalSlash(); + return aWorkPathObj.GetMainURL( INetURLObject::NO_DECODE ); + } + + //--------------------------------------------------------------------- + void convertStringListToUrls( const String& _rColonSeparatedList, ::std::vector< String >& _rTokens, bool _bFinalSlash ) + { + const sal_Unicode s_cSeparator = +#if defined(WNT) || defined(OS2) + ';' +#else + ':' +#endif + ; + xub_StrLen nTokens = _rColonSeparatedList.GetTokenCount( s_cSeparator ); + _rTokens.resize( 0 ); _rTokens.reserve( nTokens ); + for ( xub_StrLen i=0; i<nTokens; ++i ) + { + // the current token in the list + String sCurrentToken = _rColonSeparatedList.GetToken( i, s_cSeparator ); + if ( !sCurrentToken.Len() ) + continue; + + INetURLObject aCurrentURL; + + String sURL; + if ( ::utl::LocalFileHelper::ConvertPhysicalNameToURL( sCurrentToken, sURL ) ) + aCurrentURL = INetURLObject( sURL ); + else + { + // smart URL parsing, assuming FILE protocol + aCurrentURL = INetURLObject( sCurrentToken, INET_PROT_FILE ); + } + + if ( _bFinalSlash ) + aCurrentURL.setFinalSlash( ); + else + aCurrentURL.removeFinalSlash( ); + _rTokens.push_back( aCurrentURL.GetMainURL( INetURLObject::NO_DECODE ) ); + } + } + + //--------------------------------------------------------------------- + struct RemoveFinalSlash : public ::std::unary_function< String, void > + { + void operator()( String& _rURL ) + { + INetURLObject aURL( _rURL ); +#if defined(WNT) || defined(OS2) + if ( aURL.getSegmentCount() > 1 ) +#endif + aURL.removeFinalSlash( ); + _rURL = aURL.GetMainURL( INetURLObject::NO_DECODE ); + } + }; + + // ----------------------------------------------------------------------- + /** retrieves the value of an environment variable + @return <TRUE/> if and only if the retrieved string value is not empty + */ + bool getEnvironmentValue( const sal_Char* _pAsciiEnvName, ::rtl::OUString& _rValue ) + { + _rValue = ::rtl::OUString(); + ::rtl::OUString sEnvName = ::rtl::OUString::createFromAscii( _pAsciiEnvName ); + osl_getEnvironment( sEnvName.pData, &_rValue.pData ); + return _rValue.getLength() != 0; + } +} + +//*************************************************************************** +// ControlChain_Impl +//*************************************************************************** + +struct ControlChain_Impl +{ + Window* _pControl; + ControlChain_Impl* _pNext; + BOOL _bHasOwnerShip; + + ControlChain_Impl( Window* pControl, ControlChain_Impl* pNext ); + ~ControlChain_Impl(); +}; + +//*************************************************************************** + +ControlChain_Impl::ControlChain_Impl +( + Window* pControl, + ControlChain_Impl* pNext +) + : _pControl( pControl ), + _pNext( pNext ), + _bHasOwnerShip( TRUE ) +{ +} + +//*************************************************************************** + +ControlChain_Impl::~ControlChain_Impl() +{ + if ( _bHasOwnerShip ) + { + delete _pControl; + } + delete _pNext; +} + +//***************************************************************************** +// ResMgrHolder +//***************************************************************************** +namespace +{ + struct ResMgrHolder + { + ResMgr * operator ()() + { + return ResMgr::CreateResMgr (CREATEVERSIONRESMGR_NAME(fps_office)); + } + + static ResMgr * getOrCreate() + { + return rtl_Instance< + ResMgr, ResMgrHolder, + osl::MutexGuard, osl::GetGlobalMutex >::create ( + ResMgrHolder(), osl::GetGlobalMutex()); + } + }; + + struct SvtResId : public ResId + { + SvtResId (USHORT nId) : ResId (nId, *ResMgrHolder::getOrCreate()) {} + }; +} + +//***************************************************************************** +// SvtFileDialog +//***************************************************************************** +SvtFileDialog::SvtFileDialog +( + Window* _pParent, + WinBits nBits, + WinBits nExtraBits +) : + ModalDialog( _pParent, SvtResId( DLG_SVT_EXPLORERFILE ) ) + + ,_pUserControls( NULL ) + ,_pCbReadOnly( NULL ) + ,_pCbLinkBox( NULL) + ,_pCbPreviewBox( NULL ) + ,_pCbSelection( NULL ) + ,_pPbPlay( NULL ) + ,_pPrevWin( NULL ) + ,_pPrevBmp( NULL ) + ,_pFileView( NULL ) + ,_pFileNotifier( NULL ) + ,_pImp( new SvtExpFileDlg_Impl( nBits ) ) + ,_nExtraBits( nExtraBits ) + ,_bIsInExecute( FALSE ) + ,m_bInExecuteAsync( false ) + ,m_bHasFilename( false ) +{ + Init_Impl( nBits ); +} + +//***************************************************************************** + +SvtFileDialog::SvtFileDialog ( Window* _pParent, WinBits nBits ) + :ModalDialog( _pParent, SvtResId( DLG_SVT_EXPLORERFILE ) ) + ,_pUserControls( NULL ) + ,_pCbReadOnly( NULL ) + ,_pCbLinkBox( NULL) + ,_pCbPreviewBox( NULL ) + ,_pCbSelection( NULL ) + ,_pPbPlay( NULL ) + ,_pPrevWin( NULL ) + ,_pPrevBmp( NULL ) + ,_pFileView( NULL ) + ,_pFileNotifier( NULL ) + ,_pImp( new SvtExpFileDlg_Impl( nBits ) ) + ,_nExtraBits( 0L ) + ,_bIsInExecute( FALSE ) + ,m_bHasFilename( false ) +{ + Init_Impl( nBits ); +} + +//***************************************************************************** + +SvtFileDialog::~SvtFileDialog() +{ + if ( _pImp->_aIniKey.Len() ) + { + // save window state + SvtViewOptions aDlgOpt( E_DIALOG, _pImp->_aIniKey ); + aDlgOpt.SetWindowState( String( GetWindowState(), osl_getThreadTextEncoding() ) ); + String sUserData = _pFileView->GetConfigString(); + aDlgOpt.SetUserItem( ::rtl::OUString::createFromAscii( "UserData" ), + makeAny( ::rtl::OUString( sUserData ) ) ); + } + + _pFileView->SetSelectHdl( Link() ); + + delete _pImp; + delete _pFileView; + + delete _pCbReadOnly; + delete _pCbLinkBox; + delete _pCbPreviewBox; + delete _pCbSelection; + delete _pPbPlay; + delete _pPrevWin; + delete _pPrevBmp; + + delete _pUserControls; +} + +//***************************************************************************** + +void SvtFileDialog::Init_Impl +( + WinBits nStyle +) +{ + sal_Bool bIsHighContrast = GetSettings().GetStyleSettings().GetHighContrastMode(); + m_aImages = ImageList( SvtResId( bIsHighContrast ? RID_FILEPICKER_IMAGES_HC : RID_FILEPICKER_IMAGES ) ); + + _pImp->_nStyle = nStyle; + _pImp->_a6Size = LogicToPixel( Size( 6, 6 ), MAP_APPFONT ); + _pImp->_eMode = ( nStyle & WB_SAVEAS ) ? FILEDLG_MODE_SAVE : FILEDLG_MODE_OPEN; + _pImp->_eDlgType = FILEDLG_TYPE_FILEDLG; + + if ( ( nStyle & SFXWB_PATHDIALOG ) == SFXWB_PATHDIALOG ) + _pImp->_eDlgType = FILEDLG_TYPE_PATHDLG; + + // Set the directory for the "back to the default dir" button + INetURLObject aStdDirObj( SvtPathOptions().GetWorkPath() ); + SetStandardDir( aStdDirObj.GetMainURL( INetURLObject::NO_DECODE ) ); + + // Reichweite bestimmen. + if ( !( nStyle & SFXWB_NOREMOTE ) ) + { + _pImp->_nState |= FILEDLG_STATE_REMOTE; + } + + // Kontrollelement erzeugen, wobei die Reihenfolge die Tab-Steuerung + // bestimmt. + _pImp->_pFtFileName = new FixedText( this, SvtResId( FT_EXPLORERFILE_FILENAME ) ); + + SvtURLBox* pURLBox = new SvtURLBox( this ); + pURLBox->SetUrlFilter( &m_aURLFilter ); + _pImp->_pEdFileName = pURLBox; + + Edit aDummy( this, SvtResId( ED_EXPLORERFILE_FILENAME ) ); + _pImp->_pEdFileName->SetPosSizePixel( aDummy.GetPosPixel(), aDummy.GetSizePixel() ); + _pImp->_pEdFileName->Show(); + pURLBox->SetSelectHdl( LINK( this, SvtFileDialog, EntrySelectHdl_Impl ) ); + pURLBox->SetOpenHdl( STATIC_LINK( this, SvtFileDialog, OpenHdl_Impl ) ); + + // in folder picker mode, only auto-complete directories (no files) + bool bIsFolderPicker = ( _pImp->_eDlgType == FILEDLG_TYPE_PATHDLG ); + pURLBox->SetOnlyDirectories( bIsFolderPicker ); + + // in save mode, don't use the autocompletion as selection in the edit part + bool bSaveMode = ( FILEDLG_MODE_SAVE == _pImp->_eMode ); + pURLBox->SetNoURLSelection( bSaveMode ); + + _pImp->_pEdFileName->SetHelpId( HID_FILEDLG_AUTOCOMPLETEBOX ); + + _pImp->_pFtFileType = new FixedText( this, SvtResId( FT_EXPLORERFILE_FILETYPE ) ); + _pImp->CreateFilterListControl( this, SvtResId( LB_EXPLORERFILE_FILETYPE ) ); + + // move the filter listbox to the space occupied by the version listbox + // if that box isn't needed + if ( !( _nExtraBits & SFX_EXTRA_SHOWVERSIONS ) && + !( _nExtraBits & SFX_EXTRA_TEMPLATES ) && + !( _nExtraBits & SFX_EXTRA_IMAGE_TEMPLATE ) ) + { + { + FixedText aSharedListBoxLabel( this, SvtResId( FT_EXPLORERFILE_SHARED_LISTBOX ) ); + _pImp->_pFtFileType->SetPosPixel( aSharedListBoxLabel.GetPosPixel() ); + } + + { + ListBox aSharedListBox( this, SvtResId( LB_EXPLORERFILE_SHARED_LISTBOX ) ); + _pImp->GetFilterListControl()->SetPosPixel( aSharedListBox.GetPosPixel() ); + } + } + + _pImp->_pFtCurrentPath = new FixedText( this, SvtResId( FT_EXPLORERFILE_CURRENTPATH ) ); + WinBits nTmpStyle = _pImp->_pFtCurrentPath->GetStyle(); + nTmpStyle |= WB_PATHELLIPSIS; + _pImp->_pFtCurrentPath->SetStyle( nTmpStyle ); + + _pImp->_pBtnFileOpen = new PushButton( this, SvtResId( BTN_EXPLORERFILE_OPEN ) ); + _pImp->_pBtnCancel = new CancelButton( this, SvtResId( BTN_EXPLORERFILE_CANCEL ) ); + _pImp->_pBtnHelp = new HelpButton( this, SvtResId( BTN_EXPLORERFILE_HELP ) ); + + _pImp->_pBtnUp = new SvtUpButton_Impl( this, SvtResId( BTN_EXPLORERFILE_UP ) ); + _pImp->_pBtnNewFolder = new ImageButton( this, SvtResId( BTN_EXPLORERFILE_NEWFOLDER ) ); + _pImp->_pBtnNewFolder->SetStyle( _pImp->_pBtnNewFolder->GetStyle() | WB_NOPOINTERFOCUS ); + _pImp->_pBtnStandard = new SvtTravelButton_Impl( this, SvtResId( BTN_EXPLORERFILE_STANDARD ) ); + + _pImp->_pBtnUp->SetAccessibleName( _pImp->_pBtnUp->GetQuickHelpText() ); + _pImp->_pBtnNewFolder->SetAccessibleName( _pImp->_pBtnNewFolder->GetQuickHelpText() ); + _pImp->_pBtnStandard->SetAccessibleName( _pImp->_pBtnStandard->GetQuickHelpText() ); + + if ( ( nStyle & SFXWB_MULTISELECTION ) == SFXWB_MULTISELECTION ) + _pImp->_bMultiSelection = TRUE; + + _pFileView = new SvtFileView( this, SvtResId( CTL_EXPLORERFILE_FILELIST ), + FILEDLG_TYPE_PATHDLG == _pImp->_eDlgType, + _pImp->_bMultiSelection ); + _pFileView->SetUrlFilter( &m_aURLFilter ); + _pFileView->EnableAutoResize(); + + _pFileView->SetHelpId( HID_FILEDLG_STANDARD ); + _pFileView->SetStyle( _pFileView->GetStyle() | WB_TABSTOP ); + + // Positionen und Groessen der Knoepfe bestimmen. + Image aNewFolderImg( GetButtonImage( IMG_FILEDLG_CREATEFOLDER ) ); + _pImp->_pBtnNewFolder->SetModeImage( aNewFolderImg ); + + Size aSize( aNewFolderImg.GetSizePixel() ); + aSize.Width() += FILEDIALOG_DEF_IMAGEBORDER; + aSize.Height() += FILEDIALOG_DEF_IMAGEBORDER; + _pImp->_pBtnNewFolder->SetSizePixel( aSize ); + _pImp->_pBtnUp->SetSizePixel( aSize ); + _pImp->_pBtnStandard->SetSizePixel( aSize ); + + Size aDlgSize = GetOutputSizePixel(); + long n6AppFontInPixel = + LogicToPixel( Size( 6, 0 ), MAP_APPFONT ).Width(); + long n3AppFontInPixel = + LogicToPixel( Size( 3, 0 ), MAP_APPFONT ).Width(); + + // calculate the length of all buttons + const USHORT nBtnCount = 3; // "previous level", "new folder" and "standard dir" + long nDelta = n6AppFontInPixel; // right border + nDelta += ( nBtnCount * aSize.Width() ); // button count * button width + nDelta += ( n3AppFontInPixel + n3AppFontInPixel / 2 ); // spacing 1*big 1*small + + Point aPos( + aDlgSize.Width() - nDelta, + _pImp->_pBtnUp->GetPosPixel().Y() + ); + Size aCurPathSize( + aPos.X() - n6AppFontInPixel, + _pImp->_pFtCurrentPath->GetOutputSizePixel().Height() + ); + _pImp->_pFtCurrentPath->SetOutputSizePixel( aCurPathSize ); + _pImp->_pBtnUp->SetPosPixel( aPos ); + aPos.X() += aSize.Width(); + aPos.X() += n3AppFontInPixel; + _pImp->_pBtnNewFolder->SetPosPixel( aPos ); + aPos.X() += aSize.Width(); + aPos.X() += n3AppFontInPixel / 2; + _pImp->_pBtnStandard->SetPosPixel( aPos ); + nDelta = aSize.Height(); + nDelta -= aCurPathSize.Height(); + nDelta /= 2; + Point aCurPathPos = _pImp->_pFtCurrentPath->GetPosPixel(); + aCurPathPos.Y() += nDelta; + _pImp->_pFtCurrentPath->SetPosPixel( aCurPathPos ); + + if ( nStyle & SFXWB_READONLY ) + { + _pCbReadOnly = new CheckBox( this, SvtResId( CB_EXPLORERFILE_READONLY ) ); + _pCbReadOnly->SetHelpId( HID_FILEOPEN_READONLY ); + _pCbReadOnly->SetText( SvtResId( STR_SVT_FILEPICKER_READONLY ) ); + AddControl( _pCbReadOnly ); + ReleaseOwnerShip( _pCbReadOnly ); + _pCbReadOnly->SetClickHdl( LINK( this, SvtFileDialog, ClickHdl_Impl ) ); + } + + if ( nStyle & SFXWB_PASSWORD ) + { + _pImp->_pCbPassword = new CheckBox( this, SvtResId( CB_EXPLORERFILE_PASSWORD ) ); + _pImp->_pCbPassword->SetText( SvtResId( STR_SVT_FILEPICKER_PASSWORD ) ); + AddControl( _pImp->_pCbPassword ); + ReleaseOwnerShip( _pImp->_pCbPassword ); + _pImp->_pCbPassword->SetClickHdl( LINK( this, SvtFileDialog, ClickHdl_Impl ) ); + } + + // set the ini file for extracting the size + _pImp->_aIniKey = IODLG_CONFIGNAME; + + AddControls_Impl( ); + + // Zahl der Pixel bestimmen, um die die anderen Elemente in der Position + // Angepasst werden muessen. + aPos.Y() += aSize.Height(); + aPos.Y() += LogicToPixel( Size( 0, 6 ), MAP_APPFONT ).Height(); + long nYOffset = aPos.Y(); + aPos = _pFileView->GetPosPixel(); + nYOffset -= aPos.Y(); + + // Positionen der uebrigen Elemente anpassen. + aPos.Y() += nYOffset; + _pFileView->SetPosPixel( aPos ); + + lcl_MoveControl( _pImp->_pFtFileName, 0, nYOffset ); + lcl_MoveControl( _pImp->_pEdFileName, 0, nYOffset ); + + lcl_MoveControl( _pImp->_pFtFileVersion, 0, nYOffset ); + lcl_MoveControl( _pImp->_pLbFileVersion, 0, nYOffset ); + + lcl_MoveControl( _pImp->_pFtTemplates, 0, nYOffset ); + lcl_MoveControl( _pImp->_pLbTemplates, 0, nYOffset ); + + lcl_MoveControl( _pImp->_pFtImageTemplates, 0, nYOffset ); + lcl_MoveControl( _pImp->_pLbImageTemplates, 0, nYOffset ); + + lcl_MoveControl( _pImp->_pFtFileType, 0, nYOffset ); + lcl_MoveControl( _pImp->GetFilterListControl(), 0, nYOffset ); + + lcl_MoveControl( _pImp->_pBtnFileOpen, 0, nYOffset ); + lcl_MoveControl( _pImp->_pBtnCancel, 0, nYOffset ); + + lcl_MoveControl( _pImp->_pBtnHelp, 0, nYOffset + 3 ); + // a little more spacing between Cancel- and HelpButton + + // Groesse des Dialoges anpassen. + aSize = GetSizePixel(); + aSize.Height() += nYOffset; + SetSizePixel( aSize ); + + // Beschriftungen dem Modus anpassen. + USHORT nResId = STR_EXPLORERFILE_OPEN; + USHORT nButtonResId = 0; + + if ( nStyle & WB_SAVEAS ) + { + nResId = STR_EXPLORERFILE_SAVE; + nButtonResId = STR_EXPLORERFILE_BUTTONSAVE; + } + + if ( ( nStyle & SFXWB_PATHDIALOG ) == SFXWB_PATHDIALOG ) + { + _pImp->_pFtFileName->SetText( SvtResId( STR_PATHNAME ) ); + nResId = STR_PATHSELECT; + nButtonResId = STR_BUTTONSELECT; + } + + SetText( SvtResId( nResId ) ); + + if ( nButtonResId ) + _pImp->_pBtnFileOpen->SetText( SvtResId( nButtonResId ) ); + + if ( FILEDLG_TYPE_FILEDLG != _pImp->_eDlgType ) + { + _pImp->_pFtFileType->Hide(); + _pImp->GetFilterListControl()->Hide(); + } + + // Einstellungen der Steuerelemente vornehmen. + _pImp->_pBtnNewFolder->SetClickHdl( STATIC_LINK( this, SvtFileDialog, NewFolderHdl_Impl ) ); + _pImp->_pBtnFileOpen->SetClickHdl( STATIC_LINK( this, SvtFileDialog, OpenHdl_Impl ) ); + _pImp->_pBtnCancel->SetClickHdl( LINK( this, SvtFileDialog, CancelHdl_Impl ) ); + _pImp->SetFilterListSelectHdl( STATIC_LINK( this, SvtFileDialog, FilterSelectHdl_Impl ) ); + _pImp->_pEdFileName->SetGetFocusHdl( STATIC_LINK( this, SvtFileDialog, FileNameGetFocusHdl_Impl ) ); + _pImp->_pEdFileName->SetModifyHdl( STATIC_LINK( this, SvtFileDialog, FileNameModifiedHdl_Impl ) ); + _pFileView->SetSelectHdl( LINK( this, SvtFileDialog, SelectHdl_Impl ) ); + _pFileView->SetDoubleClickHdl( LINK( this, SvtFileDialog, DblClickHdl_Impl ) ); + _pFileView->SetOpenDoneHdl( LINK( this, SvtFileDialog, OpenDoneHdl_Impl ) ); + + // Resourcen freigeben. + FreeResource(); + + // Timer fuer Filterbox Travel setzen + _pImp->_aFilterTimer.SetTimeout( TRAVELFILTER_TIMEOUT ); + _pImp->_aFilterTimer.SetTimeoutHdl( STATIC_LINK( this, SvtFileDialog, FilterSelectHdl_Impl ) ); + + if ( WB_SAVEAS & nStyle ) + { + // different help ids if in save-as mode + // 90744 - 09.08.2001 - frank.schoenheit@sun.com + SetHelpId( HID_FILESAVE_DIALOG ); + + _pImp->_pEdFileName->SetHelpId( HID_FILESAVE_FILEURL ); + _pImp->_pBtnFileOpen->SetHelpId( HID_FILESAVE_DOSAVE ); + _pImp->_pBtnNewFolder->SetHelpId( HID_FILESAVE_CREATEDIRECTORY ); + _pImp->_pBtnStandard->SetHelpId( HID_FILESAVE_DEFAULTDIRECTORY ); + _pImp->_pBtnUp->SetHelpId( HID_FILESAVE_LEVELUP ); + _pImp->GetFilterListControl()->SetHelpId( HID_FILESAVE_FILETYPE ); + _pFileView->SetHelpId( HID_FILESAVE_FILEVIEW ); + + // formerly, there was only _pLbFileVersion, which was used for 3 different + // use cases. For reasons of maintainability, I introduced extra members (_pLbTemplates, _pLbImageTemplates) + // for the extra use cases, and separated _pLbFileVersion + // I did not find out in which cases the help ID is really needed HID_FILESAVE_TEMPLATE - all + // tests I made lead to a dialog where _no_ of the three list boxes was present. + // 96930 - 15.08.2002 - fs@openoffice.org + if ( _pImp->_pLbFileVersion ) + _pImp->_pLbFileVersion->SetHelpId( HID_FILESAVE_TEMPLATE ); + if ( _pImp->_pLbTemplates ) + _pImp->_pLbTemplates->SetHelpId( HID_FILESAVE_TEMPLATE ); + if ( _pImp->_pLbImageTemplates ) + _pImp->_pLbImageTemplates->SetHelpId( HID_FILESAVE_TEMPLATE ); + + if ( _pImp->_pCbPassword ) _pImp->_pCbPassword->SetHelpId( HID_FILESAVE_SAVEWITHPASSWORD ); + if ( _pImp->_pCbAutoExtension ) _pImp->_pCbAutoExtension->SetHelpId( HID_FILESAVE_AUTOEXTENSION ); + if ( _pImp->_pCbOptions ) _pImp->_pCbOptions->SetHelpId( HID_FILESAVE_CUSTOMIZEFILTER ); + if ( _pCbSelection ) _pCbSelection->SetHelpId( HID_FILESAVE_SELECTION ); + } + + // correct the z-order of the controls + implArrangeControls(); + + // special URLs, such as favourites and "restricted" paths + implInitializeSpecialURLLists( ); + + /// read our settings from the configuration + m_aConfiguration = OConfigurationTreeRoot::createWithServiceFactory( + ::comphelper::getProcessServiceFactory(), + ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "/org.openoffice.Office.UI/FilePicker" ) ) + ); +} + +//***************************************************************************** + +IMPL_STATIC_LINK( SvtFileDialog, NewFolderHdl_Impl, PushButton*, EMPTYARG ) +{ + pThis->_pFileView->EndInplaceEditing( false ); + + INetURLObject aObj( pThis->_pFileView->GetViewURL() ); + String sFolderName = aObj.getName( INetURLObject::LAST_SEGMENT, true, INetURLObject::DECODE_WITH_CHARSET, RTL_TEXTENCODING_UTF8 ); + svtools::QueryFolderNameDialog aDlg( pThis, sFolderName, String( SvtResId( STR_SVT_NEW_FOLDER ) ) ); + sal_Bool bHandled = sal_False; + + while ( !bHandled ) + { + if ( aDlg.Execute() == RET_OK ) + bHandled = pThis->_pFileView->CreateNewFolder( aDlg.GetName() ); + else + bHandled = sal_True; + } + + return 0; +} + +//***************************************************************************** + +IMPL_STATIC_LINK_NOINSTANCE( SvtFileDialog, ViewHdl_Impl, ImageButton*, EMPTYARG ) +{ + return 0; +} + +//***************************************************************************** +//----------------------------------------------------------------------------- +sal_Bool SvtFileDialog::createNewUserFilter( const String& _rNewFilter, sal_Bool _bAllowUserDefExt ) +{ + // delete the old user filter and create a new one + DELETEZ( _pImp->_pUserFilter ); + _pImp->_pUserFilter = new SvtFileDialogFilter_Impl( _rNewFilter, _rNewFilter ); + + // remember the extension + sal_Bool bIsAllFiles = _rNewFilter.EqualsAscii( FILEDIALOG_FILTER_ALL ); + if ( bIsAllFiles ) + EraseDefaultExt(); + else + SetDefaultExt( _rNewFilter.Copy( 2 ) ); + // TODO: this is nonsense. In the whole file there are a lotta places where we assume that a user filter + // is always "*.<something>". But changing this would take some more time than I have now ... + // 05.12.2001 - 95486 - fs@openoffice.org + + // now, the default extension is set to the one of the user filter (or empty) + // if the former is not allowed (_bAllowUserDefExt = <FALSE/>), we have to use the ext of the current filter + // (if possible) + sal_Bool bUseCurFilterExt = sal_True; + String sUserFilter = _pImp->_pUserFilter->GetType(); + xub_StrLen nSepPos = sUserFilter.SearchBackward( '.' ); + if ( STRING_NOTFOUND != nSepPos ) + { + String sUserExt = sUserFilter.Copy( nSepPos + 1 ); + if ( ( STRING_NOTFOUND == sUserExt.Search( '*' ) ) + && ( STRING_NOTFOUND == sUserExt.Search( '?' ) ) + ) + bUseCurFilterExt = sal_False; + } + + if ( !_bAllowUserDefExt || bUseCurFilterExt ) + { + if ( _pImp->GetCurFilter( ) ) + SetDefaultExt( _pImp->GetCurFilter( )->GetExtension() ); + else + EraseDefaultExt(); + } + + // outta here + return bIsAllFiles; +} + +//----------------------------------------------------------------------------- +#define FLT_NONEMPTY 0x0001 +#define FLT_CHANGED 0x0002 +#define FLT_USERFILTER 0x0004 +#define FLT_ALLFILESFILTER 0x0008 + +//----------------------------------------------------------------------------- +sal_uInt16 SvtFileDialog::adjustFilter( const String& _rFilter ) +{ + sal_uInt16 nReturn = 0; + + const sal_Bool bNonEmpty = ( _rFilter.Len() != 0 ); + if ( bNonEmpty ) + { + nReturn |= FLT_NONEMPTY; + + sal_Bool bFilterChanged = sal_True; + + // search for a corresponding filter + SvtFileDialogFilter_Impl* pFilter = FindFilter_Impl( _rFilter, FALSE, bFilterChanged ); + +#ifdef AUTOSELECT_USERFILTER + // if we found a filter which without allowing multi-extensions -> select it + if ( pFilter ) + { + _pImp->SelectFilterListEntry( pFilter->GetName() ); + _pImp->SetCurFilter( pFilter ); + } +#endif // AUTOSELECT_USERFILTER + + // look for multi-ext filters if necessary + if ( !pFilter ) + pFilter = FindFilter_Impl( _rFilter, TRUE, bFilterChanged ); + + if ( bFilterChanged ) + nReturn |= FLT_CHANGED; + + if ( !pFilter ) + { + nReturn |= FLT_USERFILTER; + // no filter found : use it as user defined filter +#ifdef AUTOSELECT_USERFILTER + if ( createNewUserFilter( _rFilter, sal_True ) ) +#else + if ( createNewUserFilter( _rFilter, sal_False ) ) +#endif + { // it's the "all files" filter + nReturn |= FLT_ALLFILESFILTER; + +#ifdef AUTOSELECT_USERFILTER + // select the "all files" entry + String sAllFilesFilter( SvtResId( STR_FILTERNAME_ALL ) ); + if ( _pImp->HasFilterListEntry( sAllFilesFilter ) ) + { + _pImp->SelectFilterListEntry( sAllFilesFilter ); + _pImp->SetCurFilter( _pImp->GetSelectedFilterEntry( sAllFilesFilter ) ); + } + else + _pImp->SetNoFilterListSelection( ); // there is no "all files" entry +#endif // AUTOSELECT_USERFILTER + } +#ifdef AUTOSELECT_USERFILTER + else + _pImp->SetNoFilterListSelection( ); +#endif // AUTOSELECT_USERFILTER + } + } + + return nReturn; +} + +//----------------------------------------------------------------------------- +IMPL_LINK( SvtFileDialog, CancelHdl_Impl, void*, EMPTYARG ) +{ + if ( m_pCurrentAsyncAction.is() ) + { + m_pCurrentAsyncAction->cancel(); + onAsyncOperationFinished(); + } + else + { + EndDialog( FALSE ); + } + return 1L; +} + +//----------------------------------------------------------------------------- +IMPL_STATIC_LINK( SvtFileDialog, OpenHdl_Impl, void*, pVoid ) +{ + if ( pThis->_pImp->_bMultiSelection && pThis->_pFileView->GetSelectionCount() > 1 ) + { + // bei Multiselektion spezielles Open + pThis->OpenMultiSelection_Impl(); + return 0; + } + + String aFileName; + String aOldPath( pThis->_pFileView->GetViewURL() ); + if ( pThis->_pImp->_bDoubleClick || pThis->_pFileView->HasChildPathFocus() ) + // Selection done by doubleclicking in the view, get filename from the view + aFileName = pThis->_pFileView->GetCurrentURL(); + + if ( !aFileName.Len() ) + { + // if an entry is selected in the view .... + if ( pThis->_pFileView->GetSelectionCount() ) + { // -> use this one. This will allow us to step down this folder + // #i8928# - 2002-12-20 - fs@openoffice.org + aFileName = pThis->_pFileView->GetCurrentURL(); + } + } + + if ( !aFileName.Len() ) + { + if ( pThis->_pImp->_eMode == FILEDLG_MODE_OPEN && pThis->_pImp->_pEdFileName->IsTravelSelect() ) + // OpenHdl called from URLBox; travelling through the list of URLs should not cause an opening + return 0; // MBA->PB: seems to be called never ?! + + // get the URL from from the edit field ( if not empty ) + if ( pThis->_pImp->_pEdFileName->GetText().Len() ) + { + String aText = pThis->_pImp->_pEdFileName->GetText(); + + // did we reach the root? + if ( !INetURLObject( aOldPath ).getSegmentCount() ) + { + if ( ( aText.Len() == 2 && aText.EqualsAscii( ".." ) ) || + ( aText.Len() == 3 && ( aText.EqualsAscii( "..\\" ) || aText.EqualsAscii( "../" ) ) ) ) + // don't go higher than the root + return 0; + } + +#if defined( UNX ) || defined( FS_PRIV_DEBUG ) + if ( ( 1 == aText.Len() ) && ( '~' == aText.GetBuffer()[0] ) ) + { + // go to the home directory + if ( lcl_getHomeDirectory( pThis->_pFileView->GetViewURL(), aFileName ) ) + // in case we got a home dir, reset the text of the edit + pThis->_pImp->_pEdFileName->SetText( String() ); + } + if ( !aFileName.Len() ) +#endif + { + // get url from autocomplete edit + aFileName = pThis->_pImp->_pEdFileName->GetURL(); + } + } + else if ( pVoid == pThis->_pImp->_pBtnFileOpen ) + // OpenHdl was called for the "Open" Button; if edit field is empty, use selected element in the view + aFileName = pThis->_pFileView->GetCurrentURL(); + } + + // MBA->PB: ?! + if ( !aFileName.Len() && pVoid == pThis->_pImp->_pEdFileName && pThis->_pImp->_pUserFilter ) + { + DELETEZ( pThis->_pImp->_pUserFilter ); + return 0; + } + + USHORT nLen = aFileName.Len(); + if ( !nLen ) + { + // if the dialog was opened to select a folder, the last selected folder should be selected + if( pThis->_pImp->_eDlgType == FILEDLG_TYPE_PATHDLG ) + { + aFileName = pThis->_pImp->_pFtCurrentPath->GetText(); + nLen = aFileName.Len(); + } + else + // no file selected ! + return 0; + } + + // mark input as selected + pThis->_pImp->_pEdFileName->SetSelection( Selection( 0, nLen ) ); + + // if a path with wildcards is given, divide the string into path and wildcards + String aFilter; + if ( !pThis->IsolateFilterFromPath_Impl( aFileName, aFilter ) ) + return 0; + + // if a filter was retrieved, there were wildcards ! + sal_uInt16 nNewFilterFlags = pThis->adjustFilter( aFilter ); + if ( nNewFilterFlags & FLT_CHANGED ) + { + // cut off all text before wildcard in edit and select wildcard + pThis->_pImp->_pEdFileName->SetText( aFilter ); + pThis->_pImp->_pEdFileName->SetSelection( Selection( 0, aFilter.Len() ) ); + } + + { + INetURLObject aFileObject( aFileName ); + if ( ( aFileObject.GetProtocol() == INET_PROT_NOT_VALID ) && aFileName.Len() ) + { + String sCompleted = SvtURLBox::ParseSmart( aFileName, pThis->_pFileView->GetViewURL(), SvtPathOptions().GetWorkPath() ); + if ( sCompleted.Len() ) + aFileName = sCompleted; + } + } + + // Pr"ufen, ob es sich um einen Ordner handelt. + BOOL bIsFolder = FALSE; + + // first thing before doing anyhing with the content: Reset it. When the user presses "open" (or "save" or "export", + // for that matter), s/he wants the complete handling, including all possible error messages, even if s/he + // does the same thing for the same content twice, s/he wants both fails to be displayed. + // Without the reset, it could be that the content cached all relevant information, and will not display any + // error messages for the same content a second time .... + pThis->m_aContent.bindTo( ::rtl::OUString( ) ); + + // #97148# & #102204# --------- + if ( aFileName.Len() ) + { + // Make sure we have own Interaction Handler in place. We do not need + // to intercept interactions here, but to record the fact that there + // was an interaction. + SmartContent::InteractionHandlerType eInterActionHandlerType + = pThis->m_aContent.queryCurrentInteractionHandler(); + if ( ( eInterActionHandlerType == SmartContent::IHT_NONE ) || + ( eInterActionHandlerType == SmartContent::IHT_DEFAULT ) ) + pThis->m_aContent.enableOwnInteractionHandler( + OFilePickerInteractionHandler::E_NOINTERCEPTION ); + + bIsFolder = pThis->m_aContent.isFolder( aFileName ); + + // access denied to the given resource - and interaction was already + // used => break following operations + OFilePickerInteractionHandler* pHandler + = pThis->m_aContent.getOwnInteractionHandler(); + + OSL_ENSURE( pHandler, "Got no Interaction Handler!!!" ); + + if ( pHandler->wasAccessDenied() ) + return 0; + + if ( pThis->m_aContent.isInvalid() && + ( pThis->_pImp->_eMode == FILEDLG_MODE_OPEN ) ) + { + if ( !pHandler->wasUsed() ) + ErrorHandler::HandleError( ERRCODE_IO_NOTEXISTS ); + + return 0; + } + + // restore previous Interaction Handler + if ( eInterActionHandlerType == SmartContent::IHT_NONE ) + pThis->m_aContent.disableInteractionHandler(); + else if ( eInterActionHandlerType == SmartContent::IHT_DEFAULT ) + pThis->m_aContent.enableDefaultInteractionHandler(); + } + + if ( !bIsFolder // no existent folder + && pThis->_pImp->_pCbAutoExtension // auto extension is enabled in general + && pThis->_pImp->_pCbAutoExtension->IsChecked() // auto extension is really to be used + && pThis->GetDefaultExt().Len() // there is a default extension + && pThis->GetDefaultExt() != '*' // the default extension is not "all" + && !( FILEDLG_MODE_SAVE == pThis->_pImp->_eMode // we're saving a file + && pThis->_pFileView->GetSelectionCount() // there is a selected file in the file view -> it will later on + ) // (in SvtFileDialog::GetPathList) be taken as file to save to + // (#114818# - 2004-03-17 - fs@openoffice.org) + && FILEDLG_MODE_OPEN != pThis->_pImp->_eMode // pb: #i83408# don't append extension on open + ) + { + // check extension and append the default extension if necessary + appendDefaultExtension(aFileName, + pThis->GetDefaultExt(), + pThis->_pImp->GetCurFilter()->GetType()); + } + + BOOL bOpenFolder = ( FILEDLG_TYPE_PATHDLG == pThis->_pImp->_eDlgType ) && + !pThis->_pImp->_bDoubleClick && pVoid != pThis->_pImp->_pEdFileName; + if ( bIsFolder ) + { + if ( bOpenFolder ) + { + pThis->_aPath = aFileName; + } + else + { + if ( aFileName != pThis->_pFileView->GetViewURL() ) + { + if ( !pThis->m_aURLFilter.isUrlAllowed( aFileName ) ) + { + pThis->simulateAccessDenied( aFileName ); + return 0; + } + + pThis->OpenURL_Impl( aFileName ); + } + else + { + if ( nNewFilterFlags & FLT_CHANGED ) + pThis->ExecuteFilter(); + } + + return 0; + } + } + else if ( !( nNewFilterFlags & FLT_NONEMPTY ) ) + { + // Ggf. URL speichern. + pThis->_aPath = aFileName; + } + else + { + // Ggf. neu filtern. + if ( nNewFilterFlags & FLT_CHANGED ) + pThis->ExecuteFilter(); + return 0; + } + + INetURLObject aFileObj( aFileName ); + if ( aFileObj.HasError() ) + { + ErrorHandler::HandleError( ERRCODE_IO_GENERAL ); + return 0; + } + + // if restrictions for the allowed folders are in place, we need to do a check here + if ( !pThis->m_aURLFilter.isUrlAllowed( aFileObj.GetMainURL( INetURLObject::NO_DECODE ) ) ) + { + pThis->simulateAccessDenied( aFileName ); + return 0; + } + + switch ( pThis->_pImp->_eMode ) + { + case FILEDLG_MODE_SAVE: + { + if ( ::utl::UCBContentHelper::Exists( aFileObj.GetMainURL( INetURLObject::NO_DECODE ) ) ) + { + QueryBox aBox( pThis, WB_YES_NO, SvtResId( STR_SVT_ALREADYEXISTOVERWRITE ) ); + if ( aBox.Execute() != RET_YES ) + return 0; + } + else + { + String aCurPath; + if ( ::utl::LocalFileHelper::ConvertURLToSystemPath( aFileName, aCurPath ) ) + { + // if content does not exist: at least its path must exist + INetURLObject aPathObj = aFileObj; + aPathObj.removeSegment(); + // #97148# & #102204# ------------ + BOOL bFolder = pThis->m_aContent.isFolder( aPathObj.GetMainURL( INetURLObject::NO_DECODE ) ); + if ( !bFolder ) + { + ErrorHandler::HandleError( ERRCODE_IO_NOTEXISTSPATH ); + return 0; + } + } + } + } + break; + + case FILEDLG_MODE_OPEN: + { + // do an existence check herein, again + // 16.11.2001 - 93107 - frank.schoenheit@sun.com + + if ( INET_PROT_FILE == aFileObj.GetProtocol( ) ) + { + sal_Bool bExists = sal_False; + // #102204# -------------- + bExists = pThis->m_aContent.is( aFileObj.GetMainURL( INetURLObject::NO_DECODE ) ); + + + if ( !bExists ) + { + String sError( SvtResId( RID_FILEOPEN_NOTEXISTENTFILE ) ); + + String sInvalidFile( aFileObj.GetMainURL( INetURLObject::DECODE_TO_IURI ) ); + if ( INET_PROT_FILE == aFileObj.GetProtocol() ) + { // if it's a file URL, transform the URL into system notation + ::rtl::OUString sURL( sInvalidFile ); + ::rtl::OUString sSystem; + osl_getSystemPathFromFileURL( sURL.pData, &sSystem.pData ); + sInvalidFile = sSystem; + } + sError.SearchAndReplaceAscii( "$name$", sInvalidFile ); + + ErrorBox aError( pThis, WB_OK, sError ); + aError.Execute(); + return 0; + } + } + } + break; + + default: + DBG_ERROR("SvtFileDialog, OpenHdl_Impl: invalid mode!"); + } + + // Interessenten benachrichtigen. + long nRet; + + if ( pThis->_aOKHdl.IsSet() ) + nRet = pThis->_aOKHdl.Call( pThis ); + else + nRet = pThis->OK(); + + if ( nRet ) + { + pThis->EndDialog( TRUE ); + } + + return nRet; +} + +//***************************************************************************** + +void SvtFileDialog::EnableAutocompletion( BOOL _bEnable ) +{ + _pImp->_pEdFileName->EnableAutocompletion( _bEnable ); +} + +//***************************************************************************** + +IMPL_STATIC_LINK( SvtFileDialog, FilterSelectHdl_Impl, ListBox*, pBox ) +{ + DBG_ASSERT( pBox, "SvtFileDialog:keine Instanz" ); + + // wurde der Handler vom Travel-Timer gefeuert? + if ( pBox == (ListBox*)&pThis->_pImp->_aFilterTimer ) + { + // Anzeige erneut filtern. + pThis->ExecuteFilter(); + return 0; + } + + String sSelectedFilterDisplayName; + SvtFileDialogFilter_Impl* pSelectedFilter = pThis->_pImp->GetSelectedFilterEntry( sSelectedFilterDisplayName ); + if ( !pSelectedFilter ) + { // there is no current selection. This happens if for instance the user selects a group separator using + // the keyboard, and then presses enter: When the selection happens, we immediately deselect the entry, + // so in this situation there is no current selection. + if ( restoreCurrentFilter( pThis->_pImp ) ) + pThis->ExecuteFilter(); + } + else + { + if ( pSelectedFilter->isGroupSeparator() ) + { // group separators can't be selected + // return to the previously selected entry + if ( pThis->_pImp->IsFilterListTravelSelect() ) + { + pThis->_pImp->SetNoFilterListSelection( ); + + // stop the timer for executing the filter + if ( pThis->_pImp->_aFilterTimer.IsActive() ) + pThis->_pImp->m_bNeedDelayedFilterExecute = sal_True; + pThis->_pImp->_aFilterTimer.Stop(); + } + else + { + if ( restoreCurrentFilter( pThis->_pImp ) ) + pThis->ExecuteFilter(); + } + } + else if ( ( pSelectedFilter != pThis->_pImp->GetCurFilter() ) + || pThis->_pImp->_pUserFilter + ) + { + // Store the old filter for the auto extension handling + String sLastFilterExt = pThis->_pImp->GetCurFilter()->GetExtension(); + DELETEZ( pThis->_pImp->_pUserFilter ); + + // Ggf. Filter des Benutzers entfernen. + pThis->_pImp->SetCurFilter( pSelectedFilter, sSelectedFilterDisplayName ); + + // Ggf. Endung anzeigen. + pThis->SetDefaultExt( pSelectedFilter->GetExtension() ); + USHORT nSepPos = pThis->GetDefaultExt().Search( FILEDIALOG_DEF_EXTSEP ); + + if ( nSepPos != STRING_NOTFOUND ) + pThis->EraseDefaultExt( nSepPos ); + + // update the extension of the current file if necessary + lcl_autoUpdateFileExtension( pThis, sLastFilterExt ); + + // wenn der Benutzer schnell durch die Filterbox + // travelt, nicht sofort Filtern + if ( pThis->_pImp->IsFilterListTravelSelect() ) + { + // FilterSelectHdl_Impl soll in + // TRAVELFILTER_TIMEOUT ms neu gefeuert werden + pThis->_pImp->_aFilterTimer.Start(); + } + else + { + // evtl. vorher gestarteten Timer stoppen + pThis->_pImp->_aFilterTimer.Stop(); + + // Anzeige erneut filtern. + pThis->ExecuteFilter(); + } + } + } + + return 0; +} + +//***************************************************************************** + +IMPL_STATIC_LINK( SvtFileDialog, FileNameGetFocusHdl_Impl, void*, EMPTYARG ) +{ + pThis->_pFileView->SetNoSelection(); + pThis->_pFileView->Update(); + return 0; +} + +//***************************************************************************** + +IMPL_STATIC_LINK( SvtFileDialog, FileNameModifiedHdl_Impl, void*, EMPTYARG ) +{ + FileNameGetFocusHdl_Impl( pThis, NULL ); + return 0; +} + +//***************************************************************************** + +SvtFileDialogFilter_Impl* SvtFileDialog::FindFilter_Impl +( + const String& _rFilter, + sal_Bool _bMultiExt,/* TRUE - auch Filter mit mehreren Endungen + beruecksichtigen + FALSE - keine ... + */ + sal_Bool& _rFilterChanged +) + +/* [Beschreibung] + + Die Methode sucht in den eingef"ugten Filtern nach der + spezifizierten Endung. +*/ + +{ + SvtFileDialogFilter_Impl* pFoundFilter = NULL; + SvtFileDialogFilterList_Impl* pList = _pImp->_pFilter; + USHORT nFilter = pList->Count(); + + while ( nFilter-- ) + { + SvtFileDialogFilter_Impl* pFilter = pList->GetObject( nFilter ); + const String& rType = pFilter->GetType(); + String aSingleType = rType; + + if ( _bMultiExt ) + { + USHORT nIdx = 0; + while ( !pFoundFilter && nIdx != STRING_NOTFOUND ) + { + aSingleType = rType.GetToken( 0, FILEDIALOG_DEF_EXTSEP, nIdx ); +#ifdef UNX + if ( aSingleType.CompareTo( _rFilter ) == COMPARE_EQUAL ) +#else + if ( aSingleType.CompareIgnoreCaseToAscii( _rFilter ) == COMPARE_EQUAL ) +#endif + pFoundFilter = pFilter; + } + } +#ifdef UNX + else if ( rType.CompareTo( _rFilter ) == COMPARE_EQUAL ) +#else + else if ( rType.CompareIgnoreCaseToAscii( _rFilter ) == COMPARE_EQUAL ) +#endif + pFoundFilter = pFilter; + + if ( pFoundFilter ) + { + // Filter aktivieren. + _rFilterChanged = _pImp->_pUserFilter || ( _pImp->GetCurFilter() != pFilter ); + + createNewUserFilter( _rFilter, sal_False ); + + break; + } + } + return pFoundFilter; +} + +//***************************************************************************** + +void SvtFileDialog::ExecuteFilter() +{ + _pImp->m_bNeedDelayedFilterExecute = sal_False; + executeAsync( AsyncPickerAction::eExecuteFilter, String(), getMostCurrentFilter( _pImp ) ); +} + +//***************************************************************************** + +void SvtFileDialog::OpenMultiSelection_Impl() + +/* [Beschreibung] + + OpenHandler f"ur MultiSelektion +*/ + +{ + String aPath; + ULONG nCount = _pFileView->GetSelectionCount(); + SvLBoxEntry* pEntry = nCount ? _pFileView->FirstSelected() : NULL; + + if ( nCount && pEntry ) + _aPath = _pFileView->GetURL( pEntry ); + + // Interessenten benachrichtigen. + long nRet; + + if ( _aOKHdl.IsSet() ) + nRet = _aOKHdl.Call( this ); + else + nRet = OK(); + + if ( nRet ) + EndDialog( TRUE ); +} + +//***************************************************************************** + +void SvtFileDialog::UpdateControls( const String& rURL ) +{ + _pImp->_pEdFileName->SetBaseURL( rURL ); + + INetURLObject aObj( rURL ); + + //========================================================================= + { + String sText; + DBG_ASSERT( INET_PROT_NOT_VALID != aObj.GetProtocol(), "SvtFileDialog::UpdateControls: Invalid URL!" ); + + if ( aObj.getSegmentCount() ) + { + ::utl::LocalFileHelper::ConvertURLToSystemPath( rURL, sText ); + if ( sText.Len() ) + { + // no Fsys path for server file system ( only UCB has mountpoints! ) + if ( INET_PROT_FILE != aObj.GetProtocol() ) + sText = rURL.Copy( static_cast< USHORT >( + INetURLObject::GetScheme( aObj.GetProtocol() ).getLength() ) ); + } + + if ( !sText.Len() && aObj.getSegmentCount() ) + sText = rURL; + } + + // path mode ? + if ( FILEDLG_TYPE_PATHDLG == _pImp->_eDlgType ) + // -> set new path in the edit field + _pImp->_pEdFileName->SetText( sText ); + + // in the "current path" field, truncate the trailing slash + if ( aObj.hasFinalSlash() ) + { + aObj.removeFinalSlash(); + String sURL( aObj.GetMainURL( INetURLObject::NO_DECODE ) ); + if ( !::utl::LocalFileHelper::ConvertURLToSystemPath( sURL, sText ) ) + sText = sURL; + } + + if ( !sText.Len() && rURL.Len() ) + // happens, for instance, for URLs which the INetURLObject does not know to belong to a hierarchical scheme + sText = rURL; + _pImp->_pFtCurrentPath->SetText( sText ); + } + + //========================================================================= + _aPath = rURL; + if ( _pFileNotifier ) + _pFileNotifier->notify( DIRECTORY_CHANGED, 0 ); +} + +//***************************************************************************** + +IMPL_LINK( SvtFileDialog, SelectHdl_Impl, SvTabListBox*, pBox ) +{ + SvLBoxEntry* pEntry = pBox->FirstSelected(); + DBG_ASSERT( pEntry, "SelectHandler without selected entry" ); + SvtContentEntry* pUserData = (SvtContentEntry*)pEntry->GetUserData(); + + if ( pUserData ) + { + INetURLObject aObj( pUserData->maURL ); + if ( FILEDLG_TYPE_PATHDLG == _pImp->_eDlgType ) + { + if ( aObj.GetProtocol() == INET_PROT_FILE ) + { + if ( !pUserData->mbIsFolder ) + aObj.removeSegment(); + String aName = aObj.getFSysPath( (INetURLObject::FSysStyle)(INetURLObject::FSYS_DETECT & ~INetURLObject::FSYS_VOS) ); + _pImp->_pEdFileName->SetText( aName ); + _pImp->_pEdFileName->SetSelection( Selection( 0, aName.Len() ) ); + _aPath = pUserData->maURL; + } + else if ( !pUserData->mbIsFolder ) + { + _pImp->_pEdFileName->SetText( pUserData->maURL ); + _pImp->_pEdFileName->SetSelection( Selection( 0, pUserData->maURL.Len() ) ); + _aPath = pUserData->maURL; + } + else + _pImp->_pEdFileName->SetText( UniString() ); + } + else + { + if ( !pUserData->mbIsFolder ) + { + String aName = pBox->GetEntryText( pEntry, 0 ); + _pImp->_pEdFileName->SetText( aName ); + _pImp->_pEdFileName->SetSelection( Selection( 0, aName.Len() ) ); + _aPath = pUserData->maURL; + } + } + } + + if ( _pImp->_bMultiSelection && _pFileView->GetSelectionCount() > 1 ) + { + // bei Multiselektion den Datei-Edit leeren + _pImp->_pEdFileName->SetText( String() ); + } + + FileSelect(); + + return 0; +} + +//***************************************************************************** + +IMPL_LINK( SvtFileDialog, DblClickHdl_Impl, SvTabListBox*, EMPTYARG ) +{ + _pImp->_bDoubleClick = TRUE; + OpenHdl_Impl( this, NULL ); + _pImp->_bDoubleClick = FALSE; + + return 0; +} + +//***************************************************************************** + +IMPL_LINK( SvtFileDialog, EntrySelectHdl_Impl, ComboBox*, EMPTYARG ) +{ + FileSelect(); + + return 0; +} + +//***************************************************************************** + +IMPL_LINK( SvtFileDialog, OpenDoneHdl_Impl, SvtFileView*, pView ) +{ + String sCurrentFolder( pView->GetViewURL() ); + // check if we can create new folders + EnableControl( _pImp->_pBtnNewFolder, ContentCanMakeFolder( sCurrentFolder ) && m_aURLFilter.isUrlAllowed( sCurrentFolder, false ) ); + + // check if we can travel one level up + bool bCanTravelUp = ContentHasParentFolder( pView->GetViewURL() ); + if ( bCanTravelUp ) + { + // additional check: the parent folder should not be prohibited + INetURLObject aCurrentFolder( sCurrentFolder ); + DBG_ASSERT( INET_PROT_NOT_VALID != aCurrentFolder.GetProtocol(), + "SvtFileDialog::OpenDoneHdl_Impl: invalid current URL!" ); + + aCurrentFolder.removeSegment(); + bCanTravelUp &= m_aURLFilter.isUrlAllowed( aCurrentFolder.GetMainURL( INetURLObject::NO_DECODE ) ); + } + EnableControl( _pImp->_pBtnUp, bCanTravelUp ); + + return 0; +} + +//***************************************************************************** + +IMPL_LINK( SvtFileDialog, AutoExtensionHdl_Impl, CheckBox*, EMPTYARG ) +{ + if ( _pFileNotifier ) + _pFileNotifier->notify( CTRL_STATE_CHANGED, + CHECKBOX_AUTOEXTENSION ); + + // update the extension of the current file if necessary + lcl_autoUpdateFileExtension( this, _pImp->GetCurFilter()->GetExtension() ); + + return 0; +} + +//***************************************************************************** + +IMPL_LINK( SvtFileDialog, ClickHdl_Impl, CheckBox*, pCheckBox ) +{ + if ( ! _pFileNotifier ) + return 0; + + sal_Int16 nId = -1; + + if ( pCheckBox == _pImp->_pCbOptions ) + nId = CHECKBOX_FILTEROPTIONS; + else if ( pCheckBox == _pCbSelection ) + nId = CHECKBOX_SELECTION; + else if ( pCheckBox == _pCbReadOnly ) + nId = CHECKBOX_READONLY; + else if ( pCheckBox == _pImp->_pCbPassword ) + nId = CHECKBOX_PASSWORD; + else if ( pCheckBox == _pCbLinkBox ) + nId = CHECKBOX_LINK; + else if ( pCheckBox == _pCbPreviewBox ) + nId = CHECKBOX_PREVIEW; + + if ( nId != -1 ) + _pFileNotifier->notify( CTRL_STATE_CHANGED, nId ); + + return 0; +} + +//***************************************************************************** + +IMPL_LINK( SvtFileDialog, PlayButtonHdl_Impl, PushButton*, EMPTYARG ) +{ + if ( _pFileNotifier ) + _pFileNotifier->notify( CTRL_STATE_CHANGED, + PUSHBUTTON_PLAY ); + + return 0; +} + +//***************************************************************************** + +long SvtFileDialog::Notify( NotifyEvent& rNEvt ) + +/* [Beschreibung] + + Die Methode wird gerufen, <BACKSPACE> abzufangen. +*/ + +{ + USHORT nType = rNEvt.GetType(); + long nRet = 0; + + if ( EVENT_KEYINPUT == nType && rNEvt.GetKeyEvent() ) + { + const KeyCode& rKeyCode = rNEvt.GetKeyEvent()->GetKeyCode(); + USHORT nCode = rKeyCode.GetCode(); + + if ( !rKeyCode.GetModifier() && + KEY_BACKSPACE == nCode && !_pImp->_pEdFileName->HasChildPathFocus() ) + { + nRet = 0; //! (long)_pFileView->DoBeamerKeyInput( *rNEvt.GetKeyEvent() ); + + if ( !nRet && _pImp->_pBtnUp->IsEnabled() ) + { + PrevLevel_Impl(); + nRet = 1; + } + } +// else if ( rKeyCode.IsMod1() && ( KEY_C == nCode || KEY_V == nCode || KEY_X == nCode ) ) +// { +/* (mhu) + String aVerb = KEY_C == nCode ? UniString(RTL_CONSTASCII_USTRINGPARAM(SVT_MENUPART_VERB_COPY)) : + ( KEY_V == nCode ? UniString(RTL_CONSTASCII_USTRINGPARAM(SVT_MENUPART_VERB_PASTE)) : UniString(RTL_CONSTASCII_USTRINGPARAM(SVT_MENUPART_VERB_CUT)) ); +//(dv) if ( !CntPopupMenu::DoVerbCommand( aVerb, _pFileView->GetView() ) ) +//(dv) Sound::Beep(); +*/ +// } + } + return nRet ? nRet : ModalDialog::Notify( rNEvt ); +} + +//***************************************************************************** + +long SvtFileDialog::OK() +{ + return TRUE; +} + +//***************************************************************************** + +class SvtDefModalDialogParent_Impl +{ +private: + Window* _pOld; + +public: + SvtDefModalDialogParent_Impl( Window *pNew ) : + _pOld( Application::GetDefDialogParent() ) + { Application::SetDefDialogParent( pNew ); } + + ~SvtDefModalDialogParent_Impl() { Application::SetDefDialogParent( _pOld ); } +}; + +//***************************************************************************** + +//--------------------------------------------------------------------- +void SvtFileDialog::updateListboxLabelSizes() +{ + sal_Int16 nLineControlId[5] = { + LISTBOX_VERSION, LISTBOX_TEMPLATE, LISTBOX_IMAGE_TEMPLATE, LISTBOX_FILTER, EDIT_FILEURL + }; + + // determine the maximum width needed for the listbox labels + long nMaxWidth = 0; + for ( sal_Int32 i=0; i<5; ++i ) + { + FixedText* pLabel = static_cast< FixedText* >( getControl( nLineControlId[i], sal_True ) ); + if ( !pLabel ) + continue; + nMaxWidth = ::std::max( pLabel->GetTextWidth( pLabel->GetText() ), nMaxWidth ); + } + + // ensure that all labels are wide enough + for ( sal_Int32 i=0; i<5; ++i ) + { + FixedText* pLabel = static_cast< FixedText* >( getControl( nLineControlId[i], sal_True ) ); + ListBox* pListbox = static_cast< ListBox* >( getControl( nLineControlId[i], sal_False ) ); + if ( !pLabel || !pListbox ) + continue; + Size aCurrentSize( pLabel->GetSizePixel() ); + if ( aCurrentSize.Width() >= nMaxWidth ) + continue; + + long nChange = nMaxWidth - aCurrentSize.Width(); + pLabel->SetSizePixel( Size( nMaxWidth, aCurrentSize.Height() ) ); + + aCurrentSize = pListbox->GetSizePixel(); + pListbox->SetSizePixel( Size( aCurrentSize.Width() - nChange, aCurrentSize.Height() ) ); + lcl_MoveControl( pListbox, nChange, 0 ); + } +} + +namespace +{ + +bool implIsInvalid( const String & rURL ) +{ + SmartContent aContent( rURL ); + aContent.enableOwnInteractionHandler( ::svt::OFilePickerInteractionHandler::E_DOESNOTEXIST ); + aContent.isFolder(); // do this _before_ asking isInvalid! Otherwise result might be wrong. + return aContent.isInvalid(); +} + +} + +//--------------------------------------------------------------------- +String SvtFileDialog::implGetInitialURL( const String& _rPath, const String& _rFallback ) +{ + // an URL parser for the fallback + INetURLObject aURLParser; + + // set the path + bool bWasAbsolute = FALSE; + aURLParser = aURLParser.smartRel2Abs( _rPath, bWasAbsolute ); + + // is it a valid folder? + m_aContent.bindTo( aURLParser.GetMainURL( INetURLObject::NO_DECODE ) ); + sal_Bool bIsFolder = m_aContent.isFolder( ); // do this _before_ asking isInvalid! + sal_Bool bIsInvalid = m_aContent.isInvalid(); + + if ( bIsInvalid && m_bHasFilename && !aURLParser.hasFinalSlash() ) + { // check if the parent folder exists + // #108429# - 2003-03-26 - fs@openoffice.org + INetURLObject aParent( aURLParser ); + aParent.removeSegment( ); + aParent.setFinalSlash( ); + bIsInvalid = implIsInvalid( aParent.GetMainURL( INetURLObject::NO_DECODE ) ); + } + + if ( bIsInvalid ) + { + INetURLObject aFallback( _rFallback ); + bIsInvalid = implIsInvalid( aFallback.GetMainURL( INetURLObject::NO_DECODE ) ); + + if ( !bIsInvalid ) + aURLParser = aFallback; + } + + if ( bIsInvalid ) + { + INetURLObject aParent( aURLParser ); + while ( bIsInvalid && aParent.removeSegment() ) + { + aParent.setFinalSlash( ); + bIsInvalid = implIsInvalid( aParent.GetMainURL( INetURLObject::NO_DECODE ) ); + } + + if ( !bIsInvalid ) + aURLParser = aParent; + } + + if ( !bIsInvalid && bIsFolder ) + { + aURLParser.setFinalSlash(); + } + return aURLParser.GetMainURL( INetURLObject::NO_DECODE ); +} + +//--------------------------------------------------------------------- +short SvtFileDialog::Execute() +{ + if ( !PrepareExecute() ) + return 0; + + // Start des Dialogs. + _bIsInExecute = TRUE; + short nResult = ModalDialog::Execute(); + _bIsInExecute = FALSE; + + DBG_ASSERT( !m_pCurrentAsyncAction.is(), "SvtFilePicker::Execute: still running an async action!" ); + // the dialog should not be cancellable while an async action is running - firs, the action + // needs to be cancelled + + // letztes Verzeichnis merken + if ( RET_OK == nResult ) + { + INetURLObject aURL( _aPath ); + if ( aURL.GetProtocol() == INET_PROT_FILE ) + { + // nur bei File-URL's und nicht bei virtuelle Folder + // das ausgew"ahlte Verzeichnis merken + sal_Int32 nLevel = aURL.getSegmentCount(); + // #97148# & #102204# ------ + sal_Bool bDir = m_aContent.isFolder( aURL.GetMainURL( INetURLObject::NO_DECODE ) ); + // BOOL bClassPath = ( ( _pImp->_nStyle & SFXWB_CLASSPATH ) == SFXWB_CLASSPATH ); + if ( nLevel > 1 && ( FILEDLG_TYPE_FILEDLG == _pImp->_eDlgType || !bDir ) ) + aURL.removeSegment(); + } + } + + return nResult; +} + +//--------------------------------------------------------------------- +void SvtFileDialog::StartExecuteModal( const Link& rEndDialogHdl ) +{ + PrepareExecute(); + + // Start des Dialogs. +// _bIsInExecute = TRUE; + ModalDialog::StartExecuteModal( rEndDialogHdl ); +} + +//----------------------------------------------------------------------------- +void SvtFileDialog::onAsyncOperationStarted() +{ + EnableUI( FALSE ); + // the cancel button must be always enabled + _pImp->_pBtnCancel->Enable( TRUE ); + _pImp->_pBtnCancel->GrabFocus(); +} + +//----------------------------------------------------------------------------- +void SvtFileDialog::onAsyncOperationFinished() +{ + EnableUI( TRUE ); + m_pCurrentAsyncAction = NULL; + if ( !m_bInExecuteAsync ) + _pImp->_pEdFileName->GrabFocus(); + // (if m_bInExecuteAsync is true, then the operation was finished within the minium wait time, + // and to the user, the operation appears to be synchronous) +} + +//------------------------------------------------------------------------- +void SvtFileDialog::displayIOException( const String& _rURL, IOErrorCode _eCode ) +{ + try + { + // create make a human-readable string from the URL + String sDisplayPath( _rURL ); + ::utl::LocalFileHelper::ConvertURLToSystemPath( _rURL, sDisplayPath ); + + // build an own exception which tells "access denied" + InteractiveAugmentedIOException aException; + aException.Arguments.realloc( 2 ); + aException.Arguments[ 0 ] <<= ::rtl::OUString( sDisplayPath ); + aException.Arguments[ 1 ] <<= PropertyValue( + ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Uri" ) ), + -1, aException.Arguments[ 0 ], PropertyState_DIRECT_VALUE + ); + // (formerly, it was sufficient to put the URL first parameter. Nowadays, + // the services expects the URL in a PropertyValue named "Uri" ...) + aException.Code = _eCode; + aException.Classification = InteractionClassification_ERROR; + + // let and interaction handler handle this exception + ::comphelper::OInteractionRequest* pRequest = NULL; + Reference< ::com::sun::star::task::XInteractionRequest > xRequest = pRequest = + new ::comphelper::OInteractionRequest( makeAny( aException ) ); + pRequest->addContinuation( new ::comphelper::OInteractionAbort( ) ); + + Reference< XInteractionHandler > xHandler( + ::comphelper::getProcessServiceFactory()->createInstance( + ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("com.sun.star.task.InteractionHandler") ) + ), + UNO_QUERY + ); + if ( xHandler.is() ) + xHandler->handle( xRequest ); + } + catch( const Exception& ) + { + DBG_ERROR( "iodlg::displayIOException: caught an exception!" ); + } +} + +//----------------------------------------------------------------------------- +void SvtFileDialog::EnableUI( BOOL _bEnable ) +{ + Enable( _bEnable ); + + if ( _bEnable ) + { + for ( ::std::set< Control* >::iterator aLoop = m_aDisabledControls.begin(); + aLoop != m_aDisabledControls.end(); + ++aLoop + ) + { + (*aLoop)->Enable( FALSE ); + } + } +} + +//----------------------------------------------------------------------------- +void SvtFileDialog::EnableControl( Control* _pControl, BOOL _bEnable ) +{ + if ( !_pControl ) + { + DBG_ERRORFILE( "SvtFileDialog::EnableControl: invalid control!" ); + return; + } + + _pControl->Enable( _bEnable ); + + if ( _bEnable ) + { + ::std::set< Control* >::iterator aPos = m_aDisabledControls.find( _pControl ); + if ( m_aDisabledControls.end() != aPos ) + m_aDisabledControls.erase( aPos ); + } + else + m_aDisabledControls.insert( _pControl ); +} + +//---------------------------------------------------------------------------- + +short SvtFileDialog::PrepareExecute() +{ + rtl::OUString aEnvValue; + if ( getEnvironmentValue( "WorkDirMustContainRemovableMedia", aEnvValue ) && + aEnvValue.equalsAscii( "1" ) ) + { + try + { + INetURLObject aStdDir( GetStandardDir() ); + ::ucbhelper::Content aCnt( rtl::OUString( aStdDir.GetMainURL( + INetURLObject::NO_DECODE ) ), + Reference< XCommandEnvironment >() ); + Sequence< rtl::OUString > aProps(2); + aProps[0] = rtl::OUString::createFromAscii( "IsVolume" ); + aProps[1] = rtl::OUString::createFromAscii( "IsRemoveable" ); + + Reference< XResultSet > xResultSet + = aCnt.createCursor( aProps, ::ucbhelper::INCLUDE_FOLDERS_ONLY ); + if ( xResultSet.is() ) + { + Reference< XRow > xRow( xResultSet, UNO_QUERY ); + + bool bEmpty = true; + if ( !xResultSet->next() ) + { + // folder is empty + bEmpty = true; + } + else + { +// @@@ KSO 05/18/2006: support for removable media currently hardcoded/incomplete in OSL +// +// do +// { +// // check, whether child is a removable volume +// if ( xRow->getBoolean( 1 ) && !xRow->wasNull() ) +// { +// if ( xRow->getBoolean( 2 ) && !xRow->wasNull() ) +// { + bEmpty = false; +// break; +// } +// } +// } +// while ( xResultSet->next() ); + } + + if ( bEmpty ) + { + ErrorBox aBox( this, WB_OK, SvtResId( STR_SVT_NOREMOVABLEDEVICE ) ); + aBox.Execute(); + return 0; + } + } + } + catch ( ContentCreationException const & ) + { + } + catch ( CommandAbortedException const & ) + { + } + } + + // #102204# --------------- + if ( ( _pImp->_nStyle & WB_SAVEAS ) && m_bHasFilename ) + // when doing a save-as, we do not want the handler to handle "this file does not exist" messages + // - finally we're going to save that file, aren't we? + // #105812# - 2002-12-02 - fs@openoffice.org + m_aContent.enableOwnInteractionHandler(::svt::OFilePickerInteractionHandler::E_DOESNOTEXIST); + else + m_aContent.enableDefaultInteractionHandler(); + + // #53016# evtl. nur ein Filename ohne Pfad? + String aFileNameOnly; + if( _aPath.Len() && (_pImp->_eMode == FILEDLG_MODE_SAVE) + && (_aPath.Search(':') == STRING_NOTFOUND) + && (_aPath.Search('\\') == STRING_NOTFOUND) + && (_aPath.Search('/') == STRING_NOTFOUND)) + { + aFileNameOnly = _aPath; + _aPath.Erase(); + } + + // kein Startpfad angegeben? + if ( !_aPath.Len() ) + { + // dann das Standard-Dir verwenden + _aPath = lcl_ensureFinalSlash( _pImp->GetStandardDir() ); + + // #53016# vorgegebener Dateiname an Pfad anh"angen + if ( aFileNameOnly.Len() ) + _aPath += aFileNameOnly; + } + + //..................................................................... + _aPath = implGetInitialURL( _aPath, GetStandardDir() ); + + if ( _pImp->_nStyle & WB_SAVEAS && !m_bHasFilename ) + // when doing a save-as, we do not want the handler to handle "this file does not exist" messages + // - finally we're going to save that file, aren't we? + m_aContent.enableOwnInteractionHandler(::svt::OFilePickerInteractionHandler::E_DOESNOTEXIST); + + //..................................................................... + // care for possible restrictions on the paths we're allowed to show + if ( !m_aURLFilter.isUrlAllowed( _aPath ) ) + _aPath = m_aURLFilter.getFilter()[0]; + + // Ggf. Filter anzeigen. + _pImp->InitFilterList(); + + // Initialen Filter einstellen. + USHORT nFilterCount = GetFilterCount(); + String aAll( SvtResId( STR_FILTERNAME_ALL ) ); + BOOL bHasAll = _pImp->HasFilterListEntry( aAll ); + if ( _pImp->GetCurFilter() || nFilterCount == 1 || ( nFilterCount == 2 && bHasAll ) ) + { + // Ggf. einzigen Filter als aktuellen Filter setzen oder den einzigen + // Filter, der nicht auf alle Dateien verweist. + if ( !_pImp->GetCurFilter() ) + { + USHORT nPos = 0; + if ( 2 == nFilterCount && bHasAll ) + { + nPos = nFilterCount; + while ( nPos-- ) + { + if ( GetFilterName( nPos ) != aAll ) + break; + } + } + SvtFileDialogFilter_Impl* pNewCurFilter = _pImp->_pFilter->GetObject( nPos ); + DBG_ASSERT( pNewCurFilter, "SvtFileDialog::Execute: invalid filter pos!" ); + _pImp->SetCurFilter( pNewCurFilter, pNewCurFilter->GetName() ); + } + + // Anzeige anpassen. + _pImp->SelectFilterListEntry( _pImp->GetCurFilter()->GetName() ); + SetDefaultExt( _pImp->GetCurFilter()->GetExtension() ); + USHORT nSepPos = GetDefaultExt().Search( FILEDIALOG_DEF_EXTSEP ); + if ( nSepPos != STRING_NOTFOUND ) + EraseDefaultExt( nSepPos ); + } + else + { + // Ggf. Filter fuer alle Dateien setzen bzw. erzeugen. + if ( !bHasAll ) + { + SvtFileDialogFilter_Impl* pAllFilter = implAddFilter( aAll, UniString(RTL_CONSTASCII_USTRINGPARAM(FILEDIALOG_FILTER_ALL)) ); + _pImp->InsertFilterListEntry( pAllFilter ); + _pImp->SetCurFilter( pAllFilter, aAll ); + } + _pImp->SelectFilterListEntry( aAll ); + } + + _pImp->_pDefaultFilter = _pImp->GetCurFilter(); + + // HACK #50065# + // ggf. Filter isolieren. + String aFilter; + + if ( !IsolateFilterFromPath_Impl( _aPath, aFilter ) ) + return 0; + + sal_uInt16 nNewFilterFlags = adjustFilter( aFilter ); + if ( nNewFilterFlags & ( FLT_NONEMPTY | FLT_USERFILTER ) ) + { + _pImp->_pEdFileName->SetText( aFilter ); + } + // HACK #50065# + + // Instanz fuer den gesetzten Pfad erzeugen und anzeigen. + INetURLObject aFolderURL( _aPath ); + String aFileName( aFolderURL.getName( INetURLObject::LAST_SEGMENT, false ) ); + xub_StrLen nFileNameLen = aFileName.Len(); + bool bFileToSelect = nFileNameLen != 0; + if ( bFileToSelect && aFileName.GetChar( nFileNameLen - 1 ) != INET_PATH_TOKEN ) + { + _pImp->_pEdFileName->SetText( GET_DECODED_NAME( aFolderURL ) ); + aFolderURL.removeSegment(); + } + + INetURLObject aObj = aFolderURL; + if ( aObj.GetProtocol() == INET_PROT_FILE ) + { + // Ordner als aktuelles Verzeichnis setzen. + aObj.setFinalSlash(); + } + + UpdateControls( aObj.GetMainURL( INetURLObject::NO_DECODE ) ); + + // Somebody might want to enable some controls acording to the current filter + FilterSelect(); + + // Zustand der Steuerelemente anpassen. +// EndListeningAll(); + + ViewHdl_Impl( this, NULL ); + OpenURL_Impl( aObj.GetMainURL( INetURLObject::NO_DECODE ) ); + + _pFileView->Show(); + SvtDefModalDialogParent_Impl aDefParent( this ); + + // ggf. Gr"osse aus Ini lesen und setzen + InitSize(); + + return 1; +} + +//----------------------------------------------------------------------------- +void SvtFileDialog::implInitializeSpecialURLLists( ) +{ + m_aURLFilter = ::svt::RestrictedPaths(); + + ::std::vector< String > aFavourites; + if ( m_aURLFilter.hasFilter() ) + { + // if we have restrictions, then the "favourites" are the restricted folders only + aFavourites = m_aURLFilter.getFilter(); + // for approved URLs, we needed the final slashes, for + // favourites, we do not want to have them + ::std::for_each( aFavourites.begin(), aFavourites.end(), RemoveFinalSlash() ); + } + else + { + ::rtl::OUString sFavouritesList; + if ( getEnvironmentValue( "PathFavourites", sFavouritesList ) ) + convertStringListToUrls( sFavouritesList, aFavourites, false ); + } + + DBG_ASSERT( _pImp->_pBtnStandard, "SvtFileDialog::implInitializeSpecialURLLists: how this?" ); + if ( _pImp->_pBtnStandard ) + _pImp->_pBtnStandard->SetFavouriteLocations( aFavourites ); +} + +//----------------------------------------------------------------------------- +void SvtFileDialog::executeAsync( ::svt::AsyncPickerAction::Action _eAction, + const String& _rURL, const String& _rFilter ) +{ + DBG_ASSERT( !m_pCurrentAsyncAction.is(), "SvtFileDialog::executeAsync: previous async action not yet finished!" ); + + m_pCurrentAsyncAction = new AsyncPickerAction( this, _pFileView, _eAction ); + + bool bReallyAsync = true; + m_aConfiguration.getNodeValue( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "FillAsynchronously" ) ) ) >>= bReallyAsync; + + sal_Int32 nMinTimeout = 0; + m_aConfiguration.getNodeValue( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Timeout/Min" ) ) ) >>= nMinTimeout; + sal_Int32 nMaxTimeout = 0; + m_aConfiguration.getNodeValue( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Timeout/Max" ) ) ) >>= nMaxTimeout; + + m_bInExecuteAsync = true; + m_pCurrentAsyncAction->execute( _rURL, _rFilter, bReallyAsync ? nMinTimeout : -1, nMaxTimeout, GetBlackList() ); + m_bInExecuteAsync = false; +} + +//***************************************************************************** + +void SvtFileDialog::FileSelect() +{ + if ( _pFileNotifier ) + _pFileNotifier->notify( FILE_SELECTION_CHANGED, 0 ); +} + +//***************************************************************************** + +void SvtFileDialog::FilterSelect() +{ + if ( _pFileNotifier ) + _pFileNotifier->notify( CTRL_STATE_CHANGED, + LISTBOX_FILTER ); +} + +//***************************************************************************** + +void SvtFileDialog::SetStandardDir( const String& rStdDir ) + +/* [Beschreibung] + + Die Methode setzt den Pfad f"ur den Standardknopf. +*/ + +{ + INetURLObject aObj( rStdDir ); + DBG_ASSERT( aObj.GetProtocol() != INET_PROT_NOT_VALID, "Invalid protocol!" ); + aObj.setFinalSlash(); + _pImp->SetStandardDir( aObj.GetMainURL( INetURLObject::NO_DECODE ) ); +} + +void SvtFileDialog::SetBlackList( const ::com::sun::star::uno::Sequence< ::rtl::OUString >& rBlackList ) +{ + _pImp->SetBlackList( rBlackList ); +} + +//***************************************************************************** + +const ::com::sun::star::uno::Sequence< ::rtl::OUString >& SvtFileDialog::GetBlackList() const +{ + return _pImp->GetBlackList(); +} +//***************************************************************************** + +const String& SvtFileDialog::GetStandardDir() const + +/* [Beschreibung] + + Diese Methode gibt den eingestellten Standardpfad zur"uck. +*/ + +{ + return _pImp->GetStandardDir(); +} + +//***************************************************************************** + +void SvtFileDialog::PrevLevel_Impl() +{ + _pFileView->EndInplaceEditing( false ); + + String sDummy; + executeAsync( AsyncPickerAction::ePrevLevel, sDummy, sDummy ); +} + +//***************************************************************************** + +void SvtFileDialog::OpenURL_Impl( const String& _rURL ) +{ + _pFileView->EndInplaceEditing( false ); + + DBG_ASSERT( m_aURLFilter.isUrlAllowed( _rURL ), "SvtFileDialog::OpenURL_Impl: forbidden URL! Should have been handled by the caller!" ); + executeAsync( AsyncPickerAction::eOpenURL, _rURL, getMostCurrentFilter( _pImp ) ); +} + +//***************************************************************************** +SvtFileDialogFilter_Impl* SvtFileDialog::implAddFilter( const String& _rFilter, const String& _rType ) +{ + SvtFileDialogFilter_Impl* pNewFilter = new SvtFileDialogFilter_Impl( _rFilter, _rType ); + _pImp->_pFilter->C40_INSERT( SvtFileDialogFilter_Impl, pNewFilter, (USHORT)0 ); + + if ( !_pImp->GetCurFilter() ) + _pImp->SetCurFilter( pNewFilter, _rFilter ); + + return pNewFilter; +} + +//***************************************************************************** + +void SvtFileDialog::AddFilter( const String& _rFilter, const String& _rType ) +{ + DBG_ASSERT( !IsInExecute(), "SvtFileDialog::AddFilter: currently executing!" ); + implAddFilter ( _rFilter, _rType ); +} + +//***************************************************************************** +void SvtFileDialog::AddFilterGroup( const String& _rFilter, const Sequence< StringPair >& _rFilters ) +{ + DBG_ASSERT( !IsInExecute(), "SvtFileDialog::AddFilter: currently executing!" ); + + implAddFilter( _rFilter, String() ); + const StringPair* pSubFilters = _rFilters.getConstArray(); + const StringPair* pSubFiltersEnd = pSubFilters + _rFilters.getLength(); + for ( ; pSubFilters != pSubFiltersEnd; ++pSubFilters ) + implAddFilter( pSubFilters->First, pSubFilters->Second ); +} + +//***************************************************************************** + +//----------------------------------------------------------------------------- +void SvtFileDialog::SetCurFilter( const String& rFilter ) +{ + DBG_ASSERT( !IsInExecute(), "SvtFileDialog::SetCurFilter: currently executing!" ); + + // Entsprechenden Filter suchen. + USHORT nPos = _pImp->_pFilter->Count(); + + while ( nPos-- ) + { + SvtFileDialogFilter_Impl* pFilter = _pImp->_pFilter->GetObject( nPos ); + if ( pFilter->GetName() == rFilter ) + { + _pImp->SetCurFilter( pFilter, rFilter ); + break; + } + } +} + +//***************************************************************************** + +String SvtFileDialog::GetCurFilter() const +{ + String aFilter; + + const SvtFileDialogFilter_Impl* pCurrentFilter = _pImp->GetCurFilter(); + if ( pCurrentFilter ) + aFilter = pCurrentFilter->GetName(); + + return aFilter; +} + +String SvtFileDialog::getCurFilter( ) const +{ + return GetCurFilter(); +} + +//***************************************************************************** + +USHORT SvtFileDialog::GetFilterCount() const +{ + return _pImp->_pFilter->Count(); +} + +//***************************************************************************** + +const String& SvtFileDialog::GetFilterName( USHORT nPos ) const +{ + DBG_ASSERT( nPos < GetFilterCount(), "invalid index" ); + return _pImp->_pFilter->GetObject( nPos )->GetName(); +} + +//***************************************************************************** + +void SvtFileDialog::InitSize() +{ + if ( ! _pImp->_aIniKey.Len() ) + return; + + Size aDlgSize = GetResizeOutputSizePixel(); + SetMinOutputSizePixel( aDlgSize ); + + if ( !_pImp->_nFixDeltaHeight ) + { + // Fixgr"ossen errechnen und merken + Point aPnt = _pFileView->GetPosPixel(); + long nBoxH = _pFileView->GetSizePixel().Height(); + long nH = GetSizePixel().Height(); + _pImp->_nFixDeltaHeight = nH - nBoxH; + } + + // initialize from config + SvtViewOptions aDlgOpt( E_DIALOG, _pImp->_aIniKey ); + + if ( aDlgOpt.Exists() ) + { + SetWindowState( ByteString( String( aDlgOpt.GetWindowState() ), osl_getThreadTextEncoding() ) ); + + Any aUserData = aDlgOpt.GetUserItem( ::rtl::OUString::createFromAscii( "UserData" ) ); + ::rtl::OUString sCfgStr; + if ( aUserData >>= sCfgStr ) + _pFileView->SetConfigString( String( sCfgStr ) ); + } +} + +//***************************************************************************** + +SvStringsDtor* SvtFileDialog::GetPathList() const +{ + SvStringsDtor* pList = new SvStringsDtor; + ULONG nCount = _pFileView->GetSelectionCount(); + SvLBoxEntry* pEntry = nCount ? _pFileView->FirstSelected() : NULL; + + if ( ! pEntry ) + { + String* pURL; + + if ( _pImp->_pEdFileName->GetText().Len() && _bIsInExecute ) + pURL = new String( _pImp->_pEdFileName->GetURL() ); + else + pURL = new String( _aPath ); + + pList->Insert( pURL, pList->Count() ); + } + else + { + while ( pEntry ) + { + String* pURL = new String( _pFileView->GetURL( pEntry ) ); + pList->Insert( pURL, pList->Count() ); + pEntry = _pFileView->NextSelected( pEntry ); + } + } + + return pList; +} + +//***************************************************************************** + +void SvtFileDialog::implArrangeControls() +{ + // this is the list of controls in the order they should be tabbed + // from topleft to bottomright + // pb: #136070# new order so all LabeledBy relations are correct now + Control* pControls[] = + { + _pImp->_pFtCurrentPath, + _pImp->_pBtnUp, _pImp->_pBtnNewFolder, _pImp->_pBtnStandard, // image buttons + _pFileView, // the file view + _pImp->_pFtFileName, _pImp->_pEdFileName, + _pImp->_pFtFileVersion, _pImp->_pLbFileVersion, + _pImp->_pFtTemplates, _pImp->_pLbTemplates, + _pImp->_pFtImageTemplates, _pImp->_pLbImageTemplates, + _pImp->_pFtFileType, _pImp->GetFilterListControl(), // edit fields/list boxes + _pImp->_pCbPassword, _pImp->_pCbAutoExtension, _pImp->_pCbOptions, // checkboxes + _pCbReadOnly, _pCbLinkBox, _pCbPreviewBox, _pCbSelection, _pPbPlay, // check boxes (continued) + _pImp->_pBtnFileOpen, _pImp->_pBtnCancel, _pImp->_pBtnHelp // buttons + + // (including the FixedTexts is important - not for tabbing order (they're irrelevant there), + // but for working keyboard shortcuts) + // 96861 - 23.01.2002 - fs@openoffice.org + }; + + // loop through all these controls and adjust the z-order + Window* pPreviousWin = NULL; + Control** pCurrent = pControls; + for ( sal_Int32 i = 0; i < sal_Int32(sizeof( pControls ) / sizeof( pControls[ 0 ] )); ++i, ++pCurrent ) + { + if ( !*pCurrent ) + // this control is not available in the current operation mode -> skip + continue; + + if ( pPreviousWin ) + (*pCurrent)->SetZOrder( pPreviousWin, WINDOW_ZORDER_BEHIND ); + else + (*pCurrent)->SetZOrder( NULL, WINDOW_ZORDER_FIRST ); + + pPreviousWin = *pCurrent; + } + + // FileName edit not the first control but it should have the focus initially + _pImp->_pEdFileName->GrabFocus(); +} + +//***************************************************************************** + +BOOL SvtFileDialog::IsolateFilterFromPath_Impl( String& rPath, String& rFilter ) +{ + String aEmpty; + String aReversePath( rPath ); + aReversePath.Reverse(); + USHORT nQuestionMarkPos = rPath.Search( '?' ); + + if ( nQuestionMarkPos != STRING_NOTFOUND ) + { + // Fragezeichen als Wildcard nur bei Files + INetProtocol eProt = INetURLObject::CompareProtocolScheme( rPath ); + + if ( INET_PROT_NOT_VALID != eProt && INET_PROT_FILE != eProt ) + nQuestionMarkPos = STRING_NOTFOUND; + } + USHORT nWildCardPos = Min( rPath.Search( FILEDIALOG_DEF_WILDCARD ), nQuestionMarkPos ); + rFilter = aEmpty; + + if ( nWildCardPos != STRING_NOTFOUND ) + { + USHORT nPathTokenPos = aReversePath.Search( INET_PATH_TOKEN ); + + if ( nPathTokenPos == STRING_NOTFOUND ) + { + String aDelim( +#if defined(WNT) || defined(OS2) + '\\' +#else + '/' +#endif + ); + + nPathTokenPos = aReversePath.Search( aDelim ); +#if defined(OS2) + if ( nPathTokenPos == STRING_NOTFOUND ) + { + nPathTokenPos = aReversePath.Search( '/' ); + } +#endif +#if !defined( UNX ) + if ( nPathTokenPos == STRING_NOTFOUND ) + { + nPathTokenPos = aReversePath.Search( ':' ); + } +#endif + } + + // Syntax pr"ufen. + if ( nPathTokenPos != STRING_NOTFOUND ) + { + if ( nPathTokenPos < (rPath.Len() - nWildCardPos - 1) ) + { + ErrorHandler::HandleError( ERRCODE_SFX_INVALIDSYNTAX ); + return FALSE; + } + + // Filter abschneiden. + rFilter = aReversePath; + rFilter.Erase( nPathTokenPos ); + rFilter.Reverse(); + + // Ordner bestimmen. + rPath = aReversePath; + rPath.Erase( 0, nPathTokenPos ); + rPath.Reverse(); + } + else + { + rFilter = rPath; + rPath = aEmpty; + } + } + + return TRUE; +} + +//***************************************************************************** + +//----------------------------------------------------------------------------- +void SvtFileDialog::implUpdateImages( ) +{ + // determine high contrast mode + { + sal_Bool bIsHighContrast = GetSettings().GetStyleSettings().GetHighContrastMode(); + m_aImages = ImageList( SvtResId( bIsHighContrast ? RID_FILEPICKER_IMAGES_HC : RID_FILEPICKER_IMAGES ) ); + } + + // set the appropriate images on the buttons + if ( _pImp->_pBtnUp ) + _pImp->_pBtnUp->SetModeImage( GetButtonImage( IMG_FILEDLG_BTN_UP ) ); + + if ( _pImp->_pBtnStandard ) + _pImp->_pBtnStandard->SetModeImage( GetButtonImage( IMG_FILEDLG_BTN_STD ) ); + + if ( _pImp->_pBtnNewFolder ) + _pImp->_pBtnNewFolder->SetModeImage( GetButtonImage( IMG_FILEDLG_CREATEFOLDER ) ); +} + +//----------------------------------------------------------------------------- +void SvtFileDialog::DataChanged( const DataChangedEvent& _rDCEvt ) +{ + if ( DATACHANGED_SETTINGS == _rDCEvt.GetType() ) + implUpdateImages( ); + + ModalDialog::DataChanged( _rDCEvt ); +} + +//----------------------------------------------------------------------------- +void SvtFileDialog::Resize() +{ + if ( IsRollUp() ) + return; + + Size aDlgSize = GetResizeOutputSizePixel(); + Size aOldSize = _pImp->_aDlgSize; + _pImp->_aDlgSize = aDlgSize; + long nWinDeltaW = 0; + + if ( _pPrevWin && + _pPrevWin->GetPosPixel().X() > _pFileView->GetPosPixel().X() ) + { + nWinDeltaW = _pPrevWin->GetOutputSizePixel().Width() + _pImp->_a6Size.Width(); + } + + Size aNewSize = _pFileView->GetSizePixel(); + Point aBoxPos( _pFileView->GetPosPixel() ); + long nDeltaY = aNewSize.Height(); + long nDeltaX = aNewSize.Width(); + aNewSize.Height() = aDlgSize.Height() - _pImp->_nFixDeltaHeight; + aNewSize.Width() = aDlgSize.Width() - aBoxPos.X() - _pImp->_a6Size.Width() - nWinDeltaW; + if ( aOldSize.Height() ) + nDeltaY = _pImp->_aDlgSize.Height() - aOldSize.Height(); + else + nDeltaY = aNewSize.Height() - nDeltaY; + nDeltaX = aNewSize.Width() - nDeltaX; + + if ( nWinDeltaW ) + nWinDeltaW = nDeltaX * 2 / 3; + aNewSize.Width() -= nWinDeltaW; + nDeltaX -= nWinDeltaW; + + _pFileView->SetSizePixel( aNewSize ); + + if ( !nDeltaY && !nDeltaX ) + // Dieses Resize wurde nur zum Ein - oder Ausblenden des Indicators aufgerufen + return; + + // ------------- + // move controls + + // controls to move vertically + { + Control* aMoveControlsVert[] = + { + _pImp->_pFtFileName, _pImp->_pEdFileName, _pImp->_pFtFileVersion, _pImp->_pLbFileVersion, + _pImp->_pFtTemplates, _pImp->_pLbTemplates, _pImp->_pFtImageTemplates, _pImp->_pLbImageTemplates, + _pImp->_pFtFileType, _pImp->GetFilterListControl(), _pCbReadOnly, _pCbLinkBox, _pCbPreviewBox, + _pPbPlay, _pImp->_pCbPassword, _pImp->_pCbAutoExtension, _pImp->_pCbOptions, _pCbSelection + }; + Control** ppMoveControls = aMoveControlsVert; + Control** ppMoveControlsEnd = ppMoveControls + sizeof( aMoveControlsVert ) / sizeof( aMoveControlsVert[0] ); + for ( ; ppMoveControls != ppMoveControlsEnd; ++ppMoveControls ) + lcl_MoveControl( *ppMoveControls, 0, nDeltaY ); + } + + // controls to move vertically and horizontally + { + Control* aMoveControlsBoth[] = + { + _pImp->_pBtnFileOpen, _pImp->_pBtnCancel, _pImp->_pBtnHelp + }; + Control** ppMoveControls = aMoveControlsBoth; + Control** ppMoveControlsEnd = ppMoveControls + sizeof( aMoveControlsBoth ) / sizeof( aMoveControlsBoth[0] ); + for ( ; ppMoveControls != ppMoveControlsEnd; ++ppMoveControls ) + lcl_MoveControl( *ppMoveControls, nDeltaX, nDeltaY ); + } + + // controls to move horizontally + { + Control* aMoveControlsHor[] = + { + _pImp->_pBtnUp, _pImp->_pBtnNewFolder, _pImp->_pBtnStandard + }; + Control** ppMoveControls = aMoveControlsHor; + Control** ppMoveControlsEnd = ppMoveControls + sizeof( aMoveControlsHor ) / sizeof( aMoveControlsHor[0] ); + for ( ; ppMoveControls != ppMoveControlsEnd; ++ppMoveControls ) + lcl_MoveControl( *ppMoveControls, nDeltaX, 0 ); + } + + // --------------- + // resize controls + { + Control* aSizeControls[] = + { + _pImp->_pEdFileName, _pImp->_pLbFileVersion, _pImp->_pLbTemplates, _pImp->_pLbImageTemplates, + _pImp->GetFilterListControl(), _pImp->_pFtCurrentPath, + }; + sal_Int32 nSizeControls = sizeof( aSizeControls ) / sizeof( aSizeControls[0] ); + Control** ppSizeControls = aSizeControls; + for ( sal_Int32 j=0; j<nSizeControls; ++j, ++ppSizeControls ) + { + if ( *ppSizeControls ) + { + aNewSize = (*ppSizeControls)->GetSizePixel(); + aNewSize.Width() += nDeltaX; + (*ppSizeControls)->SetSizePixel( aNewSize ); + } + } + } + + // zus"atzliche Controls ausrichten + if ( _pPrevWin && + _pPrevWin->GetPosPixel().X() > _pFileView->GetPosPixel().X() ) + { + // Controls vom Typ Window speziell ausrichten + // auch die Gr"osse anpassen + Point aNewPos = _pPrevWin->GetPosPixel(); + aNewPos.X() += nDeltaX; + _pPrevWin->SetPosPixel( aNewPos ); + _pPrevBmp->SetPosPixel( aNewPos ); + aNewSize = _pPrevWin->GetOutputSizePixel(); + aNewSize.Width() += nWinDeltaW; + aNewSize.Height() += nDeltaY; + if ( !aOldSize.Height() ) + aNewSize.Height() -= ( _pImp->_a6Size.Height() / 2 ); + _pPrevWin->SetOutputSizePixel( aNewSize ); + _pPrevBmp->SetOutputSizePixel( aNewSize ); + _pPrevBmp->Invalidate(); + } + + if ( _pFileNotifier ) + _pFileNotifier->notify( DIALOG_SIZE_CHANGED, 0 ); +} + +//***************************************************************************** + +//----------------------------------------------------------------------------- +Control* SvtFileDialog::getControl( sal_Int16 _nControlId, sal_Bool _bLabelControl ) const +{ + Control* pReturn = NULL; + + switch ( _nControlId ) + { + case CONTROL_FILEVIEW: + pReturn = _bLabelControl ? NULL : static_cast< Control* >( _pFileView ); + break; + + case EDIT_FILEURL: + pReturn = _bLabelControl + ? static_cast< Control* >( _pImp->_pFtFileName ) + : static_cast< Control* >( _pImp->_pEdFileName ); + break; + + case EDIT_FILEURL_LABEL: + pReturn = static_cast< Control* >( _pImp->_pFtFileName ); + break; + + case CHECKBOX_AUTOEXTENSION: + pReturn = _pImp->_pCbAutoExtension; + break; + + case CHECKBOX_PASSWORD: + pReturn = _pImp->_pCbPassword; + break; + + case CHECKBOX_FILTEROPTIONS: + pReturn = _pImp->_pCbOptions; + break; + + case CHECKBOX_READONLY: + pReturn = _pCbReadOnly; + break; + + case CHECKBOX_LINK: + pReturn = _pCbLinkBox; + break; + + case CHECKBOX_PREVIEW: + pReturn = _pCbPreviewBox; + break; + + case CHECKBOX_SELECTION: + pReturn = _pCbSelection; + break; + + case LISTBOX_FILTER: + pReturn = _bLabelControl ? _pImp->_pFtFileType : _pImp->GetFilterListControl(); + break; + + case LISTBOX_FILTER_LABEL: + pReturn = _pImp->_pFtFileType; + break; + + case FIXEDTEXT_CURRENTFOLDER: + pReturn = _pImp->_pFtCurrentPath; + break; + + case LISTBOX_VERSION: + pReturn = _bLabelControl + ? static_cast< Control* >( _pImp->_pFtFileVersion ) + : static_cast< Control* >( _pImp->_pLbFileVersion ); + break; + + case LISTBOX_TEMPLATE: + pReturn = _bLabelControl + ? static_cast< Control* >( _pImp->_pFtTemplates ) + : static_cast< Control* >( _pImp->_pLbTemplates ); + break; + + case LISTBOX_IMAGE_TEMPLATE: + pReturn = _bLabelControl + ? static_cast< Control* >( _pImp->_pFtImageTemplates ) + : static_cast< Control* >( _pImp->_pLbImageTemplates ); + break; + + case LISTBOX_VERSION_LABEL: + pReturn = _pImp->_pFtFileVersion; + break; + + case LISTBOX_TEMPLATE_LABEL: + pReturn = _pImp->_pFtTemplates; + break; + + case LISTBOX_IMAGE_TEMPLATE_LABEL: + pReturn = _pImp->_pFtImageTemplates; + break; + + case PUSHBUTTON_OK: + pReturn = _pImp->_pBtnFileOpen; + break; + + case PUSHBUTTON_CANCEL: + pReturn = _pImp->_pBtnCancel; + break; + + case PUSHBUTTON_PLAY: + pReturn = _pPbPlay; + break; + + case PUSHBUTTON_HELP: + pReturn = _pImp->_pBtnHelp; + break; + + case TOOLBOXBUTOON_DEFAULT_LOCATION: + pReturn = _pImp->_pBtnStandard; + break; + + case TOOLBOXBUTOON_LEVEL_UP: + pReturn = _pImp->_pBtnUp; + break; + + case TOOLBOXBUTOON_NEW_FOLDER: + pReturn = _pImp->_pBtnNewFolder; + break; + + case LISTBOX_FILTER_SELECTOR: + // only exists on SalGtkFilePicker + break; + + default: + DBG_ERRORFILE( "SvtFileDialog::getControl: invalid id!" ); + } + return pReturn; +} + +// ----------------------------------------------------------------------- +void SvtFileDialog::enableControl( sal_Int16 _nControlId, sal_Bool _bEnable ) +{ + Control* pControl = getControl( _nControlId, sal_False ); + if ( pControl ) + EnableControl( pControl, _bEnable ); + Control* pLabel = getControl( _nControlId, sal_True ); + if ( pLabel ) + EnableControl( pLabel, _bEnable ); +} + +// ----------------------------------------------------------------------- +void SvtFileDialog::AddControls_Impl( ) +{ + // create the "insert as link" checkbox, if needed + if ( _nExtraBits & SFX_EXTRA_INSERTASLINK ) + { + _pCbLinkBox = new CheckBox( this ); + _pCbLinkBox ->SetText( SvtResId( STR_SVT_FILEPICKER_INSERT_AS_LINK ) ); + _pCbLinkBox ->SetHelpId( HID_FILEDLG_LINK_CB ); + AddControl( _pCbLinkBox ); + ReleaseOwnerShip( _pCbLinkBox ); + _pCbLinkBox->SetClickHdl( LINK( this, SvtFileDialog, ClickHdl_Impl ) ); + } + + // create the "show preview" checkbox ( and the preview window, too ), if needed + if ( _nExtraBits & SFX_EXTRA_SHOWPREVIEW ) + { + _pImp->_aIniKey = IMPGRF_CONFIGNAME; + // because the "<All Formats> (*.bmp,*...)" entry is to wide, + // we need to disable the auto width feature of the filter box + _pImp->DisableFilterBoxAutoWidth(); + + // "Vorschau" + _pCbPreviewBox = new CheckBox( this ); + _pCbPreviewBox->SetText( SvtResId( STR_SVT_FILEPICKER_SHOW_PREVIEW ) ); + _pCbPreviewBox->SetHelpId( HID_FILEDLG_PREVIEW_CB ); + AddControl( _pCbPreviewBox ); + ReleaseOwnerShip( _pCbPreviewBox ); + _pCbPreviewBox->SetClickHdl( LINK( this, SvtFileDialog, ClickHdl_Impl ) ); + + // Preview-Fenster erst hier erzeugen + _pPrevWin = new Window( this, WinBits( WB_BORDER ) ); + AddControl( _pPrevWin ); + ReleaseOwnerShip( _pPrevWin ); + _pPrevWin->Hide(); + + _pPrevBmp = new FixedBitmap( this, WinBits( WB_BORDER ) ); + _pPrevBmp->SetBackground( Wallpaper( Color( COL_WHITE ) ) ); + _pPrevBmp->Show(); + } + + if ( _nExtraBits & SFX_EXTRA_AUTOEXTENSION ) + { + _pImp->_pCbAutoExtension = new CheckBox( this, SvtResId( CB_AUTO_EXTENSION ) ); + _pImp->_pCbAutoExtension->SetText( SvtResId( STR_SVT_FILEPICKER_AUTO_EXTENSION ) ); + _pImp->_pCbAutoExtension->Check( TRUE ); + AddControl( _pImp->_pCbAutoExtension ); + ReleaseOwnerShip( _pImp->_pCbAutoExtension ); + _pImp->_pCbAutoExtension->SetClickHdl( LINK( this, SvtFileDialog, AutoExtensionHdl_Impl ) ); + } + + if ( _nExtraBits & SFX_EXTRA_FILTEROPTIONS ) + { + _pImp->_pCbOptions = new CheckBox( this, SvtResId( CB_OPTIONS ) ); + _pImp->_pCbOptions->SetText( SvtResId( STR_SVT_FILEPICKER_FILTER_OPTIONS ) ); + AddControl( _pImp->_pCbOptions ); + ReleaseOwnerShip( _pImp->_pCbOptions ); + _pImp->_pCbOptions->SetClickHdl( LINK( this, SvtFileDialog, ClickHdl_Impl ) ); + } + + if ( _nExtraBits & SFX_EXTRA_SELECTION ) + { + _pCbSelection = new CheckBox( this, SvtResId( CB_OPTIONS ) ); + _pCbSelection->SetText( SvtResId( STR_SVT_FILEPICKER_SELECTION ) ); + AddControl( _pCbSelection ); + ReleaseOwnerShip( _pCbSelection ); + _pCbSelection->SetClickHdl( LINK( this, SvtFileDialog, ClickHdl_Impl ) ); + } + + if ( _nExtraBits & SFX_EXTRA_PLAYBUTTON ) + { + _pPbPlay = new PushButton( this ); + _pPbPlay->SetText( SvtResId( STR_SVT_FILEPICKER_PLAY ) ); + _pPbPlay->SetHelpId( HID_FILESAVE_DOPLAY ); + AddControl( _pPbPlay ); + ReleaseOwnerShip( _pPbPlay ); + _pPbPlay->SetClickHdl( LINK( this, SvtFileDialog, PlayButtonHdl_Impl ) ); + } + + if ( _nExtraBits & SFX_EXTRA_SHOWVERSIONS ) + { + _pImp->_pFtFileVersion = new FixedText( this, SvtResId( FT_EXPLORERFILE_SHARED_LISTBOX ) ); + _pImp->_pFtFileVersion->SetText( SvtResId( STR_SVT_FILEPICKER_VERSION ) ); + + _pImp->_pLbFileVersion = new ListBox( this, SvtResId( LB_EXPLORERFILE_SHARED_LISTBOX ) ); + _pImp->_pLbFileVersion->SetHelpId( HID_FILEOPEN_VERSION ); + } + else if ( _nExtraBits & SFX_EXTRA_TEMPLATES ) + { + _pImp->_pFtTemplates = new FixedText( this, SvtResId( FT_EXPLORERFILE_SHARED_LISTBOX ) ); + _pImp->_pFtTemplates->SetText( SvtResId( STR_SVT_FILEPICKER_TEMPLATES ) ); + + _pImp->_pLbTemplates = new ListBox( this, SvtResId( LB_EXPLORERFILE_SHARED_LISTBOX ) ); + _pImp->_pLbTemplates->SetHelpId( HID_FILEOPEN_VERSION ); + // This is strange. During the re-factoring during 96930, I discovered that this help id + // is set in the "Templates mode". This was hidden in the previous implementation. + // Shouldn't this be a more meaningfull help id. + // 96930 - 15.08.2002 - fs@openoffice.org + } + else if ( _nExtraBits & SFX_EXTRA_IMAGE_TEMPLATE ) + { + _pImp->_pFtImageTemplates = new FixedText( this, SvtResId( FT_EXPLORERFILE_SHARED_LISTBOX ) ); + _pImp->_pFtImageTemplates->SetText( SvtResId( STR_SVT_FILEPICKER_IMAGE_TEMPLATE ) ); + + _pImp->_pLbImageTemplates = new ListBox( this, SvtResId( LB_EXPLORERFILE_SHARED_LISTBOX ) ); + _pImp->_pLbImageTemplates->SetHelpId( HID_FILEOPEN_IMAGE_TEMPLATE ); + } +} + +// ----------------------------------------------------------------------- +sal_Int32 SvtFileDialog::getTargetColorDepth() +{ + if ( _pPrevBmp ) + return _pPrevBmp->GetBitCount(); + else + return 0; +} + +// ----------------------------------------------------------------------- +sal_Int32 SvtFileDialog::getAvailableWidth() +{ + if ( _pPrevBmp ) + return _pPrevBmp->GetOutputSizePixel().Width(); + else + return 0; +} + +// ----------------------------------------------------------------------- +sal_Int32 SvtFileDialog::getAvailableHeight() +{ + if ( _pPrevBmp ) + return _pPrevBmp->GetOutputSizePixel().Height(); + else + return 0; +} + +// ----------------------------------------------------------------------- +void SvtFileDialog::setImage( sal_Int16 /*aImageFormat*/, const Any& rImage ) +{ + if ( ! _pPrevBmp || ! _pPrevBmp->IsVisible() ) + return; + + Sequence < sal_Int8 > aBmpSequence; + + if ( rImage >>= aBmpSequence ) + { + Bitmap aBmp; + SvMemoryStream aData( aBmpSequence.getArray(), + aBmpSequence.getLength(), + STREAM_READ ); + aData >> aBmp; + + _pPrevBmp->SetBitmap( aBmp ); + } + else + { + Bitmap aEmpty; + _pPrevBmp->SetBitmap( aEmpty ); + } +} + +// ----------------------------------------------------------------------- +sal_Bool SvtFileDialog::setShowState( sal_Bool /*bShowState*/ ) +{ + // #97633 for the system filedialog it's + // usefull to make the preview switchable + // because the preview occupies + // half of the size of the file listbox + // which is not the case here, + // so we (TRA/FS) decided not to make + // the preview window switchable because + // else we would have to change the layout + // of the file dialog dynamically + // support for set/getShowState is opionally + // see com::sun::star::ui::dialogs::XFilePreview + /* + if ( _pPrevBmp ) + { + _pPrevBmp->Show( bShowState ); + return sal_True; + } + else + return sal_False; + */ + + return sal_False; +} + +// ----------------------------------------------------------------------- +String SvtFileDialog::getCurrentFileText( ) const +{ + String sReturn; + if ( _pImp && _pImp->_pEdFileName ) + sReturn = _pImp->_pEdFileName->GetText(); + return sReturn; +} + +// ----------------------------------------------------------------------- +void SvtFileDialog::setCurrentFileText( const String& _rText, bool _bSelectAll ) +{ + if ( _pImp && _pImp->_pEdFileName ) + { + _pImp->_pEdFileName->SetText( _rText ); + if ( _bSelectAll ) + _pImp->_pEdFileName->SetSelection( Selection( 0, _rText.Len() ) ); + } +} + +// ----------------------------------------------------------------------- +sal_Bool SvtFileDialog::isAutoExtensionEnabled() +{ + return _pImp->_pCbAutoExtension && _pImp->_pCbAutoExtension->IsChecked(); +} + +// ----------------------------------------------------------------------- +sal_Bool SvtFileDialog::getShowState() +{ + if ( _pPrevBmp ) + return _pPrevBmp->IsVisible(); + else + return sal_False; +} + +// ----------------------------------------------------------------------- +void SvtFileDialog::ReleaseOwnerShip( Window* pUserControl ) + +/* + [Beschreibung] + Die Methode sorgt dafuer das das spezifizierte Element nicht mehr im Besitz + der Instanz ist. +*/ + +{ + ControlChain_Impl* pElement = _pUserControls; + while ( pElement ) + { + if ( pElement->_pControl == pUserControl ) + { + pElement->_bHasOwnerShip = FALSE; + break; + } + pElement = pElement->_pNext; + } +} + +//*************************************************************************** + +BOOL SvtFileDialog::AddControl( Window* pControl, BOOL bNewLine ) +{ + // control already exists + ControlChain_Impl* pElement = _pUserControls; + while ( pElement ) + { + if ( pElement->_pControl == pControl ) + return FALSE; + pElement = pElement->_pNext; + } + + // Check if controls have already been added. + Size aNewControlSize( pControl->GetOutputSizePixel() ); + Size aDlgSize( GetOutputSizePixel() ); + WindowType nType = pControl->GetType(); + if ( !aNewControlSize.Height() ) + { + // Detect a size. + Size aSize( 0, 10 ); + if ( nType == WINDOW_PUSHBUTTON ) + { + Size aDefSiz = LogicToPixel( Size( 50, 14 ), MAP_APPFONT ); + long nTextWidth = pControl->GetTextWidth( pControl->GetText() ); + aSize.Width() = nTextWidth + WIDTH_ADDITION; + + // PushButton: Mindestbreite 50 logische Einheiten, + // H"ohe immer 14 logische Einheiten + if ( aDefSiz.Width() > aSize.Width() ) + aSize.Width() = aDefSiz.Width(); + aSize.Height() = aDefSiz.Height(); + aNewControlSize = aSize; + } + else + aNewControlSize = LogicToPixel( aSize, MAP_APPFONT ); + if ( nType != WINDOW_PUSHBUTTON ) + aNewControlSize.Width() = pControl->GetTextWidth( pControl->GetText() ) + WIDTH_ADDITION; + if ( nType == WINDOW_CHECKBOX ) + aNewControlSize.Width() += WIDTH_ADDITION; + if ( nType == WINDOW_WINDOW ) + { + aNewControlSize.Height() = GetOutputSizePixel().Height() - 18; + aNewControlSize.Width() = 200; + aDlgSize.Width() += 210; + SetOutputSizePixel( aDlgSize ); + } + pControl->SetOutputSizePixel( aNewControlSize ); + } + Point aNewControlPos; + Size* pNewDlgSize = NULL; + BOOL bNewRow = bNewLine; + FASTBOOL bFirstNewRow = FALSE; + + if ( nType == WINDOW_WINDOW ) + { + aNewControlPos.X() = aDlgSize.Width() - 210; + aNewControlPos.Y() = 8; + } + else if ( _pUserControls ) + { + Point aNewControlRange( _pUserControls->_pControl->GetPosPixel() ); + long nPrevControlHeight = _pUserControls->_pControl->GetSizePixel().Height(); + aNewControlRange += + Point( _pUserControls->_pControl->GetOutputSizePixel().Width(), 0 ); + aNewControlPos = aNewControlRange; + if ( nPrevControlHeight > aNewControlSize.Height() ) + { + long nY = nPrevControlHeight; + nY -= aNewControlSize.Height(); + nY /= 2; + aNewControlPos.Y() += nY; + } + aNewControlPos += LogicToPixel( Point( 3, 0 ), MAP_APPFONT ); + aNewControlRange += LogicToPixel( Point( 9, 0 ), MAP_APPFONT ); + aNewControlRange += Point( aNewControlSize.Width(), 0 ); + + // Check if a new row has to be created. + if ( aNewControlRange.X() > aDlgSize.Width() ) + bNewRow = TRUE; + } + else + { + // Create a new row if there was no usercontrol before. + bNewRow = TRUE; + bFirstNewRow = TRUE; + } + + // Check if a new row has to be created. + Size aBorderSize = LogicToPixel( Size( 6, 6 ), MAP_APPFONT ); + long nLeftBorder = aBorderSize.Width(); + long nLowerBorder = aBorderSize.Height(); + if ( bNewRow ) + { + // Set control at the beginning of a new line. + long nSmallBorderHeight = nLowerBorder / 2; + aNewControlPos = Point( nLeftBorder, 0 ); + aNewControlPos += Point( 0, aDlgSize.Height() ); + aNewControlPos.Y() -= nSmallBorderHeight; + // Set new size. + pNewDlgSize = new Size( aDlgSize ); + pNewDlgSize->Height() -= nSmallBorderHeight; + pNewDlgSize->Height() += aNewControlSize.Height(); + pNewDlgSize->Height() += nLowerBorder; + } + else + { + // Check if the window has to be resized. + Size aNewControlRange( 0, aNewControlPos.Y() ); + aNewControlRange.Height() += aNewControlSize.Height(); + aNewControlRange.Height() += nLowerBorder; + if ( aNewControlRange.Height() > aDlgSize.Height() ) + pNewDlgSize = new Size( aDlgSize.Width(), aNewControlRange.Height() ); + } + + // Update view. + if ( pNewDlgSize ) + { + SetOutputSizePixel( *pNewDlgSize ); + delete pNewDlgSize; + } + pControl->SetPosPixel( aNewControlPos ); + pControl->Show(); + _pUserControls = new ControlChain_Impl( pControl, _pUserControls ); + + return TRUE; +} + +sal_Bool SvtFileDialog::ContentHasParentFolder( const rtl::OUString& rURL ) +{ + m_aContent.bindTo( rURL ); + + if ( m_aContent.isInvalid() ) + return sal_False; + + return m_aContent.hasParentFolder( ) && m_aContent.isValid(); +} + +sal_Bool SvtFileDialog::ContentCanMakeFolder( const rtl::OUString& rURL ) +{ + m_aContent.bindTo( rURL ); + + if ( m_aContent.isInvalid() ) + return sal_False; + + return m_aContent.canCreateFolder( ) && m_aContent.isValid(); +} + +sal_Bool SvtFileDialog::ContentGetTitle( const rtl::OUString& rURL, String& rTitle ) +{ + m_aContent.bindTo( rURL ); + + if ( m_aContent.isInvalid() ) + return sal_False; + + ::rtl::OUString sTitle; + m_aContent.getTitle( sTitle ); + rTitle = sTitle; + + return m_aContent.isValid(); +} + +void SvtFileDialog::appendDefaultExtension(String& _rFileName, + const String& _rFilterDefaultExtension, + const String& _rFilterExtensions) +{ + String aTemp(_rFileName); + aTemp.ToLowerAscii(); + String aType(_rFilterExtensions); + aType.ToLowerAscii(); + + if ( ! aType.EqualsAscii(FILEDIALOG_FILTER_ALL) ) + { + USHORT nWildCard = aType.GetTokenCount( FILEDIALOG_DEF_EXTSEP ); + USHORT nIndex, nPos = 0; + + for ( nIndex = 0; nIndex < nWildCard; nIndex++ ) + { + String aExt(aType.GetToken( 0, FILEDIALOG_DEF_EXTSEP, nPos )); + // take care of a leading * + USHORT nExtOffset = (aExt.GetBuffer()[0] == '*' ? 1 : 0); + sal_Unicode* pExt = aExt.GetBufferAccess() + nExtOffset; + xub_StrLen nExtLen = aExt.Len() - nExtOffset; + xub_StrLen nOffset = aTemp.Len() - nExtLen; + // minimize search by starting at last possible index + if ( aTemp.Search(pExt, nOffset) == nOffset ) + break; + } + + if ( nIndex >= nWildCard ) + { + _rFileName += '.'; + _rFileName += _rFilterDefaultExtension; + } + } +} + +// ----------------------------------------------------------------------- + +// QueryFolderNameDialog ------------------------------------------------------- + +namespace svtools { + +QueryFolderNameDialog::QueryFolderNameDialog +( + Window* _pParent, + const String& rTitle, + const String& rDefaultText, + String* pGroupName +) : + ModalDialog( _pParent, SvtResId( DLG_SVT_QUERYFOLDERNAME ) ), + + aNameText ( this, SvtResId( FT_SVT_QUERYFOLDERNAME_DLG_NAME ) ), + aNameEdit ( this, SvtResId( ED_SVT_QUERYFOLDERNAME_DLG_NAME ) ), + aNameLine ( this, SvtResId( FL_SVT_QUERYFOLDERNAME_DLG_NAME ) ), + aOKBtn ( this, SvtResId( BT_SVT_QUERYFOLDERNAME_DLG_OK ) ), + aCancelBtn ( this, SvtResId( BT_SVT_QUERYFOLDERNAME_DLG_CANCEL ) ) +{ + FreeResource(); + SetText( rTitle ); + aNameEdit.SetText( rDefaultText ); + aNameEdit.SetSelection( Selection( 0, rDefaultText.Len() ) ); + aOKBtn.SetClickHdl( LINK( this, QueryFolderNameDialog, OKHdl ) ); + aNameEdit.SetModifyHdl( LINK( this, QueryFolderNameDialog, NameHdl ) ); + + if ( pGroupName ) + aNameLine.SetText( *pGroupName ); +}; + +// ----------------------------------------------------------------------- +IMPL_LINK( QueryFolderNameDialog, OKHdl, Button *, EMPTYARG ) +{ + // trim the strings + aNameEdit.SetText( aNameEdit.GetText().EraseLeadingChars().EraseTrailingChars() ); + EndDialog( RET_OK ); + return 1; +} + +// ----------------------------------------------------------------------- +IMPL_LINK( QueryFolderNameDialog, NameHdl, Edit *, EMPTYARG ) +{ + // trim the strings + String aName = aNameEdit.GetText(); + aName.EraseLeadingChars().EraseTrailingChars(); + if ( aName.Len() ) + { + if ( !aOKBtn.IsEnabled() ) + aOKBtn.Enable( TRUE ); + } + else + { + if ( aOKBtn.IsEnabled() ) + aOKBtn.Enable( FALSE ); + } + + return 0; +} + +} diff --git a/fpicker/source/office/iodlg.hrc b/fpicker/source/office/iodlg.hrc new file mode 100644 index 000000000000..b87082b56cbd --- /dev/null +++ b/fpicker/source/office/iodlg.hrc @@ -0,0 +1,89 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +#ifndef _SVTOOLS_IODLGIMPL_HRC +#define _SVTOOLS_IODLGIMPL_HRC + +#include "svtools/svtools.hrc" +#include "svtools/helpid.hrc" + +// ModalDialog DLG_SVT_EXPLORERFILE + +#define FT_EXPLORERFILE_CURRENTPATH 10 +#define BTN_EXPLORERFILE_NEWFOLDER 11 +#define BTN_EXPLORERFILE_LISTVIEW 12 +#define BTN_EXPLORERFILE_DETAILSVIEW 13 +#define BTN_EXPLORERFILE_UP 14 +#define BTN_EXPLORERFILE_STANDARD 15 +#define BTN_EXPLORERFILE_OPEN 16 +#define BTN_EXPLORERFILE_CANCEL 17 +#define BTN_EXPLORERFILE_HELP 18 + +#define IMG_FILEDLG_BTN_UP 10 +#define IMG_FILEDLG_BTN_STD 11 +#define IMG_FILEDLG_CREATEFOLDER 14 + +#define CTL_EXPLORERFILE_FILELIST 20 + +#define FT_EXPLORERFILE_FILENAME 30 +#define ED_EXPLORERFILE_FILENAME 31 +#define FT_EXPLORERFILE_SHARED_LISTBOX 32 +#define LB_EXPLORERFILE_SHARED_LISTBOX 33 +#define FT_EXPLORERFILE_FILETYPE 34 +#define LB_EXPLORERFILE_FILETYPE 35 + +#define CB_EXPLORERFILE_READONLY 40 +#define CB_EXPLORERFILE_PASSWORD 41 +#define CB_AUTO_EXTENSION 42 +#define CB_OPTIONS 43 + +// ----------------------------------------------- + +#define STR_EXPLORERFILE_OPEN 1 +#define STR_EXPLORERFILE_SAVE 2 +#define STR_EXPLORERFILE_BUTTONSAVE 3 +#define STR_PATHNAME 4 +#define STR_PATHSELECT 5 +#define STR_BUTTONSELECT 6 +#define STR_ACTUALVERSION 7 + +// DLG_SVT_QUERYFOLDERNAME ----------------------- + +#define FT_SVT_QUERYFOLDERNAME_DLG_NAME 10 +#define ED_SVT_QUERYFOLDERNAME_DLG_NAME 11 +#define FL_SVT_QUERYFOLDERNAME_DLG_NAME 12 +#define BT_SVT_QUERYFOLDERNAME_DLG_OK 13 +#define BT_SVT_QUERYFOLDERNAME_DLG_CANCEL 14 +#define BT_SVT_QUERYFOLDERNAME_DLG_HELP 15 + +// ----------------------------------------------- + +#define SID_SFX_START 5000 +#define SID_OPENURL (SID_SFX_START + 596) + +#endif + diff --git a/fpicker/source/office/iodlg.hxx b/fpicker/source/office/iodlg.hxx new file mode 100644 index 000000000000..fbfa9a9355a5 --- /dev/null +++ b/fpicker/source/office/iodlg.hxx @@ -0,0 +1,475 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ +#ifndef _IODLGIMPL_HXX +#define _IODLGIMPL_HXX + +#ifndef _VCL_DIALOG_HXX +#include <vcl/dialog.hxx> +#endif +#ifndef _SV_BUTTON_HXX +#include <vcl/button.hxx> +#endif +#include <vcl/fixed.hxx> +#include <vcl/edit.hxx> +#include <vcl/combobox.hxx> +#include <vcl/lstbox.hxx> +#include <com/sun/star/beans/StringPair.hpp> +#include <com/sun/star/uno/Any.hxx> +#include <com/sun/star/uno/Sequence.hxx> +#include <com/sun/star/ucb/IOErrorCode.hpp> +#include <com/sun/star/ui/dialogs/XDialogClosedListener.hpp> +#include <unotools/confignode.hxx> +#include "svl/inettype.hxx" +#include "svl/urlfilter.hxx" +#include <svl/restrictedpaths.hxx> +#include "asyncfilepicker.hxx" +#include "OfficeControlAccess.hxx" +#include "fpsmartcontent.hxx" + +#include <set> + +// @@@ using namespace com::sun::star::ucb; + +//***************************************************************************** + +class SvTabListBox; +class SvStringsDtor; +class SvtFileView; +struct ControlChain_Impl; +class SvtFileDialogFilter_Impl; + +//***************************************************************************** + +#define SFXWB_INSERT ( 0x04000000L | WB_OPEN ) +#define SFXWB_PASSWORD WB_PASSWORD +#define SFXWB_READONLY WB_READONLY +#define SFXWB_PATHDIALOG WB_PATH +#define SFXWB_CLASSPATH ( 0x08000000L | SFXWB_PATHDIALOG ) +#define SFXWB_SHOWALLFOLDER 0x10000000L // alle Ordner auch Mail/News/... +#define SFXWB_MULTISELECTION 0x20000000L // Multiselection an +#define SFXWB_NOREMOTE 0x40000000L +#define SFXWB_SHOWVERSIONS 0x80000000L // Versionsauswahl anzeigen + +#define SFX_EXTRA_AUTOEXTENSION 0x00000001L +#define SFX_EXTRA_FILTEROPTIONS 0x00000002L +#define SFX_EXTRA_SHOWVERSIONS 0x00000004L +#define SFX_EXTRA_INSERTASLINK 0x00000008L +#define SFX_EXTRA_SHOWPREVIEW 0x00000010L +#define SFX_EXTRA_TEMPLATES 0x00000020L +#define SFX_EXTRA_PLAYBUTTON 0x00000040L +#define SFX_EXTRA_SELECTION 0x00000080L +#define SFX_EXTRA_IMAGE_TEMPLATE 0x00000100L + +#define RET_MANAGER 100 + +#define FILEDIALOG_FILTER_ALL "*.*" + +//***************************************************************************** +// SvtFileDialog +//***************************************************************************** + +class SvtExpFileDlg_Impl; +class SvtFileDialog : public ModalDialog, public ::svt::IFilePickerController +{ +private: + // originally from VclFileDialog + ControlChain_Impl* _pUserControls; + + CheckBox* _pCbReadOnly; + CheckBox* _pCbLinkBox; + CheckBox* _pCbPreviewBox; + CheckBox* _pCbSelection; + PushButton* _pPbPlay; + Window* _pPrevWin; + FixedBitmap* _pPrevBmp; + SvtFileView* _pFileView; + ::svt::IFilePickerListener* _pFileNotifier; + SvtExpFileDlg_Impl* _pImp; + WinBits _nExtraBits; + BOOL _bIsInExecute : 1; + + ImageList m_aImages; + ::svt::SmartContent m_aContent; + + ::svt::RestrictedPaths m_aURLFilter; + ::std::set< Control* > m_aDisabledControls; + + ::utl::OConfigurationNode m_aConfiguration; + ::rtl::Reference< ::svt::AsyncPickerAction > + m_pCurrentAsyncAction; + ::com::sun::star::uno::Reference< + ::com::sun::star::ui::dialogs::XDialogClosedListener > + m_xListener; + bool m_bInExecuteAsync; + bool m_bHasFilename; + + DECL_STATIC_LINK( SvtFileDialog, FilterSelectHdl_Impl, ListBox* ); + DECL_STATIC_LINK( SvtFileDialog, NewFolderHdl_Impl, PushButton* ); + DECL_STATIC_LINK( SvtFileDialog, ViewHdl_Impl, ImageButton* ); + DECL_STATIC_LINK( SvtFileDialog, OpenHdl_Impl, void* ); + DECL_LINK ( CancelHdl_Impl, void* ); + DECL_STATIC_LINK( SvtFileDialog, FileNameGetFocusHdl_Impl, void* ); + DECL_STATIC_LINK( SvtFileDialog, FileNameModifiedHdl_Impl, void* ); + + void Init_Impl( WinBits nBits ); + /** find a filter with the given wildcard + @param _rFilter + the wildcard pattern to look for in the filter list + @param _bMultiExt + allow for filters with more than one extension pattern + @param _rFilterChanged + set to <TRUE/> if the filter changed + @return + the filter which has been found + */ + SvtFileDialogFilter_Impl* FindFilter_Impl( const String& _rFilter, + sal_Bool _bMultiExt, + sal_Bool& _rFilterChanged + ); + void ExecuteFilter(); + void OpenMultiSelection_Impl(); + void AddControls_Impl( ); + + DECL_LINK( SelectHdl_Impl, SvTabListBox* ); + DECL_LINK( DblClickHdl_Impl, SvTabListBox* ); + DECL_LINK( EntrySelectHdl_Impl, ComboBox* ); + DECL_LINK( OpenDoneHdl_Impl, SvtFileView* ); + DECL_LINK( AutoExtensionHdl_Impl, CheckBox* ); + DECL_LINK( ClickHdl_Impl, CheckBox* ); + DECL_LINK( PlayButtonHdl_Impl, PushButton* ); + + // entfernt einen Filter mit Wildcards aus dem Path und gibt in zurueck + BOOL IsolateFilterFromPath_Impl( String& rPath, String& rFilter ); + + void implArrangeControls(); + void implUpdateImages( ); + +protected: + virtual long Notify( NotifyEvent& rNEvt ); + void EnableInternet( BOOL bInternet ); + + // originally from VclFileDialog + Link _aOKHdl; + Link _aFileSelectHdl; + Link _aFilterSelectHdl; + + String _aPath; + String _aDefExt; + + void ReleaseOwnerShip( Window* pUserControl ); + + /** enables or disables the complete UI of the file picker, with only offering a + cancel button + + This method preserves the "enabled" state of its controls in the following sense: + If you disable a certain control, then disable the dialog UI, then enable the dialog + UI, the control will still be disabled. + This is under the assumption that you'll use EnableControl. Direct access to the control + (such as pControl->Enable()) will break this. + */ + void EnableUI( BOOL _bEnable ); + + /** enables or disables a control + + You are strongly encouraged to prefer this method over pControl->Enable( _bEnable ). See + <member>EnableUI</member> for details. + */ + void EnableControl( Control* _pControl, BOOL _bEnable ); + short PrepareExecute(); + +public: + SvtFileDialog( Window* _pParent, WinBits nBits, WinBits nExtraBits ); + SvtFileDialog( Window* _pParent, WinBits nBits ); + ~SvtFileDialog(); + + virtual long OK(); + virtual short Execute(); + virtual void StartExecuteModal( const Link& rEndDialogHdl ); + + void FileSelect(); + void FilterSelect(); + + void SetBlackList( const ::com::sun::star::uno::Sequence< ::rtl::OUString >& rBlackList ); + const ::com::sun::star::uno::Sequence< ::rtl::OUString >& GetBlackList() const; + void SetStandardDir( const String& rStdDir ); + const String& GetStandardDir() const; + SvStringsDtor* GetPathList() const; // bei MultiSelektion + + void AddFilter( const String& rFilter, + const String& rType ); + + void AddFilterGroup( + const String& _rFilter, + const com::sun::star::uno::Sequence< com::sun::star::beans::StringPair >& rFilters ); + + void SetCurFilter( const String& rFilter ); + String GetCurFilter() const; + USHORT GetFilterCount() const; + const String& GetFilterName( USHORT nPos ) const; + + virtual void Resize(); + virtual void DataChanged( const DataChangedEvent& _rDCEvt ); + + void PrevLevel_Impl(); + void OpenURL_Impl( const String& rURL ); + + inline SvtFileView* GetView() const; + + void DisableSaveLastDirectory(); + void InitSize(); + void UpdateControls( const String& rURL ); + void EnableAutocompletion( BOOL _bEnable = TRUE ); + + void SetFileCallback( ::svt::IFilePickerListener *pNotifier ) { _pFileNotifier = pNotifier; } + + sal_Int32 getTargetColorDepth(); + sal_Int32 getAvailableWidth(); + sal_Int32 getAvailableHeight(); + void setImage( sal_Int16 aImageFormat, const ::com::sun::star::uno::Any& rImage ); + sal_Bool setShowState( sal_Bool bShowState ); + sal_Bool getShowState(); + sal_Bool isAutoExtensionEnabled(); + + String getCurrentFileText( ) const; + void setCurrentFileText( const String& _rText, bool _bSelectAll = false ); + + void onAsyncOperationStarted(); + void onAsyncOperationFinished(); + + void displayIOException( const String& _rURL, ::com::sun::star::ucb::IOErrorCode _eCode ); + void simulateAccessDenied( const String& _rURL ) + { + displayIOException( _rURL, ::com::sun::star::ucb::IOErrorCode_ACCESS_DENIED ); + } + + // originally from VclFileDialog + virtual BOOL AddControl( Window* pControl, BOOL bNewLine = FALSE ); + + // inline + inline void SetPath( const String& rNewURL ); + inline void SetHasFilename( bool bHasFilename ); + inline const String& GetPath() const; + inline void SetDefaultExt( const String& rExt ); + inline void EraseDefaultExt( xub_StrLen _nIndex = 0 ); + inline const String& GetDefaultExt() const; + inline void SetOKHdl( const Link& rLink ); + inline const Link& GetOKHdl() const; + inline void SetFileSelectHdl( const Link& rLink ); + inline const Link& GetFileSelectHdl() const; + inline void SetFilterSelectHdl( const Link& rLink ); + inline const Link& GetFilterSelectHdl() const; + + inline Image GetButtonImage( sal_uInt16 _nButtonId ) const { return m_aImages.GetImage( _nButtonId ); } + + sal_Bool ContentIsFolder( const rtl::OUString& rURL ) { return m_aContent.isFolder( rURL ) && m_aContent.isValid(); } + sal_Bool ContentHasParentFolder( const rtl::OUString& rURL ); + sal_Bool ContentCanMakeFolder( const rtl::OUString& rURL ); + sal_Bool ContentGetTitle( const rtl::OUString& rURL, String& rTitle ); + + /** updates the sizes of the listboxes in the bottom area of the dialog, and of their labels, + according to the space occupied by the current label texts + + @since #i42824# + */ + void updateListboxLabelSizes(); + + /** checks URL access permissions + + <p>with the "restriction" feature we have in the file dialog, it's possible that + only certain URLs can be browsed. This method checks whether a given URL belongs + to this set of permitted URLs.</p> + + <p>If no "access restriction" is effective, this method always returns <TRUE/>.</p> + */ + inline bool isUrlAllowed( const String& _rURL ) const { return m_aURLFilter.isUrlAllowed( _rURL ); } + +private: + SvtFileDialogFilter_Impl* implAddFilter( const String& _rFilter, const String& _rType ); + + /** updates _pUserFilter with a new filter + <p>No checks for necessity are made.</p> + @param _bAllowUserDefExt + set to <TRUE/> if a filter like "*.txt" should reset the DefaultExtension to doc. + <p> + In a file-save-dialog this would have the following effect:<br/> + Say that auto-extension is checked, and the user enters *.txt, while a non-txt filter is selected.<br/> + If _bAllowUserDefExt is set to <TRUE/>, then a user input of "foo" would save a foo.txt, but in a format + which is determined by the filter selected (which is no txt file as said above).<br/> + If _bAllowUserDefExt is set to <FALSE/>, the default extension will be the one of the selected filter, means + in the above scenario a file "foo.<ext>" will be saved where ext is the extension of the selected filter. + </p> + @return <TRUE/> if the new filter is "*.*" + */ + sal_Bool createNewUserFilter( const String& _rNewFilter, sal_Bool _bAllowUserDefExt ); + + sal_uInt16 adjustFilter( const String& _rFilter ); + + // IFilePickerController, needed by OControlAccess + virtual Control* getControl( sal_Int16 _nControlId, sal_Bool _bLabelControl = sal_False ) const; + virtual void enableControl( sal_Int16 _nControlId, sal_Bool _bEnable ); + virtual String getCurFilter( ) const; + + String implGetInitialURL( const String& _rPath, const String& _rFallback ); + + /// initializes the special URL lists, such as our favourites and our restricted paths + void implInitializeSpecialURLLists( ); + + /// executes a certain FileView action asynchronously + void executeAsync( + ::svt::AsyncPickerAction::Action _eAction, + const String& _rURL, + const String& _rFilter + ); + + /** helper function to check and append the default filter extension if + necessary. + The function checks if the specified filename already contains one of + the valid extensions of the specified filter. If not the filter default + extension is appended to the filename. + + @param _rFileName the filename which is checked and extended if necessary. + @param _rFilterDefaultExtension the default extension of the used filter. + @param _rFilterExtensions a list of one or more valid filter extensions + of the used filter. + + */ + static void appendDefaultExtension( + String& _rFileName, + const String& _rFilterDefaultExtension, + const String& _rFilterExtensions); +}; + +//*************************************************************************** + +inline void SvtFileDialog::SetPath( const String& rNewURL ) +{ + _aPath = rNewURL; +} + +//*************************************************************************** + +inline void SvtFileDialog::SetHasFilename( bool bHasFilename ) +{ + m_bHasFilename = bHasFilename; +} + +//*************************************************************************** + +inline const String& SvtFileDialog::GetPath() const +{ + return _aPath; +} + +//*************************************************************************** + +inline void SvtFileDialog::SetDefaultExt( const String& rExt ) +{ + _aDefExt = rExt; +} + +inline void SvtFileDialog::EraseDefaultExt( xub_StrLen _nIndex ) +{ + _aDefExt.Erase( _nIndex ); +} + +inline const String& SvtFileDialog::GetDefaultExt() const +{ + return _aDefExt; +} + +//***************************************************************************** + +inline void SvtFileDialog::SetOKHdl +( + const Link& rLink +) +{ + _aOKHdl = rLink; +} + +//***************************************************************************** + +inline const Link& SvtFileDialog::GetOKHdl() const +{ + return _aOKHdl; +} + +//***************************************************************************** + +inline void SvtFileDialog::SetFileSelectHdl +( + const Link& rLink +) +{ + _aFileSelectHdl = rLink; +} + +//***************************************************************************** + +inline const Link& SvtFileDialog::GetFileSelectHdl() const +{ + return _aFileSelectHdl; +} + +//***************************************************************************** + +inline void SvtFileDialog::SetFilterSelectHdl +( + const Link& rLink +) +{ + _aFilterSelectHdl = rLink; +} + +//***************************************************************************** + +inline const Link& SvtFileDialog::GetFilterSelectHdl() const +{ + return _aFilterSelectHdl; +} + +//***************************************************************************** + +inline SvtFileView* SvtFileDialog::GetView() const +{ + return _pFileView; +} + +//***************************************************************************** +//***************************************************************************** +//***************************************************************************** + +class SvtFilePicker; + +#define FILE_SELECTION_CHANGED 1 +#define DIRECTORY_CHANGED 2 +#define HELP_REQUESTED 3 +#define CTRL_STATE_CHANGED 4 +#define DIALOG_SIZE_CHANGED 5 + + +#endif // #ifndef _IODLG_HXX diff --git a/fpicker/source/office/iodlg.src b/fpicker/source/office/iodlg.src new file mode 100644 index 000000000000..da2d1cd926b6 --- /dev/null +++ b/fpicker/source/office/iodlg.src @@ -0,0 +1,333 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + + // includes ****************************************************************** +#include "svtools/svtools.hrc" +#include "svtools/helpid.hrc" +#include "iodlg.hrc" + +#define FILEPICKER_IL_IDLIST \ + IdList = \ + { \ + IMG_FILEDLG_BTN_UP; \ + IMG_FILEDLG_BTN_STD; \ + IMG_FILEDLG_CREATEFOLDER; \ + }; \ + IdCount = \ + { \ + 3; \ + }; + +#define MASKCOLOR MaskColor = Color { Red = 0xFFFF; Green = 0x0000; Blue = 0xFFFF; }; + + // image lists *************************************************************** + +ImageList RID_FILEPICKER_IMAGES +{ + Prefix = "fp"; + MASKCOLOR + FILEPICKER_IL_IDLIST +}; + +ImageList RID_FILEPICKER_IMAGES_HC +{ + Prefix = "fph"; + MASKCOLOR + FILEPICKER_IL_IDLIST +}; + + // dialogs ******************************************************************* + +ModalDialog DLG_SVT_EXPLORERFILE +{ + OutputSize = TRUE ; + SVLook = TRUE ; + Moveable = TRUE ; + Closeable = TRUE ; + Sizeable = TRUE; + HelpId = HID_EXPLORERDLG_FILE ; + Size = MAP_APPFONT ( 280 , 174 ) ; + FixedText FT_EXPLORERFILE_CURRENTPATH + { + Pos = MAP_APPFONT ( 6 , 6 ) ; + Size = MAP_APPFONT ( 100 , 10 ) ; + NoLabel = TRUE ; + }; + ImageButton BTN_EXPLORERFILE_NEWFOLDER + { + HelpID = "fpicker:ImageButton:DLG_SVT_EXPLORERFILE:BTN_EXPLORERFILE_NEWFOLDER"; + TabStop = FALSE ; + Pos = MAP_APPFONT ( 59 , 6 ) ; + QuickHelpText [ en-US ] = "Create New Directory" ; + }; + ImageButton BTN_EXPLORERFILE_LISTVIEW + { + HelpID = "fpicker:ImageButton:DLG_SVT_EXPLORERFILE:BTN_EXPLORERFILE_LISTVIEW"; + TabStop = FALSE ; + Pos = MAP_APPFONT ( 109 , 6 ) ; + ButtonImage = Image + { + ImageBitmap = Bitmap + { + File = "list.bmp" ; + }; + MASKCOLOR + }; + QuickHelpText [ en-US ] = "List"; + }; + ImageButton BTN_EXPLORERFILE_DETAILSVIEW + { + HelpID = "fpicker:ImageButton:DLG_SVT_EXPLORERFILE:BTN_EXPLORERFILE_DETAILSVIEW"; + TabStop = FALSE ; + Pos = MAP_APPFONT ( 109 , 6 ) ; + ButtonImage = Image + { + ImageBitmap = Bitmap + { + File = "sc06356.bmp" ; + }; + MASKCOLOR + }; + QuickHelpText [ en-US ] = "Details"; + }; + MenuButton BTN_EXPLORERFILE_UP + { + HelpID = "fpicker:MenuButton:DLG_SVT_EXPLORERFILE:BTN_EXPLORERFILE_UP"; + TabStop = FALSE ; + Pos = MAP_APPFONT ( 109 , 6 ) ; + QuickHelpText [ en-US ] = "Up One Level" ; + }; + + MenuButton BTN_EXPLORERFILE_STANDARD + { + HelpID = "fpicker:MenuButton:DLG_SVT_EXPLORERFILE:BTN_EXPLORERFILE_STANDARD"; + TabStop = FALSE ; + Pos = MAP_APPFONT ( 59 , 6 ) ; + QuickHelpText [ en-US ] = "Default Directory" ; + }; + Control CTL_EXPLORERFILE_FILELIST + { + TabStop = TRUE ; + Pos = MAP_APPFONT ( 6 , 26 ) ; + Size = MAP_APPFONT ( 268 , 85 ) ; + Border = TRUE ; + }; + FixedText FT_EXPLORERFILE_FILENAME + { + Pos = MAP_APPFONT ( 6 , 118 ) ; + Size = MAP_APPFONT ( 50 , 10 ) ; + Text [ en-US ] = "File ~name:" ; + }; + Edit ED_EXPLORERFILE_FILENAME + { + HelpID = "fpicker:Edit:DLG_SVT_EXPLORERFILE:ED_EXPLORERFILE_FILENAME"; + Pos = MAP_APPFONT ( 59 , 117 ) ; + Size = MAP_APPFONT ( 159 , 12 ) ; + Border = TRUE ; + }; + FixedText FT_EXPLORERFILE_SHARED_LISTBOX + { + Pos = MAP_APPFONT ( 6 , 133 ) ; + Size = MAP_APPFONT ( 50 , 10 ) ; + // Note: this control does not have a text. The text is filled at runtime from the STR_SVT_FILEPICKER_VERSION, + // STR_SVT_FILEPICKER_TEMPLATES, or STR_SVT_FILEPICKER_IMAGE_TEMPLATE resource + }; + ListBox LB_EXPLORERFILE_SHARED_LISTBOX + { + HelpID = "fpicker:ListBox:DLG_SVT_EXPLORERFILE:LB_EXPLORERFILE_SHARED_LISTBOX"; + Pos = MAP_APPFONT ( 59 , 132 ) ; + Size = MAP_APPFONT ( 159 , 40 ) ; + DropDown = TRUE ; + AutoSize = TRUE ; + AutoHScroll = TRUE ; + }; + FixedText FT_EXPLORERFILE_FILETYPE + { + Pos = MAP_APPFONT ( 6 , 148 ) ; + Size = MAP_APPFONT ( 50 , 10 ) ; + Text [ en-US ] = "File ~type:" ; + }; + ListBox LB_EXPLORERFILE_FILETYPE + { + HelpID = "fpicker:ListBox:DLG_SVT_EXPLORERFILE:LB_EXPLORERFILE_FILETYPE"; + Pos = MAP_APPFONT ( 59 , 147 ) ; + Size = MAP_APPFONT ( 159 , 80 ) ; + DropDown = TRUE ; + AutoSize = TRUE ; + AutoHScroll = TRUE ; + Sort = FALSE ; + }; + CheckBox CB_EXPLORERFILE_READONLY + { + HelpID = "fpicker:CheckBox:DLG_SVT_EXPLORERFILE:CB_EXPLORERFILE_READONLY"; + Size = MAP_APPFONT ( 80 , 10 ) ; + Text [ en-US ] = "~Read-only" ; + }; + CheckBox CB_EXPLORERFILE_PASSWORD + { + HelpID = "fpicker:CheckBox:DLG_SVT_EXPLORERFILE:CB_EXPLORERFILE_PASSWORD"; + Size = MAP_APPFONT ( 100, 10 ) ; + Text [ en-US ] = "Save with password" ; + }; + CheckBox CB_AUTO_EXTENSION + { + HelpID = "fpicker:CheckBox:DLG_SVT_EXPLORERFILE:CB_AUTO_EXTENSION"; + Size = MAP_APPFONT ( 160 , 10 ) ; + Text [ en-US ] = "~Automatic file name extension" ; + }; + CheckBox CB_OPTIONS + { + HelpID = "fpicker:CheckBox:DLG_SVT_EXPLORERFILE:CB_OPTIONS"; + Size = MAP_APPFONT ( 120 , 10 ) ; + Text [ en-US ] = "Edit ~filter settings"; + }; + PushButton BTN_EXPLORERFILE_OPEN + { + HelpID = "fpicker:PushButton:DLG_SVT_EXPLORERFILE:BTN_EXPLORERFILE_OPEN"; + Pos = MAP_APPFONT ( 224 , 117 ) ; + Size = MAP_APPFONT ( 50 , 14 ) ; + DefButton = TRUE ; + Text [ en-US ] = "~Open" ; + }; + CancelButton BTN_EXPLORERFILE_CANCEL + { + Pos = MAP_APPFONT ( 224 , 134 ) ; + Size = MAP_APPFONT ( 50 , 14 ) ; + }; + HelpButton BTN_EXPLORERFILE_HELP + { + Pos = MAP_APPFONT ( 224 , 151 ) ; + Size = MAP_APPFONT ( 50 , 14 ) ; + }; + String STR_EXPLORERFILE_OPEN + { + Text [ en-US ] = "Open" ; + }; + String STR_EXPLORERFILE_SAVE + { + Text [ en-US ] = "Save as" ; + }; + String STR_EXPLORERFILE_BUTTONSAVE + { + Text [ en-US ] = "~Save" ; + }; + String STR_PATHNAME + { + Text [ en-US ] = "~Path:" ; + }; + String STR_PATHSELECT + { + Text [ en-US ] = "Select path" ; + }; + String STR_BUTTONSELECT + { + Text [ en-US ] = "~Select"; + }; + String STR_ACTUALVERSION + { + Text [ en-US ] = "Current version"; + }; +}; + +// QueryFolderNameDialog ---------------------------------------------------------- +ModalDialog DLG_SVT_QUERYFOLDERNAME +{ + HelpID = "fpicker:ModalDialog:DLG_SVT_QUERYFOLDERNAME"; + Border = TRUE ; + Moveable = TRUE ; + OutputSize = TRUE ; + SVLook = TRUE ; + Text = "Ordner" ; + Size = MAP_APPFONT ( 218 , 45 ) ; + FixedText FT_SVT_QUERYFOLDERNAME_DLG_NAME + { + Pos = MAP_APPFONT ( 12 , 14 ) ; + Size = MAP_APPFONT ( 138 , 10 ) ; + Text [ en-US ] = "Na~me" ; + }; + Edit ED_SVT_QUERYFOLDERNAME_DLG_NAME + { + HelpID = "fpicker:Edit:DLG_SVT_QUERYFOLDERNAME:ED_SVT_QUERYFOLDERNAME_DLG_NAME"; + Pos = MAP_APPFONT ( 12 , 27 ) ; + Size = MAP_APPFONT ( 138 , 12 ) ; + Border = TRUE ; + Left = TRUE ; + }; + FixedLine FL_SVT_QUERYFOLDERNAME_DLG_NAME + { + Group = TRUE ; + Pos = MAP_APPFONT ( 6 , 3 ) ; + Size = MAP_APPFONT ( 150 , 8 ) ; + Text [ en-US ] = "Create new folder" ; + }; + OKButton BT_SVT_QUERYFOLDERNAME_DLG_OK + { + Pos = MAP_APPFONT ( 162 , 6 ) ; + Size = MAP_APPFONT ( 50 , 14 ) ; + DefButton = TRUE ; + }; + CancelButton BT_SVT_QUERYFOLDERNAME_DLG_CANCEL + { + Pos = MAP_APPFONT ( 162 , 23 ) ; + Size = MAP_APPFONT ( 50 , 14 ) ; + }; +}; + +// strings ******************************************************************* + +String RID_FILEOPEN_INVALIDFOLDER +{ + Text [ en-US ] = "$name$ does not exist."; +}; + +String RID_FILEOPEN_NOTEXISTENTFILE +{ + Text [ en-US ] = "The file $name$ does not exist.\nMake sure you have entered the correct file name."; +}; + +String STR_FILTERNAME_ALL +{ + Text [ en-US ] = "All files (*.*)" ; +}; + +String STR_SVT_ALREADYEXISTOVERWRITE +{ + Text [ en-US ] = "The file already exists. Overwrite?" ; +}; + +String STR_SVT_NEW_FOLDER +{ + Text [ en-US ] = "Folder" ; +}; + +String STR_SVT_NOREMOVABLEDEVICE +{ + Text [ en-US ] = "No removable storage device detected.\nMake sure it is plugged in properly and try again." ; +}; + +//******************************************************************** EOF + diff --git a/fpicker/source/office/iodlgimp.cxx b/fpicker/source/office/iodlgimp.cxx new file mode 100644 index 000000000000..5e57075a6bb7 --- /dev/null +++ b/fpicker/source/office/iodlgimp.cxx @@ -0,0 +1,507 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_fpicker.hxx" + +// includes ******************************************************************* + +#include "iodlgimp.hxx" +#include "svtools/headbar.hxx" +#include <tools/debug.hxx> +#include <tools/wldcrd.hxx> +#include <tools/urlobj.hxx> +#include <vcl/menu.hxx> +#include <vcl/msgbox.hxx> +#include <vcl/lstbox.hxx> +#include <vcl/svapp.hxx> +// #97148# --------------- +#include "svl/ctypeitm.hxx" +#include "svl/eitem.hxx" +#include "unotools/viewoptions.hxx" +#include "svtools/fileview.hxx" +#include "svtools/inettbc.hxx" +#include "iodlg.hxx" +#include "iodlg.hrc" +#include "svtools/imagemgr.hxx" +#include <unotools/localfilehelper.hxx> +#include "unotools/useroptions.hxx" +#include "rtl/instance.hxx" +#include <svl/svl.hrc> + +#define _SVSTDARR_STRINGSSORTDTOR +#define _SVSTDARR_STRINGSDTOR +#define _SVSTDARR_USHORTS +#include "svl/svstdarr.hxx" + +using namespace ::com::sun::star::uno; +using namespace ::com::sun::star::lang; +using namespace ::utl; + +// some stuff for easier changes for SvtViewOptions +static const sal_Char* pViewOptDataName = "dialog data"; +#define VIEWOPT_DATANAME ::rtl::OUString::createFromAscii( pViewOptDataName ) + +static inline void SetViewOptUserItem( SvtViewOptions& rOpt, const String& rData ) +{ + rOpt.SetUserItem( VIEWOPT_DATANAME, makeAny( ::rtl::OUString( rData ) ) ); +} + +static inline String GetViewOptUserItem( const SvtViewOptions& rOpt ) +{ + Any aAny( rOpt.GetUserItem( VIEWOPT_DATANAME ) ); + ::rtl::OUString aUserData; + aAny >>= aUserData; + + return String( aUserData ); +} + + +// defines f"ur den Style der BrowseBox + +#define STYLE_MULTI_SELECTION \ + CNTVIEWSTYLE_NODE_BUTTONS | \ + CNTVIEWSTYLE_NODE_BUTTONS_AT_ROOT | \ + CNTVIEWSTYLE_SHOW_MESSAGES | \ + CNTVIEWSTYLE_SHOW_FOLDERS | \ + CNTVIEWSTYLE_NO_SMARTHIGHLIGHT | \ + CNTVIEWSTYLE_HIDE_OPENMENU | \ + CNTVIEWSTYLE_DEFAULT_APPEARANCE | \ + CNTVIEWSTYLE_SORT_BY_FOLDER + +#define STYLE_SINGLE_SELECTION \ + STYLE_MULTI_SELECTION | CNTVIEWSTYLE_SINGLE_SELECTION + +#define BOOL_NOT_INITIALIZE ((sal_Bool)2) + +//***************************************************************************** +// ResMgrHolder / SvtSimpleResId +//***************************************************************************** +namespace +{ + struct ResMgrHolder + { + ResMgr * operator ()() + { + return ResMgr::CreateResMgr (CREATEVERSIONRESMGR_NAME(svs)); + } + static ResMgr * getOrCreate() + { + return rtl_Instance< + ResMgr, ResMgrHolder, + osl::MutexGuard, osl::GetGlobalMutex >::create ( + ResMgrHolder(), osl::GetGlobalMutex()); + } + }; + + struct SvtSimpleResId : public ResId + { + SvtSimpleResId (USHORT nId) : ResId (nId, *ResMgrHolder::getOrCreate()) {} + }; +} + +//***************************************************************************** +// SvtFileDialogFilter_Impl +//***************************************************************************** + +DBG_NAME( SvtFileDialogFilter_Impl ) +SvtFileDialogFilter_Impl::SvtFileDialogFilter_Impl( const String& rName, const String& rType ) + :m_aName( rName ) + ,m_aType( rType ) +{ + DBG_CTOR( SvtFileDialogFilter_Impl, NULL ); + + m_aType.ToLowerAscii(); +} + +//***************************************************************************** + +SvtFileDialogFilter_Impl::~SvtFileDialogFilter_Impl() +{ + DBG_DTOR( SvtFileDialogFilter_Impl, NULL ); +} + +//***************************************************************************** +// SvtFileDialogFilterList_Impl +//***************************************************************************** + +SV_IMPL_PTRARR( SvtFileDialogFilterList_Impl, SvtFileDialogFilter_Impl* ); + +//============================================================================= +//= SvtFileDialogURLSelector +//============================================================================= + +//----------------------------------------------------------------------------- +SvtFileDialogURLSelector::SvtFileDialogURLSelector( SvtFileDialog* _pParent, const ResId& _rResId, sal_uInt16 _nButtonId ) + :MenuButton ( _pParent, _rResId ) + ,m_pParent ( _pParent ) + ,m_pMenu ( new PopupMenu ) +{ + SetStyle( GetStyle() | WB_NOPOINTERFOCUS | WB_RECTSTYLE | WB_SMALLSTYLE ); + SetModeImage( m_pParent->GetButtonImage( _nButtonId ) ); + SetMenuMode( MENUBUTTON_MENUMODE_TIMED ); + SetDropDown( PUSHBUTTON_DROPDOWN_TOOLBOX ); +} + +//----------------------------------------------------------------------------- +SvtFileDialogURLSelector::~SvtFileDialogURLSelector() +{ + delete m_pMenu; +} + +//----------------------------------------------------------------------------- +void SvtFileDialogURLSelector::OpenURL( const String& rURL ) +{ + INetURLObject aObj( rURL ); + DBG_ASSERT( aObj.GetProtocol() != INET_PROT_NOT_VALID, "SvtFileDialogURLSelector::OpenURL: Invalid URL!" ); + m_pParent->OpenURL_Impl( aObj.GetMainURL( INetURLObject::NO_DECODE ) ); +} + +//----------------------------------------------------------------------------- +void SvtFileDialogURLSelector::Activate() +{ + m_pMenu->Clear(); + + FillURLMenu( m_pMenu ); + + SetPopupMenu( m_pMenu ); +} + +//============================================================================= +//= SvtUpButton_Impl +//============================================================================= + +//----------------------------------------------------------------------------- +SvtUpButton_Impl::SvtUpButton_Impl( SvtFileDialog* pParent, const ResId& rResId ) + :SvtFileDialogURLSelector( pParent, rResId, IMG_FILEDLG_BTN_UP ) + ,_pURLs ( NULL ) +{ +} + +//----------------------------------------------------------------------------- +SvtUpButton_Impl::~SvtUpButton_Impl() +{ + delete _pURLs; +} + +//----------------------------------------------------------------------------- +void SvtUpButton_Impl::FillURLMenu( PopupMenu* _pMenu ) +{ + SvtFileView* pBox = GetDialogParent()->GetView(); + + sal_uInt16 nItemId = 1; + + delete _pURLs; + _pURLs = new SvStringsDtor; + + // "Ubergeordnete Ebenen bestimmen. + INetURLObject aObject( pBox->GetViewURL() ); + sal_Int32 nCount = aObject.getSegmentCount(); + + ::svtools::VolumeInfo aVolInfo( sal_True /* volume */, sal_False /* remote */, + sal_False /* removable */, sal_False /* floppy */, + sal_False /* compact disk */ ); + sal_Bool bIsHighContrast = pBox->GetSettings().GetStyleSettings().GetHighContrastMode(); + Image aVolumeImage( SvFileInformationManager::GetFolderImage( aVolInfo, bIsHighContrast ) ); + + while ( nCount >= 1 ) + { + aObject.removeSegment(); + String* pParentURL = new String( aObject.GetMainURL( INetURLObject::NO_DECODE ) ); + + if ( GetDialogParent()->isUrlAllowed( *pParentURL ) ) + { + String aTitle; + // 97148# -------------------------------- + if ( !GetDialogParent()->ContentGetTitle( *pParentURL, aTitle ) || aTitle.Len() == 0 ) + aTitle = aObject.getName(); + + Image aImage = ( nCount > 1 ) // if nCount == 1 means workplace, which detects the wrong image + ? SvFileInformationManager::GetImage( aObject, bIsHighContrast ) + : aVolumeImage; + + _pMenu->InsertItem( nItemId++, aTitle, aImage ); + _pURLs->Insert( pParentURL, _pURLs->Count() ); + + if ( nCount == 1 ) + { + // adjust the title of the top level entry (the workspace) + _pMenu->SetItemText( --nItemId, SvtSimpleResId( STR_SVT_MIMETYPE_CNT_FSYSBOX ) ); + } + } + + --nCount; + } +} + +//----------------------------------------------------------------------------- +void SvtUpButton_Impl::Select() +{ + sal_uInt16 nId = GetCurItemId(); + + if ( nId ) + { + --nId; + DBG_ASSERT( nId <= _pURLs->Count(), "SvtUpButton_Impl:falscher Index" ); + + String aURL = *(_pURLs->GetObject( nId )); + GetDialogParent()->OpenURL_Impl( aURL ); + } +} + +//----------------------------------------------------------------------------- +void SvtUpButton_Impl::Click() +{ + GetDialogParent()->PrevLevel_Impl(); +} + +//============================================================================= +//= SvtTravelButton_Impl +//============================================================================= + +//----------------------------------------------------------------------------- +SvtTravelButton_Impl::SvtTravelButton_Impl( SvtFileDialog* pParent, const ResId& rResId ) + :SvtFileDialogURLSelector ( pParent, rResId, IMG_FILEDLG_BTN_STD ) +{ + SetDropDown( 0 ); // by default, don't drop down, as we don't have favourites +} + +//----------------------------------------------------------------------------- +void SvtTravelButton_Impl::SetFavouriteLocations( const ::std::vector< String >& _rLocations ) +{ + m_aFavourites = _rLocations; + // enable the drop down if and only if we have favourites + SetDropDown( m_aFavourites.empty() ? 0 : PUSHBUTTON_DROPDOWN_TOOLBOX ); +} + +//----------------------------------------------------------------------------- +SvtTravelButton_Impl::~SvtTravelButton_Impl() +{ +} + +//----------------------------------------------------------------------------- +void SvtTravelButton_Impl::FillURLMenu( PopupMenu* _pMenu ) +{ + if ( m_aFavourites.empty() ) + // though we claimed that we do not want to have a drop down button + // in this case, VCL nevertheless behaves as if we had one .... :( + return; + + _pMenu->Clear(); + + sal_Bool bIsHighContrast = GetDialogParent()->GetView()->GetSettings().GetStyleSettings().GetHighContrastMode(); + + USHORT nItemId = 1; + String sDisplayName; + + ::std::vector< String >::const_iterator aLoop; + for ( aLoop = m_aFavourites.begin(); aLoop != m_aFavourites.end(); ++aLoop, ++nItemId ) + { + if ( GetDialogParent()->isUrlAllowed( *aLoop ) ) + { + Image aImage = SvFileInformationManager::GetImage( + INetURLObject(*aLoop), bIsHighContrast ); + if ( LocalFileHelper::ConvertURLToSystemPath(*aLoop, sDisplayName) ) + _pMenu->InsertItem( nItemId, sDisplayName, aImage ); + else + _pMenu->InsertItem( nItemId, *aLoop, aImage ); + } + } +} + +//----------------------------------------------------------------------------- +void SvtTravelButton_Impl::Select() +{ + sal_uInt16 nId = GetCurItemId(); + if ( nId ) + { + --nId; + DBG_ASSERT( nId < m_aFavourites.size(), "SvtTravelButton_Impl::Select: invalid index!" ); + if ( nId < m_aFavourites.size() ) + OpenURL( m_aFavourites[ nId ] ); + } +} + +//----------------------------------------------------------------------------- +void SvtTravelButton_Impl::Click() +{ + OpenURL( GetDialogParent()->GetStandardDir() ); +} + +//***************************************************************************** +// SvtExpFileDlg_Impl +//***************************************************************************** + +SvtExpFileDlg_Impl::SvtExpFileDlg_Impl( WinBits ) : + + _pLbFilter ( NULL ), + _pCurFilter ( NULL ), + _pFilter ( new SvtFileDialogFilterList_Impl() ), + _pUserFilter ( NULL ), + _pFtFileName ( NULL ), + _pEdFileName ( NULL ), + _pFtFileVersion ( NULL ), + _pLbFileVersion ( NULL ), + _pFtTemplates ( NULL ), + _pLbTemplates ( NULL ), + _pFtImageTemplates ( NULL ), + _pLbImageTemplates ( NULL ), + _pFtFileType ( NULL ), + _pBtnFileOpen ( NULL ), + _pBtnCancel ( NULL ), + _pBtnHelp ( NULL ), + _pBtnUp ( NULL ), + _pBtnNewFolder ( NULL ), + _pBtnStandard ( NULL ), + _pCbPassword ( NULL ), + _pFtCurrentPath ( NULL ), + _pCbAutoExtension ( NULL ), + _pCbOptions ( NULL ), + _nState ( FILEDLG_STATE_REMOTE ), + _nStyle ( 0 ), + _bDoubleClick ( sal_False ), + m_bNeedDelayedFilterExecute ( sal_False ), + _pDefaultFilter ( NULL ), + _bMultiSelection ( sal_False ), + _nFixDeltaHeight ( 0 ), + _bFolderHasOpened ( sal_False ) +{ +} + +//***************************************************************************** + +SvtExpFileDlg_Impl::~SvtExpFileDlg_Impl() +{ + delete _pFtCurrentPath; + delete _pCbPassword; + delete _pCbAutoExtension; + delete _pCbOptions; + delete _pBtnStandard; + delete _pBtnNewFolder; + delete _pBtnUp; + delete _pBtnHelp; + delete _pBtnCancel; + delete _pBtnFileOpen; + delete _pLbFilter; + delete _pFtFileType; + delete _pLbFileVersion; + delete _pFtFileVersion; + delete _pFtTemplates; + delete _pLbTemplates; + delete _pFtImageTemplates; + delete _pLbImageTemplates; + delete _pEdFileName; + delete _pFtFileName; + delete _pUserFilter; + delete _pFilter; +} + +//***************************************************************************** + +void SvtExpFileDlg_Impl::SetStandardDir( const String& _rDir ) +{ + _aStdDir = _rDir; + if ( 0 == _aStdDir.Len() ) + _aStdDir.AssignAscii( "file:///" ); +} + +//***************************************************************************** +#if OSL_DEBUG_LEVEL > 0 +//----------------------------------------------------------------------------- +namespace { + String lcl_DecoratedFilter( const String& _rOriginalFilter ) + { + String aDecoratedFilter = '<'; + aDecoratedFilter += _rOriginalFilter; + aDecoratedFilter += '>'; + return aDecoratedFilter; + } +} +#endif +//----------------------------------------------------------------------------- + +void SvtExpFileDlg_Impl::ClearFilterList( ) +{ + _pLbFilter->Clear(); +} + +//----------------------------------------------------------------------------- +void SvtExpFileDlg_Impl::SetCurFilter( SvtFileDialogFilter_Impl* pFilter, const String& rDisplayName ) +{ + DBG_ASSERT( pFilter, "SvtExpFileDlg_Impl::SetCurFilter: invalid filter!" ); + DBG_ASSERT( ( rDisplayName == pFilter->GetName() ) + || ( rDisplayName == lcl_DecoratedFilter( pFilter->GetName() ) ), + "SvtExpFileDlg_Impl::SetCurFilter: arguments are inconsistent!" ); + + _pCurFilter = pFilter; + m_sCurrentFilterDisplayName = rDisplayName; +} + +//----------------------------------------------------------------------------- +void SvtExpFileDlg_Impl::InsertFilterListEntry( const SvtFileDialogFilter_Impl* _pFilterDesc ) +{ + String sName = _pFilterDesc->GetName(); + if ( _pFilterDesc->isGroupSeparator() ) + sName = String::CreateFromAscii( "------------------------------------------" ); + else + sName = _pFilterDesc->GetName(); + + // insert an set user data + USHORT nPos = _pLbFilter->InsertEntry( sName ); + _pLbFilter->SetEntryData( nPos, const_cast< void* >( static_cast< const void* >( _pFilterDesc ) ) ); +} + +//----------------------------------------------------------------------------- + +void SvtExpFileDlg_Impl::InitFilterList( ) +{ + // clear the current list + ClearFilterList( ); + + // reinit it + USHORT nPos = _pFilter->Count(); + + // search for the first entry which is no group separator + while ( nPos-- && _pFilter->GetObject( nPos ) && _pFilter->GetObject( nPos )->isGroupSeparator() ) + ; + + // add all following entries + while ( (sal_Int16)nPos >= 0 ) + InsertFilterListEntry( _pFilter->GetObject( nPos-- ) ); +} + +//----------------------------------------------------------------------------- + +void SvtExpFileDlg_Impl::CreateFilterListControl( Window* _pParent, const ResId& _rId ) +{ + DBG_ASSERT( !_pLbFilter, "SvtExpFileDlg_Impl::CreateFilterListControl: already created the control!" ); + if ( !_pLbFilter ) + { + _pLbFilter = new ListBox( _pParent, _rId ); + _pLbFilter->SetDropDownLineCount( 10 ); + } +} diff --git a/fpicker/source/office/iodlgimp.hxx b/fpicker/source/office/iodlgimp.hxx new file mode 100644 index 000000000000..f7a4f9026388 --- /dev/null +++ b/fpicker/source/office/iodlgimp.hxx @@ -0,0 +1,339 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ +#ifndef _IODLGIMP_HXX +#define _IODLGIMP_HXX + +#include <tools/string.hxx> +#include <vcl/fixed.hxx> +#include <vcl/lstbox.hxx> +#include <vcl/menubtn.hxx> +#include <vcl/timer.hxx> +#include <vcl/group.hxx> + +#include "svl/svarray.hxx" + +#include <vector> + +//***************************************************************************** + +class Accelerator; +class CheckBox; +class SvtFileDialog; +class SvStringsDtor; +class SvUShorts; + +//***************************************************************************** + +#define FILEDIALOG_DEF_EXTSEP ';' +#define FILEDIALOG_DEF_WILDCARD '*' +#define FILEDIALOG_DEF_IMAGEBORDER 10 +#define FILEDIALOG_DEF_TIMEOUT 250 + +//***************************************************************************** +// SvtFileDialogFilter_Impl +//***************************************************************************** + +/* [Beschreibung] + + Instanzen dieser Klasse repr"asentieren einen Filter +*/ + +class SvtFileDialogFilter_Impl +{ +private: + String m_aName; // name of the entry + String m_aType; // filter wildcard - if empty, the entry marks a group + +public: + SvtFileDialogFilter_Impl( const String& rName, const String& rType ); + ~SvtFileDialogFilter_Impl(); + + const String& GetName() const { return m_aName; } + const String& GetType() const { return m_aType; } + const String GetExtension() const { return m_aType.Copy( 2 ); } + + sal_Bool isGroupSeparator() const { return 0 == m_aType.Len(); } +}; + +//***************************************************************************** +// SvtFileDialogFilterList_Impl +//***************************************************************************** + +SV_DECL_PTRARR_DEL( SvtFileDialogFilterList_Impl, SvtFileDialogFilter_Impl*, 3, 3 ) + +//***************************************************************************** +// SvtFileDlgMode +//***************************************************************************** + +enum SvtFileDlgMode +{ + FILEDLG_MODE_OPEN = 0, + FILEDLG_MODE_SAVE = 1 +}; + +//***************************************************************************** +// SvtFileDlgType +//***************************************************************************** + +enum SvtFileDlgType +{ + FILEDLG_TYPE_FILEDLG = 0, + FILEDLG_TYPE_PATHDLG +}; + +//***************************************************************************** +// SvtFileDialogURLSelector +//***************************************************************************** +class SvtFileDialogURLSelector : public MenuButton +{ +private: + SvtFileDialog* m_pParent; + PopupMenu* m_pMenu; + +protected: + inline SvtFileDialog* GetDialogParent() { return m_pParent; } + +protected: + void OpenURL( const String& rURL ); + + virtual void FillURLMenu( PopupMenu* _pMenu ) = 0; + +protected: + SvtFileDialogURLSelector( SvtFileDialog* _pParent, const ResId& _rResId, sal_uInt16 _nButtonId ); + ~SvtFileDialogURLSelector(); + + virtual void Activate(); +}; + +//***************************************************************************** +// SvtUpButton_Impl +//***************************************************************************** + +class SvtUpButton_Impl : public SvtFileDialogURLSelector +{ +private: + SvStringsDtor* _pURLs; + +public: + SvtUpButton_Impl( SvtFileDialog* pParent, const ResId& rResId ); + ~SvtUpButton_Impl(); + +protected: + virtual void FillURLMenu( PopupMenu* _pMenu ); + virtual void Select(); + virtual void Click(); +}; + +//***************************************************************************** +// SvtTravelButton_Impl +//***************************************************************************** + +class SvtTravelButton_Impl : public SvtFileDialogURLSelector +{ +private: + ::std::vector< String > m_aFavourites; + +public: + SvtTravelButton_Impl( SvtFileDialog* pParent, const ResId& rResId ); + ~SvtTravelButton_Impl(); + + void SetFavouriteLocations( const ::std::vector< String >& _rLocations ); + +protected: + virtual void FillURLMenu( PopupMenu* _pMenu ); + virtual void Select(); + virtual void Click(); +}; + +//***************************************************************************** +// SvtFileDlgState +//***************************************************************************** + +typedef sal_uInt8 SvtFileDlgState; + +#define FILEDLG_STATE_NONE ((SvtFileDlgState)0x00) +#define FILEDLG_STATE_REMOTE ((SvtFileDlgState)0x01) + +//***************************************************************************** +// SvtExpFileDlg_Impl +//***************************************************************************** +class SvtURLBox; +class SvtExpFileDlg_Impl +{ +private: + DECL_STATIC_LINK( SvtExpFileDlg_Impl, UnClickHdl, Button* ); + +private: + ListBox* _pLbFilter; + + const SvtFileDialogFilter_Impl* _pCurFilter; + String m_sCurrentFilterDisplayName; // may differ from _pCurFilter->GetName in case it is a cached entry + + ::com::sun::star::uno::Sequence< ::rtl::OUString > _aBlackList; + +public: + SvtFileDialogFilterList_Impl* _pFilter; + SvtFileDialogFilter_Impl* _pUserFilter; + + FixedText* _pFtFileName; + SvtURLBox* _pEdFileName; + + FixedText* _pFtFileVersion; + ListBox* _pLbFileVersion; + + FixedText* _pFtTemplates; + ListBox* _pLbTemplates; + + FixedText* _pFtImageTemplates; + ListBox* _pLbImageTemplates; + + FixedText* _pFtFileType; + PushButton* _pBtnFileOpen; + PushButton* _pBtnCancel; + HelpButton* _pBtnHelp; + SvtUpButton_Impl* _pBtnUp; + ImageButton* _pBtnNewFolder; + SvtTravelButton_Impl* _pBtnStandard; + CheckBox* _pCbPassword; + FixedText* _pFtCurrentPath; + CheckBox* _pCbAutoExtension; + CheckBox* _pCbOptions; + + SvtFileDlgMode _eMode; + SvtFileDlgType _eDlgType; + SvtFileDlgState _nState; + WinBits _nStyle; + + String _aStdDir; + + // beim traveln der Filterbox erst Zeitversetzt filtern + Timer _aFilterTimer; + + // Zeigt der OpenHdl_Imp(), ob das Open durch einen Doppelclick ausgel"ost wurde + sal_Bool _bDoubleClick; + sal_Bool m_bNeedDelayedFilterExecute; + + // Liste mit den 5 zuletzt genutzten Filtern + // Defaultfilter fuer <Alle> oder <Alle ...> + const SvtFileDialogFilter_Impl* _pDefaultFilter; + + // Multiselektion? + sal_Bool _bMultiSelection; + + // Fixgr"ossen f"ur Resize merken + long _nFixDeltaHeight; + Size _a6Size; + Size _aDlgSize; + String _aIniKey; + + sal_Bool _bFolderHasOpened; + + SvtExpFileDlg_Impl( WinBits nBits ); + ~SvtExpFileDlg_Impl(); + + + inline void SetBlackList( const ::com::sun::star::uno::Sequence< ::rtl::OUString >& rBlackList ) { _aBlackList = rBlackList; } + inline const ::com::sun::star::uno::Sequence< ::rtl::OUString >& GetBlackList() const { return _aBlackList; } + void SetStandardDir( const String& _rDir ); + inline const String& GetStandardDir() const { return _aStdDir; } + inline void DisableFilterBoxAutoWidth() { _pLbFilter->EnableDDAutoWidth( FALSE ); } + + // ------------------------------------------ + // access to the filter listbox only as Control* - we want to maintain the entries/userdata ourself + Control* GetFilterListControl() { return _pLbFilter; } + const Control* GetFilterListControl() const { return _pLbFilter; } + void CreateFilterListControl( Window* _pParent, const ResId& _rId ); + inline void SetFilterListSelectHdl( const Link& _rHandler ); + + // inits the listbox for the filters from the filter list (_pFilter) + void ClearFilterList( ); + void InitFilterList( ); + inline sal_Bool HasFilterListEntry( const String& _rFilterName ); + inline void SelectFilterListEntry( const String& _rFilterName ); + inline void SetNoFilterListSelection( ); + void InsertFilterListEntry( const SvtFileDialogFilter_Impl* _pFilterDesc ); + // _pFilterDesc must already have been added to _pFilter + inline SvtFileDialogFilter_Impl* GetSelectedFilterEntry( String& /* [out] */ _rDisplayName ) const; + inline sal_Bool IsFilterListTravelSelect() const; + + // ------------------------------------------ + // access to the current filter via methods only - need to care for consistency between _pCurFilter and m_sCurrentFilterDisplayName + inline const SvtFileDialogFilter_Impl* GetCurFilter( ) const; + inline const String& GetCurFilterDisplayName() const; + void SetCurFilter( SvtFileDialogFilter_Impl* _pFilter, const String& _rDisplayName ); + inline void SetCurFilter( SvtFileDialogFilter_Impl* _pFilter ); +}; + +inline void SvtExpFileDlg_Impl::SetFilterListSelectHdl( const Link& _rHandler ) +{ + _pLbFilter->SetSelectHdl( _rHandler ); +} + +inline sal_Bool SvtExpFileDlg_Impl::HasFilterListEntry( const String& _rFilterName ) +{ + return ( LISTBOX_ENTRY_NOTFOUND != _pLbFilter->GetEntryPos( _rFilterName ) ); +} + +inline void SvtExpFileDlg_Impl::SelectFilterListEntry( const String& _rFilterName ) +{ + _pLbFilter->SelectEntry( _rFilterName ); +} + +inline void SvtExpFileDlg_Impl::SetNoFilterListSelection( ) +{ + _pLbFilter->SetNoSelection( ); +} + +inline SvtFileDialogFilter_Impl* SvtExpFileDlg_Impl::GetSelectedFilterEntry( String& _rDisplayName ) const +{ + _rDisplayName = _pLbFilter->GetSelectEntry(); + return static_cast< SvtFileDialogFilter_Impl* >( _pLbFilter->GetEntryData ( _pLbFilter->GetSelectEntryPos() ) ); +} + +inline sal_Bool SvtExpFileDlg_Impl::IsFilterListTravelSelect() const +{ + return _pLbFilter->IsTravelSelect(); +} + +inline const SvtFileDialogFilter_Impl* SvtExpFileDlg_Impl::GetCurFilter( ) const +{ + return _pCurFilter; +} + +inline const String& SvtExpFileDlg_Impl::GetCurFilterDisplayName() const +{ + return m_sCurrentFilterDisplayName; +} + +inline void SvtExpFileDlg_Impl::SetCurFilter( SvtFileDialogFilter_Impl* pFilter ) +{ + SetCurFilter( pFilter, pFilter->GetName() ); +} + +#endif // #ifndef _IODLGIMP_HXX + + diff --git a/fpicker/source/office/makefile.mk b/fpicker/source/office/makefile.mk new file mode 100644 index 000000000000..7481fd867ca7 --- /dev/null +++ b/fpicker/source/office/makefile.mk @@ -0,0 +1,96 @@ +#************************************************************************* +# +# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. +# +# Copyright 2000, 2010 Oracle and/or its affiliates. +# +# OpenOffice.org - a multi-platform office productivity suite +# +# This file is part of OpenOffice.org. +# +# OpenOffice.org is free software: you can redistribute it and/or modify +# it under the terms of the GNU Lesser General Public License version 3 +# only, as published by the Free Software Foundation. +# +# OpenOffice.org is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Lesser General Public License version 3 for more details +# (a copy is included in the LICENSE file that accompanied this code). +# +# You should have received a copy of the GNU Lesser General Public License +# version 3 along with OpenOffice.org. If not, see +# <http://www.openoffice.org/license.html> +# for a copy of the LGPLv3 License. +# +#************************************************************************* + +PRJ=..$/.. + +PRJNAME=fpicker +TARGET=fps_office +LIBTARGET=NO +ENABLE_EXCEPTIONS=TRUE +VISIBILITY_HIDDEN=TRUE +GEN_HID=TRUE + +# --- Settings ----------------------------------------------------- + +.INCLUDE : settings.mk +DLLPRE= + +# --- Files -------------------------------------------------------- + +SLOFILES=\ + $(SLO)$/asyncfilepicker.obj \ + $(SLO)$/commonpicker.obj \ + $(SLO)$/OfficeControlAccess.obj \ + $(SLO)$/OfficeFilePicker.obj \ + $(SLO)$/OfficeFolderPicker.obj \ + $(SLO)$/fpinteraction.obj \ + $(SLO)$/fpsmartcontent.obj \ + $(SLO)$/fps_office.obj \ + $(SLO)$/iodlg.obj \ + $(SLO)$/iodlgimp.obj + +SHL1TARGET= $(TARGET).uno +SHL1IMPLIB= i$(TARGET) +SHL1OBJS= $(SLOFILES) +SHL1STDLIBS=\ + $(SVTOOLLIB) \ + $(TKLIB) \ + $(VCLLIB) \ + $(SVLLIB) \ + $(UNOTOOLSLIB) \ + $(TOOLSLIB) \ + $(UCBHELPERLIB) \ + $(COMPHELPERLIB) \ + $(CPPUHELPERLIB) \ + $(CPPULIB) \ + $(SALLIB) + +SHL1VERSIONMAP=$(SOLARENV)/src/component.map +SHL1DEF= $(MISC)$/$(SHL1TARGET).def +DEF1NAME= $(SHL1TARGET) + +SRS1NAME= $(TARGET) +SRC1FILES= \ + OfficeFilePicker.src \ + iodlg.src + +RESLIB1NAME=$(TARGET) +RESLIB1IMAGES=$(PRJ)$/res +RESLIB1SRSFILES=\ + $(SRS)$/fps_office.srs + +# --- Targets ------------------------------------------------------ + +.INCLUDE : target.mk + +ALLTAR : $(MISC)/fps_office.component + +$(MISC)/fps_office.component .ERRREMOVE : $(SOLARENV)/bin/createcomponent.xslt \ + fps_office.component + $(XSLTPROC) --nonet --stringparam uri \ + '$(COMPONENTPREFIX_BASIS_NATIVE)$(SHL1TARGETN:f)' -o $@ \ + $(SOLARENV)/bin/createcomponent.xslt fps_office.component diff --git a/fpicker/source/office/pickercallbacks.hxx b/fpicker/source/office/pickercallbacks.hxx new file mode 100644 index 000000000000..8942c90ce496 --- /dev/null +++ b/fpicker/source/office/pickercallbacks.hxx @@ -0,0 +1,62 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +#ifndef SVTOOLS_PICKER_CALLBACKS_HXX +#define SVTOOLS_PICKER_CALLBACKS_HXX + +#include <tools/string.hxx> +#include <sal/types.h> + +class Control; + +//......................................................................... +namespace svt +{ +//......................................................................... + + // -------------------------------------------------------------------- + class IFilePickerController + { + public: + virtual Control* getControl( sal_Int16 _nControlId, sal_Bool _bLabelControl = sal_False ) const = 0; + virtual void enableControl( sal_Int16 _nControlId, sal_Bool _bEnable ) = 0; + virtual String getCurFilter( ) const = 0; + }; + + // -------------------------------------------------------------------- + class IFilePickerListener + { + public: + virtual void notify( sal_Int16 _nEventId, sal_Int16 _nControlId ) = 0; + }; + +//......................................................................... +} // namespace svt +//......................................................................... + +#endif // SVTOOLS_PICKER_CALLBACKS_HXX + |