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