1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ 2 /* 3 * This file is part of the LibreOffice project. 4 * 5 * This Source Code Form is subject to the terms of the Mozilla Public 6 * License, v. 2.0. If a copy of the MPL was not distributed with this 7 * file, You can obtain one at http://mozilla.org/MPL/2.0/. 8 * 9 * This file incorporates work covered by the following license notice: 10 * 11 * Licensed to the Apache Software Foundation (ASF) under one or more 12 * contributor license agreements. See the NOTICE file distributed 13 * with this work for additional information regarding copyright 14 * ownership. The ASF licenses this file to you under the Apache 15 * License, Version 2.0 (the "License"); you may not use this file 16 * except in compliance with the License. You may obtain a copy of 17 * the License at http://www.apache.org/licenses/LICENSE-2.0 . 18 */ 19 20 #include <core_resource.hxx> 21 #include "dsnItem.hxx" 22 #include "generalpage.hxx" 23 #include <connectivity/dbexception.hxx> 24 #include <dbu_dlg.hxx> 25 #include <strings.hrc> 26 #include <dsitems.hxx> 27 #include <stringconstants.hxx> 28 #include <dbadmin.hxx> 29 #include <sfx2/filedlghelper.hxx> 30 #include <sfx2/docfilt.hxx> 31 #include <vcl/stdtext.hxx> 32 #include <vcl/weld.hxx> 33 #include <svl/stritem.hxx> 34 #include <vcl/waitobj.hxx> 35 #include <com/sun/star/sdbc/XDriverAccess.hpp> 36 #include <com/sun/star/beans/PropertyValue.hpp> 37 #include <com/sun/star/ui/dialogs/TemplateDescription.hpp> 38 #include <com/sun/star/container/XNameAccess.hpp> 39 #include "DriverSettings.hxx" 40 #include <UITools.hxx> 41 #include <comphelper/processfactory.hxx> 42 #include <unotools/confignode.hxx> 43 #include <osl/diagnose.h> 44 #include <svtools/miscopt.hxx> 45 #include <sal/log.hxx> 46 47 namespace dbaui 48 { 49 using namespace ::com::sun::star; 50 using namespace ::com::sun::star::uno; 51 using namespace ::com::sun::star::sdbc; 52 using namespace ::com::sun::star::beans; 53 using namespace ::com::sun::star::container; 54 55 // OGeneralPage 56 OGeneralPage::OGeneralPage( vcl::Window* pParent, const OUString& _rUIXMLDescription, const SfxItemSet& _rItems ) 57 :OGenericAdministrationPage( pParent, "PageGeneral", _rUIXMLDescription, _rItems ) 58 ,m_pSpecialMessage ( nullptr ) 59 ,m_eLastMessage ( smNone ) 60 ,m_bInitTypeList ( true ) 61 ,m_pDatasourceType ( nullptr ) 62 ,m_pCollection ( nullptr ) 63 { 64 get( m_pDatasourceType, "datasourceType" ); 65 get( m_pSpecialMessage, "specialMessage" ); 66 67 // extract the datasource type collection from the item set 68 const DbuTypeCollectionItem* pCollectionItem = dynamic_cast<const DbuTypeCollectionItem*>( _rItems.GetItem(DSID_TYPECOLLECTION) ); 69 if (pCollectionItem) 70 m_pCollection = pCollectionItem->getCollection(); 71 SAL_WARN_IF(!m_pCollection, "dbaccess.ui.generalpage", "OGeneralPage::OGeneralPage : really need a DSN type collection !"); 72 73 // do some knittings 74 m_pDatasourceType->SetSelectHdl(LINK(this, OGeneralPage, OnDatasourceTypeSelected)); 75 } 76 77 OGeneralPage::~OGeneralPage() 78 { 79 disposeOnce(); 80 } 81 82 void OGeneralPage::dispose() 83 { 84 m_pSpecialMessage.clear(); 85 m_pDatasourceType.clear(); 86 OGenericAdministrationPage::dispose(); 87 } 88 89 namespace 90 { 91 struct DisplayedType 92 { 93 OUString eType; 94 OUString sDisplayName; 95 96 DisplayedType( const OUString& _eType, const OUString& _rDisplayName ) : eType( _eType ), sDisplayName( _rDisplayName ) { } 97 }; 98 typedef std::vector< DisplayedType > DisplayedTypes; 99 100 struct DisplayedTypeLess 101 { 102 bool operator() ( const DisplayedType& _rLHS, const DisplayedType& _rRHS ) 103 { 104 return _rLHS.eType < _rRHS.eType; 105 } 106 }; 107 } 108 109 void OGeneralPage::initializeTypeList() 110 { 111 if ( m_bInitTypeList ) 112 { 113 m_bInitTypeList = false; 114 m_pDatasourceType->Clear(); 115 116 if ( m_pCollection ) 117 { 118 DisplayedTypes aDisplayedTypes; 119 120 ::dbaccess::ODsnTypeCollection::TypeIterator aEnd = m_pCollection->end(); 121 for ( ::dbaccess::ODsnTypeCollection::TypeIterator aTypeLoop = m_pCollection->begin(); 122 aTypeLoop != aEnd; 123 ++aTypeLoop 124 ) 125 { 126 const OUString& sURLPrefix = aTypeLoop.getURLPrefix(); 127 if ( !sURLPrefix.isEmpty() ) 128 { 129 // skip mysql connection variations. It is handled in another window. 130 if(sURLPrefix.startsWith("sdbc:mysql:") && !sURLPrefix.startsWith("sdbc:mysql:jdbc:")) 131 continue; 132 133 OUString sDisplayName = aTypeLoop.getDisplayName(); 134 if ( m_pDatasourceType->GetEntryPos( sDisplayName ) == LISTBOX_ENTRY_NOTFOUND 135 && approveDatasourceType( sURLPrefix, sDisplayName ) ) 136 { 137 aDisplayedTypes.emplace_back( sURLPrefix, sDisplayName ); 138 } 139 } 140 } 141 std::sort( aDisplayedTypes.begin(), aDisplayedTypes.end(), DisplayedTypeLess() ); 142 DisplayedTypes::const_iterator aDisplayEnd = aDisplayedTypes.end(); 143 for ( DisplayedTypes::const_iterator loop = aDisplayedTypes.begin(); 144 loop != aDisplayEnd; 145 ++loop 146 ) 147 insertDatasourceTypeEntryData( loop->eType, loop->sDisplayName ); 148 } 149 } 150 } 151 152 void OGeneralPageWizard::initializeEmbeddedDBList() 153 { 154 if ( m_bInitEmbeddedDBList ) 155 { 156 m_bInitEmbeddedDBList = false; 157 m_pEmbeddedDBType->Clear(); 158 159 if ( m_pCollection ) 160 { 161 DisplayedTypes aDisplayedTypes; 162 163 ::dbaccess::ODsnTypeCollection::TypeIterator aEnd = m_pCollection->end(); 164 for ( ::dbaccess::ODsnTypeCollection::TypeIterator aTypeLoop = m_pCollection->begin(); 165 aTypeLoop != aEnd; 166 ++aTypeLoop 167 ) 168 { 169 const OUString& sURLPrefix = aTypeLoop.getURLPrefix(); 170 if ( !sURLPrefix.isEmpty() ) 171 { 172 OUString sDisplayName = aTypeLoop.getDisplayName(); 173 if ( m_pEmbeddedDBType->GetEntryPos( sDisplayName ) == LISTBOX_ENTRY_NOTFOUND 174 && dbaccess::ODsnTypeCollection::isEmbeddedDatabase( sURLPrefix ) ) 175 { 176 aDisplayedTypes.emplace_back( sURLPrefix, sDisplayName ); 177 } 178 } 179 } 180 std::sort( aDisplayedTypes.begin(), aDisplayedTypes.end(), DisplayedTypeLess() ); 181 for (auto const& displayedType : aDisplayedTypes) 182 insertEmbeddedDBTypeEntryData( displayedType.eType, displayedType.sDisplayName ); 183 } 184 } 185 } 186 187 void OGeneralPage::setParentTitle(const OUString&) 188 { 189 } 190 191 void OGeneralPage::switchMessage(const OUString& _sURLPrefix) 192 { 193 SPECIAL_MESSAGE eMessage = smNone; 194 if ( _sURLPrefix.isEmpty()/*_eType == m_eNotSupportedKnownType*/ ) 195 { 196 eMessage = smUnsupportedType; 197 } 198 199 if ( eMessage != m_eLastMessage ) 200 { 201 const char* pResId = nullptr; 202 if ( smUnsupportedType == eMessage ) 203 pResId = STR_UNSUPPORTED_DATASOURCE_TYPE; 204 OUString sMessage; 205 if ( pResId ) 206 sMessage = DBA_RES(pResId); 207 208 m_pSpecialMessage->SetText( sMessage ); 209 m_eLastMessage = eMessage; 210 } 211 } 212 213 void OGeneralPage::onTypeSelected(const OUString& _sURLPrefix) 214 { 215 // the new URL text as indicated by the selection history 216 implSetCurrentType( _sURLPrefix ); 217 218 switchMessage(_sURLPrefix); 219 220 m_aTypeSelectHandler.Call(*this); 221 } 222 223 void OGeneralPage::implInitControls( const SfxItemSet& _rSet, bool _bSaveValue ) 224 { 225 initializeTypeList(); 226 227 m_pDatasourceType->SelectEntry( getDatasourceName( _rSet ) ); 228 229 // notify our listener that our type selection has changed (if so) 230 // FIXME: how to detect that it did not changed? (fdo#62937) 231 setParentTitle( m_eCurrentSelection ); 232 onTypeSelected( m_eCurrentSelection ); 233 234 // a special message for the current page state 235 switchMessage( m_eCurrentSelection ); 236 237 OGenericAdministrationPage::implInitControls( _rSet, _bSaveValue ); 238 } 239 240 OUString OGeneralPageWizard::getEmbeddedDBName( const SfxItemSet& _rSet ) 241 { 242 // first check whether or not the selection is invalid or readonly (invalid implies readonly, but not vice versa) 243 bool bValid, bReadonly; 244 getFlags( _rSet, bValid, bReadonly ); 245 246 // if the selection is invalid, disable everything 247 248 implSetCurrentType( OUString() ); 249 250 // compare the DSN prefix with the registered ones 251 OUString sDisplayName; 252 253 if (m_pCollection && bValid) 254 { 255 implSetCurrentType( m_pCollection->getEmbeddedDatabase() ); 256 sDisplayName = m_pCollection->getTypeDisplayName( m_eCurrentSelection ); 257 } 258 259 // select the correct datasource type 260 if ( dbaccess::ODsnTypeCollection::isEmbeddedDatabase( m_eCurrentSelection ) 261 && ( LISTBOX_ENTRY_NOTFOUND == m_pEmbeddedDBType->GetEntryPos( sDisplayName ) ) 262 ) 263 { // this indicates it's really a type which is known in general, but not supported on the current platform 264 // show a message saying so 265 // eSpecialMessage = smUnsupportedType; 266 insertEmbeddedDBTypeEntryData( m_eCurrentSelection, sDisplayName ); 267 } 268 269 return sDisplayName; 270 } 271 272 OUString OGeneralPage::getDatasourceName( const SfxItemSet& _rSet ) 273 { 274 // first check whether or not the selection is invalid or readonly (invalid implies readonly, but not vice versa) 275 bool bValid, bReadonly; 276 getFlags( _rSet, bValid, bReadonly ); 277 278 // if the selection is invalid, disable everything 279 OUString sConnectURL; 280 if ( bValid ) 281 { 282 // collect some items and some values 283 const SfxStringItem* pUrlItem = _rSet.GetItem<SfxStringItem>(DSID_CONNECTURL); 284 assert( pUrlItem ); 285 sConnectURL = pUrlItem->GetValue(); 286 } 287 288 implSetCurrentType( OUString() ); 289 290 // compare the DSN prefix with the registered ones 291 OUString sDisplayName; 292 293 if (m_pCollection && bValid) 294 { 295 implSetCurrentType( m_pCollection->getPrefix( sConnectURL ) ); 296 sDisplayName = m_pCollection->getTypeDisplayName( m_eCurrentSelection ); 297 } 298 299 // select the correct datasource type 300 if ( approveDatasourceType( m_eCurrentSelection, sDisplayName ) 301 && ( LISTBOX_ENTRY_NOTFOUND == m_pDatasourceType->GetEntryPos( sDisplayName ) ) 302 ) 303 { // this indicates it's really a type which is known in general, but not supported on the current platform 304 // show a message saying so 305 // eSpecialMessage = smUnsupportedType; 306 insertDatasourceTypeEntryData( m_eCurrentSelection, sDisplayName ); 307 } 308 309 return sDisplayName; 310 } 311 312 // For the databaseWizard we only have one entry for the MySQL Database, 313 // because we have a separate tabpage to retrieve the respective datasource type 314 // ( ::dbaccess::DST_MYSQL_ODBC || ::dbaccess::DST_MYSQL_JDBC). Therefore we use ::dbaccess::DST_MYSQL_JDBC as a temporary 315 // representative for all MySQl databases) 316 // Also, embedded databases (embedded HSQL, at the moment), are not to appear in the list of 317 // databases to connect to. 318 bool OGeneralPage::approveDatasourceType( const OUString& _sURLPrefix, OUString& _inout_rDisplayName ) 319 { 320 return approveDatasourceType( m_pCollection->determineType(_sURLPrefix), _inout_rDisplayName ); 321 } 322 323 bool OGeneralPage::approveDatasourceType( ::dbaccess::DATASOURCE_TYPE eType, OUString& _inout_rDisplayName ) 324 { 325 if ( eType == ::dbaccess::DST_MYSQL_NATIVE_DIRECT ) 326 { 327 // do not display the Connector/OOo driver itself, it is always wrapped via the MySQL-Driver, if 328 // this driver is installed 329 if ( m_pCollection->hasDriver( "sdbc:mysql:mysqlc:" ) ) 330 _inout_rDisplayName.clear(); 331 } 332 333 if ( eType == ::dbaccess::DST_EMBEDDED_HSQLDB 334 || eType == ::dbaccess::DST_EMBEDDED_FIREBIRD ) 335 _inout_rDisplayName.clear(); 336 337 return _inout_rDisplayName.getLength() > 0; 338 } 339 340 void OGeneralPage::insertDatasourceTypeEntryData(const OUString& _sType, const OUString& sDisplayName) 341 { 342 // insert a (temporary) entry 343 const sal_Int32 nPos = m_pDatasourceType->InsertEntry(sDisplayName); 344 if ( static_cast<size_t>(nPos) >= m_aURLPrefixes.size() ) 345 m_aURLPrefixes.resize(nPos+1); 346 m_aURLPrefixes[nPos] = _sType; 347 } 348 349 void OGeneralPageWizard::insertEmbeddedDBTypeEntryData(const OUString& _sType, const OUString& sDisplayName) 350 { 351 // insert a (temporary) entry 352 const sal_Int32 nPos = m_pEmbeddedDBType->InsertEntry(sDisplayName); 353 if ( static_cast<size_t>(nPos) >= m_aEmbeddedURLPrefixes.size() ) 354 m_aEmbeddedURLPrefixes.resize(nPos+1); 355 m_aEmbeddedURLPrefixes[nPos] = _sType; 356 } 357 358 void OGeneralPage::fillWindows(std::vector< std::unique_ptr<ISaveValueWrapper> >& _rControlList) 359 { 360 _rControlList.emplace_back( new ODisableWrapper<FixedText>( m_pSpecialMessage ) ); 361 } 362 363 void OGeneralPage::fillControls(std::vector< std::unique_ptr<ISaveValueWrapper> >& _rControlList) 364 { 365 _rControlList.emplace_back( new OSaveValueWrapper<ListBox>( m_pDatasourceType ) ); 366 } 367 368 void OGeneralPage::implSetCurrentType( const OUString& _eType ) 369 { 370 if ( _eType == m_eCurrentSelection ) 371 return; 372 373 m_eCurrentSelection = _eType; 374 } 375 376 void OGeneralPage::Reset(const SfxItemSet* _rCoreAttrs) 377 { 378 // reset all locale data 379 implSetCurrentType( OUString() ); 380 // this ensures that our type selection link will be called, even if the new one is the same as the 381 // current one 382 OGenericAdministrationPage::Reset(_rCoreAttrs); 383 } 384 385 IMPL_LINK( OGeneralPageWizard, OnEmbeddedDBTypeSelected, ListBox&, _rBox, void ) 386 { 387 // get the type from the entry data 388 const sal_Int32 nSelected = _rBox.GetSelectedEntryPos(); 389 if (static_cast<size_t>(nSelected) >= m_aEmbeddedURLPrefixes.size() ) 390 { 391 SAL_WARN("dbaccess.ui.generalpage", "Got out-of-range value '" << nSelected << "' from the DatasourceType selection ListBox's GetSelectedEntryPos(): no corresponding URL prefix"); 392 return; 393 } 394 const OUString sURLPrefix = m_aEmbeddedURLPrefixes[ nSelected ]; 395 396 setParentTitle( sURLPrefix ); 397 // let the impl method do all the stuff 398 onTypeSelected( sURLPrefix ); 399 // tell the listener we were modified 400 callModifiedHdl(); 401 } 402 403 IMPL_LINK( OGeneralPage, OnDatasourceTypeSelected, ListBox&, _rBox, void ) 404 { 405 // get the type from the entry data 406 const sal_Int32 nSelected = _rBox.GetSelectedEntryPos(); 407 if ( nSelected == LISTBOX_ENTRY_NOTFOUND) 408 return; 409 if (static_cast<size_t>(nSelected) >= m_aURLPrefixes.size() ) 410 { 411 SAL_WARN("dbaccess.ui.generalpage", "Got out-of-range value '" << nSelected << "' from the DatasourceType selection ListBox's GetSelectedEntryPos(): no corresponding URL prefix"); 412 return; 413 } 414 const OUString sURLPrefix = m_aURLPrefixes[ nSelected ]; 415 416 setParentTitle( sURLPrefix ); 417 // let the impl method do all the stuff 418 onTypeSelected( sURLPrefix ); 419 // tell the listener we were modified 420 callModifiedHdl(); 421 } 422 423 // OGeneralPageDialog 424 OGeneralPageDialog::OGeneralPageDialog( vcl::Window* pParent, const SfxItemSet& _rItems ) 425 :OGeneralPage( pParent, "dbaccess/ui/generalpagedialog.ui", _rItems ) 426 { 427 } 428 429 void OGeneralPageDialog::setParentTitle( const OUString& _sURLPrefix ) 430 { 431 const OUString sName = m_pCollection->getTypeDisplayName( _sURLPrefix ); 432 if ( m_pAdminDialog ) 433 { 434 OUString sMessage = DBA_RES(STR_PARENTTITLE_GENERAL); 435 m_pAdminDialog->setTitle( sMessage.replaceAll( "#", sName ) ); 436 } 437 } 438 439 void OGeneralPageDialog::implInitControls( const SfxItemSet& _rSet, bool _bSaveValue ) 440 { 441 OGeneralPage::implInitControls( _rSet, _bSaveValue ); 442 443 // first check whether or not the selection is invalid or readonly (invalid implies readonly, but not vice versa) 444 bool bValid, bReadonly; 445 getFlags(_rSet, bValid, bReadonly ); 446 447 m_pDatasourceType->Enable( bValid ); 448 } 449 450 bool OGeneralPageDialog::FillItemSet( SfxItemSet* _rCoreAttrs ) 451 { 452 bool bChangedSomething = false; 453 454 const sal_Int32 nEntry = m_pDatasourceType->GetSelectedEntryPos(); 455 OUString sURLPrefix = m_aURLPrefixes[ nEntry ]; 456 457 if ( m_pDatasourceType->IsValueChangedFromSaved() ) 458 { 459 _rCoreAttrs->Put( SfxStringItem( DSID_CONNECTURL, sURLPrefix ) ); 460 bChangedSomething = true; 461 } 462 463 return bChangedSomething; 464 } 465 466 // OGeneralPageWizard 467 OGeneralPageWizard::OGeneralPageWizard( vcl::Window* pParent, const SfxItemSet& _rItems ) 468 :OGeneralPage( pParent, "dbaccess/ui/generalpagewizard.ui", _rItems ) 469 ,m_pRB_CreateDatabase ( nullptr ) 470 ,m_pRB_OpenExistingDatabase ( nullptr ) 471 ,m_pRB_ConnectDatabase ( nullptr ) 472 ,m_pFT_EmbeddedDBLabel ( nullptr ) 473 ,m_pEmbeddedDBType ( nullptr ) 474 ,m_pFT_DocListLabel ( nullptr ) 475 ,m_pLB_DocumentList ( nullptr ) 476 ,m_pPB_OpenDatabase ( nullptr ) 477 ,m_eOriginalCreationMode ( eCreateNew ) 478 ,m_bInitEmbeddedDBList ( true ) 479 { 480 get( m_pRB_CreateDatabase, "createDatabase" ); 481 get( m_pRB_OpenExistingDatabase, "openExistingDatabase" ); 482 get( m_pRB_ConnectDatabase, "connectDatabase" ); 483 get( m_pFT_EmbeddedDBLabel, "embeddeddbLabel" ); 484 get( m_pEmbeddedDBType, "embeddeddbList" ); 485 get( m_pFT_DocListLabel, "docListLabel" ); 486 get( m_pLB_DocumentList, "documentList" ); 487 get( m_pPB_OpenDatabase, "openDatabase" ); 488 489 // If no driver for embedded DBs is installed, and no dBase driver, then hide the "Create new database" option 490 sal_Int32 nCreateNewDBIndex = m_pCollection->getIndexOf( m_pCollection->getEmbeddedDatabase() ); 491 if ( nCreateNewDBIndex == -1 ) 492 nCreateNewDBIndex = m_pCollection->getIndexOf( "sdbc:dbase:" ); 493 bool bHideCreateNew = ( nCreateNewDBIndex == -1 ); 494 495 // also, if our application policies tell us to hide the option, do it 496 ::utl::OConfigurationTreeRoot aConfig( ::utl::OConfigurationTreeRoot::createWithComponentContext( 497 ::comphelper::getProcessComponentContext(), 498 "/org.openoffice.Office.DataAccess/Policies/Features/Base" 499 ) ); 500 bool bAllowCreateLocalDatabase( true ); 501 OSL_VERIFY( aConfig.getNodeValue( "CreateLocalDatabase" ) >>= bAllowCreateLocalDatabase ); 502 if ( !bAllowCreateLocalDatabase ) 503 bHideCreateNew = true; 504 505 if ( bHideCreateNew ) 506 { 507 m_pRB_CreateDatabase->Hide(); 508 m_pRB_ConnectDatabase->Check(); 509 } 510 else 511 m_pRB_CreateDatabase->Check(); 512 513 // do some knittings 514 m_pEmbeddedDBType->SetSelectHdl(LINK(this, OGeneralPageWizard, OnEmbeddedDBTypeSelected)); 515 m_pRB_CreateDatabase->SetClickHdl( LINK( this, OGeneralPageWizard, OnCreateDatabaseModeSelected ) ); 516 m_pRB_ConnectDatabase->SetClickHdl( LINK( this, OGeneralPageWizard, OnSetupModeSelected ) ); 517 m_pRB_OpenExistingDatabase->SetClickHdl( LINK( this, OGeneralPageWizard, OnSetupModeSelected ) ); 518 m_pLB_DocumentList->SetSelectHdl( LINK( this, OGeneralPageWizard, OnDocumentSelected ) ); 519 m_pPB_OpenDatabase->SetClickHdl( LINK( this, OGeneralPageWizard, OnOpenDocument ) ); 520 } 521 522 OGeneralPageWizard::~OGeneralPageWizard() 523 { 524 disposeOnce(); 525 } 526 527 void OGeneralPageWizard::dispose() 528 { 529 m_pRB_CreateDatabase.clear(); 530 m_pRB_OpenExistingDatabase.clear(); 531 m_pRB_ConnectDatabase.clear(); 532 m_pFT_EmbeddedDBLabel.clear(); 533 m_pEmbeddedDBType.clear(); 534 m_pFT_DocListLabel.clear(); 535 m_pLB_DocumentList.clear(); 536 m_pPB_OpenDatabase.clear(); 537 OGeneralPage::dispose(); 538 } 539 540 OGeneralPageWizard::CreationMode OGeneralPageWizard::GetDatabaseCreationMode() const 541 { 542 if ( m_pRB_CreateDatabase->IsChecked() ) 543 return eCreateNew; 544 if ( m_pRB_ConnectDatabase->IsChecked() ) 545 return eConnectExternal; 546 return eOpenExisting; 547 } 548 549 void OGeneralPageWizard::GetFocus() 550 { 551 OGeneralPage::GetFocus(); 552 if ( m_pLB_DocumentList && m_pLB_DocumentList->IsEnabled() ) 553 m_pLB_DocumentList->GrabFocus(); 554 else if ( m_pDatasourceType && m_pDatasourceType->IsEnabled() ) 555 m_pDatasourceType->GrabFocus(); 556 } 557 558 void OGeneralPageWizard::implInitControls( const SfxItemSet& _rSet, bool _bSaveValue ) 559 { 560 OGeneralPage::implInitControls( _rSet, _bSaveValue ); 561 562 initializeEmbeddedDBList(); 563 m_pEmbeddedDBType->SelectEntry( getEmbeddedDBName( _rSet ) ); 564 565 // first check whether or not the selection is invalid or readonly (invalid implies readonly, but not vice versa) 566 bool bValid, bReadonly; 567 getFlags( _rSet, bValid, bReadonly ); 568 569 SetText( OUString() ); 570 571 LayoutHelper::positionBelow( *m_pRB_ConnectDatabase, *m_pDatasourceType, INDENT_BELOW_RADIO ); 572 573 if ( !bValid || bReadonly ) 574 { 575 m_pFT_EmbeddedDBLabel->Enable( false ); 576 m_pDatasourceType->Enable( false ); 577 m_pPB_OpenDatabase->Enable( false ); 578 m_pFT_DocListLabel->Enable( false ); 579 m_pLB_DocumentList->Enable( false ); 580 } 581 else 582 { 583 m_aControlDependencies.enableOnRadioCheck( *m_pRB_CreateDatabase, *m_pEmbeddedDBType, *m_pFT_EmbeddedDBLabel ); 584 m_aControlDependencies.enableOnRadioCheck( *m_pRB_ConnectDatabase, *m_pDatasourceType ); 585 m_aControlDependencies.enableOnRadioCheck( *m_pRB_OpenExistingDatabase, *m_pPB_OpenDatabase, *m_pFT_DocListLabel, *m_pLB_DocumentList ); 586 } 587 588 m_pLB_DocumentList->SetDropDownLineCount( 20 ); 589 if ( m_pLB_DocumentList->GetEntryCount() ) 590 m_pLB_DocumentList->SelectEntryPos( 0 ); 591 592 m_eOriginalCreationMode = GetDatabaseCreationMode(); 593 } 594 595 OUString OGeneralPageWizard::getDatasourceName(const SfxItemSet& _rSet) 596 { 597 // Sets the default selected database on startup. 598 if (m_pRB_CreateDatabase->IsChecked() ) 599 { 600 SvtMiscOptions aMiscOptions; 601 if( aMiscOptions.IsExperimentalMode() ) 602 return m_pCollection->getTypeDisplayName( "sdbc:embedded:firebird" ); 603 else 604 return m_pCollection->getTypeDisplayName( "jdbc:" ); 605 } 606 607 return OGeneralPage::getDatasourceName( _rSet ); 608 } 609 610 bool OGeneralPageWizard::approveDatasourceType( ::dbaccess::DATASOURCE_TYPE eType, OUString& _inout_rDisplayName ) 611 { 612 switch ( eType ) 613 { 614 case ::dbaccess::DST_MYSQL_JDBC: 615 case ::dbaccess::DST_MYSQL_ODBC: 616 case ::dbaccess::DST_MYSQL_NATIVE: 617 _inout_rDisplayName = "MySQL"; 618 break; 619 default: 620 break; 621 } 622 623 return OGeneralPage::approveDatasourceType( eType, _inout_rDisplayName ); 624 } 625 626 bool OGeneralPageWizard::FillItemSet(SfxItemSet* _rCoreAttrs) 627 { 628 bool bChangedSomething = false; 629 630 bool bCommitTypeSelection = true; 631 632 if ( m_pRB_CreateDatabase->IsChecked() ) 633 { 634 _rCoreAttrs->Put( SfxStringItem( DSID_CONNECTURL, OUString( "sdbc:dbase:" ) ) ); 635 bChangedSomething = true; 636 bCommitTypeSelection = false; 637 } 638 else if ( m_pRB_OpenExistingDatabase->IsChecked() ) 639 { 640 if ( m_pRB_OpenExistingDatabase->IsValueChangedFromSaved() ) 641 bChangedSomething = true; 642 643 // TODO 644 bCommitTypeSelection = false; 645 } 646 647 if ( bCommitTypeSelection ) 648 { 649 const sal_Int32 nEntry = m_pDatasourceType->GetSelectedEntryPos(); 650 OUString sURLPrefix = m_aURLPrefixes[nEntry]; 651 652 if ( m_pDatasourceType->IsValueChangedFromSaved() 653 || ( GetDatabaseCreationMode() != m_eOriginalCreationMode ) 654 ) 655 { 656 _rCoreAttrs->Put( SfxStringItem( DSID_CONNECTURL,sURLPrefix ) ); 657 bChangedSomething = true; 658 } 659 else 660 implSetCurrentType( sURLPrefix ); 661 } 662 return bChangedSomething; 663 } 664 665 OGeneralPageWizard::DocumentDescriptor OGeneralPageWizard::GetSelectedDocument() const 666 { 667 DocumentDescriptor aDocument; 668 if ( !m_aBrowsedDocument.sURL.isEmpty() ) 669 aDocument = m_aBrowsedDocument; 670 else 671 { 672 aDocument.sURL = m_pLB_DocumentList->GetSelectedDocumentURL(); 673 aDocument.sFilter = m_pLB_DocumentList->GetSelectedDocumentFilter(); 674 } 675 return aDocument; 676 } 677 678 IMPL_LINK_NOARG( OGeneralPageWizard, OnCreateDatabaseModeSelected, Button*, void ) 679 { 680 m_aCreationModeHandler.Call( *this ); 681 682 OnEmbeddedDBTypeSelected( *m_pEmbeddedDBType ); 683 } 684 685 IMPL_LINK_NOARG( OGeneralPageWizard, OnSetupModeSelected, Button*, void ) 686 { 687 m_aCreationModeHandler.Call( *this ); 688 OnDatasourceTypeSelected(*m_pDatasourceType); 689 } 690 691 IMPL_LINK_NOARG( OGeneralPageWizard, OnDocumentSelected, ListBox&, void ) 692 { 693 m_aDocumentSelectionHandler.Call( *this ); 694 } 695 696 IMPL_LINK_NOARG( OGeneralPageWizard, OnOpenDocument, Button*, void ) 697 { 698 ::sfx2::FileDialogHelper aFileDlg( 699 ui::dialogs::TemplateDescription::FILEOPEN_READONLY_VERSION, 700 FileDialogFlags::NONE, "sdatabase", SfxFilterFlags::NONE, SfxFilterFlags::NONE, GetFrameWeld()); 701 std::shared_ptr<const SfxFilter> pFilter = getStandardDatabaseFilter(); 702 if ( pFilter ) 703 { 704 aFileDlg.SetCurrentFilter(pFilter->GetUIName()); 705 } 706 if ( aFileDlg.Execute() == ERRCODE_NONE ) 707 { 708 OUString sPath = aFileDlg.GetPath(); 709 if ( aFileDlg.GetCurrentFilter() != pFilter->GetUIName() || !pFilter->GetWildcard().Matches(sPath) ) 710 { 711 OUString sMessage(DBA_RES(STR_ERR_USE_CONNECT_TO)); 712 std::unique_ptr<weld::MessageDialog> xInfoBox(Application::CreateMessageDialog(GetFrameWeld(), 713 VclMessageType::Info, VclButtonsType::Ok, 714 sMessage)); 715 xInfoBox->run(); 716 m_pRB_ConnectDatabase->Check(); 717 OnSetupModeSelected( m_pRB_ConnectDatabase ); 718 return; 719 } 720 m_aBrowsedDocument.sURL = sPath; 721 m_aBrowsedDocument.sFilter.clear(); 722 m_aChooseDocumentHandler.Call( *this ); 723 } 724 } 725 726 } // namespace dbaui 727 728 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ 729
