[Tizen][ATSPI] Accessibility initial implementation
[platform/core/uifw/dali-adaptor.git] / dali / dali-bridge / src / Accessible.cpp
1 #include "Common.hpp"
2
3 using namespace Dali::Accessibility;
4
5 std::vector< std::string > Accessible::GetInterfaces()
6 {
7   std::vector< std::string > tmp;
8   tmp.push_back( ATSPI_DBUS_INTERFACE_ACCESSIBLE );
9   if( dynamic_cast< Collection* >( this ) )
10     tmp.push_back( ATSPI_DBUS_INTERFACE_COLLECTION );
11   if( dynamic_cast< Text* >( this ) )
12     tmp.push_back( ATSPI_DBUS_INTERFACE_TEXT );
13   if( dynamic_cast< Value* >( this ) )
14     tmp.push_back( ATSPI_DBUS_INTERFACE_VALUE );
15   if( dynamic_cast< Component* >( this ) )
16     tmp.push_back( ATSPI_DBUS_INTERFACE_COMPONENT );
17   if( auto d = dynamic_cast< Action* >( this ) )
18   {
19     if( d->GetActionCount() > 0 )
20       tmp.push_back( ATSPI_DBUS_INTERFACE_ACTION );
21   }
22   return tmp;
23 }
24
25 thread_local std::atomic< Bridge* > threadLocalBridge{};
26 std::atomic< Bridge* > allThreads{};
27
28 Bridge* Bridge::GetCurrentBridge()
29 {
30   auto p = threadLocalBridge.load();
31   if( !p )
32     p = allThreads.load();
33   return p;
34 }
35
36 Accessible::Accessible()
37 {
38 }
39
40 Accessible::~Accessible()
41 {
42   auto b = bridgeData.lock();
43   if( b )
44     b->objects.erase( it );
45 }
46
47 void Bridge::MakePublic( Visibility vis )
48 {
49   bool res = false;
50   Bridge* expected = this;
51
52   switch( vis )
53   {
54     case Visibility::hidden:
55     {
56       threadLocalBridge.compare_exchange_strong( expected, nullptr );
57       allThreads.compare_exchange_strong( expected, nullptr );
58       break;
59     }
60     case Visibility::thisThreadOnly:
61     {
62       res = threadLocalBridge.exchange( this );
63       assert( !res );
64       break;
65     }
66     case Visibility::allThreads:
67     {
68       res = allThreads.exchange( this );
69       assert( !res );
70       break;
71     }
72   }
73 }
74
75 void Accessible::EmitShowing( bool showing )
76 {
77   if( auto b = GetBridgeData() )
78   {
79     b->bridge->EmitStateChanged( this, State::Showing, showing ? 1 : 0, 0 );
80   }
81 }
82
83 void Accessible::EmitVisible( bool visible )
84 {
85   if( auto b = GetBridgeData() )
86   {
87     b->bridge->EmitStateChanged( this, State::Visible, visible ? 1 : 0, 0 );
88   }
89 }
90
91 void Accessible::EmitHighlighted( bool set )
92 {
93   if( auto b = GetBridgeData() )
94   {
95     b->bridge->EmitStateChanged( this, State::Highlighted, set ? 1 : 0, 0 );
96   }
97 }
98
99 void Accessible::Emit( WindowEvent we, unsigned int detail1 )
100 {
101   if( auto b = GetBridgeData() )
102   {
103     b->bridge->Emit( this, we, detail1 );
104   }
105 }
106
107 std::vector< Accessible* > Accessible::GetChildren()
108 {
109   std::vector< Accessible* > tmp( GetChildCount() );
110   for( auto i = 0u; i < tmp.size(); ++i )
111   {
112     tmp[i] = GetChildAtIndex( i );
113   }
114   return tmp;
115 }
116
117 std::shared_ptr< Bridge::Data > Accessible::GetBridgeData()
118 {
119   auto b = bridgeData.lock();
120   if( !b )
121   {
122     auto p = Bridge::GetCurrentBridge();
123     if( !p )
124       return {};
125     b = p->data;
126   }
127   return b;
128 }
129
130 Address Accessible::GetAddress()
131 {
132   auto b = bridgeData.lock();
133   if( !b )
134   {
135     b = GetBridgeData();
136     assert( b );
137     b->bridge->RegisterOnBridge( this );
138   }
139   return {b->busName, b->root == this ? "root" : std::to_string( it->first )};
140 }
141
142 void Bridge::RegisterOnBridge( Accessible* obj )
143 {
144   assert( !obj->bridgeData.lock() || obj->bridgeData.lock() == data );
145   if( !obj->bridgeData.lock() )
146   {
147     assert( data );
148     auto oid = ++data->objectId;
149     obj->it = data->objects.insert( {oid, obj} ).first;
150     obj->bridgeData = data;
151   }
152 }
153
154 bool Accessible::IsProxy()
155 {
156   return false;
157 }