Howto:Use Property Tree Objects: Difference between revisions

From FlightGear wiki
Jump to navigation Jump to search
mNo edit summary
Line 29: Line 29:


= Introducing: Property Objects =
= Introducing: Property Objects =
Moving us along the road to supporting better thread- and process- separation  
It's not really tenable to have pieces of the API frozen in perpetuity - whether next year or in ten years, things evolve - especially, since the property code was designed over a decade ago, multi-core machines have become rather common!
of the simulator elements, James has added  a first attempt at a 'propertyObject'.  
 
Moving us along the road to supporting better thread- and process- separation of the simulator elements, James has added  a first attempt at a 'propertyObject'.  


This is a template wrapper for SGPropertyNode*, with conversion operators  
This is a template wrapper for SGPropertyNode*, with conversion operators  

Revision as of 14:21, 30 May 2012

Background: Tied properties are problematic

There have been many issues reported due to tied properties, pretty much since the very beginning of tying. And even David Megginson himself suggested to abandon tying altogether. Even til today, tied properties still cause problems and error messages when re-initializing or terminating FlightGear.

There have been lots of discussions on phasing out tied properties completely, because using them often means that other features cannot work properly (think listeners, I/O protocols etc).

When David Megginson came up with the SGPropertyChangeListener API, he wanted it to be a viable alternative to tying, for these very reasons:

In particular, see David’s comments here, where he suggest to fefrain from binding/tying properties: http://www.mail-archive.com/flightgear-devel@flightgear.org/msg03176.html

Note that some of these threads are as old as 10+ years meanwhile, and there’s still tons of code making use of tying.

This is even though, people generally tend to suggest not to use tying:

More than a decade ago, tied properties were a performance hack. All the ideas of using the property tree for IPC between processes (i.e. using HLA) won’t work directly with tied properties.

If you really WANT tied properties, the same effect (but much cleaner) could be accomplished here by using a PropertyObject and extending the PropertyObject as required, for example by making it derive from SGPropertyChangeListener.

Introducing: Property Objects

It's not really tenable to have pieces of the API frozen in perpetuity - whether next year or in ten years, things evolve - especially, since the property code was designed over a decade ago, multi-core machines have become rather common!

Moving us along the road to supporting better thread- and process- separation of the simulator elements, James has added a first attempt at a 'propertyObject'.

This is a template wrapper for SGPropertyNode*, with conversion operators to/from the related primitive type.

#include <simgear/props/propertyObject.hxx>

simgear::PropertyObject<int> frameRate("/sim/rendering/fps");
int theFrameRate = frameRate; // maps to getIntValue
frameRate = 1234; // maps to setIntValue
if (frameRate == 789) {
 //...
}

and so on. (The std::string variant tries to convert nicely to char* too, where possible)

To the extent possible by C++, once you've declared a property object, you should be able to treat it exactly like a plain int/double/bool/string, but of course the actual storage is the property. (if you find areas where this falls down, of course let me know, or fix them)

The goal of the PropertyObject is that it's hard to use inefficiently - it lazily does the the property lookup, but caches the result.

It has another interesting feature, suggested by ThorstenB - if you try to read an invalid path, it doesn't silently succeed - it throws an exception! This is to avoid lurking typos in property paths, which has been an issue. (I will be adding a 'weak' variant, that takes a default value, for the cases where people want to read a property that might not exist)

Suggestions are most welcome - for example there's no read-only version at the moment, but there could be.

Apart from being a nicely short syntax, there is another goal - tied properties are a menace, for thread-safety, for un-tie-ing cleanly on subsystem shutdown, and for not firing change listeners. My hope here is to create something that has semantics that work in a multi-threaed or multi-process world - but which is as painless to use in code as a tied value. I think I've succeeded, but time will tell.

(One other thing I will be adding, probably to SGPropertyNode itself, is a nicer listener syntax, since I'm aware of various pieces of code that use tied setters as a value-changed notification - SGPropertyChangeListener is a rather cumbersome solution for this)

I'm not going to start converting tied properties to use propertyObjects next week, or next month, but certainly next year. The hope is that by that time, this code is mature, efficient and so on - so please try it, use it and fix it!