1/* 2 * Copyright 2010 Haiku Inc. All rights reserved. 3 * Distributed under the terms of the MIT License. 4 * 5 * Authors: 6 * Alex Wilson, yourpalal2@gmail.com 7 * 8 * Corresponds to: 9 * headers/os/interface/Layout.h rev 38207 10 * src/kits/interface/Layout.cpp rev 38207 11 */ 12 13 14/*! 15 \file Layout.h 16 \ingroup interface 17 \ingroup layout 18 \ingroup libbe 19 \brief Defines the BLayout class. 20*/ 21 22 23/*! 24 \class BLayout 25 \ingroup interface 26 \ingroup layout 27 \ingroup libbe 28 \brief The BLayout class provides an interface, and some basic 29 implementation to manage the positioning and sizing of BLayoutItem s. 30 31 BLayouts can be attached to a BView, managing the BLayoutItem's and 32 BView's that reside in that view, or can be nested within another 33 BLayout as a BLayoutItem. 34 35 Before adding a BLayoutItem to a BLayout, that layout must have a target 36 view. When a BLayout is attached directly to a BView via BView::SetLayout() 37 then that BView becomes the target of the layout. When a BLayout is nested 38 in another BLayout (via BLayout::AddItem()) the nested BLayout inherits the 39 target of the layout it's nested in, if it does not have a target already. 40 You can retrieve the target view for a layout with the TargetView() method. 41 When adding a BLayoutItem to a BLayout, the item's view (as returned by 42 BLayoutItem::View()) is added to the BLayout's target view. 43 44\code 45BView* topView = new BGroupView(); 46BLayout* topLayout = topView->GetLayout(); 47 48BLayout* nestedLayout = new BGroupLayout(B_HORIZONTAL); 49topLayout->AddItem(nestedLayout); 50 51BLayout* veryNestedLayout = new BGroupLayout(B_VERTICAL); 52nestedLayout->AddItem(veryNestedLayout); 53\endcode 54 55 After executing this code, \c veryNestedLayout, \c nestedLayout, and 56 \c topLayout all have the same target view: \c topView. 57 58 Continuing with the same objects... 59 60\code 61BLayout* nestedLayoutWithView = (new BGroupView())->GetLayout(); 62topLayout->AddItem(nestedLayoutWithView); 63\endcode 64 65 \c nestedLayoutWithView does have a target view of \c topView. This is 66 because \c nestedLayoutWithView is attached directly to a BView. 67 68 \warning This class is not yet finalized, if you use it in your software 69 assume that it will break some time in the future. 70*/ 71 72 73/*! 74 \fn BLayout::BLayout() 75 \brief Default constructor. 76 77 After this constructor has finished, this BLayout holds no 78 BLayoutItem's and does not have a target BView. 79 80 \warning Because a new BLayout does not have a target BView, calls to the 81 AddItem() and AddView() will fail methods will fail. 82*/ 83 84 85/*! 86 \fn BLayout::BLayout(BMessage* archive) 87 \brief Archive constructor. 88 89 \param archive The archive message. 90*/ 91 92 93/*! 94 \fn BLayout::~BLayout() 95 \brief Destructor, deletes all BLayoutItem's that this layout manages, 96 and detaches from this BLayout's owner view if there is one. 97 98 Each BLayoutItem's BView (as returned by BLayoutItem::View()) is also 99 removed from their parent. 100 101 \note Because nested BLayout's are treated as BLayoutItem's, 102 any layouts nested in this BLayout will be deleted. 103*/ 104 105 106/*! 107 \name BView targeting and attachment information. 108*/ 109 110 111//! @{ 112 113 114/*! 115 \fn BView* BLayout::Owner() const 116 \brief Returns the Owner of this layout, i.e. the view this layout manages. 117*/ 118 119 120/*! 121 \fn BView* BLayout::TargetView() const 122 \brief Returns the target view of this layout. 123 124 The target view of a layout becomes the parent of any BView's in this 125 layout, as well as the BView's returned by BLayoutItem::View() for 126 each BLayoutItem in this layout. 127*/ 128 129 130/*! 131 \fn BView* BLayout::View() 132 \brief Returns the same BView* as BLayout::Owner(), this method is 133 inherited from BLayoutItem. 134*/ 135 136 137//! @} 138 139 140/*! 141 \name Adding, removing, counting and accessing BLayout children 142*/ 143 144 145//! @{ 146 147 148/*! 149 \fn BLayoutItem* BLayout::AddView(BView* child) 150 \brief Creates a BLayoutItem to represent a BView, and adds that item to 151 this layout. 152 153 \a child is added to this BLayout's target view. 154 155 \returns The BLayoutItem created to represent \a child is, or \c NULL if 156 there was an error. 157 158 \param child The BView to be added to this BLayout. 159*/ 160 161 162/*! 163 \fn BLayoutItem* BLayout::AddView(int32 index, BView* child) 164 \brief Creates a BLayoutItem to represent \a child, and adds that item at 165 \a index to this layout. \a child is added to this BLayout's target view. 166*/ 167 168 169/*! 170 \fn bool BLayout::AddItem(BLayoutItem* item) 171 \brief Adds a BLayoutItem to this layout, and adds the BView it represents 172 to this BLayout's target view. 173 174 \param item The BLayoutItem to be added. 175 \retval true success 176 \retval false failure 177*/ 178 179 180/*! 181 \fn bool BLayout::AddItem(int32 index, BLayoutItem* item) 182 \brief Adds \a item to this layout, and adds the BView \a item represents 183 to this BLayout's target view. 184 185 \param item The BLayoutItem to be added. 186 \param index The index at which to add \c item. 187 188 If \a index is out of bounds, \a item will be added at the end. If \a index 189 is somewhere between the first and last indices, then items from \a index 190 to the end will be shuffled over by one. 191 192 \retval true success 193 \retval false failure 194*/ 195 196 197/*! 198 \fn bool BLayout::RemoveView(BView* child) 199 \brief Removes and deletes all BLayoutItem representing a BView from 200 this layout. 201 202 \param child The BView to be removed. 203 204 \retval true success 205 \retval false failure 206*/ 207 208 209/*! 210 \fn bool BLayout::RemoveItem(BLayoutItem* item) 211 \brief Removes a BLayoutItem from this layout, and also removes the view 212 it represents from this BLayout's target view. 213 214 \param item The BLayoutItem to be removed 215 216 \warning \a item is not deleted, you must delete it manually, or add it to 217 another BLayout. 218 \warning \a item->View(), even when it is removed from the target view, 219 is not deleted. If you want it deleted, you must delete it yourself! 220 221 \retval true success 222 \retval false failure 223*/ 224 225 226/*! 227 \fn BLayoutItem* BLayout::RemoveItem(int32 index) 228 \brief Remove the BLayoutItem at \a index. 229 230 \see RemoveItem(BLayoutItem*) 231 232 \returns The BLayoutItem that was removed. 233*/ 234 235 236/*! 237 \fn BLayoutItem* BLayout::ItemAt(int32 index) const 238 \brief Get the BLayoutItem at \a index. Returns \c NULL if \a index is 239 out of bounds. 240*/ 241 242 243/*! 244 \fn int32 BLayout::CountItems() const 245 \brief Get the number of BLayoutItem s in this layout. 246*/ 247 248 249/*! 250 \fn int32 BLayout::IndexOfItem(const BLayoutItem* item) const 251 \brief Get the index of a BLayoutItem in this layout. 252 253 \param item The BLayoutItem whose index you want. 254 255 \retval -1 \a item was not found in this BLayout. 256*/ 257 258 259/*! 260 \fn int32 BLayout::IndexOfView(BView* child) const 261 \brief Get the index of \a child in this layout. 262 263 \note This finds the index of views added through BLayout::AddView(), not 264 the index of an item which represents \a child that was added through 265 BLayout::AddItem(). 266*/ 267 268 269//! @} 270 271 272/*! 273 \name Subclass helpers. 274 \brief These methods are meant to ease the development of BLayout 275 subclasses. 276*/ 277 278 279//! @{ 280 281 282/*! 283 \fn bool BLayout::AncestorsVisible() const 284 \brief Get the visibility of the ancestors of this layout. 285 286 If a BLayout is connected to a BView, this will always return \c true. 287 If a BLayout is nested in another layout (it was passed to AddItem()), then 288 this will reflect the visibility of this BLayout's parent layout. If 289 any layout is hidden (by BLayout::SetVisible()) between this layout and its 290 target BView's layout, then this method will return \c false. 291*/ 292 293 294/*! 295 \fn BRect BLayout::LayoutArea() 296 \brief Returns the on-screen area this layout has received to lay out its 297 items in. 298 299 The return value is in the coordinate space of this BLayout's target 300 view. If this BLayout is attached directly to a BView, then 301 <tt> LayoutArea().LeftTop() == B_ORIGIN </tt>. 302*/ 303 304 305/*! 306 \fn void BLayout::VisibilityChanged(bool show) 307 \brief Method to be called by derived classes in their SetVisible() 308 implementation. Calls AncestorVisibilityChanged() on the items in this 309 BLayout. 310 311 \param show \c true to show, \c false to hide. 312*/ 313 314 315//! @} 316 317 318/*! 319 \name Methods triggering or related to laying out this BLayout. 320*/ 321 322 323//! @{ 324 325 326/*! 327 \fn void BLayout::Relayout(bool immediate = false) 328 \brief Request this BLayout to reposition and resize its items as required. 329 330 If \a immediate is \c false, and there is already a request to have the 331 window this layout resides in re-laid-out, then the layout will happen at 332 that time. If \a immediate is \c true, and there is no such pending 333 request, nor is this BLayout's parent layout in the process of laying 334 out its items, then this BLayout will now layout its items. 335 336 \param immediate Whether or not to Relayout immediately or wait for pending 337 requests first. 338*/ 339 340 341/*! 342 \fn void BLayout::LayoutItems(bool force = false) 343 \brief If there is no layout currently ongoing, and \a force is \c false, 344 creates a new BLayoutContext and calls the DoLayout() method 345 of this BLayout and any BLayout s nested in this BLayout. 346 347 This method also guarantees that the owner view of this layout (as returned 348 by BLayout::Owner()) performs a layout as well (if it is suitable to do so). 349 350 \param force Force the LayoutItems. 351*/ 352 353 354/*! 355 \fn BLayoutContext* BLayout::LayoutContext() const 356 \brief Returns the BLayoutContext this BLayout is currently operating in, 357 or \c NULL. 358*/ 359 360 361//! @} 362 363 364/*! 365 \name Invalidation and state mutators and accessors. 366*/ 367 368 369//! @{ 370 371 372/*! 373 \fn void BLayout::RequireLayout() 374 \brief Flag this layout as stale, i.e. any cached data may still be valid, 375 but the items need to be repositioned or resized. 376*/ 377 378 379/*! 380 \fn void BLayout::InvalidateLayout(bool children = false) 381 \brief Invalidate this layout and any cached data this layout has relating 382 to positioning and sizing of its items. 383 384 Invalidating a BLayout also invalidates the view it is connected to 385 (if there is one) and the BLayout this layout (or this BLayout's view) 386 resides in. 387 388 Although this method is virtual, you should not override it, override the 389 BLayout::LayoutInvalidated() hook instead. 390 391 This method should be called whenever the layout becomes invalid. This might 392 happen if the size constraints of an item in this layout change, this layout 393 is given more or less space than it previously had, or an object in this 394 layout has had its InvalidateLayout() method called. 395 396 \sa BView::InvalidateLayout(), BLayoutItem::InvalidateLayout(), 397 BLayout::LayoutInvalidated() 398*/ 399 400/*! 401 \fn bool BLayout::IsValid() 402 \brief Returns whether this layout has been invalidated (via 403 BLayout::InvalidateLayout()) and has not yet been validated (by doing a 404 layout, or by its ResetLayoutInvalidation() method. 405*/ 406 407 408/*! 409 \fn void BLayout::EnableLayoutInvalidation() 410 \brief Re-enable layout invalidation after a call to 411 DisableLayoutInvalidation(). 412*/ 413 414 415/*! 416 \fn void BLayout::DisableLayoutInvalidation() 417 \brief Disable layout invalidation notifications, i.e. calls to 418 this object's InvalidateLayout() method. 419*/ 420 421 422/*! 423 \fn void BLayout::ResetLayoutInvalidation() 424 \brief Reset layout invalidation, causing InvalidateLayout calls to proceed 425 again. This method should be called once any cached data has been 426 validated, or updated to valid values. 427*/ 428 429 430//! @} 431 432 433/*! 434 \name Archiving methods 435 \brief These methods relate to the archiving or unarchiving of this object 436 and the BLayoutItem's it contains 437*/ 438 439 440//! @{ 441 442 443/*! 444 \fn status_t BLayout::Archive(BMessage* archive, bool deep = true) const 445 \brief Archives this layout into \a archive. If deep is true, also archives 446 the items in this layout, calling ItemArchived() for each one. 447*/ 448 449 450/*! 451 \fn status_t BLayout::AllUnarchived(const BMessage* from) 452 \brief Unarchives the BLayoutItem's for this layout, calling 453 ItemUnarchived() for each one. 454*/ 455 456 457/*! 458 \fn status_t BLayout::ItemArchived(BMessage* into, BLayoutItem* item, 459 int32 index) const 460 \brief Hook for derived classes to add data specific to \a item to the 461 \a into BMessage. \a item resides at \a index. 462 463 \note The same archive is passed to BLayout::ItemArchived() for all items, 464 so any data added for each item will be stored in an array. 465*/ 466 467 468/*! 469 \fn status_t BLayout::ItemUnarchived(const BMessage* from, 470 BLayoutItem* item, int32 index) 471 \brief Hook for derived classes to retrieve data specific to \a item from 472 the \a from BMessage. \a item resides at \a index. 473 474 \note The same archive is passed to BLayout::ItemArchived() for all items, 475 so any data added for each item will be stored in an array. You should pass 476 \a index to the BMessage methods you will be using in this method. 477*/ 478 479 480//! @} 481 482 483/*! 484 \name BLayout Hook methods 485*/ 486 487 488//! @{ 489 490 491/*! 492 \fn bool BLayout::ItemAdded(BLayoutItem* item, int32 atIndex) 493 \brief Hook method called when \a item is added to this layout. 494 495 \param item The BLayoutItem that is being added. 496 \param atIndex The index of the BLayoutItem. 497 498 \retval true success 499 \retval false failure, \a item will not be added. 500 501 \note This is a good time to allocate data for a BLayoutItem and attach it 502 to \a item via BLayoutItem::SetLayoutData(). 503*/ 504 505 506/*! 507 \fn void BLayout::ItemRemoved(BLayoutItem* item, int32 fromIndex) 508 \brief Hook method called when \a item is removed from this layout. 509 510 \param item The BLayoutItem being removed. 511 \param fromIndex The index where \a item used to reside. 512 513 When this hook is called, \a item is not yet completely removed. It can 514 no longer be accessed with LayoutItemAt(), nor does it contribute to the 515 value of CountItems(), but the item has not yet had its ItemDetached() 516 hook called. 517 518 \note This is a good time to delete the data you've attached to \a item 519 via BLayoutItem::SetLayoutData(). 520*/ 521 522 523/*! 524 \fn void BLayout::DoLayout() = 0 525 \brief Implemented by derived classes to position and resize the items in 526 this layout. 527*/ 528 529 530/*! 531 \fn void BLayout::LayoutInvalidated(bool children) 532 533 Hook method called when this layout becomes invalid. This is a good place 534 to clear any caches your object might hold. 535 536 \param children Whether or not child layouts have also been invalidated. 537*/ 538 539 540/*! 541 \fn void BLayout::OwnerChanged(BView* was) 542 \brief Hook method called when this layout is attached to a BView. 543 544 \param was The previous owner of this BLayout, for new BLayout s, this 545 will be \c NULL. 546*/ 547 548 549/*! 550 \fn void BLayout::AttachedToLayout() 551 \brief Hook method inherited from BLayoutItem, classes derived from 552 BLayout must include the BLayout version of this method in their 553 implementation. 554*/ 555 556 557/*! 558 \fn void BLayout::DetachedFromLayout(BLayout* layout) 559 \brief Hook method inherited from BLayoutItem, classes derived from 560 BLayout must include the BLayout version of this method in their 561 implementation. 562 563 \param layout The BLayout that this BLayout was detached from. 564*/ 565 566 567/*! 568 \fn void BLayout::AncestorVisibilityChanged(bool shown) 569 \brief Hook method inherited from BLayoutItem, classes derived from 570 BLayout must include the BLayout version of this method in their 571 implementation. 572*/ 573 574 575//! @} 576