2 * Copyright (c) 2016 Samsung Electronics Co., Ltd.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
19 #include <pepper-dali/internal/object-impl.h>
22 #include <pepper-dali/internal/shell-client-impl.h>
23 #include <pepper-dali/internal/object-view-impl.h>
26 #include <dali/integration-api/debug.h>
27 #include <dali/public-api/images/buffer-image.h>
28 #include <dali/public-api/events/touch-event.h>
29 #include <dali/public-api/adaptor-framework/native-image-source.h>
30 #include <wayland-tbm-server.h>
44 #if defined(DEBUG_ENABLED)
45 Integration::Log::Filter* gPepperObjectLogging = Integration::Log::Filter::New( Debug::Verbose, false, "LOG_PEPPER_OBJECT" );
48 } // unnamed namespace
50 ObjectPtr Object::New( pepper_surface_t* surface, Pepper::Input input )
52 ObjectPtr impl = new Object();
54 // Second-phase init of the implementation
55 impl->Initialize( surface, input );
68 mSurfaceDestroyListener( NULL ),
69 mBufferDestroyListener( NULL ),
79 pepper_buffer_unreference( mBuffer );
80 pepper_event_listener_remove( mBufferDestroyListener );
83 if( mSurfaceDestroyListener )
85 pepper_event_listener_remove( mSurfaceDestroyListener );
89 void Object::Initialize( pepper_surface_t* surface, Pepper::Input input )
93 mPointer = input.GetPointer();
94 mKeyboard = input.GetKeyboard();
95 mTouch = input.GetTouch();
97 mSurfaceDestroyListener = pepper_object_add_event_listener( (pepper_object_t*)surface, PEPPER_EVENT_OBJECT_DESTROY, 0, Object::OnDestroySurface, this );
99 DALI_LOG_INFO( gPepperObjectLogging, Debug::Verbose, "Object::Initialize: success\n" );
102 bool Object::AttchBuffer( int* width, int* height )
104 pepper_buffer_t* buffer;
105 wl_resource* bufferResource;
106 wl_shm_buffer* shmBuffer = NULL;
107 tbm_surface_h tbmSurface = NULL;
108 int bufWidth, bufHeight;
110 buffer = pepper_surface_get_buffer( mSurface );
113 DALI_LOG_INFO( gPepperObjectLogging, Debug::General, "Object::AttchBuffer: pepper_surface_get_buffer is failed\n" );
119 pepper_buffer_unreference( mBuffer );
120 pepper_event_listener_remove( mBufferDestroyListener );
123 pepper_buffer_reference( buffer );
126 mBufferDestroyListener = pepper_object_add_event_listener( (pepper_object_t*)buffer, PEPPER_EVENT_OBJECT_DESTROY, 0, Object::OnDestroyBuffer, this );
128 bufferResource = pepper_buffer_get_resource( buffer );
132 mObjectView = Pepper::ObjectView::New();
134 mObjectView.TouchedSignal().Connect( this, &Object::OnTouched );
137 Pepper::GetImplementation( mObjectView ).SetSurface( mSurface );
139 // TODO: support multi touch, focus in/out, mouse in/out
141 // TODO: resize callback
143 Pepper::Object handle( this );
144 mObjectViewAddedSignal.Emit( handle, mObjectView );
147 shmBuffer = wl_shm_buffer_get( bufferResource );
150 bufWidth = wl_shm_buffer_get_width( shmBuffer );
151 bufHeight = wl_shm_buffer_get_height( shmBuffer );
153 if( shmBuffer != mShmBuffer )
155 // create a new image
156 PixelBuffer* pixelBuffer = static_cast< PixelBuffer* >( wl_shm_buffer_get_data( shmBuffer ) );
157 mBufferImage = BufferImage::New( pixelBuffer, bufWidth, bufHeight );
159 mObjectView.SetImage( mBufferImage );
161 mShmBuffer = shmBuffer;
166 tbmSurface = wayland_tbm_server_get_surface( NULL, bufferResource );
169 bufWidth = tbm_surface_get_width( tbmSurface );
170 bufHeight = tbm_surface_get_height( tbmSurface );
172 if ( tbmSurface != mTbmSurface )
174 // create a new image
175 NativeImageSourcePtr nativeImageSource = NativeImageSource::New( tbmSurface );
176 mNativeImage = NativeImage::New( *nativeImageSource );
178 mObjectView.SetImage( mNativeImage );
180 mTbmSurface = tbmSurface;
185 DALI_LOG_INFO( gPepperObjectLogging, Debug::General, "Object::AttchBuffer: Failed to get buffer\n" );
190 if( ( mWidth != bufWidth ) || ( mHeight != bufHeight ) )
196 mObjectView.SetSize( mWidth, mHeight );
209 DALI_LOG_INFO( gPepperObjectLogging, Debug::Verbose, "Object::AttchBuffer: this = %p, width = %d, height = %d", this, bufWidth, bufHeight );
214 Pepper::Object::ObjectSignalType& Object::ObjectViewAddedSignal()
216 return mObjectViewAddedSignal;
219 Pepper::Object::ObjectSignalType& Object::ObjectViewDeletedSignal()
221 return mObjectViewDeletedSignal;
224 bool Object::OnTouched( Actor actor, const TouchEvent& touchEvent )
226 const TouchPoint& point = touchEvent.GetPoint(0);
228 Pepper::Internal::ShellClientPtr shellClient = reinterpret_cast< Pepper::Internal::ShellClient* >( pepper_object_get_user_data( reinterpret_cast< pepper_object_t* >( mSurface ), pepper_surface_get_role( mSurface ) ) );
231 DALI_LOG_INFO( gPepperObjectLogging, Debug::General, "Object::OnTouched: shellClient is null. mSurface = %p\n", mSurface );
235 switch( point.state )
237 case TouchPoint::Down:
239 pepper_touch_add_point( mTouch, point.deviceId, point.local.x, point.local.y );
240 pepper_touch_send_down( mTouch, shellClient->GetView(), touchEvent.time, point.deviceId, point.local.x, point.local.y );
242 DALI_LOG_INFO( gPepperObjectLogging, Debug::Verbose, "Object::OnTouched: Touch Down (%.2f, %.2f) device = %d surface = %p\n", point.local.x, point.local.y, point.deviceId, mSurface );
247 pepper_touch_send_up( mTouch, shellClient->GetView(), touchEvent.time, point.deviceId );
248 pepper_touch_remove_point( mTouch, point.deviceId );
250 DALI_LOG_INFO( gPepperObjectLogging, Debug::Verbose, "Object::OnTouched: Touch Up (%.2f, %.2f) surface = %p\n", point.local.x, point.local.y, mSurface );
253 case TouchPoint::Motion:
255 pepper_touch_send_motion( mTouch, shellClient->GetView(), touchEvent.time, point.deviceId, point.local.x, point.local.y );
257 // DALI_LOG_INFO( gPepperObjectLogging, Debug::Verbose, "Object::OnTouched: Touch Motion (%.2f, %.2f)\n", point.local.x, point.local.y );
269 void Object::OnDestroySurface( pepper_event_listener_t* listener, pepper_object_t* pepperObject, uint32_t id, void* info, void* data )
271 Object* object = static_cast< Object* >( data );
273 Pepper::Object handle( object );
274 object->mObjectViewDeletedSignal.Emit( handle, object->mObjectView );
276 object->mSurface = NULL;
277 object->mTbmSurface = NULL;
279 if( object->mSurfaceDestroyListener )
281 pepper_event_listener_remove( object->mSurfaceDestroyListener );
285 void Object::OnDestroyBuffer( pepper_event_listener_t* listener, pepper_object_t* pepperObject, uint32_t id, void* info, void* data )
287 Object* object = static_cast< Object* >( data );
289 if( object->mBuffer )
291 pepper_buffer_unreference( object->mBuffer );
292 pepper_event_listener_remove( object->mBufferDestroyListener );
296 if( object->mShmBuffer )
298 void* shmData = wl_shm_buffer_get_data( object->mShmBuffer );
300 object->mBufferImage = BufferImage::New( object->mWidth, object->mHeight );
302 PixelBuffer* buffer = object->mBufferImage.GetBuffer();
303 memcpy(buffer, shmData, object->mWidth * object->mHeight * 4);
305 object->mBufferImage.Update();
307 object->mObjectView.SetImage( object->mBufferImage );
309 else if( object->mTbmSurface )
315 } // namespace Internal
317 } // namespace Pepper