Merge "Add native render surface for wayland" into devel/master
[platform/core/uifw/dali-adaptor.git] / adaptors / base / performance-logging / networking / event / automation.cpp
1
2 /*
3  * Copyright (c) 2015 Samsung Electronics Co., Ltd.
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  *
17  */
18
19 // CLASS HEADER
20 #include "automation.h"
21
22 // EXTERNAL INCLUDES
23 #include <sstream>
24 #include <iomanip>
25 #include <stdio.h>
26 #include <dali/public-api/dali-core.h>
27 #include <dali/integration-api/debug.h>
28
29
30 namespace  // un-named namespace
31 {
32
33 const unsigned int MAX_SET_PROPERTY_STRING_LENGTH = 256; ///< maximum length of a set property command
34
35 class JsonPropertyValue
36 {
37 public:
38   JsonPropertyValue( const std::string& str )
39   {
40     std::size_t strLength = str.length();
41
42     mString.reserve( strLength );
43     for( std::size_t i = 0; i < strLength; ++i )
44     {
45       const char c = str[i];
46       if( (c != '[') && c != ']')
47       {
48         mString.push_back( c );
49       }
50     }
51
52   }
53   std::string GetString() const
54   {
55     return mString;
56   }
57   float GetFloat() const
58   {
59     return atof( mString.c_str() );
60   }
61   int GetInt()
62   {
63     return atoi( mString.c_str() );
64   }
65   bool GetBoolean()
66   {
67     return (GetInt() != 0);
68   }
69
70   Dali::Vector2 GetVector2()
71   {
72     Dali::Vector2 vec2;
73
74     int count = sscanf( mString.c_str(),"%f,%f",&vec2.x,&vec2.y );
75     if( count != 2 )
76     {
77       DALI_LOG_ERROR("Bad format\n");
78     }
79     return vec2;
80   }
81
82   Dali::Vector3 GetVector3()
83   {
84     Dali::Vector3 vec3;
85
86     int count = sscanf( mString.c_str(),"%f,%f,%f",&vec3.x,&vec3.y,&vec3.z );
87     if( count != 3 )
88     {
89       DALI_LOG_ERROR("Bad format\n");
90     }
91     return vec3;
92   }
93
94   Dali::Vector4 GetVector4()
95   {
96     Dali::Vector4 vec4;
97
98     int count = sscanf( mString.c_str(),"%f,%f,%f,%f", &vec4.x, &vec4.y, &vec4.z, &vec4.w );
99     if( count != 4 )
100     {
101       DALI_LOG_ERROR("Bad format\n");
102     }
103     return vec4;
104   }
105
106 private:
107   std::string mString;
108
109 };
110
111 void SetProperty( Dali::Handle handle, int propertyId, JsonPropertyValue& propertyValue )
112 {
113   Dali::Property::Type type = handle.GetPropertyType( propertyId );
114   switch( type )
115   {
116   case Dali::Property::FLOAT:
117   {
118     float val = propertyValue.GetFloat();
119     handle.SetProperty( propertyId, Dali::Property::Value( val ) );
120     break;
121   }
122   case Dali::Property::INTEGER:
123   {
124     int val = propertyValue.GetInt();
125     handle.SetProperty( propertyId, Dali::Property::Value( val ) );
126     break;
127   }
128   case Dali::Property::BOOLEAN:
129   {
130     bool val = propertyValue.GetBoolean();
131     handle.SetProperty( propertyId, Dali::Property::Value( val ) );
132     break;
133   }
134   case Dali::Property::STRING:
135   {
136     std::string str = propertyValue.GetString();
137     handle.SetProperty( propertyId, Dali::Property::Value( str ) );
138     break;
139   }
140   case Dali::Property::VECTOR2:
141   {
142     Dali::Vector2 val = propertyValue.GetVector2();
143     handle.SetProperty( propertyId, Dali::Property::Value( val ) );
144     break;
145   }
146   case Dali::Property::VECTOR3:
147   {
148     Dali::Vector3 val = propertyValue.GetVector3();
149     handle.SetProperty( propertyId, Dali::Property::Value( val ) );
150     break;
151   }
152   case Dali::Property::VECTOR4:
153   {
154     Dali::Vector4 val = propertyValue.GetVector4();
155     handle.SetProperty( propertyId, Dali::Property::Value( val ) );
156     break;
157   }
158   default:
159   {
160     break;
161   }
162   }
163 }
164
165 int SetProperties( const std::string& setPropertyMessage )
166 {
167   std::istringstream iss( setPropertyMessage );
168   std::string token;
169   getline( iss, token, '|' ); // swallow command name
170   while( getline( iss, token, '|' ) )
171   {
172     std::string actorId, propName, propValue;
173     if( token.compare( "---" ) != 0 )
174     {
175       std::istringstream propss( token );
176       getline( propss, actorId, ';' );
177       getline( propss, propName, ';' );
178       getline( propss, propValue );
179
180       Dali::Actor root = Dali::Stage::GetCurrent().GetRootLayer();
181       int id = atoi( actorId.c_str() );
182       Dali::Actor a = root.FindChildById( id );
183       if( a )
184       {
185         // lookup by name for custom properties
186         int propId = a.GetPropertyIndex( propName );
187         if( propId > 0 )
188         {
189           JsonPropertyValue pv( propValue );
190           SetProperty( a, propId, pv );
191         }
192
193       }
194     }
195   }
196
197   return 0;
198 }
199
200
201 }; //   un-named namespace
202
203 inline std::string Quote( const std::string& in )
204 {
205   return (std::string( "\"" ) + in + std::string( "\"" ));
206 }
207
208 template<class T>
209 std::string ToString( T i )
210 {
211   std::stringstream ss;
212   std::string s;
213   ss << i;
214   s = ss.str();
215
216   return s;
217 }
218
219
220 // currently rotations are output in Euler format ( may change)
221 void AppendPropertyNameAndValue( Dali::Handle handle, int propertyIndex, std::ostringstream& outputStream)
222 {
223   // get the property name and the value as a string
224   std::string propertyName( handle.GetPropertyName( propertyIndex ) );
225   Dali::Property::Value value = handle.GetProperty( propertyIndex );
226
227   // Apply quotes around the property name and the value.. "color", "1.3, 3.4, 2.6"
228   outputStream << "\"" << propertyName << "\"" << ",";
229   outputStream << "\"" << value << "\"";
230
231 }
232
233 bool ExcludeProperty( int propIndex )
234 {
235   return (propIndex == Dali::Actor::Property::NAME    ||
236
237       // all of these are repeat properties of values in vectors....
238       // We don't really need these in the UI
239       propIndex == Dali::Actor::Property::ANCHOR_POINT_X || propIndex == Dali::Actor::Property::ANCHOR_POINT_Y || propIndex == Dali::Actor::Property::ANCHOR_POINT_Z || propIndex == Dali::Actor::Property::PARENT_ORIGIN_X
240       || propIndex == Dali::Actor::Property::PARENT_ORIGIN_Y || propIndex == Dali::Actor::Property::PARENT_ORIGIN_Z || propIndex == Dali::Actor::Property::COLOR_RED || propIndex == Dali::Actor::Property::COLOR_GREEN
241       || propIndex == Dali::Actor::Property::COLOR_BLUE || propIndex == Dali::Actor::Property::COLOR_ALPHA|| propIndex == Dali::Actor::Property::POSITION_X || propIndex == Dali::Actor::Property::POSITION_Y
242       || propIndex == Dali::Actor::Property::POSITION_Z|| propIndex == Dali::Actor::Property::SIZE_WIDTH|| propIndex == Dali::Actor::Property::SIZE_HEIGHT || propIndex == Dali::Actor::Property::SCALE_X || propIndex == Dali::Actor::Property::SCALE_Y
243       || propIndex == Dali::Actor::Property::SCALE_Z || propIndex == Dali::Actor::Property::SIZE_DEPTH);
244 }
245
246 std::string DumpJson( Dali::Actor actor, int level )
247 {
248   // All the information about this actor
249   std::ostringstream msg;
250   msg << "{ " << Quote( "Name" ) << " : " << Quote( actor.GetName() ) << ", " << Quote( "level" ) << " : " << level << ", " << Quote( "id" ) << " : " << actor.GetId() << ", " << Quote( "IsVisible" )
251       << " : " << actor.IsVisible() << ", " << Quote( "IsSensitive" ) << " : " << actor.IsSensitive();
252
253   msg << ", " << Quote( "properties" ) << ": [ ";
254
255   Dali::Property::IndexContainer indices;
256   actor.GetPropertyIndices( indices );
257
258   Dali::Property::IndexContainer::Iterator iter = indices.Begin();
259   int numCustom = 0;
260   for( ; iter != indices.End() ; iter++ )
261   {
262     int i = *iter;
263     if( !ExcludeProperty( i ) )
264     {
265       if( numCustom++ != 0 )
266       {
267         msg << ", ";
268       }
269       msg << "[";
270
271       AppendPropertyNameAndValue( actor, i,msg );
272
273       msg << "]";
274     }
275   }
276   msg << "]";
277   msg << ", " << Quote( "children" ) << " : [ ";
278
279   // Recursively dump all the children as well
280   for( unsigned int i = 0 ; i < actor.GetChildCount() ; ++i )
281   {
282     if( i )
283     {
284       msg << " , ";
285     }
286     msg << DumpJson( actor.GetChildAt( i ), level + 1 );
287   }
288   msg << "] }";
289
290   return msg.str();
291 }
292
293 std::string GetActorTree()
294 {
295   Dali::Actor actor = Dali::Stage::GetCurrent().GetRootLayer();
296   std::string str = DumpJson( actor, 0 );
297   return str;
298 }
299 namespace Dali
300 {
301
302 namespace Internal
303 {
304
305 namespace Adaptor
306 {
307
308 namespace Automation
309 {
310
311 void SetProperty( const std::string& message )
312 {
313   // check the set property length is within range
314   if( message.length() > MAX_SET_PROPERTY_STRING_LENGTH )
315   {
316     DALI_LOG_ERROR("SetProperty message length too long, size = %ul\n", message.length());
317     return;
318   }
319
320   SetProperties( message );
321 }
322
323 void DumpScene( unsigned int clientId, ClientSendDataInterface* sendData )
324 {
325   char buf[32];
326   std::string json = GetActorTree();
327   int length = json.length();
328   snprintf( buf, 32, "%d\n", length );
329   std::string header( buf );
330   json = buf + json;
331   sendData->SendData( json.c_str(), json.length(), clientId );
332 }
333
334 } // namespace Automation
335
336 } // namespace Internal
337
338 } // namespace Adaptor
339
340 } // namespace Dali