Fix for screen flickering on page have lots of contents size change
[framework/web/webkit-efl.git] / Source / WebKit2 / UIProcess / API / efl / EwkViewImpl.cpp
1 /*
2    Copyright (C) 2011 Samsung Electronics
3    Copyright (C) 2012 Intel Corporation. All rights reserved.
4
5     This library is free software; you can redistribute it and/or
6     modify it under the terms of the GNU Library General Public
7     License as published by the Free Software Foundation; either
8     version 2 of the License, or (at your option) any later version.
9
10     This library is distributed in the hope that it will be useful,
11     but WITHOUT ANY WARRANTY; without even the implied warranty of
12     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13     Library General Public License for more details.
14
15     You should have received a copy of the GNU Library General Public License
16     along with this library; see the file COPYING.LIB.  If not, write to
17     the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
18     Boston, MA 02110-1301, USA.
19 */
20
21 #include "config.h"
22 #include "EwkViewImpl.h"
23
24 #include "EflScreenUtilities.h"
25 #include "FindClientEfl.h"
26 #include "FormClientEfl.h"
27 #include "InputMethodContextEfl.h"
28 #include "PageClientImpl.h"
29 #include "PageLoadClientEfl.h"
30 #include "PagePolicyClientEfl.h"
31 #include "PageUIClientEfl.h"
32 #if ENABLE(WAIT_UPVERSION)
33 #include "PageViewportController.h"
34 #include "PageViewportControllerClientEfl.h"
35 #endif
36 #include "ResourceLoadClientEfl.h"
37 #include "WKColorPickerResultListener.h"
38 #include "WKString.h"
39 #include "WebPageProxy.h"
40 #include "WebPopupMenuProxyEfl.h"
41 #include "ewk_back_forward_list_private.h"
42 #include "ewk_context_private.h"
43 #include "ewk_favicon_database_private.h"
44 #include "ewk_popup_menu_item_private.h"
45 #include "ewk_private.h"
46 #include "ewk_settings_private.h"
47 #include "ewk_view.h"
48 #include "ewk_view_private.h"
49 #include <Ecore_Evas.h>
50 #include <Edje.h>
51 #include <WebCore/Cursor.h>
52
53 #if OS(TIZEN)
54 #if ENABLE(TIZEN_GEOLOCATION)
55 #include "ewk_geolocation_private.h"
56 #endif
57 #if ENABLE(TIZEN_MEDIA_STREAM)
58 #include "ewk_user_media_private.h"
59 #endif
60 #if ENABLE(TIZEN_NOTIFICATIONS)
61 #include "ewk_notification_private.h"
62 #endif
63 #if ENABLE(TIZEN_WEBKIT2_CREATE_VIEW_WITH_CREATED_PAGE_GROUP_WITH_IDENTIFIER)
64 #include "WebPageGroup.h"
65 #endif
66 #if ENABLE(TIZEN_SUPPORT_WEBAPP_META_TAG)
67 #include "ewk_web_application_icon_data_private.h"
68 #endif
69 #endif
70
71 using namespace WebCore;
72 using namespace WebKit;
73
74 static const int defaultCursorSize = 16;
75
76 EwkViewImpl::PageViewMap EwkViewImpl::pageViewMap;
77
78 void EwkViewImpl::addToPageViewMap(const Evas_Object* ewkView)
79 {
80     EwkViewImpl* viewImpl = EwkViewImpl::fromEvasObject(ewkView);
81
82     PageViewMap::AddResult result = pageViewMap.add(viewImpl->wkPage(), ewkView);
83     ASSERT_UNUSED(result, result.isNewEntry);
84 }
85
86 void EwkViewImpl::removeFromPageViewMap(const Evas_Object* ewkView)
87 {
88     EwkViewImpl* viewImpl = EwkViewImpl::fromEvasObject(ewkView);
89
90     ASSERT(pageViewMap.contains(viewImpl->wkPage()));
91     pageViewMap.remove(viewImpl->wkPage());
92 }
93
94 const Evas_Object* EwkViewImpl::viewFromPageViewMap(const WKPageRef page)
95 {
96     ASSERT(page);
97
98     return pageViewMap.get(page);
99 }
100
101 #if ENABLE(TIZEN_WEBKIT2_CREATE_VIEW_WITH_CREATED_PAGE_GROUP_WITH_IDENTIFIER)
102 static uint64_t generatePageGroupIdentifierID()
103 {
104     static uint64_t uniquePageGroupIdentifierID = 1;
105     return uniquePageGroupIdentifierID++;
106 }
107 #endif
108
109 EwkViewImpl::EwkViewImpl(Evas_Object* view)
110     : popupMenuProxy(0)
111     , popupMenuItems(0)
112 #if USE(ACCELERATED_COMPOSITING)
113     , evasGl(0)
114     , evasGlContext(0)
115     , evasGlSurface(0)
116 #endif
117 #if OS(TIZEN)
118 #if ENABLE(TIZEN_ORIENTATION_EVENTS)
119     , orientation(0)
120 #endif
121     , javascriptGlobalContext(0)
122 #if ENABLE(TIZEN_SUPPORT_WEBAPP_META_TAG)
123     , webAppIconURLs(0)
124 #endif
125     , isWaitingForJavaScriptPopupReply(false)
126     , authChallenge(0)
127     , policyDecision(0)
128     , openPanelListener(0)
129 #if ENABLE(TIZEN_CERTIFICATE_HANDLING)
130     , certificatePolicyDecision(0)
131 #endif
132 #if ENABLE(TIZEN_MEDIA_STREAM)
133     , userMediaPermissionRequests(0)
134 #endif
135 #if ENABLE(TIZEN_GEOLOCATION)
136     , geolocation(0)
137     , geolocationPermissionRequests(0)
138 #endif
139     , suspendRequested(false)
140     , suspendedPainting(false)
141     , suspendedResources(false)
142 #if ENABLE(TIZEN_NOTIFICATIONS)
143     , notifications(0)
144     , notificationPermissionRequests(0)
145 #endif
146 #if ENABLE(TIZEN_SQL_DATABASE)
147     , exceededDatabaseQuota(0)
148 #endif
149 #if ENABLE(TIZEN_WEBKIT2_POPUP_INTERNAL)
150     , popupPicker(0)
151 #endif
152     , isVerticalEdge(false)
153     , isHorizontalEdge(false)
154 #if ENABLE(TIZEN_GESTURE)
155 #if ENABLE(TOUCH_EVENTS)
156     , exceedTouchMoveThreshold(false)
157     , wasHandledTouchStart(false)
158     , wasHandledTouchMove(false)
159 #endif
160     , holdHorizontalPanning(false)
161     , holdVerticalPanning(false)
162 #endif // #if ENABLE(TIZEN_GESTURE)
163 #if ENABLE(TIZEN_RUNTIME_BACKEND_SELECTION)
164     , compositionAnimator(0)
165 #endif
166 #if ENABLE(TIZEN_DATALIST_ELEMENT)
167     , dataList(0)
168 #endif
169 #if ENABLE(TIZEN_APPLICATION_CACHE)
170     , applicationCachePermissionOrigin(0)
171     , isWaitingForApplicationCachePermission(false)
172 #endif
173     , exceededQuotaOrigin(0)
174     , isWaitingForExceededQuotaPopupReply(false)
175 #endif // #if OS(TIZEN)
176     , m_view(view)
177     , m_settings(Ewk_Settings::create(this))
178     , m_mouseEventsEnabled(false)
179 #if ENABLE(TOUCH_EVENTS)
180     , m_touchEventsEnabled(false)
181 #endif
182     , m_displayTimer(this, &EwkViewImpl::displayTimerFired)
183     , m_inputMethodContext(InputMethodContextEfl::create(this, smartData()->base.evas))
184 #if OS(TIZEN)
185 #if USE(TILED_BACKING_STORE)
186     , m_scaleFactor(1)
187 #endif
188 #endif // #if OS(TIZEN)
189 {
190     ASSERT(view);
191
192     // Enable mouse events by default
193     setMouseEventsEnabled(true);
194
195 #if OS(TIZEN)
196     javascriptPopup = adoptPtr<JavaScriptPopup>(new JavaScriptPopup(m_view));
197     openPanel = adoptPtr<OpenPanel>(new OpenPanel(m_view));
198
199 #if ENABLE(TIZEN_INPUT_TAG_EXTENSION)
200     inputPicker = adoptPtr<InputPicker>(new InputPicker(m_view));
201 #endif
202
203 #if ENABLE(TIZEN_GESTURE)
204 #if ENABLE(TOUCH_EVENTS)
205     touchDownPoint.x = 0;
206     touchDownPoint.y = 0;
207 #endif
208 #endif
209
210 #if ENABLE(TIZEN_GESTURE)
211     gestureRecognizer = GestureRecognizer::create(m_view);
212     gestureClient = GestureClient::create(this);
213 #endif
214
215 #if ENABLE(TIZEN_WEBKIT2_TILED_SCROLLBAR)
216     const char* hideScrollbar = getenv("TIZEN_WEBKIT2_TILED_SCROLLBAR_HIDE");
217     if (hideScrollbar && atoi(hideScrollbar) == 1)
218         mainFrameScrollbarVisibility = false;
219     else
220         mainFrameScrollbarVisibility = true;
221 #endif
222
223 #if ENABLE(TIZEN_SCREEN_ORIENTATION_SUPPORT_INTERNAL)
224     orientationLock.callback = 0;
225     orientationLock.data = 0;
226 #endif
227
228 #if ENABLE(TIZEN_WEBKIT2_CREATE_VIEW_WITH_CREATED_PAGE_GROUP_WITH_IDENTIFIER)
229     String pageGroupIdentifierID = String::number(generatePageGroupIdentifierID());
230     String pageGroupIdentifier = String::format("PageGroup%s", pageGroupIdentifierID.utf8().data());
231
232     WKRetainPtr<WKStringRef> pageGroupIdentifierRef(AdoptWK, WKStringCreateWithUTF8CString(pageGroupIdentifier.utf8().data()));
233     pageGroup = WebPageGroup::create(toWTFString(pageGroupIdentifierRef.get()));
234 #endif
235 #endif // #if OS(TIZEN)
236 }
237
238 EwkViewImpl::~EwkViewImpl()
239 {
240     void* item;
241     EINA_LIST_FREE(popupMenuItems, item)
242         delete static_cast<Ewk_Popup_Menu_Item*>(item);
243
244 #if OS(TIZEN)
245     if (javascriptGlobalContext)
246         JSGlobalContextRelease(javascriptGlobalContext);
247
248 #if ENABLE(TIZEN_SUPPORT_WEBAPP_META_TAG)
249     if (webAppIconURLs) {
250         void* data = 0;
251         EINA_LIST_FREE(webAppIconURLs, data)
252             ewkWebAppIconDataDelete(static_cast<Ewk_Web_App_Icon_Data*>(data));
253     }
254 #endif
255
256     if (authChallenge)
257         ewkAuthChallengeDelete(authChallenge);
258     if (policyDecision)
259         ewkPolicyDecisionDelete(policyDecision);
260
261 #if ENABLE(TIZEN_CERTIFICATE_HANDLING)
262     if (certificatePolicyDecision)
263         ewkCertificatePolicyDecisionDelete(certificatePolicyDecision);
264 #endif
265
266 #if ENABLE(TIZEN_MEDIA_STREAM)
267     if (userMediaPermissionRequests)
268         ewkUserMediaDeletePermissionRequestList(userMediaPermissionRequests);
269 #endif
270
271 #if ENABLE(TIZEN_DATALIST_ELEMENT)
272     deleteDataList();
273 #endif
274
275 #if ENABLE(TIZEN_GEOLOCATION)
276     if (geolocation)
277         ewkGeolocationDeleteGeolocation(geolocation);
278     if (geolocationPermissionRequests)
279         ewkGeolocationDeletePermissionRequestList(geolocationPermissionRequests);
280 #endif
281
282 #if ENABLE(TIZEN_NOTIFICATIONS)
283     if (notifications)
284         ewkNotificationDeleteNotificationList(notifications);
285     if (notificationPermissionRequests)
286         ewkNotificationDeletePermissionRequestList(notificationPermissionRequests);
287 #endif
288
289 #if ENABLE(TIZEN_SQL_DATABASE)
290     if (exceededDatabaseQuota)
291         ewkContextDeleteExceededQuota(exceededDatabaseQuota);
292 #endif
293
294 #if ENABLE(TIZEN_RUNTIME_BACKEND_SELECTION)
295     if (compositionAnimator)
296         ecore_animator_del(compositionAnimator);
297 #endif
298
299 #if ENABLE(TIZEN_APPLICATION_CACHE)
300     if (applicationCachePermissionOrigin)
301         deleteSecurityOrigin(applicationCachePermissionOrigin);
302 #endif
303
304     if (exceededQuotaOrigin)
305         deleteSecurityOrigin(exceededQuotaOrigin);
306 #endif // #if OS(TIZEN)
307 }
308
309 Ewk_View_Smart_Data* EwkViewImpl::smartData() const
310 {
311     return static_cast<Ewk_View_Smart_Data*>(evas_object_smart_data_get(m_view));
312 }
313
314 EwkViewImpl* EwkViewImpl::fromEvasObject(const Evas_Object* view)
315 {
316     ASSERT(view);
317     Ewk_View_Smart_Data* sd = static_cast<Ewk_View_Smart_Data*>(evas_object_smart_data_get(view));
318     ASSERT(sd);
319     ASSERT(sd->priv);
320     return sd->priv;
321 }
322
323 /**
324  * @internal
325  * Retrieves the internal WKPage for this view.
326  */
327 WKPageRef EwkViewImpl::wkPage()
328 {
329     return toAPI(pageProxy.get());
330 }
331
332 void EwkViewImpl::setCursor(const Cursor& cursor)
333 {
334     Ewk_View_Smart_Data* sd = smartData();
335
336     const char* group = cursor.platformCursor();
337     if (!group || group == m_cursorGroup)
338         return;
339
340     m_cursorGroup = group;
341     m_cursorObject = adoptRef(edje_object_add(sd->base.evas));
342
343     Ecore_Evas* ecoreEvas = ecore_evas_ecore_evas_get(sd->base.evas);
344     if (!m_theme || !edje_object_file_set(m_cursorObject.get(), m_theme, group)) {
345         m_cursorObject.clear();
346
347         ecore_evas_object_cursor_set(ecoreEvas, 0, 0, 0, 0);
348 #ifdef HAVE_ECORE_X
349         if (WebCore::isUsingEcoreX(sd->base.evas))
350             WebCore::applyFallbackCursor(ecoreEvas, group);
351 #endif
352         return;
353     }
354
355     Evas_Coord width, height;
356     edje_object_size_min_get(m_cursorObject.get(), &width, &height);
357     if (width <= 0 || height <= 0)
358         edje_object_size_min_calc(m_cursorObject.get(), &width, &height);
359     if (width <= 0 || height <= 0) {
360         width = defaultCursorSize;
361         height = defaultCursorSize;
362     }
363     evas_object_resize(m_cursorObject.get(), width, height);
364
365     const char* data;
366     int hotspotX = 0;
367     data = edje_object_data_get(m_cursorObject.get(), "hot.x");
368     if (data)
369         hotspotX = atoi(data);
370
371     int hotspotY = 0;
372     data = edje_object_data_get(m_cursorObject.get(), "hot.y");
373     if (data)
374         hotspotY = atoi(data);
375
376     ecore_evas_object_cursor_set(ecoreEvas, m_cursorObject.get(), EVAS_LAYER_MAX, hotspotX, hotspotY);
377 }
378
379 void EwkViewImpl::displayTimerFired(WebCore::Timer<EwkViewImpl>*)
380 {
381     Ewk_View_Smart_Data* sd = smartData();
382
383     if (!sd->image)
384         return;
385
386 #if USE(COORDINATED_GRAPHICS)
387     EWK_VIEW_IMPL_GET_OR_RETURN(sd, viewImpl);
388 #endif
389
390     Region dirtyRegion;
391     for (Vector<IntRect>::iterator it = m_dirtyRects.begin(); it != m_dirtyRects.end(); ++it)
392         dirtyRegion.unite(*it);
393
394     m_dirtyRects.clear();
395
396     Vector<IntRect> rects = dirtyRegion.rects();
397     Vector<IntRect>::iterator end = rects.end();
398
399     for (Vector<IntRect>::iterator it = rects.begin(); it != end; ++it) {
400         IntRect rect = *it;
401 #if USE(COORDINATED_GRAPHICS)
402         evas_gl_make_current(viewImpl->evasGl, viewImpl->evasGlSurface, viewImpl->evasGlContext);
403         viewImpl->pageViewportControllerClient->display(rect, IntPoint(sd->view.x, sd->view.y));
404 #endif
405
406         evas_object_image_data_update_add(sd->image, rect.x(), rect.y(), rect.width(), rect.height());
407     }
408 }
409
410 void EwkViewImpl::redrawRegion(const IntRect& rect)
411 {
412     if (!m_displayTimer.isActive())
413         m_displayTimer.startOneShot(0);
414     m_dirtyRects.append(rect);
415 }
416
417 /**
418  * @internal
419  * A download for that view was cancelled.
420  *
421  * Emits signal: "download,cancelled" with pointer to a Ewk_Download_Job.
422  */
423 void EwkViewImpl::informDownloadJobCancelled(Ewk_Download_Job* download)
424 {
425     evas_object_smart_callback_call(m_view, "download,cancelled", download);
426 }
427
428 /**
429  * @internal
430  * A download for that view has failed.
431  *
432  * Emits signal: "download,failed" with pointer to a Ewk_Download_Job_Error.
433  */
434 void EwkViewImpl::informDownloadJobFailed(Ewk_Download_Job* download, Ewk_Error* error)
435 {
436     Ewk_Download_Job_Error downloadError = { download, error };
437     evas_object_smart_callback_call(m_view, "download,failed", &downloadError);
438 }
439
440 /**
441  * @internal
442  * A download for that view finished successfully.
443  *
444  * Emits signal: "download,finished" with pointer to a Ewk_Download_Job.
445  */
446 void EwkViewImpl::informDownloadJobFinished(Ewk_Download_Job* download)
447 {
448     evas_object_smart_callback_call(m_view, "download,finished", download);
449 }
450
451 /**
452  * @internal
453  * A new download has been requested for that view.
454  *
455  * Emits signal: "download,request" with pointer to a Ewk_Download_Job.
456  */
457 void EwkViewImpl::informDownloadJobRequested(Ewk_Download_Job* download)
458 {
459     evas_object_smart_callback_call(m_view, "download,request", download);
460 }
461
462 /**
463  * @internal
464  * informs that a form request is about to be submitted.
465  *
466  * Emits signal: "form,submission,request" with pointer to Ewk_Form_Submission_Request.
467  */
468 void EwkViewImpl::informNewFormSubmissionRequest(Ewk_Form_Submission_Request* request)
469 {
470     evas_object_smart_callback_call(m_view, "form,submission,request", request);
471 }
472
473 #if ENABLE(FULLSCREEN_API)
474 /**
475  * @internal
476  * Calls fullscreen_enter callback or falls back to default behavior and enables fullscreen mode.
477  */
478 void EwkViewImpl::enterFullScreen()
479 {
480     Ewk_View_Smart_Data* sd = smartData();
481
482     if (!sd->api->fullscreen_enter || !sd->api->fullscreen_enter(sd)) {
483         Ecore_Evas* ecoreEvas = ecore_evas_ecore_evas_get(sd->base.evas);
484         ecore_evas_fullscreen_set(ecoreEvas, true);
485     }
486
487 #if OS(TIZEN)
488     ewk_view_main_frame_scrollbar_visible_set(m_view, false);
489     evas_object_smart_callback_call(m_view, "fullscreen,enterfullscreen", 0);
490 #endif
491 }
492
493 /**
494  * @internal
495  * Calls fullscreen_exit callback or falls back to default behavior and disables fullscreen mode.
496  */
497 void EwkViewImpl::exitFullScreen()
498 {
499     Ewk_View_Smart_Data* sd = smartData();
500
501     if (!sd->api->fullscreen_exit || !sd->api->fullscreen_exit(sd)) {
502         Ecore_Evas* ecoreEvas = ecore_evas_ecore_evas_get(sd->base.evas);
503         ecore_evas_fullscreen_set(ecoreEvas, false);
504     }
505
506 #if OS(TIZEN)
507     ewk_view_main_frame_scrollbar_visible_set(m_view, true);
508     evas_object_smart_callback_call(m_view, "fullscreen,exitfullscreen", 0);
509 #endif
510 }
511 #endif
512
513 void EwkViewImpl::setImageData(void* imageData, const IntSize& size)
514 {
515     Ewk_View_Smart_Data* sd = smartData();
516     if (!imageData || !sd->image)
517         return;
518
519     evas_object_resize(sd->image, size.width(), size.height());
520     evas_object_image_size_set(sd->image, size.width(), size.height());
521     evas_object_image_data_copy_set(sd->image, imageData);
522 }
523
524 #if ENABLE(INPUT_TYPE_COLOR)
525 bool EwkViewImpl::setColorPickerColor(const WebCore::Color& color)
526 {
527     if (!m_colorPickerResultListener)
528         return false;
529
530     WKRetainPtr<WKStringRef> colorString(AdoptWK, WKStringCreateWithUTF8CString(color.serialized().utf8().data()));
531     WKColorPickerResultListenerSetColor(m_colorPickerResultListener.get(), colorString.get());
532     m_colorPickerResultListener.clear();
533
534     return true;
535 }
536 #endif
537
538 /**
539  * @internal
540  * informs load failed with error information.
541  *
542  * Emits signal: "load,error" with pointer to Ewk_Error.
543  */
544 void EwkViewImpl::informLoadError(Ewk_Error* error)
545 {
546     evas_object_smart_callback_call(m_view, "load,error", error);
547 }
548
549 /**
550  * @internal
551  * informs load finished.
552  *
553  * Emits signal: "load,finished".
554  */
555 void EwkViewImpl::informLoadFinished()
556 {
557     informURLChange();
558     evas_object_smart_callback_call(m_view, "load,finished", 0);
559
560 #if OS(TIZEN)
561 #if ENABLE(TIZEN_CSS_OVERFLOW_SCROLL_ACCELERATION)
562     pageProxy->setLoadingFinished(true);
563 #endif
564     if (pageClient->wasViewportFitsToContent())
565         pageClient->fitViewportToContent();
566
567 #if ENABLE(TIZEN_WEBKIT2_FORM_DATABASE)
568     ewk_view_form_password_data_fill(m_view);
569 #endif
570
571     if (!suspendRequested)
572         return;
573
574     suspendRequested = false;
575
576     if (!suspendedPainting) {
577         pageProxy->suspendPainting();
578         suspendedPainting = true;
579     }
580     if (!suspendedResources) {
581         pageProxy->suspendJavaScriptAndResource();
582         suspendedResources = true;
583     }
584 #endif
585 }
586
587 /**
588  * @internal
589  * informs load progress changed.
590  *
591  * Emits signal: "load,progress" with pointer to a double from 0.0 to 1.0.
592  */
593 void EwkViewImpl::informLoadProgress(double progress)
594 {
595     evas_object_smart_callback_call(m_view, "load,progress", &progress);
596 }
597
598 /**
599  * @internal
600  * informs view provisional load failed with error information.
601  *
602  * Emits signal: "load,provisional,failed" with pointer to Ewk_Error.
603  */
604 void EwkViewImpl::informProvisionalLoadFailed(Ewk_Error* error)
605 {
606     evas_object_smart_callback_call(m_view, "load,provisional,failed", error);
607 }
608
609 #if ENABLE(WAIT_UPVERSION)
610 #if USE(TILED_BACKING_STORE)
611 void EwkViewImpl::informLoadCommitted()
612 {
613     pageViewportController->didCommitLoad();
614 }
615 #endif
616 #endif
617
618 /**
619  * @internal
620  * informs view received redirect for provisional load.
621  *
622  * Emits signal: "load,provisional,redirect".
623  */
624 void EwkViewImpl::informProvisionalLoadRedirect()
625 {
626     informURLChange();
627     evas_object_smart_callback_call(m_view, "load,provisional,redirect", 0);
628 }
629
630 /**
631  * @internal
632  * informs view provisional load started.
633  *
634  * Emits signal: "load,provisional,started".
635  */
636 void EwkViewImpl::informProvisionalLoadStarted()
637 {
638 #if OS(TIZEN)
639     evas_object_smart_callback_call(m_view, "load,started", 0);
640 #endif
641
642 #if ENABLE(TIZEN_DRAG_SUPPORT)
643     if (pageClient->isDragMode())
644         pageClient->setDragMode(false);
645 #endif
646
647 #if ENABLE(TIZEN_CSS_OVERFLOW_SCROLL_ACCELERATION)
648     pageProxy->setLoadingFinished(false);
649 #endif
650
651     informURLChange();
652     evas_object_smart_callback_call(m_view, "load,provisional,started", 0);
653 }
654
655 /**
656  * @internal
657  * informs that a navigation policy decision should be taken.
658  *
659  * Emits signal: "policy,decision,navigation".
660  */
661 void EwkViewImpl::informNavigationPolicyDecision(Ewk_Navigation_Policy_Decision* decision)
662 {
663     evas_object_smart_callback_call(m_view, "policy,decision,navigation", decision);
664 }
665
666 /**
667  * @internal
668  * informs that a new window policy decision should be taken.
669  *
670  * Emits signal: "policy,decision,new,window".
671  */
672 void EwkViewImpl::informNewWindowPolicyDecision(Ewk_Navigation_Policy_Decision* decision)
673 {
674     evas_object_smart_callback_call(m_view, "policy,decision,new,window", decision);
675 }
676
677 /**
678  * @internal
679  * Load was initiated for a resource in the view.
680  *
681  * Emits signal: "resource,request,new" with pointer to resource request.
682  */
683 void EwkViewImpl::informResourceLoadStarted(Ewk_Resource* resource, Ewk_Url_Request* request)
684 {
685     Ewk_Resource_Request resourceRequest = {resource, request, 0};
686
687     evas_object_smart_callback_call(m_view, "resource,request,new", &resourceRequest);
688 }
689
690 /**
691  * @internal
692  * Received a response to a resource load request in the view.
693  *
694  * Emits signal: "resource,request,response" with pointer to resource response.
695  */
696 void EwkViewImpl::informResourceLoadResponse(Ewk_Resource* resource, Ewk_Url_Response* response)
697 {
698     Ewk_Resource_Load_Response resourceLoadResponse = {resource, response};
699     evas_object_smart_callback_call(m_view, "resource,request,response", &resourceLoadResponse);
700 }
701
702 /**
703  * @internal
704  * Failed loading a resource in the view.
705  *
706  * Emits signal: "resource,request,finished" with pointer to the resource load error.
707  */
708 void EwkViewImpl::informResourceLoadFailed(Ewk_Resource* resource, Ewk_Error* error)
709 {
710     Ewk_Resource_Load_Error resourceLoadError = {resource, error};
711     evas_object_smart_callback_call(m_view, "resource,request,failed", &resourceLoadError);
712 }
713
714 /**
715  * @internal
716  * Finished loading a resource in the view.
717  *
718  * Emits signal: "resource,request,finished" with pointer to the resource.
719  */
720 void EwkViewImpl::informResourceLoadFinished(Ewk_Resource* resource)
721 {
722     evas_object_smart_callback_call(m_view, "resource,request,finished", resource);
723 }
724
725 /**
726  * @internal
727  * Request was sent for a resource in the view.
728  *
729  * Emits signal: "resource,request,sent" with pointer to resource request and possible redirect response.
730  */
731 void EwkViewImpl::informResourceRequestSent(Ewk_Resource* resource, Ewk_Url_Request* request, Ewk_Url_Response* redirectResponse)
732 {
733     Ewk_Resource_Request resourceRequest = {resource, request, redirectResponse};
734     evas_object_smart_callback_call(m_view, "resource,request,sent", &resourceRequest);
735 }
736
737 /**
738  * @internal
739  * The view title was changed by the frame loader.
740  *
741  * Emits signal: "title,changed" with pointer to new title string.
742  */
743 void EwkViewImpl::informTitleChange(const String& title)
744 {
745     evas_object_smart_callback_call(m_view, "title,changed", const_cast<char*>(title.utf8().data()));
746 }
747
748 /**
749  * @internal
750  */
751 void EwkViewImpl::informTooltipTextChange(const String& text)
752 {
753     if (text.isEmpty())
754         evas_object_smart_callback_call(m_view, "tooltip,text,unset", 0);
755     else
756         evas_object_smart_callback_call(m_view, "tooltip,text,set", const_cast<char*>(text.utf8().data()));
757
758 }
759
760 /**
761  * @internal
762  * informs that the requested text was found.
763  *
764  * Emits signal: "text,found" with the number of matches.
765  */
766 void EwkViewImpl::informTextFound(unsigned matchCount)
767 {
768     evas_object_smart_callback_call(m_view, "text,found", &matchCount);
769 }
770
771 IntSize EwkViewImpl::size() const
772 {
773     int width, height;
774     evas_object_geometry_get(m_view, 0, 0, &width, &height);
775     return IntSize(width, height);
776 }
777
778 bool EwkViewImpl::isFocused() const
779 {
780     return evas_object_focus_get(m_view);
781 }
782
783 bool EwkViewImpl::isVisible() const
784 {
785     return evas_object_visible_get(m_view);
786 }
787
788 const char* EwkViewImpl::title() const
789 {
790     m_title = pageProxy->pageTitle().utf8().data();
791
792     return m_title;
793 }
794
795 /**
796  * @internal
797  * This function may return @c NULL.
798  */
799 InputMethodContextEfl* EwkViewImpl::inputMethodContext()
800 {
801     return m_inputMethodContext.get();
802 }
803
804 const char* EwkViewImpl::themePath() const
805 {
806     return m_theme;
807 }
808
809 void EwkViewImpl::setThemePath(const char* theme)
810 {
811     if (m_theme != theme) {
812         m_theme = theme;
813         pageProxy->setThemePath(theme);
814     }
815 }
816
817 const char* EwkViewImpl::customTextEncodingName() const
818 {
819     String customEncoding = pageProxy->customTextEncodingName();
820     if (customEncoding.isEmpty())
821         return 0;
822
823     m_customEncoding = customEncoding.utf8().data();
824
825     return m_customEncoding;
826 }
827
828 void EwkViewImpl::setCustomTextEncodingName(const char* encoding)
829 {
830     m_customEncoding = encoding;
831     pageProxy->setCustomTextEncodingName(encoding ? encoding : String());
832 }
833
834 void EwkViewImpl::setMouseEventsEnabled(bool enabled)
835 {
836     if (m_mouseEventsEnabled == enabled)
837         return;
838
839     m_mouseEventsEnabled = enabled;
840     if (enabled) {
841         Ewk_View_Smart_Data* sd = smartData();
842         evas_object_event_callback_add(m_view, EVAS_CALLBACK_MOUSE_DOWN, onMouseDown, sd);
843         evas_object_event_callback_add(m_view, EVAS_CALLBACK_MOUSE_UP, onMouseUp, sd);
844         evas_object_event_callback_add(m_view, EVAS_CALLBACK_MOUSE_MOVE, onMouseMove, sd);
845     } else {
846         evas_object_event_callback_del(m_view, EVAS_CALLBACK_MOUSE_DOWN, onMouseDown);
847         evas_object_event_callback_del(m_view, EVAS_CALLBACK_MOUSE_UP, onMouseUp);
848         evas_object_event_callback_del(m_view, EVAS_CALLBACK_MOUSE_MOVE, onMouseMove);
849     }
850 }
851
852 #if ENABLE(TOUCH_EVENTS)
853 void EwkViewImpl::setTouchEventsEnabled(bool enabled)
854 {
855     if (m_touchEventsEnabled == enabled)
856         return;
857
858     m_touchEventsEnabled = enabled;
859
860     if (enabled) {
861         // FIXME: We have to connect touch callbacks with mouse and multi events
862         // because the Evas creates mouse events for first touch and multi events
863         // for second and third touches. Below codes should be fixed when the Evas
864         // supports the touch events.
865         // See https://bugs.webkit.org/show_bug.cgi?id=97785 for details.
866         Ewk_View_Smart_Data* sd = smartData();
867         evas_object_event_callback_add(m_view, EVAS_CALLBACK_MOUSE_DOWN, onTouchDown, sd);
868         evas_object_event_callback_add(m_view, EVAS_CALLBACK_MOUSE_UP, onTouchUp, sd);
869         evas_object_event_callback_add(m_view, EVAS_CALLBACK_MOUSE_MOVE, onTouchMove, sd);
870         evas_object_event_callback_add(m_view, EVAS_CALLBACK_MULTI_DOWN, onTouchDown, sd);
871         evas_object_event_callback_add(m_view, EVAS_CALLBACK_MULTI_UP, onTouchUp, sd);
872         evas_object_event_callback_add(m_view, EVAS_CALLBACK_MULTI_MOVE, onTouchMove, sd);
873     } else {
874         evas_object_event_callback_del(m_view, EVAS_CALLBACK_MOUSE_DOWN, onTouchDown);
875         evas_object_event_callback_del(m_view, EVAS_CALLBACK_MOUSE_UP, onTouchUp);
876         evas_object_event_callback_del(m_view, EVAS_CALLBACK_MOUSE_MOVE, onTouchMove);
877         evas_object_event_callback_del(m_view, EVAS_CALLBACK_MULTI_DOWN, onTouchDown);
878         evas_object_event_callback_del(m_view, EVAS_CALLBACK_MULTI_UP, onTouchUp);
879         evas_object_event_callback_del(m_view, EVAS_CALLBACK_MULTI_MOVE, onTouchMove);
880     }
881 }
882 #endif
883
884 /**
885  * @internal
886  * Update the view's favicon and emits a "icon,changed" signal if it has
887  * changed.
888  *
889  * This function is called whenever the URL has changed or when the icon for
890  * the current page URL has changed.
891  */
892 void EwkViewImpl::informIconChange()
893 {
894     Ewk_Favicon_Database* iconDatabase = context->faviconDatabase();
895     ASSERT(iconDatabase);
896
897     m_faviconURL = ewk_favicon_database_icon_url_get(iconDatabase, m_url);
898     evas_object_smart_callback_call(m_view, "icon,changed", 0);
899 }
900
901 #if ENABLE(WEB_INTENTS)
902 /**
903  * @internal
904  * The view received a new intent request.
905  *
906  * Emits signal: "intent,request,new" with pointer to a Ewk_Intent.
907  */
908 void EwkViewImpl::informIntentRequest(Ewk_Intent* ewkIntent)
909 {
910     evas_object_smart_callback_call(m_view, "intent,request,new", ewkIntent);
911 }
912 #endif
913
914 #if ENABLE(WEB_INTENTS_TAG)
915 /**
916  * @internal
917  * The view received a new intent service registration.
918  *
919  * Emits signal: "intent,service,register" with pointer to a Ewk_Intent_Service.
920  */
921 void EwkViewImpl::informIntentServiceRegistration(Ewk_Intent_Service* ewkIntentService)
922 {
923     evas_object_smart_callback_call(m_view, "intent,service,register", ewkIntentService);
924 }
925 #endif // ENABLE(WEB_INTENTS_TAG)
926
927 #if USE(ACCELERATED_COMPOSITING)
928 bool EwkViewImpl::createGLSurface(const IntSize& viewSize)
929 {
930     Ewk_View_Smart_Data* sd = smartData();
931
932     Evas_GL_Config evasGlConfig = {
933         EVAS_GL_RGBA_8888,
934         EVAS_GL_DEPTH_BIT_8,
935         EVAS_GL_STENCIL_NONE,
936         EVAS_GL_OPTIONS_NONE,
937         EVAS_GL_MULTISAMPLE_NONE
938     };
939
940     ASSERT(!evasGlSurface);
941     evasGlSurface = evas_gl_surface_create(evasGl, &evasGlConfig, viewSize.width(), viewSize.height());
942     if (!evasGlSurface)
943         return false;
944
945     Evas_Native_Surface nativeSurface;
946     evas_gl_native_surface_get(evasGl, evasGlSurface, &nativeSurface);
947     evas_object_image_native_surface_set(sd->image, &nativeSurface);
948
949     return true;
950 }
951
952 bool EwkViewImpl::enterAcceleratedCompositingMode()
953 {
954     if (evasGl) {
955         EINA_LOG_DOM_WARN(_ewk_log_dom, "Accelerated compositing mode already entered.");
956         return false;
957     }
958
959     Evas* evas = evas_object_evas_get(m_view);
960     evasGl = evas_gl_new(evas);
961     if (!evasGl)
962         return false;
963
964     evasGlContext = evas_gl_context_create(evasGl, 0);
965     if (!evasGlContext) {
966         evas_gl_free(evasGl);
967         evasGl = 0;
968         return false;
969     }
970
971     if (!createGLSurface(size())) {
972         evas_gl_context_destroy(evasGl, evasGlContext);
973         evasGlContext = 0;
974
975         evas_gl_free(evasGl);
976         evasGl = 0;
977         return false;
978     }
979
980 #if ENABLE(WAIT_UPVERSION)
981     pageViewportControllerClient->setRendererActive(true);
982 #endif
983     return true;
984 }
985
986 bool EwkViewImpl::exitAcceleratedCompositingMode()
987 {
988     EINA_SAFETY_ON_NULL_RETURN_VAL(evasGl, false);
989
990     if (evasGlSurface) {
991         evas_gl_surface_destroy(evasGl, evasGlSurface);
992         evasGlSurface = 0;
993     }
994
995     if (evasGlContext) {
996         evas_gl_context_destroy(evasGl, evasGlContext);
997         evasGlContext = 0;
998     }
999
1000     evas_gl_free(evasGl);
1001     evasGl = 0;
1002
1003     return true;
1004 }
1005 #endif
1006
1007 #if ENABLE(INPUT_TYPE_COLOR)
1008 /**
1009  * @internal
1010  * Requests to show external color picker.
1011  */
1012 void EwkViewImpl::requestColorPicker(int r, int g, int b, int a, WKColorPickerResultListenerRef listener)
1013 {
1014     Ewk_View_Smart_Data* sd = smartData();
1015     EINA_SAFETY_ON_NULL_RETURN(sd->api->input_picker_color_request);
1016
1017     m_colorPickerResultListener = listener;
1018
1019     sd->api->input_picker_color_request(sd, r, g, b, a);
1020 }
1021
1022 /**
1023  * @internal
1024  * Requests to hide external color picker.
1025  */
1026 void EwkViewImpl::dismissColorPicker()
1027 {
1028     Ewk_View_Smart_Data* sd = smartData();
1029     EINA_SAFETY_ON_NULL_RETURN(sd->api->input_picker_color_dismiss);
1030
1031     m_colorPickerResultListener.clear();
1032
1033     sd->api->input_picker_color_dismiss(sd);
1034 }
1035 #endif
1036
1037 /**
1038  * @internal
1039  * informs that the view's back / forward list has changed.
1040  *
1041  * Emits signal: "back,forward,list,changed".
1042  */
1043 void EwkViewImpl::informBackForwardListChange()
1044 {
1045     evas_object_smart_callback_call(m_view, "back,forward,list,changed", 0);
1046 }
1047
1048 /**
1049  * @internal
1050  * Web process has crashed.
1051  *
1052  * Emits signal: "webprocess,crashed" with pointer to crash handling boolean.
1053  */
1054 void EwkViewImpl::informWebProcessCrashed()
1055 {
1056     bool handled = false;
1057     evas_object_smart_callback_call(m_view, "webprocess,crashed", &handled);
1058
1059     if (!handled) {
1060         CString url = pageProxy->urlAtProcessExit().utf8();
1061         WARN("WARNING: The web process experienced a crash on '%s'.\n", url.data());
1062
1063         // Display an error page
1064         ewk_view_html_string_load(m_view, "The web process has crashed.", 0, url.data());
1065     }
1066 }
1067
1068 void EwkViewImpl::informContentsSizeChange(const IntSize& size)
1069 {
1070 #if USE(COORDINATED_GRAPHICS)
1071     pageViewportControllerClient->didChangeContentsSize(size);
1072 #else
1073     UNUSED_PARAM(size);
1074 #endif
1075 }
1076
1077 COMPILE_ASSERT_MATCHING_ENUM(EWK_TEXT_DIRECTION_RIGHT_TO_LEFT, RTL);
1078 COMPILE_ASSERT_MATCHING_ENUM(EWK_TEXT_DIRECTION_LEFT_TO_RIGHT, LTR);
1079
1080 #if ENABLE(TIZEN_MULTIPLE_SELECT)
1081 void EwkViewImpl::requestPopupMenu(WebPopupMenuProxyEfl* popupMenu, const IntRect& rect, TextDirection textDirection, double pageScaleFactor, const Vector<WebPopupItem>& items, int32_t selectedIndex, bool multiple)
1082 #else
1083 void EwkViewImpl::requestPopupMenu(WebPopupMenuProxyEfl* popupMenu, const IntRect& rect, TextDirection textDirection, double pageScaleFactor, const Vector<WebPopupItem>& items, int32_t selectedIndex)
1084 #endif
1085 {
1086     Ewk_View_Smart_Data* sd = smartData();
1087     ASSERT(sd->api);
1088
1089     ASSERT(popupMenu);
1090
1091 #if ENABLE(TIZEN_MULTIPLE_SELECT)
1092     if (multiple ? !sd->api->multiple_popup_menu_show : !sd->api->popup_menu_show)
1093 #else
1094     if (!sd->api->popup_menu_show)
1095 #endif
1096         return;
1097
1098     if (popupMenuProxy)
1099         ewk_view_popup_menu_close(m_view);
1100     popupMenuProxy = popupMenu;
1101
1102     Eina_List* popupItems = 0;
1103     const size_t size = items.size();
1104     for (size_t i = 0; i < size; ++i)
1105         popupItems = eina_list_append(popupItems, Ewk_Popup_Menu_Item::create(items[i]).leakPtr());
1106     popupMenuItems = popupItems;
1107
1108 #if ENABLE(TIZEN_WEBKIT2_POPUP_INTERNAL)
1109 #if ENABLE(TIZEN_MULTIPLE_SELECT)
1110     if (multiple ? sd->api->multiple_popup_menu_show(sd, rect, static_cast<Ewk_Text_Direction>(textDirection), pageScaleFactor, popupMenuItems)
1111         : sd->api->popup_menu_show(sd, rect, static_cast<Ewk_Text_Direction>(textDirection), pageScaleFactor, popupMenuItems, selectedIndex)) {
1112 #else
1113     if (sd->api->popup_menu_show(sd, rect, static_cast<Ewk_Text_Direction>(textDirection), pageScaleFactor, popupMenuItems, selectedIndex)) {
1114 #endif
1115         /* maps.google.com generate mouse event in touch down without preventDefault.
1116          * So, popup menu is opend in touch down event and closed via fake mouse down
1117          * which generated by endTap.
1118          * In order to fix select of maps.google.com (based on touch behavior),
1119          * We should disable touch events when select popup is open.
1120          */
1121
1122 #if ENABLE(TIZEN_GESTURE)
1123         gestureClient->reset();
1124 #endif
1125         ewk_view_touch_events_enabled_set(m_view, false);
1126     }
1127 #else
1128     sd->api->popup_menu_show(sd, rect, static_cast<Ewk_Text_Direction>(textDirection), pageScaleFactor, popupItems, selectedIndex);
1129 #endif
1130 }
1131
1132 /**
1133  * @internal
1134  * Calls a smart member function for javascript alert().
1135  */
1136 void EwkViewImpl::requestJSAlertPopup(const WKEinaSharedString& message)
1137 {
1138     Ewk_View_Smart_Data* sd = smartData();
1139     ASSERT(sd->api);
1140
1141     if (!sd->api->run_javascript_alert)
1142         return;
1143
1144     sd->api->run_javascript_alert(sd, message);
1145 }
1146
1147 /**
1148  * @internal
1149  * Calls a smart member function for javascript confirm() and returns a value from the function. Returns false by default.
1150  */
1151 bool EwkViewImpl::requestJSConfirmPopup(const WKEinaSharedString& message)
1152 {
1153     Ewk_View_Smart_Data* sd = smartData();
1154     ASSERT(sd->api);
1155
1156     if (!sd->api->run_javascript_confirm)
1157         return false;
1158
1159     return sd->api->run_javascript_confirm(sd, message);
1160 }
1161
1162 /**
1163  * @internal
1164  * Calls a smart member function for javascript prompt() and returns a value from the function. Returns null string by default.
1165  */
1166 WKEinaSharedString EwkViewImpl::requestJSPromptPopup(const WKEinaSharedString& message, const WKEinaSharedString& defaultValue)
1167 {
1168     Ewk_View_Smart_Data* sd = smartData();
1169     ASSERT(sd->api);
1170
1171     if (!sd->api->run_javascript_prompt)
1172         return WKEinaSharedString();
1173
1174     return WKEinaSharedString::adopt(sd->api->run_javascript_prompt(sd, message, defaultValue));
1175 }
1176
1177 #if ENABLE(SQL_DATABASE)
1178 /**
1179  * @internal
1180  * Calls exceeded_database_quota callback or falls back to default behavior returns default database quota.
1181  */
1182 unsigned long long EwkViewImpl::informDatabaseQuotaReached(const String& databaseName, const String& displayName, unsigned long long currentQuota, unsigned long long currentOriginUsage, unsigned long long currentDatabaseUsage, unsigned long long expectedUsage)
1183 {
1184     Ewk_View_Smart_Data* sd = smartData();
1185     ASSERT(sd->api);
1186
1187     static const unsigned long long defaultQuota = 5 * 1024 * 1204; // 5 MB
1188     if (sd->api->exceeded_database_quota)
1189         return sd->api->exceeded_database_quota(sd, databaseName.utf8().data(), displayName.utf8().data(), currentQuota, currentOriginUsage, currentDatabaseUsage, expectedUsage);
1190
1191     return defaultQuota;
1192 }
1193 #endif
1194
1195 /**
1196  * @internal
1197  * The url of view was changed by the frame loader.
1198  *
1199  * Emits signal: "url,changed" with pointer to new url string.
1200  */
1201 void EwkViewImpl::informURLChange()
1202 {
1203     String activeURL = pageProxy->activeURL();
1204     if (activeURL.isEmpty())
1205         return;
1206
1207     CString rawActiveURL = activeURL.utf8();
1208     if (m_url == rawActiveURL.data())
1209         return;
1210
1211     m_url = rawActiveURL.data();
1212     const char* callbackArgument = static_cast<const char*>(m_url);
1213     evas_object_smart_callback_call(m_view, "url,changed", const_cast<char*>(callbackArgument));
1214 #if OS(TIZEN)
1215     evas_object_smart_callback_call(m_view, "uri,changed", const_cast<char*>(callbackArgument));
1216 #endif
1217
1218     // Update the view's favicon.
1219     informIconChange();
1220 }
1221
1222 WKPageRef EwkViewImpl::createNewPage()
1223 {
1224     Evas_Object* newEwkView = 0;
1225     evas_object_smart_callback_call(m_view, "create,window", &newEwkView);
1226
1227     if (!newEwkView)
1228         return 0;
1229
1230     EwkViewImpl* newViewImpl = EwkViewImpl::fromEvasObject(newEwkView);
1231     ASSERT(newViewImpl);
1232
1233     return static_cast<WKPageRef>(WKRetain(newViewImpl->page()));
1234 }
1235
1236 void EwkViewImpl::closePage()
1237 {
1238     evas_object_smart_callback_call(m_view, "close,window", 0);
1239 }
1240
1241 void EwkViewImpl::onMouseDown(void* data, Evas*, Evas_Object*, void* eventInfo)
1242 {
1243     Evas_Event_Mouse_Down* downEvent = static_cast<Evas_Event_Mouse_Down*>(eventInfo);
1244     Ewk_View_Smart_Data* sd = static_cast<Ewk_View_Smart_Data*>(data);
1245     EINA_SAFETY_ON_NULL_RETURN(sd->api);
1246     EINA_SAFETY_ON_NULL_RETURN(sd->api->mouse_down);
1247     sd->api->mouse_down(sd, downEvent);
1248 }
1249
1250 void EwkViewImpl::onMouseUp(void* data, Evas*, Evas_Object*, void* eventInfo)
1251 {
1252     Evas_Event_Mouse_Up* upEvent = static_cast<Evas_Event_Mouse_Up*>(eventInfo);
1253     Ewk_View_Smart_Data* sd = static_cast<Ewk_View_Smart_Data*>(data);
1254     EINA_SAFETY_ON_NULL_RETURN(sd->api);
1255     EINA_SAFETY_ON_NULL_RETURN(sd->api->mouse_up);
1256     sd->api->mouse_up(sd, upEvent);
1257 }
1258
1259 void EwkViewImpl::onMouseMove(void* data, Evas*, Evas_Object*, void* eventInfo)
1260 {
1261     Evas_Event_Mouse_Move* moveEvent = static_cast<Evas_Event_Mouse_Move*>(eventInfo);
1262     Ewk_View_Smart_Data* sd = static_cast<Ewk_View_Smart_Data*>(data);
1263     EINA_SAFETY_ON_NULL_RETURN(sd->api);
1264     EINA_SAFETY_ON_NULL_RETURN(sd->api->mouse_move);
1265     sd->api->mouse_move(sd, moveEvent);
1266 }
1267
1268 #if ENABLE(TOUCH_EVENTS)
1269 void EwkViewImpl::feedTouchEvents(Ewk_Touch_Event_Type type)
1270 {
1271     Ewk_View_Smart_Data* sd = smartData();
1272
1273     unsigned count = evas_touch_point_list_count(sd->base.evas);
1274     if (!count)
1275         return;
1276
1277     Eina_List* points = 0;
1278     for (unsigned i = 0; i < count; ++i) {
1279         Ewk_Touch_Point* point = new Ewk_Touch_Point;
1280         point->id = evas_touch_point_list_nth_id_get(sd->base.evas, i);
1281         evas_touch_point_list_nth_xy_get(sd->base.evas, i, &point->x, &point->y);
1282         point->state = evas_touch_point_list_nth_state_get(sd->base.evas, i);
1283 #if ENABLE(TOUCH_EVENTS) && ENABLE(TIZEN_GESTURE)
1284         if (type == EWK_TOUCH_CANCEL)
1285             point->state = EVAS_TOUCH_POINT_CANCEL;
1286 #endif
1287         points = eina_list_append(points, point);
1288     }
1289
1290     ewk_view_feed_touch_event(m_view, type, points, evas_key_modifier_get(sd->base.evas));
1291
1292     void* data;
1293     EINA_LIST_FREE(points, data)
1294         delete static_cast<Ewk_Touch_Point*>(data);
1295 }
1296
1297 void EwkViewImpl::onTouchDown(void* /* data */, Evas* /* canvas */, Evas_Object* ewkView, void* /* eventInfo */)
1298 {
1299     EwkViewImpl* viewImpl = EwkViewImpl::fromEvasObject(ewkView);
1300     viewImpl->feedTouchEvents(EWK_TOUCH_START);
1301 }
1302
1303 void EwkViewImpl::onTouchUp(void* /* data */, Evas* /* canvas */, Evas_Object* ewkView, void* /* eventInfo */)
1304 {
1305     EwkViewImpl* viewImpl = EwkViewImpl::fromEvasObject(ewkView);
1306     viewImpl->feedTouchEvents(EWK_TOUCH_END);
1307 }
1308
1309 void EwkViewImpl::onTouchMove(void* /* data */, Evas* /* canvas */, Evas_Object* ewkView, void* /* eventInfo */)
1310 {
1311     EwkViewImpl* viewImpl = EwkViewImpl::fromEvasObject(ewkView);
1312     viewImpl->feedTouchEvents(EWK_TOUCH_MOVE);
1313 }
1314 #endif
1315
1316 #if OS(TIZEN)
1317 #if ENABLE(TIZEN_WEBKIT2_TILED_BACKING_STORE)
1318 AffineTransform EwkViewImpl::transformFromView() const
1319 {
1320     AffineTransform transform;
1321     transform.scale(1 / m_scaleFactor);
1322     transform.translate(m_scrollPosition.x(), m_scrollPosition.y());
1323
1324     return transform;
1325 }
1326
1327 AffineTransform EwkViewImpl::transformToView() const
1328 {
1329     return transformFromView().inverse();
1330 }
1331 #endif
1332
1333 AffineTransform EwkViewImpl::transformFromScene() const
1334 {
1335     AffineTransform transform;
1336
1337 #if USE(TILED_BACKING_STORE)
1338     // FIXME: We have to scale firstly unlike open source, because we are using scaled scroll position.
1339     //transform.translate(m_scrollPosition.x(), m_scrollPosition.y());
1340     //transform.scale(1 / m_scaleFactor);
1341     transform.scale(1 / m_scaleFactor);
1342     transform.translate(m_scrollPosition.x(), m_scrollPosition.y());
1343 #endif
1344
1345     Ewk_View_Smart_Data* sd = smartData();
1346     transform.translate(-sd->view.x, -sd->view.y);
1347
1348     return transform;
1349 }
1350
1351 AffineTransform EwkViewImpl::transformToScene() const
1352 {
1353     return transformFromScene().inverse();
1354 }
1355
1356 AffineTransform EwkViewImpl::transformToScreen() const
1357 {
1358     AffineTransform transform;
1359
1360     int windowGlobalX = 0;
1361     int windowGlobalY = 0;
1362
1363     Ewk_View_Smart_Data* sd = smartData();
1364
1365 #ifdef HAVE_ECORE_X
1366     Ecore_Evas* ecoreEvas = ecore_evas_ecore_evas_get(sd->base.evas);
1367     Ecore_X_Window window = ecore_evas_software_x11_window_get(ecoreEvas); // Returns 0 if none.
1368
1369     int x, y; // x, y are relative to parent (in a reparenting window manager).
1370     while (window) {
1371         ecore_x_window_geometry_get(window, &x, &y, 0, 0);
1372         windowGlobalX += x;
1373         windowGlobalY += y;
1374         window = ecore_x_window_parent_get(window);
1375     }
1376 #endif
1377
1378     transform.translate(-sd->view.x, -sd->view.y);
1379     transform.translate(windowGlobalX, windowGlobalY);
1380
1381     return transform;
1382 }
1383
1384 #if ENABLE(TIZEN_WEBKIT2_SEPERATE_LOAD_PROGRESS)
1385 void EwkViewImpl::informLoadProgressStarted()
1386 {
1387     evas_object_smart_callback_call(m_view, "load,progress,started", 0);
1388 }
1389
1390 void EwkViewImpl::informLoadProgressFinished()
1391 {
1392     evas_object_smart_callback_call(m_view, "load,progress,finished", 0);
1393 }
1394 #endif
1395
1396 #if ENABLE(TIZEN_DATALIST_ELEMENT)
1397 void EwkViewImpl::deleteDataList()
1398 {
1399     EINA_SAFETY_ON_NULL_RETURN(dataList);
1400
1401     void* item;
1402     EINA_LIST_FREE(dataList, item)
1403         eina_stringshare_del(static_cast<char*>(item));
1404
1405     dataList = 0;
1406 }
1407 #endif
1408
1409 #if ENABLE(TOUCH_EVENTS) && ENABLE(TIZEN_GESTURE)
1410 void EwkViewImpl::feedTouchEventsByType(Ewk_Touch_Event_Type type)
1411 {
1412     feedTouchEvents(type);
1413 }
1414 #endif
1415 #endif //#if OS(TIZEN)