Difference between revisions of "NewModelViewArchitecture"

From CEGUI Wiki - Crazy Eddie's GUI System (Open Source)
Jump to: navigation, search
(List rendering)
(Add performance process)
Line 106: Line 106:
 
===Item(s) modified/isolated rendering===
 
===Item(s) modified/isolated rendering===
 
Triggered when some parts of the model changed, but not all.
 
Triggered when some parts of the model changed, but not all.
 +
 +
=Performance=
 +
We want to measure how well the new views perform compared to the old ones.
 +
 +
==Tested views/widgets==
 +
The following combinations of related views/widgets will be compared:
 +
* ListWidget, ListView - Listbox, ItemListbox
 +
* TreeView, TreeWidget - Tree
 +
 +
==Process==
 +
The process of measuring the performance will be the following:
 +
 +
For each view/widget
 +
* Insert 1000 items
 +
* Render
 +
* Clear list
 +
* Render
 +
* Insert 1001 items
 +
* Render
 +
* Delete first 150 items
 +
* Render
 +
* Repeat the following 17 times
 +
** Delete 13 items
 +
** Render
 +
* Delete last 123 items
 +
* Render
 +
* Clear list
 +
* Render
 +
* Insert 137 items
 +
* Render
 +
* Insert 10 items after the 100'th item
 +
* Render
 +
* Clear list
 +
* Render
 +
* Insert 1000 items
 +
* Render
 +
* Sort items
 +
* Render
 +
 +
For the tree-based views/widgets only:
 +
* Insert 100 root items, each with 100 items
 +
* Render
 +
* Expand all items
 +
* Render
 +
* Clear first 3 root item's children
 +
* Render
 +
* Sort
 +
* Render

Revision as of 19:29, 8 August 2014

Homepage for the WIP Model-View architecture for CEGUI widgets!

Introduction

The new architecture aims to unify the underlying implementation of several widgets so that they will use a common base model provider. This will involve a lot of ABI and API breakage.

Proposed architecture

ModelIndex

Identifies uniquely items in the model. This acts as a "dumb token" that it's entirely model's task to understand/process it.

Properties:

  • modelData : void *

ItemDataRole

This is an enum, that contains the types of data the model is requested to provide.

Enum members:

  • Text
  • ImageDecoration
  • Tooltip
  • <etc>
  • UserDefined (used as a base for user-defined custom roles)

ItemModel

The model for the view, that provides data like items count to the view. This is implemented by the developers that want to use this new architecture.

Structure-related methods:

  • childrenCount(modelIndex)
  • makeIndex(child, parentModelIndex)
  • getParentIndex(modelIndex)

Data-provider methods:

  • getData(modelIndex, role)

Events:

  • ChildrenAdded - startIndex, count
  • ChildrenRemoved - startIndex, count
  • ChildrenDataChanged - startIndex, count

TODO: Should we instead allow for a rectangular notification area? Like: startIndex / endIndex ?

ModelIndex Invalidation

Views might (read: will) store indices for a faster rendering or operations on the view. But these indices might become invalid if:

  • the underlying model instance changes (i.e.: model is set to another instance)
    • Solution: Just invalidate the memorized indices
  • an index from the "middle" is removed
    • Solution1: Create persistent model indices, like Qt does.
      • Con: too much management required, prone to errors.
    • Solution2: Query the model for validity
      • isValid will be moved to the ViewModel
    • Solution3: Other?

Affected widgets

Changed (to the new architecture) widgets

  • ComboBox + ComboDropList -> ComboView
  • Tree -> TreeView
  • ListBox -> ListView

New widgets

  • GridView
  • ListBoxWidget (combines model & view together for simple usage cases)

Removed/deprecated widgets

  • MultiColumnList (replaced by GridView)
  • ItemListbox (duplicated by ListBox)

To decide

  • ItemListBase
    • It's used in other places like: MenuBase and ScrolledItemListBase
    • Remove the other usages as well?

Workflow examples

List rendering

  • Create root model index (parent=0)
  • Query the number of children for root
  • For each child (value=[0, childrenCount))
    • Create child model index (parent=rootModelIndex)
    • Query the image to be displayed for child index (Role=Imagedecoration)
    • Draw image
    • Query the text to be displayed for child index (Role=text)
    • Draw text
  • Render non-child elements

Tree rendering

Full/first-time rendering

Triggered first time, or when whole model changes.

Recursive rendering procedure starting with a model index

  • > Given a parent model index
  • Query the number of children for index
  • For each child (value=[0, childrenCount))
    • Create child model index (parent=parentModelIndex)
    • Query the image to be displayed for child index (Role=imageDecoration)
    • Draw image
    • Query the text to be displayed for child index (Role=Text)
    • Draw text
    • Call procedure with child model index.

Actual rendering:

  • Call procedure defined above with root model index (parent = 0)
  • Render non-row elements

Item(s) modified/isolated rendering

Triggered when some parts of the model changed, but not all.

Performance

We want to measure how well the new views perform compared to the old ones.

Tested views/widgets

The following combinations of related views/widgets will be compared:

  • ListWidget, ListView - Listbox, ItemListbox
  • TreeView, TreeWidget - Tree

Process

The process of measuring the performance will be the following:

For each view/widget

  • Insert 1000 items
  • Render
  • Clear list
  • Render
  • Insert 1001 items
  • Render
  • Delete first 150 items
  • Render
  • Repeat the following 17 times
    • Delete 13 items
    • Render
  • Delete last 123 items
  • Render
  • Clear list
  • Render
  • Insert 137 items
  • Render
  • Insert 10 items after the 100'th item
  • Render
  • Clear list
  • Render
  • Insert 1000 items
  • Render
  • Sort items
  • Render

For the tree-based views/widgets only:

  • Insert 100 root items, each with 100 items
  • Render
  • Expand all items
  • Render
  • Clear first 3 root item's children
  • Render
  • Sort
  • Render