xref: /AOO41X/main/dbaccess/source/ui/querydesign/TableConnection.cxx (revision 96de54900b79e13b861fbc62cbf36018b54e21b7)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_dbaccess.hxx"
26 #ifndef DBAUI_TABLECONNECTION_HXX
27 #include "TableConnection.hxx"
28 #endif
29 #ifndef DBAUI_CONNECTIONLINE_HXX
30 #include "ConnectionLine.hxx"
31 #endif
32 #ifndef DBAUI_TABLECONNECTIONDATA_HXX
33 #include "TableConnectionData.hxx"
34 #endif
35 #ifndef DBAUI_JOINTABLEVIEW_HXX
36 #include "JoinTableView.hxx"
37 #endif
38 #ifndef _COMPHELPER_STLTYPES_HXX_
39 #include <comphelper/stl_types.hxx>
40 #endif
41 #ifndef DBACCESS_CONNECTIONLINEACCESS_HXX
42 #include "ConnectionLineAccess.hxx"
43 #endif
44 #include <algorithm>
45 
46 
47 using namespace dbaui;
48 using namespace comphelper;
49 using namespace ::com::sun::star::uno;
50 using namespace ::com::sun::star::accessibility;
51 
52 //========================================================================
53 // class OTableConnection
54 //========================================================================
55 namespace dbaui
56 {
DBG_NAME(OTableConnection)57     DBG_NAME(OTableConnection)
58     //------------------------------------------------------------------------
59     OTableConnection::OTableConnection( OJoinTableView* _pContainer,const TTableConnectionData::value_type& _pTabConnData )
60         :Window(_pContainer)
61         ,m_pData( _pTabConnData )
62         ,m_pParent( _pContainer )
63         ,m_bSelected( sal_False )
64     {
65         DBG_CTOR(OTableConnection,NULL);
66         Init();
67         Show();
68     }
69 
70     //------------------------------------------------------------------------
OTableConnection(const OTableConnection & _rConn)71     OTableConnection::OTableConnection( const OTableConnection& _rConn ) : Window(_rConn.m_pParent)
72         ,m_pData(_rConn.GetData()->NewInstance())
73     {
74         DBG_CTOR(OTableConnection,NULL);
75         *this = _rConn;
76     }
77 
78     //------------------------------------------------------------------------
Init()79     void OTableConnection::Init()
80     {
81         //////////////////////////////////////////////////////////////////////
82         // Linienliste mit Defaults initialisieren
83         OConnectionLineDataVec* pLineData = GetData()->GetConnLineDataList();
84         OConnectionLineDataVec::const_iterator aIter = pLineData->begin();
85         OConnectionLineDataVec::const_iterator aEnd = pLineData->end();
86         m_vConnLine.reserve(pLineData->size());
87         for(;aIter != aEnd;++aIter)
88             m_vConnLine.push_back( new OConnectionLine(this, *aIter) );
89     }
90 
91     //------------------------------------------------------------------------
CreateConnLine(const OConnectionLine & rConnLine)92     OConnectionLine* OTableConnection::CreateConnLine( const OConnectionLine& rConnLine )
93     {
94         return new OConnectionLine( rConnLine );
95     }
96     // -----------------------------------------------------------------------------
clearLineData()97     void OTableConnection::clearLineData()
98     {
99         ::std::vector<OConnectionLine*>::iterator aLineEnd = m_vConnLine.end();
100         for(::std::vector<OConnectionLine*>::iterator aLineIter = m_vConnLine.begin();aLineIter != aLineEnd;++aLineIter)
101             delete *aLineIter;
102         m_vConnLine.clear();
103     }
104     //------------------------------------------------------------------------
UpdateLineList()105     void OTableConnection::UpdateLineList()
106     {
107         //////////////////////////////////////////////////////////////////////
108         // Linienliste loeschen
109         clearLineData();
110 
111         Init();
112     }
113 
114     //------------------------------------------------------------------------
operator =(const OTableConnection & rConn)115     OTableConnection& OTableConnection::operator=( const OTableConnection& rConn )
116     {
117         if( &rConn == this )
118             return *this;
119 
120         // Linienliste loeschen
121         clearLineData();
122 
123         // Linienliste kopieren
124         if(! rConn.GetConnLineList()->empty() )
125         {
126             const ::std::vector<OConnectionLine*>* pLine = rConn.GetConnLineList();
127             ::std::vector<OConnectionLine*>::const_iterator aIter = pLine->begin();
128             ::std::vector<OConnectionLine*>::const_iterator aEnd = pLine->end();
129             m_vConnLine.reserve(pLine->size());
130             for(;aIter != aEnd;++aIter)
131                 m_vConnLine.push_back( CreateConnLine( **aIter ));
132         }
133 
134         // da mir die Daten nicht gehoeren, loesche ich die alten nicht
135         m_pData->CopyFrom(*rConn.GetData());
136             // CopyFrom ist virtuell, damit ist es kein Problem, wenn m_pData von einem von OTableConnectionData abgeleiteten Typ ist
137 
138         m_bSelected = rConn.m_bSelected;
139         m_pParent = rConn.m_pParent;
140 
141         return *this;
142     }
143 
144 
145     //------------------------------------------------------------------------
RecalcLines()146     bool OTableConnection::RecalcLines()
147     {
148         // call RecalcLines on each line
149         ::std::for_each(m_vConnLine.begin(),m_vConnLine.end(),::std::mem_fun(&OConnectionLine::RecalcLine));
150         return true;
151     }
152     //------------------------------------------------------------------------
GetSourceWin() const153     OTableWindow* OTableConnection::GetSourceWin() const
154     {
155         TTableWindowData::value_type pRef = GetData()->getReferencingTable();
156         OTableWindow* pRet = m_pParent->GetTabWindow( pRef->GetWinName() );
157         if ( !pRet )
158         {
159             pRet = m_pParent->GetTabWindow( pRef->GetComposedName() );
160         }
161         return pRet;
162     }
163     //------------------------------------------------------------------------
GetDestWin() const164     OTableWindow* OTableConnection::GetDestWin() const
165     {
166         TTableWindowData::value_type pRef = GetData()->getReferencedTable();
167         OTableWindow* pRet = m_pParent->GetTabWindow( pRef->GetWinName() );
168         if ( !pRet )
169         {
170             pRet = m_pParent->GetTabWindow( pRef->GetComposedName() );
171         }
172         return pRet;
173     }
174 
175     //------------------------------------------------------------------------
Select()176     void OTableConnection::Select()
177     {
178         m_bSelected = sal_True;
179         m_pParent->Invalidate( GetBoundingRect(), INVALIDATE_NOCHILDREN);
180     }
181 
182     //------------------------------------------------------------------------
Deselect()183     void OTableConnection::Deselect()
184     {
185         m_bSelected = sal_False;
186         InvalidateConnection();
187     }
188 
189     //------------------------------------------------------------------------
CheckHit(const Point & rMousePos) const190     sal_Bool OTableConnection::CheckHit( const Point& rMousePos ) const
191     {
192         //////////////////////////////////////////////////////////////////////
193         // check if the point hit our line
194         ::std::vector<OConnectionLine*>::const_iterator aIter = ::std::find_if(m_vConnLine.begin(),
195                                                                          m_vConnLine.end(),
196                                                                          ::std::bind2nd(TConnectionLineCheckHitFunctor(),rMousePos));
197         return aIter != m_vConnLine.end();
198     }
199 
200     //------------------------------------------------------------------------
InvalidateConnection()201     bool OTableConnection::InvalidateConnection()
202     {
203         Rectangle rcBounding = GetBoundingRect();
204         rcBounding.Bottom() += 1;
205         rcBounding.Right() += 1;
206             // ich glaube, dass sich Invalidate und Draw(Rectangle) nicht konsistent verhalten : jedenfalls waere dadurch zu
207             // erklaeren, warum ohne diesen Fake hier beim Loeschen einer Connection ein Strich an ihrem unteren Ende stehen bleibt :
208             // Invalidate erfasst dabei offensichtlich eine Pixelzeile weniger als Draw.
209             // Oder alles haengt ganz anders zusammen ... jedenfalls klappt es so ...
210         m_pParent->Invalidate( rcBounding, INVALIDATE_NOCHILDREN );
211 
212         return true;
213     }
214 
215     //------------------------------------------------------------------------
GetBoundingRect() const216     Rectangle OTableConnection::GetBoundingRect() const
217     {
218         //////////////////////////////////////////////////////////////////////
219         // Aus allen Linien das umgebende Rechteck bestimmen
220         Rectangle aBoundingRect( Point(0,0), Point(0,0) );
221         Rectangle aTempRect;
222         ::std::vector<OConnectionLine*>::const_iterator aEnd = m_vConnLine.end();
223         for(::std::vector<OConnectionLine*>::const_iterator aIter = m_vConnLine.begin();aIter != aEnd;++aIter)
224         {
225             aTempRect = (*aIter)->GetBoundingRect();
226 
227             //////////////////////////////////////////////////////////////////////
228             // Ist das BoundingRect dieser Linie gueltig?
229             if( (aTempRect.GetWidth()!=1) && (aTempRect.GetHeight()!=1) )
230             {
231                 if( (aBoundingRect.GetWidth()==1) && (aBoundingRect.GetHeight()==1) )
232                     aBoundingRect = aTempRect;
233                 else
234                     aBoundingRect.Union( aTempRect );
235             }
236         }
237 
238         return aBoundingRect;
239     }
240 
241     //------------------------------------------------------------------------
Draw(const Rectangle &)242     void OTableConnection::Draw( const Rectangle& /*rRect*/ )
243     {
244         //////////////////////////////////////////////////////////////////////
245         // Linien zeichnen
246         ::std::for_each(m_vConnLine.begin(),m_vConnLine.end(),TConnectionLineDrawFunctor(m_pParent));
247     }
248     // -----------------------------------------------------------------------------
249 }
250 
251 
252 
253