update dev300-m58
[ooovba.git] / dbaccess / source / ui / querydesign / querycontroller.cxx
blobea3ab1ca3de88289a7ad15ffdd1b67e744c28ec1
1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: querycontroller.cxx,v $
10 * $Revision: 1.119.24.1 $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_dbaccess.hxx"
34 #include "adtabdlg.hxx"
35 #include "browserids.hxx"
36 #include "dbu_qry.hrc"
37 #include "dbu_reghelper.hxx"
38 #include "dbustrings.hrc"
39 #include "defaultobjectnamecheck.hxx"
40 #include "dlgsave.hxx"
41 #include "localresaccess.hxx"
42 #include "QTableWindow.hxx"
43 #include "QTableWindowData.hxx"
44 #include "querycontainerwindow.hxx"
45 #include "querycontroller.hxx"
46 #include "QueryDesignView.hxx"
47 #include "QueryTableView.hxx"
48 #include "QueryTextView.hxx"
49 #include "queryview.hxx"
50 #include "QueryViewSwitch.hxx"
51 #include "sqlmessage.hxx"
52 #include "TableConnectionData.hxx"
53 #include "TableFieldDescription.hxx"
54 #include "UITools.hxx"
56 /** === begin UNO includes === **/
57 #include <com/sun/star/beans/PropertyAttribute.hpp>
58 #include <com/sun/star/container/XChild.hpp>
59 #include <com/sun/star/container/XNameContainer.hpp>
60 #include <com/sun/star/frame/FrameSearchFlag.hpp>
61 #include <com/sun/star/frame/XLoadEventListener.hpp>
62 #include <com/sun/star/io/XActiveDataSink.hpp>
63 #include <com/sun/star/io/XActiveDataSource.hpp>
64 #include <com/sun/star/sdb/CommandType.hpp>
65 #include <com/sun/star/sdb/SQLContext.hpp>
66 #include <com/sun/star/sdb/XQueriesSupplier.hpp>
67 #include <com/sun/star/sdb/XQueryDefinitionsSupplier.hpp>
68 #include <com/sun/star/sdb/XSQLQueryComposerFactory.hpp>
69 #include <com/sun/star/sdbc/SQLWarning.hpp>
70 #include <com/sun/star/sdbc/XRow.hpp>
71 #include <com/sun/star/sdbcx/XAppend.hpp>
72 #include <com/sun/star/sdbcx/XDataDescriptorFactory.hpp>
73 #include <com/sun/star/sdbcx/XDrop.hpp>
74 #include <com/sun/star/sdbcx/XTablesSupplier.hpp>
75 #include <com/sun/star/sdbcx/XViewsSupplier.hpp>
76 #include <com/sun/star/ui/dialogs/XExecutableDialog.hpp>
77 #include <com/sun/star/util/XCloseable.hpp>
78 #include <com/sun/star/util/VetoException.hpp>
79 #include <com/sun/star/frame/XUntitledNumbers.hpp>
80 /** === end UNO includes === **/
82 #include <comphelper/basicio.hxx>
83 #include <comphelper/extract.hxx>
84 #include <comphelper/seqstream.hxx>
85 #include <comphelper/streamsection.hxx>
86 #include <comphelper/types.hxx>
87 #include <connectivity/dbexception.hxx>
88 #include <connectivity/dbtools.hxx>
89 #include <cppuhelper/exc_hlp.hxx>
90 #include <sfx2/sfxsids.hrc>
91 #include <svtools/localresaccess.hxx>
92 #include <toolkit/helper/vclunohelper.hxx>
93 #include <tools/diagnose_ex.h>
94 #include <vcl/msgbox.hxx>
95 #include <vcl/svapp.hxx>
96 #include <vos/mutex.hxx>
98 extern "C" void SAL_CALL createRegistryInfo_OQueryControl()
100 static ::dbaui::OMultiInstanceAutoRegistration< ::dbaui::OQueryController > aAutoRegistration;
102 namespace dbaui
104 using namespace ::com::sun::star::uno;
105 using namespace ::com::sun::star::beans;
106 using namespace ::com::sun::star::frame;
107 using namespace ::com::sun::star::util;
108 using namespace ::com::sun::star::lang;
110 class OViewController : public OQueryController
112 //------------------------------------------------------------------------------
113 virtual ::rtl::OUString SAL_CALL getImplementationName() throw( RuntimeException )
115 return getImplementationName_Static();
117 //-------------------------------------------------------------------------
118 virtual Sequence< ::rtl::OUString> SAL_CALL getSupportedServiceNames() throw(RuntimeException)
120 return getSupportedServiceNames_Static();
122 public:
123 OViewController(const Reference< XMultiServiceFactory >& _rM) : OQueryController(_rM){}
125 // need by registration
126 static ::rtl::OUString getImplementationName_Static() throw( RuntimeException )
128 return ::rtl::OUString::createFromAscii("org.openoffice.comp.dbu.OViewDesign");
130 static Sequence< ::rtl::OUString > getSupportedServiceNames_Static(void) throw( RuntimeException )
132 Sequence< ::rtl::OUString> aSupported(1);
133 aSupported.getArray()[0] = ::rtl::OUString::createFromAscii("com.sun.star.sdb.ViewDesign");
134 return aSupported;
136 static Reference< XInterface > SAL_CALL Create(const Reference< XMultiServiceFactory >& _rM)
138 return *(new OViewController(_rM));
142 extern "C" void SAL_CALL createRegistryInfo_OViewControl()
144 static ::dbaui::OMultiInstanceAutoRegistration< ::dbaui::OViewController > aAutoRegistration;
147 namespace dbaui
149 using namespace ::connectivity;
150 #if OSL_DEBUG_LEVEL > 1
151 namespace
153 // -----------------------------------------------------------------------------
154 void insertParseTree(SvTreeListBox* _pBox,::connectivity::OSQLParseNode* _pNode,SvLBoxEntry* _pParent = NULL)
156 ::rtl::OUString rString;
157 if (!_pNode->isToken())
159 // Regelnamen als rule: ...
160 rString = ::rtl::OUString::createFromAscii("RULE_ID: ");
161 rString += ::rtl::OUString::valueOf( (sal_Int32)_pNode->getRuleID());
162 rString+= ::rtl::OUString::createFromAscii("(");
163 rString += OSQLParser::RuleIDToStr(_pNode->getRuleID());
164 rString+= ::rtl::OUString::createFromAscii(")");
167 _pParent = _pBox->InsertEntry(rString,_pParent);
169 // einmal auswerten wieviel Subtrees dieser Knoten besitzt
170 sal_uInt32 nStop = _pNode->count();
171 // hol dir den ersten Subtree
172 for(sal_uInt32 i=0;i<nStop;++i)
173 insertParseTree(_pBox,_pNode->getChild(i),_pParent);
175 else
177 // ein Token gefunden
178 // tabs fuer das Einruecken entsprechend nLevel
180 switch (_pNode->getNodeType())
183 case SQL_NODE_KEYWORD:
185 rString+= ::rtl::OUString::createFromAscii("SQL_KEYWORD:");
186 ::rtl::OString sT = OSQLParser::TokenIDToStr(_pNode->getTokenID());
187 rString += ::rtl::OUString(sT,sT.getLength(),RTL_TEXTENCODING_UTF8);
188 break;}
190 case SQL_NODE_COMPARISON:
191 {rString+= ::rtl::OUString::createFromAscii("SQL_COMPARISON:");
192 rString += _pNode->getTokenValue(); // haenge Nodevalue an
193 // und beginne neu Zeile
194 break;}
196 case SQL_NODE_NAME:
197 {rString+= ::rtl::OUString::createFromAscii("SQL_NAME:");
198 rString+= ::rtl::OUString::createFromAscii("\"");
199 rString += _pNode->getTokenValue();
200 rString+= ::rtl::OUString::createFromAscii("\"");
202 break;}
204 case SQL_NODE_STRING:
205 {rString += ::rtl::OUString::createFromAscii("SQL_STRING:'");
206 rString += _pNode->getTokenValue();
207 break;}
209 case SQL_NODE_INTNUM:
210 {rString += ::rtl::OUString::createFromAscii("SQL_INTNUM:");
211 rString += _pNode->getTokenValue();
212 break;}
214 case SQL_NODE_APPROXNUM:
215 {rString += ::rtl::OUString::createFromAscii("SQL_APPROXNUM:");
216 rString += _pNode->getTokenValue();
217 break;}
219 case SQL_NODE_PUNCTUATION:
220 {rString += ::rtl::OUString::createFromAscii("SQL_PUNCTUATION:");
221 rString += _pNode->getTokenValue(); // haenge Nodevalue an
222 break;}
224 case SQL_NODE_AMMSC:
225 {rString += ::rtl::OUString::createFromAscii("SQL_AMMSC:");
226 rString += _pNode->getTokenValue(); // haenge Nodevalue an
228 break;}
230 default:
231 OSL_ASSERT("OSQLParser::ShowParseTree: unzulaessiger NodeType");
232 rString += _pNode->getTokenValue();
234 _pBox->InsertEntry(rString,_pParent);
238 #endif // OSL_DEBUG_LEVEL
240 namespace
242 // -----------------------------------------------------------------------------
243 String lcl_getObjectResourceString( USHORT _nResId, sal_Int32 _nCommandType )
245 String sMessageText = String( ModuleRes( _nResId ) );
246 String sObjectType;
248 LocalResourceAccess aLocalRes( RSC_QUERY_OBJECT_TYPE, RSC_RESOURCE );
249 sObjectType = String( ModuleRes( (USHORT)( _nCommandType + 1 ) ) );
251 sMessageText.SearchAndReplace( String::CreateFromAscii( "$object$" ), sObjectType );
252 return sMessageText;
256 using namespace ::com::sun::star::uno;
257 using namespace ::com::sun::star::io;
258 using namespace ::com::sun::star::beans;
259 using namespace ::com::sun::star::frame;
260 using namespace ::com::sun::star::util;
261 using namespace ::com::sun::star::lang;
262 using namespace ::com::sun::star::container;
263 using namespace ::com::sun::star::sdbcx;
264 using namespace ::com::sun::star::sdbc;
265 using namespace ::com::sun::star::sdb;
266 using namespace ::com::sun::star::ui::dialogs;
267 using namespace ::com::sun::star::awt;
268 using namespace ::dbtools;
270 using namespace ::comphelper;
272 namespace
274 void ensureToolbars( OQueryController& _rController, sal_Bool _bDesign )
276 Reference< ::com::sun::star::frame::XLayoutManager > xLayoutManager = _rController.getLayoutManager( _rController.getFrame() );
277 if ( xLayoutManager.is() )
279 xLayoutManager->lock();
280 static ::rtl::OUString s_sDesignToolbar(RTL_CONSTASCII_USTRINGPARAM("private:resource/toolbar/designobjectbar"));
281 static ::rtl::OUString s_sSqlToolbar(RTL_CONSTASCII_USTRINGPARAM("private:resource/toolbar/sqlobjectbar"));
282 if ( _bDesign )
284 xLayoutManager->destroyElement( s_sSqlToolbar );
285 xLayoutManager->createElement( s_sDesignToolbar );
287 else
289 xLayoutManager->destroyElement( s_sDesignToolbar );
290 xLayoutManager->createElement( s_sSqlToolbar );
292 xLayoutManager->unlock();
293 xLayoutManager->doLayout();
298 //------------------------------------------------------------------------------
299 ::rtl::OUString SAL_CALL OQueryController::getImplementationName() throw( RuntimeException )
301 return getImplementationName_Static();
304 //------------------------------------------------------------------------------
305 ::rtl::OUString OQueryController::getImplementationName_Static() throw( RuntimeException )
307 return ::rtl::OUString::createFromAscii("org.openoffice.comp.dbu.OQueryDesign");
309 //------------------------------------------------------------------------------
310 Sequence< ::rtl::OUString> OQueryController::getSupportedServiceNames_Static(void) throw( RuntimeException )
312 Sequence< ::rtl::OUString> aSupported(1);
313 aSupported.getArray()[0] = ::rtl::OUString::createFromAscii("com.sun.star.sdb.QueryDesign");
314 return aSupported;
316 //-------------------------------------------------------------------------
317 Sequence< ::rtl::OUString> SAL_CALL OQueryController::getSupportedServiceNames() throw(RuntimeException)
319 return getSupportedServiceNames_Static();
321 // -------------------------------------------------------------------------
322 Reference< XInterface > SAL_CALL OQueryController::Create(const Reference<XMultiServiceFactory >& _rxFactory)
324 return *(new OQueryController(_rxFactory));
326 DBG_NAME(OQueryController);
327 // -----------------------------------------------------------------------------
328 OQueryController::OQueryController(const Reference< XMultiServiceFactory >& _rM)
329 :OJoinController(_rM)
330 ,OQueryController_PBase( getBroadcastHelper() )
331 ,m_pParseContext( new svxform::OSystemParseContext )
332 ,m_aSqlParser( _rM, m_pParseContext )
333 ,m_pSqlIterator(NULL)
334 ,m_nVisibleRows(0x400)
335 ,m_nSplitPos(-1)
336 ,m_nCommandType( CommandType::QUERY )
337 ,m_bGraphicalDesign(sal_False)
338 ,m_bDistinct(sal_False)
339 ,m_bViewAlias(sal_False)
340 ,m_bViewTable(sal_False)
341 ,m_bViewFunction(sal_False)
342 ,m_bEscapeProcessing(sal_True)
344 DBG_CTOR(OQueryController,NULL);
345 InvalidateAll();
347 registerProperty( PROPERTY_ACTIVECOMMAND, PROPERTY_ID_ACTIVECOMMAND, PropertyAttribute::READONLY | PropertyAttribute::BOUND,
348 &m_sStatement, ::getCppuType( &m_sStatement ) );
349 registerProperty( PROPERTY_ESCAPE_PROCESSING, PROPERTY_ID_ESCAPE_PROCESSING, PropertyAttribute::READONLY | PropertyAttribute::BOUND,
350 &m_bEscapeProcessing, ::getCppuType( &m_bEscapeProcessing ) );
353 // -----------------------------------------------------------------------------
354 OQueryController::~OQueryController()
356 DBG_DTOR(OQueryController,NULL);
357 if ( !getBroadcastHelper().bDisposed && !getBroadcastHelper().bInDispose )
359 OSL_ENSURE(0,"Please check who doesn't dispose this component!");
360 // increment ref count to prevent double call of Dtor
361 osl_incrementInterlockedCount( &m_refCount );
362 dispose();
366 IMPLEMENT_FORWARD_XINTERFACE2( OQueryController, OJoinController, OQueryController_PBase )
367 IMPLEMENT_FORWARD_XTYPEPROVIDER2( OQueryController, OJoinController, OQueryController_PBase )
369 //-------------------------------------------------------------------------
370 Reference< XPropertySetInfo > SAL_CALL OQueryController::getPropertySetInfo() throw(RuntimeException)
372 Reference< XPropertySetInfo > xInfo( createPropertySetInfo( getInfoHelper() ) );
373 return xInfo;
376 //-------------------------------------------------------------------------
377 ::cppu::IPropertyArrayHelper& OQueryController::getInfoHelper()
379 return *const_cast< OQueryController* >( this )->getArrayHelper();
382 //--------------------------------------------------------------------
383 ::cppu::IPropertyArrayHelper* OQueryController::createArrayHelper( ) const
385 Sequence< Property > aProps;
386 describeProperties(aProps);
387 return new ::cppu::OPropertyArrayHelper(aProps);
390 // -----------------------------------------------------------------------------
391 void OQueryController::deleteIterator()
393 if(m_pSqlIterator)
395 delete m_pSqlIterator->getParseTree();
396 m_pSqlIterator->dispose();
397 delete m_pSqlIterator;
398 m_pSqlIterator = NULL;
401 // -----------------------------------------------------------------------------
402 void OQueryController::disposing()
404 OQueryController_PBase::disposing();
406 deleteIterator();
408 delete m_pParseContext;
410 clearFields();
411 OTableFields().swap(m_vUnUsedFieldsDesc);
413 ::comphelper::disposeComponent(m_xComposer);
414 OJoinController::disposing();
415 OQueryController_PBase::disposing();
417 // -----------------------------------------------------------------------------
418 void OQueryController::clearFields()
420 OTableFields().swap(m_vTableFieldDesc);
422 // -----------------------------------------------------------------------------
423 FeatureState OQueryController::GetState(sal_uInt16 _nId) const
425 FeatureState aReturn;
426 aReturn.bEnabled = sal_True;
427 // (disabled automatically)
429 switch (_nId)
431 case ID_BROWSER_EDITDOC:
432 if ( editingCommand() )
433 aReturn.bEnabled = sal_False;
434 else if ( editingView() && !m_xAlterView.is() )
435 aReturn.bEnabled = sal_False;
436 else
437 aReturn = OJoinController::GetState( _nId );
438 break;
440 case ID_BROWSER_ESACPEPROCESSING:
441 aReturn.bChecked = !m_bEscapeProcessing;
442 aReturn.bEnabled = ( m_pSqlIterator != NULL ) && !m_bGraphicalDesign;
443 break;
444 case SID_RELATION_ADD_RELATION:
445 aReturn.bEnabled = isEditable() && m_bGraphicalDesign && m_vTableData.size() > 1;
446 break;
447 case ID_BROWSER_SAVEASDOC:
448 aReturn.bEnabled = !editingCommand() && !editingView() && (!m_bGraphicalDesign || !(m_vTableFieldDesc.empty() || m_vTableData.empty()));
449 break;
450 case ID_BROWSER_SAVEDOC:
451 aReturn.bEnabled = isModified() && (!m_bGraphicalDesign || !(m_vTableFieldDesc.empty() || m_vTableData.empty()));
452 break;
453 case SID_PRINTDOCDIRECT:
454 break;
455 case ID_BROWSER_CUT:
456 aReturn.bEnabled = isEditable() && getContainer() && getContainer()->isCutAllowed();
457 break;
458 case ID_BROWSER_COPY:
459 aReturn.bEnabled = getContainer() && getContainer()->isCopyAllowed();
460 break;
461 case ID_BROWSER_PASTE:
462 aReturn.bEnabled = isEditable() && getContainer() && getContainer()->isPasteAllowed();
463 break;
464 case ID_BROWSER_SQL:
465 aReturn.bEnabled = m_bEscapeProcessing && m_pSqlIterator;
466 aReturn.bChecked = m_bGraphicalDesign;
467 break;
468 case SID_BROWSER_CLEAR_QUERY:
469 aReturn.bEnabled = isEditable() && (m_sStatement.getLength() || !m_vTableData.empty());
470 break;
471 case SID_QUERY_VIEW_FUNCTIONS:
472 case SID_QUERY_VIEW_TABLES:
473 case SID_QUERY_VIEW_ALIASES:
474 aReturn.bChecked = getContainer() && getContainer()->isSlotEnabled(_nId);
475 aReturn.bEnabled = m_bGraphicalDesign;
476 break;
477 case SID_QUERY_DISTINCT_VALUES:
478 aReturn.bEnabled = m_bGraphicalDesign && isEditable();
479 aReturn.bChecked = m_bDistinct;
480 break;
481 case ID_BROWSER_QUERY_EXECUTE:
482 aReturn.bEnabled = sal_True;
483 break;
484 case SID_DB_QUERY_PREVIEW:
485 aReturn.bEnabled = sal_True;
486 aReturn.bChecked = getContainer() && getContainer()->getPreviewFrame().is();
487 break;
488 #if OSL_DEBUG_LEVEL > 1
489 case ID_EDIT_QUERY_SQL:
490 break;
491 case ID_EDIT_QUERY_DESIGN:
492 break;
493 #endif
494 case ID_BROWSER_ADDTABLE:
495 if ( !m_bGraphicalDesign )
497 aReturn.bEnabled = sal_False;
498 break;
500 // run through
501 default:
502 aReturn = OJoinController::GetState(_nId);
503 break;
505 return aReturn;
507 // -----------------------------------------------------------------------------
508 void OQueryController::Execute(sal_uInt16 _nId, const Sequence< PropertyValue >& aArgs)
510 switch(_nId)
512 case ID_BROWSER_ESACPEPROCESSING:
513 setEscapeProcessing_fireEvent( !m_bEscapeProcessing );
514 if ( !editingView() )
515 setModified(sal_True);
516 InvalidateFeature(ID_BROWSER_SQL);
517 break;
518 case ID_BROWSER_SAVEASDOC:
519 case ID_BROWSER_SAVEDOC:
520 doSaveAsDoc(ID_BROWSER_SAVEASDOC == _nId);
521 break;
522 case SID_RELATION_ADD_RELATION:
524 OJoinDesignView* pView = getJoinView();
525 if( pView )
526 static_cast<OQueryTableView*>(pView->getTableView())->createNewConnection();
528 break;
529 case SID_PRINTDOCDIRECT:
530 break;
531 case ID_BROWSER_CUT:
532 getContainer()->cut();
533 break;
534 case ID_BROWSER_COPY:
535 getContainer()->copy();
536 break;
537 case ID_BROWSER_PASTE:
538 getContainer()->paste();
539 break;
540 case ID_BROWSER_SQL:
542 if ( !getContainer()->checkStatement() )
543 break;
544 SQLExceptionInfo aError;
547 ::rtl::OUString aErrorMsg;
548 setStatement_fireEvent( getContainer()->getStatement() );
549 if(!m_sStatement.getLength() && m_pSqlIterator)
551 // change the view of the data
552 delete m_pSqlIterator->getParseTree();
553 m_pSqlIterator->setParseTree(NULL);
554 m_bGraphicalDesign = !m_bGraphicalDesign;
555 impl_setViewMode( &aError );
557 else
559 ::connectivity::OSQLParseNode* pNode = m_aSqlParser.parseTree(aErrorMsg,m_sStatement,m_bGraphicalDesign);
560 if ( pNode )
562 delete m_pSqlIterator->getParseTree();
563 m_pSqlIterator->setParseTree(pNode);
564 m_pSqlIterator->traverseAll();
566 if ( m_pSqlIterator->hasErrors() )
568 aError = m_pSqlIterator->getErrors();
570 else
572 const OSQLTables& xTabs = m_pSqlIterator->getTables();
573 if ( m_pSqlIterator->getStatementType() != SQL_STATEMENT_SELECT || xTabs.begin() == xTabs.end() )
575 aError = SQLException(
576 String( ModuleRes( STR_QRY_NOSELECT ) ),
577 NULL,
578 ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "S1000" ) ),
579 1000,
580 Any()
583 else
585 // change the view of the data
586 m_bGraphicalDesign = !m_bGraphicalDesign;
587 ::rtl::OUString sNewStatement;
588 pNode->parseNodeToStr( sNewStatement, getConnection() );
589 setStatement_fireEvent( sNewStatement );
590 getContainer()->SaveUIConfig();
591 m_vTableConnectionData.clear();
592 impl_setViewMode( &aError );
596 else
598 aError = SQLException(
599 String( ModuleRes( STR_QRY_SYNTAX ) ),
600 NULL,
601 ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "S1000" ) ),
602 1000,
603 Any()
608 catch(const SQLException& e)
610 aError = ::cppu::getCaughtException();
612 catch(const Exception&)
614 DBG_UNHANDLED_EXCEPTION();
617 if ( aError.isValid() )
618 showError( aError );
620 if(m_bGraphicalDesign)
622 InvalidateFeature(ID_BROWSER_ADDTABLE);
623 InvalidateFeature(SID_RELATION_ADD_RELATION);
626 break;
627 case SID_BROWSER_CLEAR_QUERY:
629 getUndoMgr()->EnterListAction( String( ModuleRes(STR_QUERY_UNDO_TABWINDELETE) ), String() );
630 getContainer()->clear();
631 getUndoMgr()->LeaveListAction();
633 setStatement_fireEvent( ::rtl::OUString() );
634 if(m_bGraphicalDesign)
635 InvalidateFeature(ID_BROWSER_ADDTABLE);
637 // InvalidateFeature(ID_BROWSER_QUERY_EXECUTE);
638 break;
639 case SID_QUERY_VIEW_FUNCTIONS:
640 case SID_QUERY_VIEW_TABLES:
641 case SID_QUERY_VIEW_ALIASES:
642 getContainer()->setSlotEnabled(_nId,!getContainer()->isSlotEnabled(_nId));
643 setModified(sal_True);
644 break;
645 case SID_QUERY_DISTINCT_VALUES:
646 m_bDistinct = !m_bDistinct;
647 setModified(sal_True);
648 break;
649 case ID_BROWSER_QUERY_EXECUTE:
650 if ( getContainer()->checkStatement() )
651 executeQuery();
652 break;
653 case SID_DB_QUERY_PREVIEW:
656 Reference< ::com::sun::star::util::XCloseable > xCloseFrame( getContainer()->getPreviewFrame(), UNO_QUERY );
657 if ( xCloseFrame.is() )
661 xCloseFrame->close( sal_True );
663 catch( const Exception& )
665 OSL_ENSURE( sal_False, "OQueryController::Execute(SID_DB_QUERY_PREVIEW): *nobody* is expected to veto closing the preview frame!" );
668 else
669 Execute(ID_BROWSER_QUERY_EXECUTE,Sequence< PropertyValue >());
671 catch(Exception&)
674 break;
675 case ID_QUERY_ZOOM_IN:
677 // m_aZoom *= Fraction(1,10);
678 // static_cast<OQueryViewSwitch*>(getView())->zoomTableView(m_aZoom);
680 break;
681 case ID_QUERY_ZOOM_OUT:
683 // if(m_aZoom != Fraction(1,1))
684 // m_aZoom /= Fraction(1,10);
685 // static_cast<OQueryViewSwitch*>(getView())->zoomTableView(m_aZoom);
687 break;
688 #if OSL_DEBUG_LEVEL > 1
689 case ID_EDIT_QUERY_DESIGN:
690 case ID_EDIT_QUERY_SQL:
692 ::rtl::OUString aErrorMsg;
693 setStatement_fireEvent( getContainer()->getStatement() );
694 ::connectivity::OSQLParseNode* pNode = m_aSqlParser.parseTree( aErrorMsg, m_sStatement, m_bGraphicalDesign );
695 if ( pNode )
697 Window* pView = getView();
698 ModalDialog* pWindow = new ModalDialog( pView, WB_STDMODAL | WB_SIZEMOVE | WB_CENTER );
699 pWindow->SetSizePixel( ::Size( pView->GetSizePixel().Width() / 2, pView->GetSizePixel().Height() / 2 ) );
700 SvTreeListBox* pTreeBox = new SvTreeListBox( pWindow, WB_BORDER | WB_HASLINES | WB_HASBUTTONS | WB_HASBUTTONSATROOT | WB_HASLINESATROOT | WB_VSCROLL );
701 pTreeBox->SetPosSizePixel( ::Point( 6, 6 ), ::Size( pWindow->GetSizePixel().Width() - 12, pWindow->GetSizePixel().Height() - 12 ));
702 pTreeBox->SetNodeDefaultImages();
704 if ( _nId == ID_EDIT_QUERY_DESIGN )
706 ::connectivity::OSQLParseNode* pTemp = pNode ? pNode->getChild(3)->getChild(1) : NULL;
707 // no where clause found
708 if ( pTemp && !pTemp->isLeaf() )
710 ::connectivity::OSQLParseNode * pCondition = pTemp->getChild(1);
711 if ( pCondition ) // no where clause
713 ::connectivity::OSQLParseNode::negateSearchCondition(pCondition);
714 ::connectivity::OSQLParseNode *pNodeTmp = pTemp->getChild(1);
716 ::connectivity::OSQLParseNode::disjunctiveNormalForm(pNodeTmp);
717 pNodeTmp = pTemp->getChild(1);
718 ::connectivity::OSQLParseNode::absorptions(pNodeTmp);
719 pNodeTmp = pTemp->getChild(1);
720 OSQLParseNode::compress(pNodeTmp);
721 pNodeTmp = pTemp->getChild(1);
722 } // if ( pCondition ) // no where clause
723 ::rtl::OUString sTemp;
724 pNode->parseNodeToStr(sTemp,getConnection());
725 getContainer()->setStatement(sTemp);
730 insertParseTree(pTreeBox,pNode);
732 pTreeBox->Show();
733 pWindow->Execute();
735 delete pTreeBox;
736 delete pWindow;
737 delete pNode;
739 break;
741 #endif
742 default:
743 OJoinController::Execute(_nId,aArgs);
744 return; // else we would invalidate twice
746 InvalidateFeature(_nId);
749 // -----------------------------------------------------------------------------
750 void OQueryController::impl_showAutoSQLViewError( const ::com::sun::star::uno::Any& _rErrorDetails )
752 SQLContext aErrorContext;
753 aErrorContext.Message = lcl_getObjectResourceString( STR_ERROR_PARSING_STATEMENT, m_nCommandType );
754 aErrorContext.Context = *this;
755 aErrorContext.Details = lcl_getObjectResourceString( STR_INFO_OPENING_IN_SQL_VIEW, m_nCommandType );
756 aErrorContext.NextException = _rErrorDetails;
757 showError( aErrorContext );
760 // -----------------------------------------------------------------------------
761 bool OQueryController::impl_setViewMode( ::dbtools::SQLExceptionInfo* _pErrorInfo )
763 OSL_PRECOND( getContainer(), "OQueryController::impl_setViewMode: illegal call!" );
765 bool wasModified = isModified();
767 SQLExceptionInfo aError;
768 bool bSuccess = getContainer()->switchView( &aError );
769 if ( !bSuccess )
771 m_bGraphicalDesign = !m_bGraphicalDesign;
772 // restore old state
773 getContainer()->switchView( NULL );
774 // don't pass &aError here, this would overwrite the error which the first switchView call
775 // returned in this location.
776 if ( _pErrorInfo )
777 *_pErrorInfo = aError;
778 else
779 showError( aError );
781 else
783 ensureToolbars( *this, m_bGraphicalDesign );
786 setModified( wasModified );
787 return bSuccess;
790 // -----------------------------------------------------------------------------
791 void OQueryController::impl_initialize()
793 OJoinController::impl_initialize();
795 const NamedValueCollection& rArguments( getInitParams() );
797 ::rtl::OUString sCommand;
798 m_nCommandType = CommandType::QUERY;
800 // legacy parameters first (later overwritten by regular parameters)
801 ::rtl::OUString sIndependentSQLCommand;
802 if ( rArguments.get_ensureType( "IndependentSQLCommand", sIndependentSQLCommand ) )
804 OSL_ENSURE( false, "OQueryController::impl_initialize: IndependentSQLCommand is regognized for compatibility only!" );
805 sCommand = sIndependentSQLCommand;
806 m_nCommandType = CommandType::COMMAND;
809 ::rtl::OUString sCurrentQuery;
810 if ( rArguments.get_ensureType( "CurrentQuery", sCurrentQuery ) )
812 OSL_ENSURE( false, "OQueryController::impl_initialize: CurrentQuery is regognized for compatibility only!" );
813 sCommand = sCurrentQuery;
814 m_nCommandType = CommandType::QUERY;
817 sal_Bool bCreateView( sal_False );
818 if ( rArguments.get_ensureType( "CreateView", bCreateView ) && bCreateView )
820 OSL_ENSURE( false, "OQueryController::impl_initialize: CurrentQuery is regognized for compatibility only!" );
821 m_nCommandType = CommandType::TABLE;
824 // non-legacy parameters which overwrite the legacy parameters
825 rArguments.get_ensureType( (::rtl::OUString)PROPERTY_COMMAND, sCommand );
826 rArguments.get_ensureType( (::rtl::OUString)PROPERTY_COMMAND_TYPE, m_nCommandType );
828 // translate Command/Type into proper members
829 // TODO/Later: all this (including those members) should be hidden behind some abstact interface,
830 // which is implemented for all the three commands
831 switch ( m_nCommandType )
833 case CommandType::QUERY:
834 m_sName = sCommand;
835 break;
836 case CommandType::TABLE:
837 m_sName = sCommand;
838 break;
839 case CommandType::COMMAND:
840 setStatement_fireEvent( sCommand );
841 m_sName = ::rtl::OUString();
842 break;
843 default:
844 OSL_ENSURE( false, "OQueryController::impl_initialize: logic error in code!" );
845 throw RuntimeException();
848 // more legacy parameters
849 sal_Bool bGraphicalDesign( sal_True );
850 if ( rArguments.get_ensureType( (::rtl::OUString)PROPERTY_QUERYDESIGNVIEW, bGraphicalDesign ) )
852 OSL_ENSURE( false, "OQueryController::impl_initialize: QueryDesignView is regognized for compatibility only!" );
853 m_bGraphicalDesign = bGraphicalDesign;
856 // more non-legacy
857 rArguments.get_ensureType( (::rtl::OUString)PROPERTY_GRAPHICAL_DESIGN, m_bGraphicalDesign );
859 bool bEscapeProcessing( sal_True );
860 if ( rArguments.get_ensureType( (::rtl::OUString)PROPERTY_ESCAPE_PROCESSING, bEscapeProcessing ) )
862 setEscapeProcessing_fireEvent( bEscapeProcessing );
864 OSL_ENSURE( m_bEscapeProcessing || !m_bGraphicalDesign, "OQueryController::impl_initialize: can't do the graphical design without escape processing!" );
865 if ( !m_bEscapeProcessing )
866 m_bGraphicalDesign = false;
869 if ( !ensureConnected( sal_False ) )
870 { // we have no connection so what else should we do
871 m_bGraphicalDesign = sal_False;
872 if ( editingView() )
874 connectionLostMessage();
875 throw SQLException();
879 // check the view capabilities
880 if ( isConnected() && editingView() )
882 Reference< XViewsSupplier > xViewsSup( getConnection(), UNO_QUERY );
883 Reference< XNameAccess > xViews;
884 if ( xViewsSup.is() )
885 xViews = xViewsSup->getViews();
887 if ( !xViews.is() )
888 { // we can't create views so we ask if the user wants to create a query instead
889 m_nCommandType = CommandType::QUERY;
890 sal_Bool bClose = sal_False;
892 String aTitle( ModuleRes( STR_QUERYDESIGN_NO_VIEW_SUPPORT ) );
893 String aMessage( ModuleRes( STR_QUERYDESIGN_NO_VIEW_ASK ) );
894 ODataView* pWindow = getView();
895 OSQLMessageBox aDlg( pWindow, aTitle, aMessage, WB_YES_NO | WB_DEF_YES, OSQLMessageBox::Query );
896 bClose = aDlg.Execute() == RET_NO;
898 if ( bClose )
899 throw VetoException();
902 // now if we are to edit an existing view, check whether this is possible
903 if ( m_sName.getLength() )
905 Any aView( xViews->getByName( m_sName ) );
906 // will throw if there is no such view
907 if ( !( aView >>= m_xAlterView ) )
909 throw IllegalArgumentException(
910 ::rtl::OUString( String( ModuleRes( STR_NO_ALTER_VIEW_SUPPORT ) ) ),
911 *this,
918 OSL_ENSURE(getDataSource().is(),"OQueryController::impl_initialize: need a datasource!");
922 getContainer()->initialize();
923 impl_reset();
925 bool bAttemptedGraphicalDesign = m_bGraphicalDesign;
926 SQLExceptionInfo aError;
927 impl_setViewMode( &aError );
928 if ( aError.isValid() && bAttemptedGraphicalDesign && !m_bGraphicalDesign )
930 if ( !editingView() )
932 impl_showAutoSQLViewError( aError.get() );
937 getUndoMgr()->Clear();
939 if ( ( m_bGraphicalDesign )
940 && ( ( !m_sName.getLength() && !editingCommand() )
941 || ( !m_sStatement.getLength() && editingCommand() )
945 Application::PostUserEvent( LINK( this, OQueryController, OnExecuteAddTable ) );
948 setModified(sal_False);
950 catch(SQLException& e)
952 DBG_UNHANDLED_EXCEPTION();
953 // we caught an exception so we switch to text only mode
955 m_bGraphicalDesign = sal_False;
956 getContainer()->initialize();
957 ODataView* pWindow = getView();
958 OSQLMessageBox(pWindow,e).Execute();
960 throw;
964 // -----------------------------------------------------------------------------
965 void OQueryController::onLoadedMenu(const Reference< ::com::sun::star::frame::XLayoutManager >& /*_xLayoutManager*/)
967 ensureToolbars( *this, m_bGraphicalDesign );
970 // -----------------------------------------------------------------------------
971 ::rtl::OUString OQueryController::getPrivateTitle( ) const
973 ::rtl::OUString sName = m_sName;
974 if ( !sName.getLength() )
976 if ( !editingCommand() )
978 ::vos::OGuard aSolarGuard(Application::GetSolarMutex());
979 ::osl::MutexGuard aGuard( getMutex() );
980 String aDefaultName = String( ModuleRes( editingView() ? STR_VIEW_TITLE : STR_QRY_TITLE ) );
981 sName = aDefaultName.GetToken(0,' ');
982 sName += ::rtl::OUString::valueOf(getCurrentStartNumber());
985 return sName;
987 // -----------------------------------------------------------------------------
988 void OQueryController::setQueryComposer()
990 if(isConnected())
992 Reference< XSQLQueryComposerFactory > xFactory(getConnection(), UNO_QUERY);
993 OSL_ENSURE(xFactory.is(),"Connection doesn't support a querycomposer");
994 if ( xFactory.is() && getContainer() )
998 m_xComposer = xFactory->createQueryComposer();
999 getContainer()->setStatement(m_sStatement);
1001 catch (Exception&)
1003 m_xComposer = NULL;
1005 OSL_ENSURE(m_xComposer.is(),"No querycomposer available!");
1006 Reference<XTablesSupplier> xTablesSup(getConnection(), UNO_QUERY);
1007 deleteIterator();
1008 m_pSqlIterator = new ::connectivity::OSQLParseTreeIterator( getConnection(), xTablesSup->getTables(), m_aSqlParser, NULL );
1012 // -----------------------------------------------------------------------------
1013 sal_Bool OQueryController::Construct(Window* pParent)
1015 // TODO: we have to check if we should create the text- or the design- view
1017 m_pView = new OQueryContainerWindow( pParent, *this, getORB() );
1019 return OJoinController::Construct(pParent);
1022 // -----------------------------------------------------------------------------
1023 OJoinDesignView* OQueryController::getJoinView()
1025 return getContainer()->getDesignView();
1027 // -----------------------------------------------------------------------------
1028 void OQueryController::describeSupportedFeatures()
1030 OJoinController::describeSupportedFeatures();
1031 implDescribeSupportedFeature( ".uno:SaveAs", ID_BROWSER_SAVEASDOC, CommandGroup::DOCUMENT );
1032 implDescribeSupportedFeature( ".uno:SbaNativeSql", ID_BROWSER_ESACPEPROCESSING,CommandGroup::FORMAT );
1033 implDescribeSupportedFeature( ".uno:DBViewFunctions", SID_QUERY_VIEW_FUNCTIONS, CommandGroup::VIEW );
1034 implDescribeSupportedFeature( ".uno:DBViewTableNames", SID_QUERY_VIEW_TABLES, CommandGroup::VIEW );
1035 implDescribeSupportedFeature( ".uno:DBViewAliases", SID_QUERY_VIEW_ALIASES, CommandGroup::VIEW );
1036 implDescribeSupportedFeature( ".uno:DBDistinctValues", SID_QUERY_DISTINCT_VALUES, CommandGroup::FORMAT );
1037 implDescribeSupportedFeature( ".uno:DBChangeDesignMode",ID_BROWSER_SQL, CommandGroup::VIEW );
1038 implDescribeSupportedFeature( ".uno:DBClearQuery", SID_BROWSER_CLEAR_QUERY, CommandGroup::EDIT );
1039 implDescribeSupportedFeature( ".uno:SbaExecuteSql", ID_BROWSER_QUERY_EXECUTE, CommandGroup::VIEW );
1040 implDescribeSupportedFeature( ".uno:DBAddRelation", SID_RELATION_ADD_RELATION, CommandGroup::EDIT );
1041 implDescribeSupportedFeature( ".uno:DBQueryPreview", SID_DB_QUERY_PREVIEW, CommandGroup::VIEW );
1043 #if OSL_DEBUG_LEVEL > 1
1044 implDescribeSupportedFeature( ".uno:DBShowParseTree", ID_EDIT_QUERY_SQL );
1045 implDescribeSupportedFeature( ".uno:DBMakeDisjunct", ID_EDIT_QUERY_DESIGN );
1046 #endif
1048 // -----------------------------------------------------------------------------
1049 void OQueryController::setModified(sal_Bool _bModified)
1051 OJoinController::setModified(_bModified);
1052 InvalidateFeature(SID_BROWSER_CLEAR_QUERY);
1053 InvalidateFeature(ID_BROWSER_SAVEASDOC);
1054 InvalidateFeature(ID_BROWSER_QUERY_EXECUTE);
1056 // -----------------------------------------------------------------------------
1057 void SAL_CALL OQueryController::disposing( const EventObject& Source ) throw(RuntimeException)
1059 ::vos::OGuard aGuard(Application::GetSolarMutex());
1061 if ( getContainer() && Source.Source.is() )
1063 if ( Source.Source == m_aCurrentFrame.getFrame() )
1064 { // our frame is beeing disposed -> close the preview window (if we have one)
1065 Reference< XFrame > xPreviewFrame( getContainer()->getPreviewFrame() );
1066 ::comphelper::disposeComponent( xPreviewFrame );
1068 else if ( Source.Source == getContainer()->getPreviewFrame() )
1070 getContainer()->disposingPreview();
1074 OJoinController::disposing(Source);
1076 // -----------------------------------------------------------------------------
1077 void OQueryController::reconnect(sal_Bool _bUI)
1079 deleteIterator();
1080 ::comphelper::disposeComponent(m_xComposer);
1082 OJoinController::reconnect( _bUI );
1084 if (isConnected())
1086 setQueryComposer();
1088 else
1090 if(m_bGraphicalDesign)
1092 m_bGraphicalDesign = sal_False;
1093 // don't call Execute(SQL) because this changes the sql statement
1094 impl_setViewMode( NULL );
1096 InvalidateAll();
1099 // -----------------------------------------------------------------------------
1100 void OQueryController::saveViewSettings(Sequence<PropertyValue>& _rViewProps)
1102 OTableFields::const_iterator aFieldIter = m_vTableFieldDesc.begin();
1103 OTableFields::const_iterator aFieldEnd = m_vTableFieldDesc.end();
1104 sal_Int32 nCount = 0;
1105 for(;aFieldIter != aFieldEnd;++aFieldIter)
1107 if(!(*aFieldIter)->IsEmpty())
1108 ++nCount;
1111 sal_Int32 nLen = _rViewProps.getLength();
1113 _rViewProps.realloc( nLen + 2 + (nCount != 0 ? 1 : 0) );
1114 PropertyValue *pIter = _rViewProps.getArray() + nLen;
1116 if ( nCount != 0 )
1118 pIter->Name = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Fields"));
1120 Sequence<PropertyValue> aFields(nCount);
1121 PropertyValue *pFieldsIter = aFields.getArray();
1122 // the fielddata
1123 aFieldIter = m_vTableFieldDesc.begin();
1124 for(sal_Int32 i = 1;aFieldIter !=aFieldEnd;++aFieldIter,++i)
1126 if ( !(*aFieldIter)->IsEmpty() )
1128 pFieldsIter->Name = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Field")) + ::rtl::OUString::valueOf(i);
1129 (*aFieldIter)->Save(*pFieldsIter++);
1132 pIter->Value <<= aFields;
1133 ++pIter;
1136 pIter->Name = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("SplitterPosition"));
1137 pIter->Value <<= m_nSplitPos;
1138 ++pIter;
1139 pIter->Name = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("VisibleRows"));
1140 pIter->Value <<= m_nVisibleRows;
1142 // -----------------------------------------------------------------------------
1143 void OQueryController::loadViewSettings(const Sequence<PropertyValue>& _rViewProps)
1145 const PropertyValue *pIter = _rViewProps.getConstArray();
1146 const PropertyValue *pEnd = pIter + _rViewProps.getLength();
1147 for (; pIter != pEnd; ++pIter)
1149 if ( pIter->Name.equalsAscii("SplitterPosition") )
1151 pIter->Value >>= m_nSplitPos;
1153 else if ( pIter->Name.equalsAscii("VisibleRows") )
1155 pIter->Value >>= m_nVisibleRows;
1157 else if ( pIter->Name.equalsAscii("Fields") )
1159 pIter->Value >>= m_aFieldInformation;
1163 // -----------------------------------------------------------------------------
1164 sal_Int32 OQueryController::getColWidth(sal_uInt16 _nColPos) const
1166 if ( _nColPos < m_aFieldInformation.getLength() )
1168 ::std::auto_ptr<OTableFieldDesc> pField( new OTableFieldDesc());
1169 pField->Load(m_aFieldInformation[_nColPos]);
1170 return pField->GetColWidth();
1172 return 0;
1174 // -----------------------------------------------------------------------------
1175 Reference<XNameAccess> OQueryController::getObjectContainer() const
1177 Reference< XNameAccess > xElements;
1178 if ( editingView() )
1180 Reference< XViewsSupplier > xViewsSupp( getConnection(), UNO_QUERY );
1181 if ( xViewsSupp.is() )
1182 xElements = xViewsSupp->getViews();
1184 else
1186 Reference< XQueriesSupplier > xQueriesSupp( getConnection(), UNO_QUERY );
1187 if ( xQueriesSupp.is() )
1188 xElements = xQueriesSupp->getQueries();
1189 else
1191 Reference< XQueryDefinitionsSupplier > xQueryDefsSupp( getDataSource(), UNO_QUERY );
1192 if ( xQueryDefsSupp.is() )
1193 xElements = xQueryDefsSupp->getQueryDefinitions();
1197 OSL_ENSURE( xElements.is(), "OQueryController::getObjectContainer: unable to obtain the container!" );
1198 return xElements;
1201 // -----------------------------------------------------------------------------
1202 void OQueryController::executeQuery()
1204 // we don't need to check the connection here because we already check the composer
1205 // which can't live without his connection
1206 ::rtl::OUString sTranslatedStmt = translateStatement( false );
1208 ::rtl::OUString sDataSourceName = getDataSourceName();
1209 if ( sDataSourceName.getLength() && sTranslatedStmt.getLength() )
1213 getContainer()->showPreview( getFrame() );
1214 InvalidateFeature(SID_DB_QUERY_PREVIEW);
1216 URL aWantToDispatch;
1217 aWantToDispatch.Complete = ::rtl::OUString::createFromAscii(".component:DB/DataSourceBrowser");
1219 ::rtl::OUString sFrameName( FRAME_NAME_QUERY_PREVIEW );
1220 sal_Int32 nSearchFlags = FrameSearchFlag::CHILDREN;
1222 Reference< XDispatch> xDisp;
1223 Reference< XDispatchProvider> xProv( getFrame()->findFrame( sFrameName, nSearchFlags ), UNO_QUERY );
1224 if(!xProv.is())
1226 xProv.set( getFrame(), UNO_QUERY );
1227 if (xProv.is())
1228 xDisp = xProv->queryDispatch(aWantToDispatch, sFrameName, nSearchFlags);
1230 else
1232 xDisp = xProv->queryDispatch(aWantToDispatch, sFrameName, FrameSearchFlag::SELF);
1234 if (xDisp.is())
1236 Sequence< PropertyValue> aProps(9);
1237 aProps[0].Name = PROPERTY_DATASOURCENAME;
1238 aProps[0].Value <<= sDataSourceName;
1240 aProps[1].Name = PROPERTY_COMMAND_TYPE;
1241 aProps[1].Value <<= CommandType::COMMAND;
1243 aProps[2].Name = PROPERTY_COMMAND;
1244 aProps[2].Value <<= sTranslatedStmt;
1246 aProps[3].Name = PROPERTY_ENABLE_BROWSER;
1247 aProps[3].Value = ::cppu::bool2any(sal_False);
1249 aProps[4].Name = PROPERTY_ACTIVE_CONNECTION;
1250 aProps[4].Value <<= getConnection();
1252 aProps[5].Name = PROPERTY_UPDATE_CATALOGNAME;
1253 aProps[5].Value <<= m_sUpdateCatalogName;
1255 aProps[6].Name = PROPERTY_UPDATE_SCHEMANAME;
1256 aProps[6].Value <<= m_sUpdateSchemaName;
1258 aProps[7].Name = PROPERTY_UPDATE_TABLENAME;
1259 aProps[7].Value <<= m_sUpdateTableName;
1261 aProps[8].Name = PROPERTY_ESCAPE_PROCESSING;
1262 aProps[8].Value = ::cppu::bool2any(m_bEscapeProcessing);
1264 xDisp->dispatch(aWantToDispatch, aProps);
1265 // check the state of the beamer
1266 // be notified when the beamer frame is closed
1267 Reference< XComponent > xComponent( getFrame()->findFrame( sFrameName, nSearchFlags ), UNO_QUERY );
1268 if (xComponent.is())
1270 OSL_ENSURE(Reference< XFrame >(xComponent, UNO_QUERY).get() == getContainer()->getPreviewFrame().get(),
1271 "OQueryController::executeQuery: oops ... which window do I have here?");
1272 Reference< XEventListener> xEvtL((::cppu::OWeakObject*)this,UNO_QUERY);
1273 xComponent->addEventListener(xEvtL);
1276 else
1278 OSL_ENSURE(0,"Couldn't create a beamer window!");
1281 catch(const Exception&)
1283 OSL_ENSURE(0,"Couldn't create a beamer window!");
1287 // -----------------------------------------------------------------------------
1288 sal_Bool OQueryController::askForNewName(const Reference<XNameAccess>& _xElements,sal_Bool _bSaveAs)
1290 OSL_ENSURE( !editingCommand(), "OQueryController::askForNewName: not to be called when designing an independent statement!" );
1291 if ( editingCommand() )
1292 return sal_False;
1294 OSL_PRECOND( _xElements.is(), "OQueryController::askForNewName: invalid container!" );
1295 if ( !_xElements.is() )
1296 return sal_False;
1298 sal_Bool bRet = sal_True;
1299 sal_Bool bNew = _bSaveAs || !_xElements->hasByName( m_sName );
1300 if(bNew)
1302 String aDefaultName;
1303 if ( ( _bSaveAs && !bNew ) || ( bNew && m_sName.getLength() ) )
1304 aDefaultName = String( m_sName );
1305 else
1307 String sName = String( ModuleRes( editingView() ? STR_VIEW_TITLE : STR_QRY_TITLE ) );
1308 aDefaultName = sName.GetToken(0,' ');
1309 //aDefaultName = getPrivateTitle( );
1310 aDefaultName = ::dbtools::createUniqueName(_xElements,aDefaultName);
1313 DynamicTableOrQueryNameCheck aNameChecker( getConnection(), CommandType::QUERY );
1314 OSaveAsDlg aDlg(
1315 getView(),
1316 m_nCommandType,
1317 getORB(),
1318 getConnection(),
1319 aDefaultName,
1320 aNameChecker,
1321 SAD_DEFAULT );
1323 bRet = ( aDlg.Execute() == RET_OK );
1324 if ( bRet )
1326 m_sName = aDlg.getName();
1327 if ( editingView() )
1329 m_sUpdateCatalogName = aDlg.getCatalog();
1330 m_sUpdateSchemaName = aDlg.getSchema();
1334 return bRet;
1336 // -----------------------------------------------------------------------------
1337 bool OQueryController::doSaveAsDoc(sal_Bool _bSaveAs)
1339 OSL_ENSURE(isEditable(),"Slot ID_BROWSER_SAVEDOC should not be enabled!");
1340 if ( !editingCommand() && !haveDataSource() )
1342 String aMessage(ModuleRes(STR_DATASOURCE_DELETED));
1343 OSQLWarningBox( getView(), aMessage ).Execute();
1344 return false;
1347 Reference< XNameAccess > xElements = getObjectContainer();
1348 if ( !xElements.is() )
1349 return false;
1351 if ( !getContainer()->checkStatement() )
1352 return false;
1354 ::rtl::OUString sTranslatedStmt = translateStatement();
1355 if ( editingCommand() )
1357 setModified( sal_False );
1358 // this is all we need to do here. translateStatement implicitly set our m_sStatement, and
1359 // notified it, and that's all
1360 return true;
1363 if ( !sTranslatedStmt.getLength() )
1364 return false;
1366 // first we need a name for our query so ask the user
1367 // did we get a name
1368 ::rtl::OUString sOriginalName( m_sName );
1369 if ( !askForNewName( xElements, _bSaveAs ) || !m_sName.getLength() )
1370 return false;
1372 SQLExceptionInfo aInfo;
1373 bool bSuccess = false;
1374 bool bNew = false;
1377 bNew = ( _bSaveAs )
1378 || ( !xElements->hasByName( m_sName ) );
1380 Reference<XPropertySet> xQuery;
1381 if ( bNew ) // just to make sure the query already exists
1383 // drop the query, in case it already exists
1384 if ( xElements->hasByName( m_sName ) )
1386 Reference< XDrop > xNameCont( xElements, UNO_QUERY );
1387 if ( xNameCont.is() )
1388 xNameCont->dropByName( m_sName );
1389 else
1391 Reference< XNameContainer > xCont( xElements, UNO_QUERY );
1392 if ( xCont.is() )
1393 xCont->removeByName( m_sName );
1397 // create a new (empty, uninitialized) query resp. view
1398 Reference< XDataDescriptorFactory > xFact( xElements, UNO_QUERY );
1399 if ( xFact.is() )
1401 xQuery = xFact->createDataDescriptor();
1402 // to set the name is only allowed when the query is new
1403 xQuery->setPropertyValue( PROPERTY_NAME, makeAny( m_sName ) );
1405 else
1407 Reference< XSingleServiceFactory > xSingleFac( xElements, UNO_QUERY );
1408 if ( xSingleFac.is() )
1409 xQuery = xQuery.query( xSingleFac->createInstance() );
1412 else
1414 xElements->getByName( m_sName ) >>= xQuery;
1416 if ( !xQuery.is() )
1417 throw RuntimeException();
1419 // the new commands
1420 if ( editingView() && !bNew )
1422 OSL_ENSURE( xQuery == m_xAlterView, "OQueryController::doSaveAsDoc: already have another alterable view ...!?" );
1423 m_xAlterView.set( xQuery, UNO_QUERY_THROW );
1424 m_xAlterView->alterCommand( sTranslatedStmt );
1426 else
1427 { // we're creating a query, or a *new* view
1428 xQuery->setPropertyValue( PROPERTY_COMMAND, makeAny( sTranslatedStmt ) );
1430 if ( editingView() )
1432 xQuery->setPropertyValue( PROPERTY_CATALOGNAME, makeAny( m_sUpdateCatalogName ) );
1433 xQuery->setPropertyValue( PROPERTY_SCHEMANAME, makeAny( m_sUpdateSchemaName ) );
1436 if ( editingQuery() )
1438 xQuery->setPropertyValue( PROPERTY_UPDATE_TABLENAME, makeAny( m_sUpdateTableName ) );
1439 xQuery->setPropertyValue( PROPERTY_ESCAPE_PROCESSING,::cppu::bool2any( m_bEscapeProcessing ) );
1441 // layout information
1442 getContainer()->SaveUIConfig();
1443 Sequence< PropertyValue > aLayout;
1444 saveTableWindows( aLayout );
1445 saveViewSettings( aLayout );
1446 xQuery->setPropertyValue( PROPERTY_LAYOUTINFORMATION, makeAny( aLayout ) );
1450 if ( bNew )
1452 Reference< XAppend > xAppend( xElements, UNO_QUERY );
1453 if ( xAppend.is() )
1455 xAppend->appendByDescriptor( xQuery );
1457 else
1459 Reference< XNameContainer > xCont( xElements, UNO_QUERY );
1460 if ( xCont.is() )
1461 xCont->insertByName( m_sName, makeAny( xQuery ) );
1464 if ( editingView() )
1466 Reference< XPropertySet > xViewProps;
1467 if ( xElements->hasByName( m_sName ) )
1468 xViewProps.set( xElements->getByName( m_sName ), UNO_QUERY );
1470 if ( !xViewProps.is() ) // correct name and try again
1471 m_sName = ::dbtools::composeTableName( getMetaData(), xQuery, ::dbtools::eInDataManipulation, false, false, false );
1473 OSL_ENSURE( xElements->hasByName( m_sName ), "OQueryController::doSaveAsDoc: newly creaed view does not exist!" );
1475 if ( xElements->hasByName( m_sName ) )
1476 m_xAlterView.set( xElements->getByName( m_sName ), UNO_QUERY );
1478 // now check if our datasource has set a tablefilter and if so, append the new table name to it
1479 ::dbaui::appendToFilter( getConnection(), m_sName, getORB(), getView() );
1480 } // if ( editingView() )
1481 Reference< XTitleChangeListener> xEventListener(impl_getTitleHelper_throw(),UNO_QUERY);
1482 if ( xEventListener.is() )
1484 TitleChangedEvent aEvent;
1485 xEventListener->titleChanged(aEvent);
1487 releaseNumberForComponent();
1490 setModified( sal_False );
1491 bSuccess = true;
1494 catch( const SQLException& )
1496 if ( !bNew )
1497 m_sName = sOriginalName;
1498 aInfo = SQLExceptionInfo( ::cppu::getCaughtException() );
1500 catch(Exception&)
1502 if ( !bNew )
1503 m_sName = sOriginalName;
1504 DBG_UNHANDLED_EXCEPTION();
1507 showError( aInfo );
1509 // update the title of our window
1510 //updateTitle();
1512 // if we successfully saved a view we were creating, then close the designer
1513 if ( bSuccess && editingView() && !m_xAlterView.is() )
1515 closeTask();
1518 if ( bSuccess && editingView() )
1519 InvalidateFeature( ID_BROWSER_EDITDOC );
1521 return bSuccess;
1523 // -----------------------------------------------------------------------------
1524 ::rtl::OUString OQueryController::translateStatement( bool _bFireStatementChange )
1526 // now set the properties
1527 setStatement_fireEvent( getContainer()->getStatement(), _bFireStatementChange );
1528 ::rtl::OUString sTranslatedStmt;
1529 if(m_sStatement.getLength() && m_xComposer.is() && m_bEscapeProcessing)
1533 ::rtl::OUString aErrorMsg;
1535 ::connectivity::OSQLParseNode* pNode = m_aSqlParser.parseTree( aErrorMsg, m_sStatement, m_bGraphicalDesign );
1536 if(pNode)
1538 pNode->parseNodeToStr( sTranslatedStmt, getConnection() );
1539 delete pNode;
1542 m_xComposer->setQuery(sTranslatedStmt);
1543 sTranslatedStmt = m_xComposer->getComposedQuery();
1545 catch(SQLException& e)
1547 ::dbtools::SQLExceptionInfo aInfo(e);
1548 showError(aInfo);
1549 // an error occured so we clear the statement
1550 sTranslatedStmt = ::rtl::OUString();
1553 else if(!m_sStatement.getLength())
1555 ModuleRes aModuleRes(STR_QRY_NOSELECT);
1556 String sTmpStr(aModuleRes);
1557 ::rtl::OUString sError(sTmpStr);
1558 showError(SQLException(sError,NULL,::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("S1000") ),1000,Any()));
1560 else
1561 sTranslatedStmt = m_sStatement;
1563 return sTranslatedStmt;
1565 // -----------------------------------------------------------------------------
1566 short OQueryController::saveModified()
1568 vos::OGuard aSolarGuard( Application::GetSolarMutex() );
1569 ::osl::MutexGuard aGuard( getMutex() );
1570 short nRet = RET_YES;
1571 if ( !isConnected() || !isModified() )
1572 return nRet;
1574 if ( !m_bGraphicalDesign
1575 || ( !m_vTableFieldDesc.empty()
1576 && !m_vTableData.empty()
1580 String sMessageText( lcl_getObjectResourceString( STR_QUERY_SAVEMODIFIED, m_nCommandType ) );
1581 QueryBox aQry( getView(), WB_YES_NO_CANCEL | WB_DEF_YES, sMessageText );
1583 nRet = aQry.Execute();
1584 if ( ( nRet == RET_YES )
1585 && !doSaveAsDoc( sal_False )
1588 nRet = RET_CANCEL;
1591 return nRet;
1593 // -----------------------------------------------------------------------------
1594 void OQueryController::impl_reset()
1596 bool bValid = false;
1598 Sequence< PropertyValue > aLayoutInformation;
1599 // get command from the query if a query name was supplied
1600 if ( !editingCommand() )
1602 if ( m_sName.getLength() )
1604 Reference< XNameAccess > xQueries = getObjectContainer();
1605 if ( xQueries.is() )
1607 Reference< XPropertySet > xProp;
1608 if( xQueries->hasByName( m_sName ) && ( xQueries->getByName( m_sName ) >>= xProp ) && xProp.is() )
1610 ::rtl::OUString sNewStatement;
1611 xProp->getPropertyValue( PROPERTY_COMMAND ) >>= sNewStatement;
1612 setStatement_fireEvent( sNewStatement );
1614 sal_Bool bNewEscapeProcessing( sal_True );
1615 if ( editingQuery() )
1617 xProp->getPropertyValue( PROPERTY_ESCAPE_PROCESSING ) >>= bNewEscapeProcessing;
1618 setEscapeProcessing_fireEvent( bNewEscapeProcessing );
1621 m_bGraphicalDesign = m_bGraphicalDesign && m_bEscapeProcessing;
1622 bValid = true;
1626 if ( editingQuery() )
1627 xProp->getPropertyValue( PROPERTY_LAYOUTINFORMATION ) >>= aLayoutInformation;
1629 catch( const Exception& )
1631 OSL_ENSURE( sal_False, "OQueryController::impl_reset: could not retrieve the layout information from the query!" );
1637 else
1639 bValid = true;
1640 // assume that we got all necessary information during initialization
1643 if ( bValid )
1645 // load the layoutInformation
1646 if ( aLayoutInformation.getLength() )
1650 // load the layoutInformation
1651 loadTableWindows(aLayoutInformation);
1652 loadViewSettings(aLayoutInformation);
1654 catch( const Exception& )
1656 DBG_UNHANDLED_EXCEPTION();
1659 if ( m_sStatement.getLength() )
1661 setQueryComposer();
1663 bool bError( false );
1665 if ( !m_pSqlIterator )
1667 bError = true;
1669 else if ( m_bEscapeProcessing )
1671 ::rtl::OUString aErrorMsg;
1672 ::std::auto_ptr< ::connectivity::OSQLParseNode > pNode(
1673 m_aSqlParser.parseTree( aErrorMsg, m_sStatement, m_bGraphicalDesign ) );
1675 if ( pNode.get() )
1677 delete m_pSqlIterator->getParseTree();
1678 m_pSqlIterator->setParseTree( pNode.release() );
1679 m_pSqlIterator->traverseAll();
1680 if ( m_pSqlIterator->hasErrors() )
1682 if ( !editingView() )
1684 impl_showAutoSQLViewError( makeAny( m_pSqlIterator->getErrors() ) );
1686 bError = true;
1689 else
1691 if ( !editingView() )
1693 String aTitle(ModuleRes(STR_SVT_SQL_SYNTAX_ERROR));
1694 OSQLMessageBox aDlg(getView(),aTitle,aErrorMsg);
1695 aDlg.Execute();
1697 bError = true;
1701 if ( bError )
1703 m_bGraphicalDesign = sal_False;
1704 if ( editingView() )
1705 // if we're editing a view whose statement could not be parsed, default to "no escape processing"
1706 setEscapeProcessing_fireEvent( sal_False );
1711 if(!m_pSqlIterator)
1712 setQueryComposer();
1713 OSL_ENSURE(m_pSqlIterator,"No SQLIterator set!");
1715 getContainer()->setNoneVisbleRow(m_nVisibleRows);
1718 // -----------------------------------------------------------------------------
1719 void OQueryController::reset()
1721 impl_reset();
1722 getContainer()->reset( NULL );
1723 getUndoMgr()->Clear();
1726 // -----------------------------------------------------------------------------
1727 void OQueryController::setStatement_fireEvent( const ::rtl::OUString& _rNewStatement, bool _bFireStatementChange )
1729 Any aOldValue = makeAny( m_sStatement );
1730 m_sStatement = _rNewStatement;
1731 Any aNewValue = makeAny( m_sStatement );
1733 sal_Int32 nHandle = PROPERTY_ID_ACTIVECOMMAND;
1734 if ( _bFireStatementChange )
1735 fire( &nHandle, &aNewValue, &aOldValue, 1, sal_False );
1738 // -----------------------------------------------------------------------------
1739 void OQueryController::setEscapeProcessing_fireEvent( const sal_Bool _bEscapeProcessing )
1741 if ( _bEscapeProcessing == m_bEscapeProcessing )
1742 return;
1744 Any aOldValue = makeAny( m_bEscapeProcessing );
1745 m_bEscapeProcessing = _bEscapeProcessing;
1746 Any aNewValue = makeAny( m_bEscapeProcessing );
1748 sal_Int32 nHandle = PROPERTY_ID_ESCAPE_PROCESSING;
1749 fire( &nHandle, &aNewValue, &aOldValue, 1, sal_False );
1752 // -----------------------------------------------------------------------------
1753 IMPL_LINK( OQueryController, OnExecuteAddTable, void*, /*pNotInterestedIn*/ )
1755 Execute( ID_BROWSER_ADDTABLE,Sequence<PropertyValue>() );
1756 return 0L;
1759 // -----------------------------------------------------------------------------
1760 bool OQueryController::allowViews() const
1762 return true;
1765 // -----------------------------------------------------------------------------
1766 bool OQueryController::allowQueries() const
1768 DBG_ASSERT( getSdbMetaData().isConnected(), "OQueryController::allowQueries: illegal call!" );
1769 if ( !getSdbMetaData().supportsSubqueriesInFrom() )
1770 return false;
1772 const NamedValueCollection& rArguments( getInitParams() );
1773 sal_Int32 nCommandType = rArguments.getOrDefault( (::rtl::OUString)PROPERTY_COMMAND_TYPE, (sal_Int32)CommandType::QUERY );
1774 sal_Bool bCreatingView = ( nCommandType == CommandType::TABLE );
1775 return !bCreatingView;
1778 // -----------------------------------------------------------------------------
1779 // -----------------------------------------------------------------------------
1780 } // namespace dbaui
1781 // -----------------------------------------------------------------------------