tdf#130857 qt weld: Support mail merge "Server Auth" dialog
[LibreOffice.git] / extensions / source / abpilot / abspilot.cxx
blobfb2be7e8ab33e5d0479e9b047fd0312afd3e2a7a
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #include "abspilot.hxx"
21 #include <helpids.h>
22 #include <strings.hrc>
23 #include <componentmodule.hxx>
24 #include <tools/debug.hxx>
25 #include "typeselectionpage.hxx"
26 #include "admininvokationpage.hxx"
27 #include "tableselectionpage.hxx"
28 #include <vcl/svapp.hxx>
29 #include <vcl/weld.hxx>
30 #include <osl/diagnose.h>
31 #include "abpfinalpage.hxx"
32 #include "fieldmappingpage.hxx"
33 #include "fieldmappingimpl.hxx"
35 using vcl::RoadmapWizardTypes::PathId;
37 namespace abp
41 #define STATE_SELECT_ABTYPE 0
42 #define STATE_INVOKE_ADMIN_DIALOG 1
43 #define STATE_TABLE_SELECTION 2
44 #define STATE_MANUAL_FIELD_MAPPING 3
45 #define STATE_FINAL_CONFIRM 4
49 using namespace ::com::sun::star::uno;
51 OAddressBookSourcePilot::OAddressBookSourcePilot(weld::Window* _pParent, const Reference< XComponentContext >& _rxORB)
52 :OAddressBookSourcePilot_Base( _pParent )
53 ,m_xORB(_rxORB)
54 ,m_aNewDataSource(_rxORB)
55 ,m_eNewDataSourceType( AST_INVALID )
57 declarePath(PathId::COMPLETE,
58 {STATE_SELECT_ABTYPE,
59 STATE_INVOKE_ADMIN_DIALOG,
60 STATE_TABLE_SELECTION,
61 STATE_MANUAL_FIELD_MAPPING,
62 STATE_FINAL_CONFIRM}
64 declarePath(PathId::NO_SETTINGS,
65 {STATE_SELECT_ABTYPE,
66 STATE_TABLE_SELECTION,
67 STATE_MANUAL_FIELD_MAPPING,
68 STATE_FINAL_CONFIRM}
70 declarePath(PathId::NO_FIELDS,
71 {STATE_SELECT_ABTYPE,
72 STATE_INVOKE_ADMIN_DIALOG,
73 STATE_TABLE_SELECTION,
74 STATE_FINAL_CONFIRM}
76 declarePath(PathId::NO_SETTINGS_NO_FIELDS,
77 {STATE_SELECT_ABTYPE,
78 STATE_TABLE_SELECTION,
79 STATE_FINAL_CONFIRM}
82 m_xPrevPage->set_help_id(HID_ABSPILOT_PREVIOUS);
83 m_xNextPage->set_help_id(HID_ABSPILOT_NEXT);
84 m_xCancel->set_help_id(HID_ABSPILOT_CANCEL);
85 m_xFinish->set_help_id(HID_ABSPILOT_FINISH);
86 m_xHelp->set_help_id(UID_ABSPILOT_HELP);
88 // some initial settings
89 #ifdef UNX
90 #ifdef MACOSX
91 m_aSettings.eType = AST_MACAB;
92 #else
93 // FIXME: if KDE use KAB instead
94 m_aSettings.eType = AST_EVOLUTION;
95 #endif
96 #else
97 m_aSettings.eType = AST_OTHER;
98 #endif
99 m_aSettings.sDataSourceName = compmodule::ModuleRes(RID_STR_DEFAULT_NAME);
100 m_aSettings.bRegisterDataSource = false;
101 m_aSettings.bEmbedDataSource = false;
102 m_aSettings.bIgnoreNoTable = false;
104 defaultButton(WizardButtonFlags::NEXT);
105 enableButtons(WizardButtonFlags::FINISH, false);
106 ActivatePage();
107 m_xAssistant->set_current_page(0);
109 typeSelectionChanged( m_aSettings.eType );
111 OUString sDialogTitle = compmodule::ModuleRes(RID_STR_ABSOURCEDIALOGTITLE);
112 setTitleBase(sDialogTitle);
113 m_xAssistant->set_help_id(HID_ABSPILOT);
116 OUString OAddressBookSourcePilot::getStateDisplayName( WizardState _nState ) const
118 TranslateId pResId;
119 switch ( _nState )
121 case STATE_SELECT_ABTYPE: pResId = RID_STR_SELECT_ABTYPE; break;
122 case STATE_INVOKE_ADMIN_DIALOG: pResId = RID_STR_INVOKE_ADMIN_DIALOG; break;
123 case STATE_TABLE_SELECTION: pResId = RID_STR_TABLE_SELECTION; break;
124 case STATE_MANUAL_FIELD_MAPPING: pResId = RID_STR_MANUAL_FIELD_MAPPING; break;
125 case STATE_FINAL_CONFIRM: pResId = RID_STR_FINAL_CONFIRM; break;
127 DBG_ASSERT( pResId, "OAddressBookSourcePilot::getStateDisplayName: don't know this state!" );
129 OUString sDisplayName;
130 if (pResId)
132 sDisplayName = compmodule::ModuleRes(pResId);
135 return sDisplayName;
138 void OAddressBookSourcePilot::implCommitAll()
140 // in real, the data source already exists in the data source context
141 // Thus, if the user changed the name, we have to rename the data source
142 if ( m_aSettings.sDataSourceName != m_aNewDataSource.getName() )
143 m_aNewDataSource.rename( m_aSettings.sDataSourceName );
145 // 1. the data source
146 m_aNewDataSource.store(m_aSettings);
148 // 2. check if we need to register the data source
149 if ( m_aSettings.bRegisterDataSource )
150 m_aNewDataSource.registerDataSource(m_aSettings.sRegisteredDataSourceName);
152 // 3. write the data source / table names into the configuration
153 addressconfig::writeTemplateAddressSource( getORB(), m_aSettings.bRegisterDataSource ? m_aSettings.sRegisteredDataSourceName : m_aSettings.sDataSourceName, m_aSettings.sSelectedTable );
155 // 4. write the field mapping
156 fieldmapping::writeTemplateAddressFieldMapping( getORB(), std::map(m_aSettings.aFieldMapping) );
159 void OAddressBookSourcePilot::implCleanup()
161 if ( m_aNewDataSource.isValid() )
162 m_aNewDataSource.remove();
165 short OAddressBookSourcePilot::run()
167 short nRet = OAddressBookSourcePilot_Base::run();
169 implCleanup();
171 return nRet;
174 bool OAddressBookSourcePilot::onFinish()
176 if ( !OAddressBookSourcePilot_Base::onFinish() )
177 return false;
179 implCommitAll();
181 addressconfig::markPilotSuccess( getORB() );
183 return true;
186 void OAddressBookSourcePilot::enterState( WizardState _nState )
188 switch ( _nState )
190 case STATE_SELECT_ABTYPE:
191 impl_updateRoadmap( static_cast< TypeSelectionPage* >( GetPage( STATE_SELECT_ABTYPE ) )->getSelectedType() );
192 break;
194 case STATE_FINAL_CONFIRM:
195 if ( !needManualFieldMapping( ) )
196 implDoAutoFieldMapping();
197 break;
199 case STATE_TABLE_SELECTION:
200 implDefaultTableName();
201 break;
204 OAddressBookSourcePilot_Base::enterState(_nState);
208 bool OAddressBookSourcePilot::prepareLeaveCurrentState( CommitPageReason _eReason )
210 if ( !OAddressBookSourcePilot_Base::prepareLeaveCurrentState( _eReason ) )
211 return false;
213 if ( _eReason == vcl::WizardTypes::eTravelBackward )
214 return true;
216 bool bAllow = true;
218 switch ( getCurrentState() )
220 case STATE_SELECT_ABTYPE:
221 implCreateDataSource();
222 if ( needAdminInvokationPage() )
223 break;
224 [[fallthrough]];
226 case STATE_INVOKE_ADMIN_DIALOG:
227 if ( !connectToDataSource( false ) )
229 // connecting did not succeed -> do not allow proceeding
230 bAllow = false;
231 break;
235 // now that we connected to the data source, check whether we need the "table selection" page
236 const StringBag& aTables = m_aNewDataSource.getTableNames();
238 if ( aTables.empty() )
240 std::unique_ptr<weld::MessageDialog> xBox(Application::CreateMessageDialog(m_xAssistant.get(),
241 VclMessageType::Question, VclButtonsType::YesNo,
242 compmodule::ModuleRes(getSettings().eType == AST_EVOLUTION_GROUPWISE ? RID_STR_QRY_NO_EVO_GW : RID_STR_QRY_NOTABLES)));
244 if (RET_YES != xBox->run())
246 // cannot ask the user, or the user chose to use this data source, though there are no tables
247 bAllow = false;
248 break;
251 m_aSettings.bIgnoreNoTable = true;
254 if ( aTables.size() == 1 )
255 // remember the one and only table we have
256 m_aSettings.sSelectedTable = *aTables.begin();
258 break;
261 impl_updateRoadmap( m_aSettings.eType );
262 return bAllow;
265 void OAddressBookSourcePilot::implDefaultTableName()
267 const StringBag& rTableNames = getDataSource().getTableNames();
268 if ( rTableNames.end() != rTableNames.find( getSettings().sSelectedTable ) )
269 // already a valid table selected
270 return;
272 const char* pGuess = nullptr;
273 switch ( getSettings().eType )
275 case AST_THUNDERBIRD : pGuess = "Personal Address book"; break;
276 case AST_EVOLUTION :
277 case AST_EVOLUTION_GROUPWISE:
278 case AST_EVOLUTION_LDAP : pGuess = "Personal"; break;
279 default:
280 OSL_FAIL( "OAddressBookSourcePilot::implDefaultTableName: unhandled case!" );
281 return;
283 const OUString sGuess = OUString::createFromAscii( pGuess );
284 if ( rTableNames.end() != rTableNames.find( sGuess ) )
285 getSettings().sSelectedTable = sGuess;
288 void OAddressBookSourcePilot::implDoAutoFieldMapping()
290 DBG_ASSERT( !needManualFieldMapping( ), "OAddressBookSourcePilot::implDoAutoFieldMapping: invalid call!" );
292 fieldmapping::defaultMapping( getORB(), m_aSettings.aFieldMapping );
295 void OAddressBookSourcePilot::implCreateDataSource()
297 if (m_aNewDataSource.isValid())
298 { // we already have a data source object
299 if ( m_aSettings.eType == m_eNewDataSourceType )
300 // and it already has the correct type
301 return;
303 // it has a wrong type -> remove it
304 m_aNewDataSource.remove();
307 ODataSourceContext aContext( getORB() );
308 aContext.disambiguate( m_aSettings.sDataSourceName );
310 switch (m_aSettings.eType)
312 case AST_THUNDERBIRD:
313 m_aNewDataSource = aContext.createNewThunderbird( m_aSettings.sDataSourceName );
314 break;
316 case AST_EVOLUTION:
317 m_aNewDataSource = aContext.createNewEvolution( m_aSettings.sDataSourceName );
318 break;
320 case AST_EVOLUTION_GROUPWISE:
321 m_aNewDataSource = aContext.createNewEvolutionGroupwise( m_aSettings.sDataSourceName );
322 break;
324 case AST_EVOLUTION_LDAP:
325 m_aNewDataSource = aContext.createNewEvolutionLdap( m_aSettings.sDataSourceName );
326 break;
328 case AST_KAB:
329 m_aNewDataSource = aContext.createNewKab( m_aSettings.sDataSourceName );
330 break;
332 case AST_MACAB:
333 m_aNewDataSource = aContext.createNewMacab( m_aSettings.sDataSourceName );
334 break;
336 case AST_OTHER:
337 m_aNewDataSource = aContext.createNewOther( m_aSettings.sDataSourceName );
338 break;
340 case AST_INVALID:
341 OSL_FAIL( "OAddressBookSourcePilot::implCreateDataSource: illegal data source type!" );
342 break;
344 m_eNewDataSourceType = m_aSettings.eType;
347 bool OAddressBookSourcePilot::connectToDataSource( bool _bForceReConnect )
349 DBG_ASSERT( m_aNewDataSource.isValid(), "OAddressBookSourcePilot::implConnect: invalid current data source!" );
351 weld::WaitObject aWaitCursor(m_xAssistant.get());
352 if ( _bForceReConnect && m_aNewDataSource.isConnected( ) )
353 m_aNewDataSource.disconnect( );
355 return m_aNewDataSource.connect(m_xAssistant.get());
358 std::unique_ptr<BuilderPage> OAddressBookSourcePilot::createPage(WizardState _nState)
360 OUString sIdent(OUString::number(_nState));
361 weld::Container* pPageContainer = m_xAssistant->append_page(sIdent);
363 std::unique_ptr<vcl::OWizardPage> xRet;
365 switch (_nState)
367 case STATE_SELECT_ABTYPE:
368 xRet = std::make_unique<TypeSelectionPage>(pPageContainer, this);
369 break;
370 case STATE_INVOKE_ADMIN_DIALOG:
371 xRet = std::make_unique<AdminDialogInvokationPage>(pPageContainer, this);
372 break;
373 case STATE_TABLE_SELECTION:
374 xRet = std::make_unique<TableSelectionPage>(pPageContainer, this);
375 break;
376 case STATE_MANUAL_FIELD_MAPPING:
377 xRet = std::make_unique<FieldMappingPage>(pPageContainer, this);
378 break;
379 case STATE_FINAL_CONFIRM:
380 xRet = std::make_unique<FinalPage>(pPageContainer, this);
381 break;
382 default:
383 assert(false && "OAddressBookSourcePilot::createPage: invalid state!");
384 break;
387 m_xAssistant->set_page_title(sIdent, getStateDisplayName(_nState));
389 return xRet;
392 void OAddressBookSourcePilot::impl_updateRoadmap( AddressSourceType _eType )
394 bool bSettingsPage = needAdminInvokationPage( _eType );
395 bool bTablesPage = needTableSelection( _eType );
396 bool bFieldsPage = needManualFieldMapping( _eType );
398 bool bConnected = m_aNewDataSource.isConnected();
399 bool bCanSkipTables =
400 ( m_aNewDataSource.hasTable( m_aSettings.sSelectedTable )
401 || m_aSettings.bIgnoreNoTable
404 enableState( STATE_INVOKE_ADMIN_DIALOG, bSettingsPage );
406 enableState( STATE_TABLE_SELECTION,
407 bTablesPage && ( bConnected ? !bCanSkipTables : !bSettingsPage )
408 // if we do not need a settings page, we connect upon "Next" on the first page
411 enableState( STATE_MANUAL_FIELD_MAPPING,
412 bFieldsPage && bConnected && m_aNewDataSource.hasTable( m_aSettings.sSelectedTable )
415 enableState( STATE_FINAL_CONFIRM,
416 bConnected && bCanSkipTables
420 void OAddressBookSourcePilot::typeSelectionChanged( AddressSourceType _eType )
422 PathId nCurrentPathID( PathId::COMPLETE );
423 bool bSettingsPage = needAdminInvokationPage( _eType );
424 bool bFieldsPage = needManualFieldMapping( _eType );
425 if ( !bSettingsPage )
426 if ( !bFieldsPage )
427 nCurrentPathID = PathId::NO_SETTINGS_NO_FIELDS;
428 else
429 nCurrentPathID = PathId::NO_SETTINGS;
430 else
431 if ( !bFieldsPage )
432 nCurrentPathID = PathId::NO_FIELDS;
433 else
434 nCurrentPathID = PathId::COMPLETE;
435 activatePath( nCurrentPathID, true );
437 m_aNewDataSource.disconnect();
438 m_aSettings.bIgnoreNoTable = false;
439 impl_updateRoadmap( _eType );
442 } // namespace abp
445 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */