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 27 #include "apitools.hxx" 28 #include "dbastrings.hrc" 29 #include "definitioncolumn.hxx" 30 #include "sdbcoretools.hxx" 31 32 /** === begin UNO includes === **/ 33 #include <com/sun/star/beans/PropertyAttribute.hpp> 34 #include <com/sun/star/sdbcx/XTablesSupplier.hpp> 35 /** === end UNO includes === **/ 36 37 #include <comphelper/property.hxx> 38 #include <comphelper/types.hxx> 39 #include <connectivity/dbtools.hxx> 40 #include <cppuhelper/typeprovider.hxx> 41 #include <tools/debug.hxx> 42 #include <tools/diagnose_ex.h> 43 44 using namespace ::com::sun::star::sdbc; 45 using namespace ::com::sun::star::sdbcx; 46 using namespace ::com::sun::star::beans; 47 using namespace ::com::sun::star::uno; 48 using namespace ::com::sun::star::lang; 49 using namespace ::com::sun::star::container; 50 using namespace ::cppu; 51 using namespace ::comphelper; 52 using namespace ::osl; 53 using namespace dbaccess; 54 55 #define HAS_DESCRIPTION 0x00000001 56 #define HAS_DEFAULTVALUE 0x00000002 57 #define HAS_ROWVERSION 0x00000004 58 #define HAS_AUTOINCREMENT_CREATION 0x00000008 59 60 //============================================================ 61 //= OTableColumnDescriptor 62 //============================================================ 63 IMPLEMENT_FORWARD_XINTERFACE2(OTableColumnDescriptor,OColumn,TXChild) 64 65 //------------------------------------------------------------------------------ 66 void OTableColumnDescriptor::impl_registerProperties() 67 { 68 sal_Int32 nDefaultAttr = m_bActAsDescriptor ? 0 : PropertyAttribute::READONLY; 69 70 registerProperty( PROPERTY_TYPENAME, PROPERTY_ID_TYPENAME, nDefaultAttr, &m_aTypeName, ::getCppuType( &m_aTypeName ) ); 71 registerProperty( PROPERTY_DESCRIPTION, PROPERTY_ID_DESCRIPTION, nDefaultAttr, &m_aDescription, ::getCppuType( &m_aDescription ) ); 72 registerProperty( PROPERTY_DEFAULTVALUE, PROPERTY_ID_DEFAULTVALUE, nDefaultAttr, &m_aDefaultValue, ::getCppuType( &m_aDefaultValue ) ); 73 74 if ( m_bActAsDescriptor ) 75 registerProperty( PROPERTY_AUTOINCREMENTCREATION, PROPERTY_ID_AUTOINCREMENTCREATION, nDefaultAttr, &m_aAutoIncrementValue, ::getCppuType( &m_aAutoIncrementValue ) ); 76 77 registerProperty( PROPERTY_TYPE, PROPERTY_ID_TYPE, nDefaultAttr, &m_nType, ::getCppuType( &m_nType ) ); 78 registerProperty( PROPERTY_PRECISION, PROPERTY_ID_PRECISION, nDefaultAttr, &m_nPrecision, ::getCppuType( &m_nPrecision ) ); 79 registerProperty( PROPERTY_SCALE, PROPERTY_ID_SCALE, nDefaultAttr, &m_nScale, ::getCppuType( &m_nScale ) ); 80 registerProperty( PROPERTY_ISNULLABLE, PROPERTY_ID_ISNULLABLE, nDefaultAttr, &m_nIsNullable, ::getCppuType( &m_nIsNullable ) ); 81 registerProperty( PROPERTY_ISAUTOINCREMENT, PROPERTY_ID_ISAUTOINCREMENT, nDefaultAttr, &m_bAutoIncrement, ::getCppuType( &m_bAutoIncrement ) ); 82 registerProperty( PROPERTY_ISROWVERSION, PROPERTY_ID_ISROWVERSION, nDefaultAttr, &m_bRowVersion, ::getCppuType( &m_bRowVersion ) ); 83 registerProperty( PROPERTY_ISCURRENCY, PROPERTY_ID_ISCURRENCY, nDefaultAttr, &m_bCurrency, ::getCppuType( &m_bCurrency ) ); 84 85 OColumnSettings::registerProperties( *this ); 86 } 87 88 //-------------------------------------------------------------------------- 89 IMPLEMENT_GET_IMPLEMENTATION_ID( OTableColumnDescriptor ) 90 91 // ::com::sun::star::lang::XServiceInfo 92 //------------------------------------------------------------------------------ 93 rtl::OUString OTableColumnDescriptor::getImplementationName( ) throw (RuntimeException) 94 { 95 return rtl::OUString::createFromAscii("com.sun.star.sdb.OTableColumnDescriptor"); 96 } 97 98 //------------------------------------------------------------------------------ 99 Sequence< ::rtl::OUString > OTableColumnDescriptor::getSupportedServiceNames( ) throw (RuntimeException) 100 { 101 Sequence< ::rtl::OUString > aSNS( 2 ); 102 aSNS[0] = m_bActAsDescriptor ? SERVICE_SDBCX_COLUMNDESCRIPTOR : SERVICE_SDBCX_COLUMN; 103 aSNS[1] = SERVICE_SDB_COLUMNSETTINGS; 104 return aSNS; 105 } 106 107 // comphelper::OPropertyArrayUsageHelper 108 //------------------------------------------------------------------------------ 109 ::cppu::IPropertyArrayHelper* OTableColumnDescriptor::createArrayHelper( ) const 110 { 111 Sequence< Property > aProps; 112 describeProperties( aProps ); 113 return new ::cppu::OPropertyArrayHelper( aProps ); 114 } 115 116 // cppu::OPropertySetHelper 117 //------------------------------------------------------------------------------ 118 ::cppu::IPropertyArrayHelper& OTableColumnDescriptor::getInfoHelper() 119 { 120 return *static_cast< ::comphelper::OPropertyArrayUsageHelper< OTableColumnDescriptor >* >(this)->getArrayHelper(); 121 } 122 123 //------------------------------------------------------------------------------ 124 void OTableColumnDescriptor::setFastPropertyValue_NoBroadcast( sal_Int32 nHandle, const Any& rValue ) throw (Exception) 125 { 126 OColumn::setFastPropertyValue_NoBroadcast( nHandle, rValue ); 127 ::dbaccess::notifyDataSourceModified( m_xParent, sal_True ); 128 } 129 130 // ----------------------------------------------------------------------------- 131 Reference< XInterface > SAL_CALL OTableColumnDescriptor::getParent( ) throw (RuntimeException) 132 { 133 ::osl::MutexGuard aGuard(m_aMutex); 134 return m_xParent; 135 } 136 // ----------------------------------------------------------------------------- 137 void SAL_CALL OTableColumnDescriptor::setParent( const Reference< XInterface >& _xParent ) throw (NoSupportException, RuntimeException) 138 { 139 ::osl::MutexGuard aGuard(m_aMutex); 140 m_xParent = _xParent; 141 } 142 //============================================================ 143 //= OTableColumn 144 //============================================================ 145 DBG_NAME(OTableColumn); 146 147 // ------------------------------------------------------------------------- 148 OTableColumn::OTableColumn( const ::rtl::OUString& _rName ) 149 :OTableColumnDescriptor( false /* do not act as descriptor */ ) 150 { 151 DBG_CTOR(OTableColumn,NULL); 152 m_sName = _rName; 153 } 154 155 // ----------------------------------------------------------------------------- 156 OTableColumn::~OTableColumn() 157 { 158 DBG_DTOR(OTableColumn,NULL); 159 } 160 161 //-------------------------------------------------------------------------- 162 IMPLEMENT_GET_IMPLEMENTATION_ID( OTableColumn ) 163 164 //------------------------------------------------------------------------------ 165 rtl::OUString OTableColumn::getImplementationName( ) throw (RuntimeException) 166 { 167 return rtl::OUString::createFromAscii("com.sun.star.sdb.OTableColumn"); 168 } 169 170 //------------------------------------------------------------------------------ 171 ::cppu::IPropertyArrayHelper& SAL_CALL OTableColumn::getInfoHelper() 172 { 173 return *OTableColumn_PBase::getArrayHelper(); 174 } 175 176 //------------------------------------------------------------------------------ 177 ::cppu::IPropertyArrayHelper* OTableColumn::createArrayHelper( ) const 178 { 179 return OTableColumnDescriptor::createArrayHelper(); 180 } 181 182 // ========================================================================= 183 //= OQueryColumn 184 // ========================================================================= 185 DBG_NAME( OQueryColumn ); 186 187 // ------------------------------------------------------------------------- 188 OQueryColumn::OQueryColumn( const Reference< XPropertySet >& _rxParserColumn, const Reference< XConnection >& _rxConnection,const ::rtl::OUString i_sLabel ) 189 :OTableColumnDescriptor( false /* do not act as descriptor */ ) 190 ,m_sLabel(i_sLabel) 191 { 192 const sal_Int32 nPropAttr = PropertyAttribute::READONLY; 193 registerProperty( PROPERTY_CATALOGNAME, PROPERTY_ID_CATALOGNAME, nPropAttr, &m_sCatalogName, ::getCppuType( &m_sCatalogName ) ); 194 registerProperty( PROPERTY_SCHEMANAME, PROPERTY_ID_SCHEMANAME, nPropAttr, &m_sSchemaName, ::getCppuType( &m_sSchemaName ) ); 195 registerProperty( PROPERTY_TABLENAME, PROPERTY_ID_TABLENAME, nPropAttr, &m_sTableName, ::getCppuType( &m_sTableName ) ); 196 registerProperty( PROPERTY_REALNAME, PROPERTY_ID_REALNAME, nPropAttr, &m_sRealName, ::getCppuType( &m_sRealName ) ); 197 registerProperty( PROPERTY_LABEL, PROPERTY_ID_LABEL, nPropAttr, &m_sLabel, ::getCppuType( &m_sLabel ) ); 198 199 DBG_CTOR( OQueryColumn, NULL ); 200 201 OSL_VERIFY( _rxParserColumn->getPropertyValue( PROPERTY_TYPENAME ) >>= m_aTypeName ); 202 OSL_VERIFY( _rxParserColumn->getPropertyValue( PROPERTY_ISNULLABLE ) >>= m_nIsNullable ); 203 OSL_VERIFY( _rxParserColumn->getPropertyValue( PROPERTY_PRECISION ) >>= m_nPrecision ); 204 OSL_VERIFY( _rxParserColumn->getPropertyValue( PROPERTY_SCALE ) >>= m_nScale ); 205 OSL_VERIFY( _rxParserColumn->getPropertyValue( PROPERTY_TYPE ) >>= m_nType ); 206 OSL_VERIFY( _rxParserColumn->getPropertyValue( PROPERTY_ISAUTOINCREMENT ) >>= m_bAutoIncrement ); 207 OSL_VERIFY( _rxParserColumn->getPropertyValue( PROPERTY_ISCURRENCY ) >>= m_bCurrency ); 208 OSL_VERIFY( _rxParserColumn->getPropertyValue( PROPERTY_NAME ) >>= m_sName ); 209 210 m_bRowVersion = sal_False; 211 212 Reference< XPropertySetInfo > xPSI( _rxParserColumn->getPropertySetInfo(), UNO_SET_THROW ); 213 if ( xPSI->hasPropertyByName( PROPERTY_DEFAULTVALUE ) ) 214 OSL_VERIFY( _rxParserColumn->getPropertyValue( PROPERTY_DEFAULTVALUE ) >>= m_aDefaultValue ); 215 216 // copy some optional properties from the parser column 217 struct PropertyDescriptor 218 { 219 ::rtl::OUString sName; 220 sal_Int32 nHandle; 221 }; 222 PropertyDescriptor aProps[] = 223 { 224 { PROPERTY_CATALOGNAME, PROPERTY_ID_CATALOGNAME }, 225 { PROPERTY_SCHEMANAME, PROPERTY_ID_SCHEMANAME }, 226 { PROPERTY_TABLENAME, PROPERTY_ID_TABLENAME }, 227 { PROPERTY_REALNAME, PROPERTY_ID_REALNAME } 228 }; 229 for ( size_t i=0; i < sizeof( aProps ) / sizeof( aProps[0] ); ++i ) 230 { 231 if ( xPSI->hasPropertyByName( aProps[i].sName ) ) 232 setFastPropertyValue_NoBroadcast( aProps[i].nHandle, _rxParserColumn->getPropertyValue( aProps[i].sName ) ); 233 } 234 235 // determine the table column we're based on 236 osl_incrementInterlockedCount( &m_refCount ); 237 { 238 m_xOriginalTableColumn = impl_determineOriginalTableColumn( _rxConnection ); 239 } 240 osl_decrementInterlockedCount( &m_refCount ); 241 } 242 243 //-------------------------------------------------------------------------- 244 OQueryColumn::~OQueryColumn() 245 { 246 DBG_DTOR( OQueryColumn, NULL ); 247 } 248 249 //-------------------------------------------------------------------------- 250 Reference< XPropertySet > OQueryColumn::impl_determineOriginalTableColumn( const Reference< XConnection >& _rxConnection ) 251 { 252 OSL_PRECOND( _rxConnection.is(), "OQueryColumn::impl_determineOriginalTableColumn: illegal connection!" ); 253 if ( !_rxConnection.is() ) 254 return NULL; 255 256 Reference< XPropertySet > xOriginalTableColumn; 257 try 258 { 259 // determine the composed table name, plus the column name, as indicated by the 260 // respective properties 261 ::rtl::OUString sCatalog, sSchema, sTable; 262 OSL_VERIFY( getPropertyValue( PROPERTY_CATALOGNAME ) >>= sCatalog ); 263 OSL_VERIFY( getPropertyValue( PROPERTY_SCHEMANAME ) >>= sSchema ); 264 OSL_VERIFY( getPropertyValue( PROPERTY_TABLENAME ) >>= sTable ); 265 if ( !sCatalog.getLength() && !sSchema.getLength() && !sTable.getLength() ) 266 return NULL; 267 268 ::rtl::OUString sComposedTableName = ::dbtools::composeTableName( 269 _rxConnection->getMetaData(), sCatalog, sSchema, sTable, sal_False, ::dbtools::eComplete ); 270 271 // retrieve the table in question 272 Reference< XTablesSupplier > xSuppTables( _rxConnection, UNO_QUERY_THROW ); 273 Reference< XNameAccess > xTables( xSuppTables->getTables(), UNO_QUERY_THROW ); 274 if ( !xTables->hasByName( sComposedTableName ) ) 275 return NULL; 276 277 Reference< XColumnsSupplier > xSuppCols( xTables->getByName( sComposedTableName ), UNO_QUERY_THROW ); 278 Reference< XNameAccess > xColumns( xSuppCols->getColumns(), UNO_QUERY_THROW ); 279 280 ::rtl::OUString sColumn; 281 OSL_VERIFY( getPropertyValue( PROPERTY_REALNAME ) >>= sColumn ); 282 if ( !xColumns->hasByName( sColumn ) ) 283 return NULL; 284 285 xOriginalTableColumn.set( xColumns->getByName( sColumn ), UNO_QUERY ); 286 } 287 catch( const Exception& ) 288 { 289 DBG_UNHANDLED_EXCEPTION(); 290 } 291 return xOriginalTableColumn; 292 } 293 294 //-------------------------------------------------------------------------- 295 IMPLEMENT_GET_IMPLEMENTATION_ID( OQueryColumn ) 296 297 //-------------------------------------------------------------------------- 298 ::rtl::OUString SAL_CALL OQueryColumn::getImplementationName( ) throw(RuntimeException) 299 { 300 return ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "org.openoffice.comp.dbaccess.OQueryColumn" ) ); 301 } 302 303 //------------------------------------------------------------------------------ 304 ::cppu::IPropertyArrayHelper& SAL_CALL OQueryColumn::getInfoHelper() 305 { 306 return *OQueryColumn_PBase::getArrayHelper(); 307 } 308 309 //-------------------------------------------------------------------------- 310 ::cppu::IPropertyArrayHelper* OQueryColumn::createArrayHelper() const 311 { 312 return OTableColumnDescriptor::createArrayHelper(); 313 } 314 315 //-------------------------------------------------------------------------- 316 void SAL_CALL OQueryColumn::getFastPropertyValue( Any& _rValue, sal_Int32 _nHandle ) const 317 { 318 OTableColumnDescriptor::getFastPropertyValue( _rValue, _nHandle ); 319 320 // special treatment for column settings: 321 if ( !OColumnSettings::isColumnSettingProperty( _nHandle ) ) 322 return; 323 324 // If the setting has its default value, then try to obtain the value from the table column which 325 // this query column is based on 326 if ( !OColumnSettings::isDefaulted( _nHandle, _rValue ) ) 327 return; 328 329 if ( !m_xOriginalTableColumn.is() ) 330 return; 331 332 try 333 { 334 // determine original property name 335 ::rtl::OUString sPropName; 336 sal_Int16 nAttributes( 0 ); 337 const_cast< OQueryColumn* >( this )->getInfoHelper().fillPropertyMembersByHandle( &sPropName, &nAttributes, _nHandle ); 338 OSL_ENSURE( sPropName.getLength(), "OColumnWrapper::impl_getPropertyNameFromHandle: property not found!" ); 339 340 _rValue = m_xOriginalTableColumn->getPropertyValue( sPropName ); 341 } 342 catch( const Exception& ) 343 { 344 DBG_UNHANDLED_EXCEPTION(); 345 } 346 } 347 348 //========================================================================== 349 //= OColumnWrapper 350 //========================================================================== 351 DBG_NAME(OColumnWrapper); 352 //-------------------------------------------------------------------------- 353 OColumnWrapper::OColumnWrapper( const Reference< XPropertySet > & rCol, const bool _bNameIsReadOnly ) 354 :OColumn( _bNameIsReadOnly ) 355 ,m_xAggregate(rCol) 356 ,m_nColTypeID(-1) 357 { 358 DBG_CTOR(OColumnWrapper,NULL); 359 // which type of aggregate property do we have? 360 // we distingish the properties by the containment of optional properties 361 m_nColTypeID = 0; 362 if ( m_xAggregate.is() ) 363 { 364 Reference <XPropertySetInfo > xInfo(m_xAggregate->getPropertySetInfo()); 365 m_nColTypeID |= xInfo->hasPropertyByName(PROPERTY_DESCRIPTION) ? HAS_DESCRIPTION : 0; 366 m_nColTypeID |= xInfo->hasPropertyByName(PROPERTY_DEFAULTVALUE) ? HAS_DEFAULTVALUE : 0; 367 m_nColTypeID |= xInfo->hasPropertyByName(PROPERTY_ISROWVERSION) ? HAS_ROWVERSION : 0; 368 m_nColTypeID |= xInfo->hasPropertyByName(PROPERTY_AUTOINCREMENTCREATION) ? HAS_AUTOINCREMENT_CREATION : 0; 369 370 m_xAggregate->getPropertyValue(PROPERTY_NAME) >>= m_sName; 371 } 372 } 373 // ----------------------------------------------------------------------------- 374 OColumnWrapper::~OColumnWrapper() 375 { 376 DBG_DTOR(OColumnWrapper,NULL); 377 } 378 379 //------------------------------------------------------------------------------ 380 ::rtl::OUString OColumnWrapper::impl_getPropertyNameFromHandle( const sal_Int32 _nHandle ) const 381 { 382 ::rtl::OUString sPropName; 383 sal_Int16 nAttributes( 0 ); 384 const_cast< OColumnWrapper* >( this )->getInfoHelper().fillPropertyMembersByHandle( &sPropName, &nAttributes, _nHandle ); 385 OSL_ENSURE( sPropName.getLength(), "OColumnWrapper::impl_getPropertyNameFromHandle: property not found!" ); 386 return sPropName; 387 } 388 389 //------------------------------------------------------------------------------ 390 void OColumnWrapper::getFastPropertyValue( Any& rValue, sal_Int32 nHandle ) const 391 { 392 // derived classes are free to either use the OPropertyContainer(Helper) mechanisms for properties, 393 // or to declare additional properties which are to be forwarded to the wrapped object. So we need 394 // to distinguish those cases. 395 if ( OColumn::isRegisteredProperty( nHandle ) ) 396 { 397 OColumn::getFastPropertyValue( rValue, nHandle ); 398 } 399 else 400 { 401 rValue = m_xAggregate->getPropertyValue( impl_getPropertyNameFromHandle( nHandle ) ); 402 } 403 } 404 405 //------------------------------------------------------------------------------ 406 sal_Bool OColumnWrapper::convertFastPropertyValue( Any & rConvertedValue, Any & rOldValue, sal_Int32 nHandle, 407 const Any& rValue ) throw (IllegalArgumentException) 408 { 409 sal_Bool bModified( sal_False ); 410 if ( OColumn::isRegisteredProperty( nHandle ) ) 411 { 412 bModified = OColumn::convertFastPropertyValue( rConvertedValue, rOldValue, nHandle, rValue ); 413 } 414 else 415 { 416 getFastPropertyValue( rOldValue, nHandle ); 417 if ( rOldValue != rValue ) 418 { 419 rConvertedValue = rValue; 420 bModified = sal_True; 421 } 422 } 423 return bModified; 424 } 425 426 //------------------------------------------------------------------------------ 427 void OColumnWrapper::setFastPropertyValue_NoBroadcast( sal_Int32 nHandle, const Any& rValue ) throw (Exception) 428 { 429 if ( OColumn::isRegisteredProperty( nHandle ) ) 430 { 431 OColumn::setFastPropertyValue_NoBroadcast( nHandle, rValue ); 432 } 433 else 434 { 435 m_xAggregate->setPropertyValue( impl_getPropertyNameFromHandle( nHandle ), rValue ); 436 } 437 } 438 439 // ----------------------------------------------------------------------------- 440 sal_Int64 SAL_CALL OColumnWrapper::getSomething( const Sequence< sal_Int8 >& aIdentifier ) throw(RuntimeException) 441 { 442 Reference< XUnoTunnel > xTunnel( m_xAggregate, UNO_QUERY); 443 if ( xTunnel.is() ) 444 return xTunnel->getSomething( aIdentifier ); 445 return 0; 446 } 447 448 //============================================================ 449 //= OTableColumnDescriptorWrapper 450 //============================================================ 451 //-------------------------------------------------------------------------- 452 OTableColumnDescriptorWrapper::OTableColumnDescriptorWrapper( const Reference< XPropertySet >& _rCol, const bool _bPureWrap, const bool _bIsDescriptor ) 453 :OColumnWrapper( _rCol, !_bIsDescriptor ) 454 ,m_bPureWrap( _bPureWrap ) 455 ,m_bIsDescriptor( _bIsDescriptor ) 456 { 457 // let the ColumnSettings register its properties 458 OColumnSettings::registerProperties( *this ); 459 } 460 461 // com::sun::star::lang::XTypeProvider 462 //-------------------------------------------------------------------------- 463 IMPLEMENT_GET_IMPLEMENTATION_ID( OTableColumnDescriptorWrapper ) 464 465 // ::com::sun::star::lang::XServiceInfo 466 //------------------------------------------------------------------------------ 467 rtl::OUString OTableColumnDescriptorWrapper::getImplementationName( ) throw (RuntimeException) 468 { 469 return rtl::OUString::createFromAscii("com.sun.star.sdb.OTableColumnDescriptorWrapper"); 470 } 471 472 //------------------------------------------------------------------------------ 473 Sequence< ::rtl::OUString > OTableColumnDescriptorWrapper::getSupportedServiceNames( ) throw (RuntimeException) 474 { 475 Sequence< ::rtl::OUString > aSNS( 2 ); 476 aSNS[0] = SERVICE_SDBCX_COLUMNDESCRIPTOR; 477 aSNS[1] = SERVICE_SDB_COLUMNSETTINGS; 478 return aSNS; 479 } 480 481 // comphelper::OPropertyArrayUsageHelper 482 //------------------------------------------------------------------------------ 483 ::cppu::IPropertyArrayHelper* OTableColumnDescriptorWrapper::createArrayHelper( sal_Int32 nId ) const 484 { 485 const sal_Int32 nHaveAlways = 7; 486 487 // Which optional properties are contained? 488 sal_Int32 nHaveOptionally = 0; 489 if (nId & HAS_DESCRIPTION) 490 ++nHaveOptionally; 491 if (nId & HAS_DEFAULTVALUE) 492 ++nHaveOptionally; 493 if (nId & HAS_ROWVERSION) 494 ++nHaveOptionally; 495 if ( nId & HAS_AUTOINCREMENT_CREATION ) 496 ++nHaveOptionally; 497 498 const sal_Int32 nPropertyCount( nHaveAlways + nHaveOptionally ); 499 Sequence< Property > aTableDescProperties( nPropertyCount ); 500 Property* pDesc = aTableDescProperties.getArray(); 501 sal_Int32 nPos = 0; 502 503 DECL_PROP0_BOOL( ISAUTOINCREMENT ); 504 DECL_PROP0_BOOL( ISCURRENCY ); 505 DECL_PROP0( ISNULLABLE, sal_Int32 ); 506 DECL_PROP0( PRECISION, sal_Int32 ); 507 DECL_PROP0( SCALE, sal_Int32 ); 508 DECL_PROP0( TYPE, sal_Int32 ); 509 DECL_PROP0( TYPENAME, ::rtl::OUString ); 510 511 if ( nId & HAS_AUTOINCREMENT_CREATION ) 512 { 513 DECL_PROP1( AUTOINCREMENTCREATION, ::rtl::OUString, MAYBEVOID ); 514 } 515 if ( nId & HAS_DEFAULTVALUE ) 516 { 517 DECL_PROP0( DEFAULTVALUE, ::rtl::OUString ); 518 } 519 if ( nId & HAS_DESCRIPTION ) 520 { 521 DECL_PROP0( DESCRIPTION, ::rtl::OUString ); 522 } 523 if ( nId & HAS_ROWVERSION ) 524 { 525 DECL_PROP0_BOOL( ISROWVERSION ); 526 } 527 528 OSL_ENSURE( nPos == nPropertyCount, "OTableColumnDescriptorWrapper::createArrayHelper: something went wrong!" ); 529 530 if ( !m_bIsDescriptor ) 531 { 532 for ( Property* prop = aTableDescProperties.getArray(); 533 prop != aTableDescProperties.getArray() + aTableDescProperties.getLength(); 534 ++prop 535 ) 536 { 537 prop->Attributes |= PropertyAttribute::READONLY; 538 } 539 } 540 541 // finally also describe the properties which are maintained by our base class, in particular the OPropertyContainerHelper 542 Sequence< Property > aBaseProperties; 543 describeProperties( aBaseProperties ); 544 545 Sequence< Property > aAllProperties( ::comphelper::concatSequences( aTableDescProperties, aBaseProperties ) ); 546 return new ::cppu::OPropertyArrayHelper( aAllProperties, sal_False ); 547 } 548 549 // cppu::OPropertySetHelper 550 //------------------------------------------------------------------------------ 551 ::cppu::IPropertyArrayHelper& OTableColumnDescriptorWrapper::getInfoHelper() 552 { 553 return *static_cast< OIdPropertyArrayUsageHelper< OTableColumnDescriptorWrapper >* >(this)->getArrayHelper(m_nColTypeID); 554 } 555 556 //------------------------------------------------------------------------------ 557 void OTableColumnDescriptorWrapper::getFastPropertyValue( Any& rValue, sal_Int32 nHandle ) const 558 { 559 if ( m_bPureWrap ) 560 { 561 rValue = m_xAggregate->getPropertyValue( impl_getPropertyNameFromHandle( nHandle ) ); 562 } 563 else 564 { 565 OColumnWrapper::getFastPropertyValue( rValue, nHandle ); 566 } 567 } 568 569 //------------------------------------------------------------------------------ 570 sal_Bool OTableColumnDescriptorWrapper::convertFastPropertyValue( Any & rConvertedValue, Any & rOldValue, sal_Int32 nHandle, const Any& rValue ) throw (IllegalArgumentException) 571 { 572 sal_Bool bModified(sal_False); 573 if ( m_bPureWrap ) 574 { 575 // do not delegate to OColumnWrapper: It would, for the properties which were registered with registerProperty, 576 // ask the OPropertyContainer base class, which is not what we want here. 577 // TODO: the whole "m_bPureWrap"-thingie is strange. We should have a dedicated class doing this wrapping, 578 // not a class which normally serves other purposes, and only sometimes does a "pure wrap". It makes the 579 // code unnecessarily hard to maintain, and error prone. 580 rOldValue = m_xAggregate->getPropertyValue( impl_getPropertyNameFromHandle( nHandle ) ); 581 if ( rOldValue != rValue ) 582 { 583 rConvertedValue = rValue; 584 bModified = sal_True; 585 } 586 } 587 else 588 { 589 bModified = OColumnWrapper::convertFastPropertyValue( rConvertedValue, rOldValue, nHandle, rValue ); 590 } 591 return bModified; 592 } 593 594 //------------------------------------------------------------------------------ 595 void OTableColumnDescriptorWrapper::setFastPropertyValue_NoBroadcast( 596 sal_Int32 nHandle, 597 const Any& rValue 598 ) 599 throw (Exception) 600 { 601 if ( m_bPureWrap ) 602 { 603 m_xAggregate->setPropertyValue( impl_getPropertyNameFromHandle( nHandle ), rValue ); 604 } 605 else 606 { 607 OColumnWrapper::setFastPropertyValue_NoBroadcast( nHandle, rValue ); 608 } 609 } 610 611 //============================================================ 612 //= OTableColumnWrapper 613 //============================================================ 614 //-------------------------------------------------------------------------- 615 OTableColumnWrapper::OTableColumnWrapper( const Reference< XPropertySet >& rCol, const Reference< XPropertySet >& _xColDefintion, 616 const bool _bPureWrap ) 617 :OTableColumnDescriptorWrapper( rCol, _bPureWrap, false ) 618 { 619 osl_incrementInterlockedCount( &m_refCount ); 620 if ( _xColDefintion.is() ) 621 { 622 try 623 { 624 ::comphelper::copyProperties( _xColDefintion, this ); 625 } 626 catch( const Exception& ) 627 { 628 DBG_UNHANDLED_EXCEPTION(); 629 } 630 } 631 osl_decrementInterlockedCount( &m_refCount ); 632 } 633 634 //-------------------------------------------------------------------------- 635 OTableColumnWrapper::~OTableColumnWrapper() 636 { 637 } 638 639 //-------------------------------------------------------------------------- 640 IMPLEMENT_GET_IMPLEMENTATION_ID( OTableColumnWrapper ) 641 642 //------------------------------------------------------------------------------ 643 rtl::OUString OTableColumnWrapper::getImplementationName( ) throw (RuntimeException) 644 { 645 return rtl::OUString::createFromAscii( "com.sun.star.sdb.OTableColumnWrapper" ); 646 } 647 648 //------------------------------------------------------------------------------ 649 Sequence< ::rtl::OUString > OTableColumnWrapper::getSupportedServiceNames( ) throw (RuntimeException) 650 { 651 Sequence< ::rtl::OUString > aSNS( 2 ); 652 aSNS[0] = SERVICE_SDBCX_COLUMN; 653 aSNS[1] = SERVICE_SDB_COLUMNSETTINGS; 654 return aSNS; 655 } 656 657 //------------------------------------------------------------------------------ 658 ::cppu::IPropertyArrayHelper& OTableColumnWrapper::getInfoHelper() 659 { 660 return *static_cast< OIdPropertyArrayUsageHelper< OTableColumnWrapper >* >(this)->getArrayHelper(m_nColTypeID); 661 } 662 663 // comphelper::OPropertyArrayUsageHelper 664 //------------------------------------------------------------------------------ 665 ::cppu::IPropertyArrayHelper* OTableColumnWrapper::createArrayHelper( sal_Int32 nId ) const 666 { 667 return OTableColumnDescriptorWrapper::createArrayHelper( nId ); 668 } 669 670