File: ExtendedTypeInfo

package info (click to toggle)
openscenegraph 2.8.3-5
  • links: PTS
  • area: main
  • in suites: squeeze
  • size: 33,968 kB
  • ctags: 30,935
  • sloc: cpp: 287,169; ansic: 9,050; sh: 654; yacc: 548; objc: 374; makefile: 264; lex: 151; perl: 119
file content (123 lines) | stat: -rw-r--r-- 4,467 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
/* -*-c++-*- OpenSceneGraph - Copyright (C) 1998-2006 Robert Osfield 
 *
 * This library is open source and may be redistributed and/or modified under  
 * the terms of the OpenSceneGraph Public License (OSGPL) version 0.0 or 
 * (at your option) any later version.  The full license is in LICENSE file
 * included with this distribution, and on the openscenegraph.org website.
 * 
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
 * OpenSceneGraph Public License for more details.
*/

#ifndef OSGINTROSPECTION_EXTENDEDTYPEINFO_
#define OSGINTROSPECTION_EXTENDEDTYPEINFO_

#include <typeinfo>
#include <string>
#include <osgIntrospection/type_traits>

namespace osgIntrospection
{
    /// This class is a wrapper for std::type_info that also records whether
    /// a type is a reference or const reference.  It permits osgIntrospection
    /// to make use of reference information that is ignored by typeid(), and
    /// to generate reference types based on it.  The ExtendedTypeInfo for a
    /// class can be produced via the extended_typeid() functions, analogous
    /// to typeid().
    ///
    class ExtendedTypeInfo
    {
    public:
        ExtendedTypeInfo(const std::type_info &ti, bool isReference, bool isConstReference) :
            _ti(&ti), _is_reference(isReference), _is_const_reference(isConstReference)
        {
        }

        /// Orders ExtendedTypeInfo based first on std::type_info, then on
        /// reference, then on const reference.  Note that we can't rely on
        /// default pointer comparison for std::type_info because it is not
        /// guaranteed that &typeid(T) always returns the same pointer for a
        /// given T (thanks Andrew Koenig).
        bool operator<(const ExtendedTypeInfo &other) const
        {
            if (_ti->before(*other._ti))
                return true;
            else if (other._ti->before(*_ti))
                return false;
            else if (_is_reference < other._is_reference)
                return true;
            else if (other._is_reference < _is_reference)
                return false;
            else
                return _is_const_reference < other._is_const_reference;
        }

        /// Returns true if *this and other are the same type.
        bool operator==(const ExtendedTypeInfo &other) const
        {
            return (*_ti == *other._ti &&
                    _is_reference == other._is_reference &&
                    _is_const_reference == other._is_const_reference);
        }

        /// Gets the std::type_info object for this type.
        const std::type_info &getStdTypeInfo() const
        {
            return *_ti;
        }

        /// Returns true if this type is a reference or const reference.
        bool isReference() const
        {
            return _is_reference;
        }

        /// Returns true if this type is a const reference.
        bool isConstReference() const
        {
            return _is_const_reference;
        }

        /// Returns the name of this type, based on the std::type_info name.
        std::string name() const
        {
            if (_is_const_reference)
                return std::string("const ") + _ti->name() + " &";
            else if (_is_reference)
                return std::string(_ti->name()) + " &";
            else
                return _ti->name();
        }

    private:
        const std::type_info *_ti;
        bool _is_reference;
        bool _is_const_reference;
    };
}

/// extended_typeid works like typeid, but returns an ExtendedTypeInfo.  This
/// version operates on expressions.
template <typename T>
osgIntrospection::ExtendedTypeInfo
extended_typeid(T)
{
  return osgIntrospection::ExtendedTypeInfo(typeid(T),
                                            is_reference<T>::value,
                                            is_const_reference<T>::value);
}

/// extended_typeid works like typeid, but returns an ExtendedTypeInfo.  This
/// version operates on types, which must be specified as a template parameter.
template <typename T>
osgIntrospection::ExtendedTypeInfo
extended_typeid()
{
  return osgIntrospection::ExtendedTypeInfo(typeid(T),
                                            is_reference<T>::value,
                                            is_const_reference<T>::value);
}

#endif