Prerender first frame of new view size before angle is changed.
[framework/web/webkit-efl.git] / Source / WebKit2 / UIProcess / API / efl / PageClientImpl.cpp
1 /*
2  * Copyright (C) 2011 Samsung Electronics
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  * 1. Redistributions of source code must retain the above copyright
8  *    notice, this list of conditions and the following disclaimer.
9  * 2. Redistributions in binary form must reproduce the above copyright
10  *    notice, this list of conditions and the following disclaimer in the
11  *    documentation and/or other materials provided with the distribution.
12  *
13  * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
14  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
15  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
17  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
18  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
19  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
20  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
21  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
22  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
23  * THE POSSIBILITY OF SUCH DAMAGE.
24  */
25
26 #include "config.h"
27 #include "PageClientImpl.h"
28
29 #include "EwkViewImpl.h"
30 #include "InputMethodContextEfl.h"
31 #include "NativeWebKeyboardEvent.h"
32 #include "NotImplemented.h"
33 #include "TransformationMatrix.h"
34 #include "WebContext.h"
35 #include "WebContextMenuProxy.h"
36 #include "WebPageProxy.h"
37 #include "WebPopupMenuProxyEfl.h"
38 #include "ewk_context.h"
39 #include "ewk_context_private.h"
40 #include "ewk_download_job.h"
41 #include "ewk_download_job_private.h"
42 #include "ewk_view.h"
43
44 #if OS(TIZEN)
45 #include "DrawingAreaProxyImpl.h"
46 #include "Editor.h"
47 #include "EflScreenUtilities.h"
48 #include "LayerTreeCoordinatorProxy.h"
49 #include "OpenGLShims.h"
50 #include "WebContextMenuProxyTizen.h"
51 #include "WebLayerTreeRenderer.h"
52 #include "WebPageGroup.h"
53 #include "WebPageMessages.h"
54 #include "WebPopupMenuProxyEfl.h"
55 #include "WebPreferences.h"
56 #include "ewk_view.h"
57 #include <Ecore_Evas.h>
58 #include <Ecore_X.h>
59
60 #if ENABLE(TIZEN_WEBKIT2_TILED_SCROLLBAR)
61 #include "MainFrameScrollbarTizen.h"
62 #endif
63
64 #if ENABLE(TIZEN_WEBKIT2_CLIPBOARD_HELPER)
65 #include "ClipboardHelper.h"
66 #endif
67
68 #if ENABLE(TIZEN_DRAG_SUPPORT)
69 #include "DragData.h"
70 #endif
71 #endif
72
73 #if ENABLE(TIZEN_CACHE_MEMORY_OPTIMIZATION)
74 #include "ewk_context_private.h"
75 #endif
76
77 #if ENABLE(TIZEN_SCREEN_READER)
78 #include "ScreenReaderProxy.h"
79 #endif
80
81 using namespace WebCore;
82 using namespace std;
83
84 namespace WebKit {
85
86 PageClientImpl::PageClientImpl(EwkViewImpl* viewImpl)
87     : m_viewImpl(viewImpl)
88 #if OS(TIZEN)
89     , m_viewportConstraints()
90     , m_viewFocused(false)
91     , m_viewWindowActive(true)
92     , m_pageDidRendered(false)
93     , m_viewportAngle(0)
94     , m_viewportFitsToContent(false)
95 #if ENABLE(TIZEN_WEBKIT2_TILED_BACKING_STORE)
96     , m_visibleContentRect(IntRect())
97     , m_scaleFactor(1.0f)
98     , m_hasSuspendedContent(false)
99 #endif
100 #if ENABLE(TIZEN_WEBKIT2_HISTORICAL_RESTORE_VISIBLE_CONTENT_RECT)
101     , m_restoredScaleFactor(0)
102 #endif
103     , m_isVisible(true)
104     , m_isScrollableLayerFocused(false)
105     , m_isScrollableNodeFocused(false)
106 #if ENABLE(TIZEN_WEBKIT2_TILED_AC_SHARED_PLATFORM_SURFACE_BACKUP_IMAGE)
107     , m_shouldMakeBackupTexture(false)
108     , m_shouldShowBackupTexture(false)
109 #endif
110 #if ENABLE(TIZEN_CONTEXT_MENU_WEBKIT_2)
111     , m_isContextMenuVisible(false)
112 #endif
113 #if ENABLE(TIZEN_PRERENDERING_FOR_ROTATION)
114     , m_waitFrameOfNewViewortSize(false)
115 #endif
116 #endif // #if OS(TIZEN)
117 {
118 #if ENABLE(TIZEN_CANVAS_CAIRO_GLES_RENDERING)
119     setenv("CAIRO_GL_COMPOSITOR", "msaa", 1);
120     setenv("CAIRO_GL_LAZY_FLUSHING", "yes", 1);
121 #endif
122
123 #if OS(TIZEN)
124 #if ENABLE(TIZEN_WEBKIT2_TEXT_SELECTION)
125     m_textSelection = TextSelection::create(m_viewImpl);
126 #endif
127 #if ENABLE(TIZEN_OFFLINE_PAGE_SAVE)
128     m_offlinePageSave = OfflinePageSave::create(m_viewImpl);
129 #endif
130 #if ENABLE(TIZEN_WEBKIT2_CLIPBOARD_HELPER)
131     m_clipboardHelper = ClipboardHelper::create(m_viewImpl);
132 #endif
133 #if ENABLE(TIZEN_DRAG_SUPPORT)
134     m_drag = Drag::create(m_viewImpl);
135 #endif
136 #if ENABLE(TIZEN_WEBKIT2_FORM_DATABASE)
137     m_formDataCandidate = FormDataCandidate::create(m_viewImpl);
138 #endif
139 #endif
140
141     setBackgroundColor(1, 1, 1, 1);
142 }
143
144 PageClientImpl::~PageClientImpl()
145 {
146     m_viewImpl->page()->close();
147 }
148
149 #if OS(TIZEN)
150 PageClientImpl::ViewportConstraints PageClientImpl::computeViewportConstraints(const WebCore::ViewportAttributes& attributes)
151 {
152     PageClientImpl::ViewportConstraints constraints;
153     constraints.minimumScale = attributes.minimumScale * attributes.devicePixelRatio;
154     constraints.maximumScale = attributes.maximumScale * attributes.devicePixelRatio;
155     constraints.userScalable = attributes.userScalable;
156     constraints.layoutSize = attributes.layoutSize;
157     constraints.contentsDefinedInitialScale = (ViewportArguments::ValueAuto != attributes.initialScale);
158
159     double defaultViewLevel = m_viewImpl->page()->pageGroup()->preferences()->defaultViewLevel();
160     // If defaultViewLevel is 1, "Default View" is set as "Readable"
161     // if not, "Default View" is set as "Fit to width"
162     if (defaultViewLevel) {
163         // if content doesn't set initial scale value, set readable scale factor
164         // if not, set initial scale factor of viewport attribute
165         if (attributes.initialScale == ViewportArguments::ValueAuto)
166             constraints.initialScale = m_viewImpl->page()->deviceScaleFactor();
167         else
168             constraints.initialScale = attributes.initialScale * attributes.devicePixelRatio;
169     } else {
170         // Minimize initial scale factor
171         constraints.initialScale = attributes.minimumScale * attributes.devicePixelRatio;
172     }
173
174     // adjust scale with both minimum and maximum scale factor
175     constraints.initialScale = clampTo(constraints.initialScale, constraints.minimumScale, constraints.maximumScale);
176
177     return constraints;
178 }
179
180 double PageClientImpl::adjustScaleWithViewport(double scale)
181 {
182     double minimumScale = min(m_viewportConstraints.minimumScale, m_viewportConstraints.maximumScale);
183     return clampTo(scale, minimumScale, m_viewportConstraints.maximumScale);
184 }
185
186 #if USE(TILED_BACKING_STORE) && ENABLE(TIZEN_WEBKIT2_TILED_BACKING_STORE)
187 void PageClientImpl::updateViewportSize(const IntSize& viewportSize, const int angle)
188 {
189     // update device width & height
190     int deviceWidth = WebCore::getDefaultScreenResolution().width();
191     int deviceHeight = WebCore::getDefaultScreenResolution().height();
192
193     if (angle == 90 || angle == 270) {
194         int tempWidth = deviceWidth;
195         deviceWidth = deviceHeight;
196         deviceHeight = tempWidth;
197     }
198     m_viewImpl->page()->pageGroup()->preferences()->setDeviceWidth(deviceWidth);
199     m_viewImpl->page()->pageGroup()->preferences()->setDeviceHeight(deviceHeight);
200
201     // update viewport size of webkit
202     m_visibleContentRect.setSize(viewportSize);
203     m_viewImpl->page()->setViewportSize(viewportSize);
204 }
205 #endif
206
207 void PageClientImpl::initializeVisibleContentRect()
208 {
209     _ewk_view_resume_painting(m_viewImpl->view());
210
211 #if ENABLE(TIZEN_WEBKIT2_TILED_BACKING_STORE)
212     IntPoint initialScrollPosition;
213     float initialScaleFactor = m_viewportConstraints.initialScale;
214 #if ENABLE(TIZEN_WEBKIT2_HISTORICAL_RESTORE_VISIBLE_CONTENT_RECT)
215     // if scroll position and scale factor are restored by history controller,
216     // move scroll position and scale factor with them
217     if (m_restoredScaleFactor) {
218         initialScrollPosition = m_restoredScrollPosition;
219         initialScaleFactor = m_restoredScaleFactor;
220     }
221 #endif
222     setVisibleContentRect(IntRect(initialScrollPosition, m_visibleContentRect.size()), initialScaleFactor);
223 #else
224     // Set initial scale.
225     m_viewImpl->page()->scalePage(m_viewportConstraints.initialScale, IntPoint(0, 0));
226 #endif
227 }
228
229 double PageClientImpl::availableMinimumScale()
230 {
231     // recalculate minimum scale factor if contents' width exceeds viewport layout width and userScalable is true.
232     // minimum scale factor shouldn't be smaller than 0.25(minimum zoom level)
233     IntSize contentsSize = m_viewImpl->page()->contentsSize();
234     double horizontalMinScale = max(((double)viewSize().width() / contentsSize.width()), 0.25);
235     double verticalMinScale = max(((double)viewSize().height() / contentsSize.height()), 0.25);
236     return min(max(horizontalMinScale, verticalMinScale), m_viewportConstraints.maximumScale);
237 }
238
239 void PageClientImpl::fitViewportToContent()
240 {
241     setVisibleContentRect(m_visibleContentRect, m_viewportConstraints.minimumScale);
242 }
243
244 void PageClientImpl::setFocusedNodeRect(const IntRect& focusedNodeRect)
245 {
246     m_focusedNodeRect = focusedNodeRect;
247 }
248
249 #if ENABLE(TIZEN_WEBKIT2_TILED_BACKING_STORE)
250 bool PageClientImpl::scrollBy(IntSize scrollOffset)
251 {
252 #if ENABLE(TIZEN_CSS_OVERFLOW_SCROLL_ACCELERATION)
253     // scrollOffset means device screen coordiate, not an actual offset of contents.
254     // Therefore, scrollOffset should be nomalized in order to make a tiled backing store
255     // in the actual scale.
256     IntSize scaledScrollOffset = m_viewImpl->transformFromScene().mapSize(scrollOffset);
257     if ((m_isScrollableLayerFocused || m_isScrollableNodeFocused)
258         && m_viewImpl->page()->scrollOverflow(FloatPoint(scaledScrollOffset.width(), scaledScrollOffset.height()))) {
259         displayViewport();
260         return false;
261     }
262 #endif
263
264     IntPoint oldScrollPosition = scrollPosition();
265     setVisibleContentRect(IntRect(oldScrollPosition + scrollOffset, m_visibleContentRect.size()), scaleFactor(), FloatPoint(scrollOffset.width(), scrollOffset.height()));
266
267     return true;
268 }
269
270 void PageClientImpl::scrollTo(IntPoint requestedScrollPosition)
271 {
272     setVisibleContentRect(IntRect(requestedScrollPosition, m_visibleContentRect.size()), scaleFactor());
273 }
274 #endif // #if ENABLE(TIZEN_WEBKIT2_TILED_BACKING_STORE)
275
276 #endif // #if OS(TIZEN)
277
278 EwkViewImpl* PageClientImpl::viewImpl() const
279 {
280     return m_viewImpl;
281 }
282
283 // PageClient
284 PassOwnPtr<DrawingAreaProxy> PageClientImpl::createDrawingAreaProxy()
285 {
286     return DrawingAreaProxyImpl::create(m_viewImpl->page());
287 }
288
289 void PageClientImpl::setViewNeedsDisplay(const WebCore::IntRect& rect)
290 {
291 #if OS(TIZEN)
292     ewk_view_mark_for_sync(m_viewImpl->view());
293 #else
294     m_viewImpl->redrawRegion(rect);
295 #endif
296
297 #if ENABLE(TIZEN_SCREEN_READER)
298     if (rect.intersects(ewkViewGetFocusRing(m_viewImpl->view())->rect()))
299         m_viewImpl->page()->recalcScreenReaderFocusRect();
300 #endif
301 }
302
303 void PageClientImpl::displayView()
304 {
305     notImplemented();
306 }
307
308 void PageClientImpl::scrollView(const WebCore::IntRect& scrollRect, const WebCore::IntSize&)
309 {
310     setViewNeedsDisplay(scrollRect);
311 }
312
313 WebCore::IntSize PageClientImpl::viewSize()
314 {
315     return m_viewImpl->size();
316 }
317
318 bool PageClientImpl::isViewVisible()
319 {
320 #if OS(TIZEN)
321     return m_isVisible;
322 #else
323     return m_viewImpl->isVisible();
324 #endif
325 }
326
327 bool PageClientImpl::isViewInWindow()
328 {
329     notImplemented();
330     return true;
331 }
332
333 void PageClientImpl::processDidCrash()
334 {
335     // Check if loading was ongoing, when web process crashed.
336     double loadProgress = ewk_view_load_progress_get(m_viewImpl->view());
337     if (loadProgress >= 0 && loadProgress < 1)
338         m_viewImpl->informLoadProgress(1);
339
340     m_viewImpl->informWebProcessCrashed();
341 }
342
343 void PageClientImpl::didRelaunchProcess()
344 {
345     const char* themePath = m_viewImpl->themePath();
346     if (themePath)
347         m_viewImpl->page()->setThemePath(themePath);
348 }
349
350 void PageClientImpl::pageClosed()
351 {
352     notImplemented();
353 }
354
355 void PageClientImpl::toolTipChanged(const String&, const String& newToolTip)
356 {
357     m_viewImpl->informTooltipTextChange(newToolTip);
358 }
359
360 void PageClientImpl::setCursor(const Cursor& cursor)
361 {
362     m_viewImpl->setCursor(cursor);
363 }
364
365 void PageClientImpl::setCursorHiddenUntilMouseMoves(bool hiddenUntilMouseMoves)
366 {
367     notImplemented();
368 }
369
370 void PageClientImpl::didChangeViewportProperties(const WebCore::ViewportAttributes& attributes)
371 {
372     m_viewportConstraints = computeViewportConstraints(attributes);
373
374     // if content is reloaded, contents size will not be changed
375     // so, we need to calculate minimum scale here.
376     // if content size is changed later, minimum scale will be re-calculated on didChangeContentsSize()
377     if (m_viewportConstraints.userScalable)
378         m_viewportConstraints.minimumScale = availableMinimumScale();
379
380     // setVisibleContentRect() should be called to adjust visible content rect only when view is resized
381     if (!m_pageDidRendered || m_viewImpl->page()->estimatedProgress() <= 0.1)
382         return;
383
384     // if IME is opened, visible content rect will be updated by ewk_view_focused_node_adjust()
385     if (ewk_view_focused_node_adjust(m_viewImpl->view()))
386         return;
387
388     float newScale = scaleFactor();
389     Ecore_Evas* ee = ecore_evas_ecore_evas_get(evas_object_evas_get(m_viewImpl->view()));
390     int angle = ecore_evas_rotation_get(ee);
391     bool isRotated = (angle != m_viewportAngle);
392
393     // if it's rotated, we need to fit content to viewport by minimize the scale
394     if (isRotated) {
395         m_viewportAngle = angle;
396         if (m_viewportFitsToContent)
397             newScale = m_viewportConstraints.minimumScale;
398     }
399
400 #if ENABLE(TIZEN_PRERENDERING_FOR_ROTATION)
401     if (m_waitFrameOfNewViewortSize)
402         ewk_view_resume(m_viewImpl->view());
403 #endif
404
405 #if ENABLE(TIZEN_WEBKIT2_TILED_BACKING_STORE)
406     setVisibleContentRect(m_visibleContentRect, newScale);
407 #else
408     m_viewImpl->page()->scalePage(newScale, m_visibleContentRect.location());
409 #endif
410
411 #if ENABLE(TIZEN_WEBKIT2_FORM_DATABASE)
412     Ewk_View_Smart_Data* smartData = static_cast<Ewk_View_Smart_Data*>(evas_object_smart_data_get(m_viewImpl->view()));
413     if (smartData->api->formdata_candidate_is_showing(smartData))
414         smartData->api->formdata_candidate_hide(smartData);
415 #endif
416 }
417
418 #if OS(TIZEN)
419 void PageClientImpl::registerEditCommand(PassRefPtr<WebEditCommandProxy> command, WebPageProxy::UndoOrRedo undoOrRedo)
420 {
421     if (undoOrRedo == WebPageProxy::Undo) {
422         m_undoCommands.append(command);
423
424         int undoSize = m_undoCommands.size();
425         evas_object_smart_callback_call(m_viewImpl->view(), "undo,size", &undoSize);
426     }
427     else {
428         m_redoCommands.append(command);
429
430         int redoSize = m_redoCommands.size();
431         evas_object_smart_callback_call(m_viewImpl->view(), "redo,size", &redoSize);
432     }
433 }
434
435 void PageClientImpl::clearAllEditCommands()
436 {
437     m_undoCommands.clear();
438     m_redoCommands.clear();
439
440     int undoSize = m_undoCommands.size();
441     evas_object_smart_callback_call(m_viewImpl->view(), "undo,size", &undoSize);
442
443     int redoSize = m_redoCommands.size();
444     evas_object_smart_callback_call(m_viewImpl->view(), "redo,size", &redoSize);
445 }
446
447 bool PageClientImpl::canUndoRedo(WebPageProxy::UndoOrRedo undoOrRedo)
448 {
449     if (undoOrRedo == WebPageProxy::Undo)
450         return !m_undoCommands.isEmpty();
451     else
452         return !m_redoCommands.isEmpty();
453 }
454
455 void PageClientImpl::executeUndoRedo(WebPageProxy::UndoOrRedo undoOrRedo)
456 {
457     if (undoOrRedo == WebPageProxy::Undo) {
458         m_undoCommands.last()->unapply();
459         m_undoCommands.removeLast();
460
461         int undoSize = m_undoCommands.size();
462         evas_object_smart_callback_call(m_viewImpl->view(), "undo,size", &undoSize);
463     } else {
464         m_redoCommands.last()->reapply();
465         m_redoCommands.removeLast();
466
467         int redoSize = m_redoCommands.size();
468         evas_object_smart_callback_call(m_viewImpl->view(), "redo,size", &redoSize);
469     }
470 }
471 #else
472 void PageClientImpl::registerEditCommand(PassRefPtr<WebEditCommandProxy>, WebPageProxy::UndoOrRedo)
473 {
474     notImplemented();
475 }
476
477 void PageClientImpl::clearAllEditCommands()
478 {
479     notImplemented();
480 }
481
482 bool PageClientImpl::canUndoRedo(WebPageProxy::UndoOrRedo)
483 {
484     notImplemented();
485     return false;
486 }
487
488 void PageClientImpl::executeUndoRedo(WebPageProxy::UndoOrRedo)
489 {
490     notImplemented();
491 }
492 #endif
493
494 FloatRect PageClientImpl::convertToDeviceSpace(const FloatRect& viewRect)
495 {
496     notImplemented();
497     return viewRect;
498 }
499
500 FloatRect PageClientImpl::convertToUserSpace(const FloatRect& viewRect)
501 {
502     notImplemented();
503     return viewRect;
504 }
505
506 IntPoint PageClientImpl::screenToWindow(const IntPoint& point)
507 {
508     notImplemented();
509     return point;
510 }
511
512 IntRect PageClientImpl::windowToScreen(const IntRect&)
513 {
514     notImplemented();
515     return IntRect();
516 }
517
518 void PageClientImpl::doneWithKeyEvent(const NativeWebKeyboardEvent&, bool)
519 {
520     notImplemented();
521 }
522
523 #if ENABLE(GESTURE_EVENTS)
524 void PageClientImpl::doneWithGestureEvent(const WebGestureEvent& event, bool wasEventHandled)
525 {
526     notImplemented();
527 }
528 #endif
529
530 #if ENABLE(TOUCH_EVENTS)
531 void PageClientImpl::doneWithTouchEvent(const NativeWebTouchEvent& event, bool wasEventHandled)
532 {
533 #if OS(TIZEN)
534     ewk_view_touch_event_handler_result_set(m_viewImpl->view(), event.type(), wasEventHandled);
535 #else
536     notImplemented();
537 #endif // #if OS(TIZEN)
538 }
539 #endif
540
541 PassRefPtr<WebPopupMenuProxy> PageClientImpl::createPopupMenuProxy(WebPageProxy* page)
542 {
543     return WebPopupMenuProxyEfl::create(m_viewImpl, page);
544 }
545
546 PassRefPtr<WebContextMenuProxy> PageClientImpl::createContextMenuProxy(WebPageProxy* page)
547 {
548 #if ENABLE(TIZEN_CONTEXT_MENU_WEBKIT_2)
549     return WebContextMenuProxyTizen::create(m_viewImpl->view(), page, this);
550 #else
551     notImplemented();
552     return 0;
553 #endif
554 }
555
556 #if ENABLE(INPUT_TYPE_COLOR)
557 PassRefPtr<WebColorChooserProxy> PageClientImpl::createColorChooserProxy(WebPageProxy*, const WebCore::Color&)
558 {
559     notImplemented();
560     return 0;
561 }
562 #endif
563
564 void PageClientImpl::setFindIndicator(PassRefPtr<FindIndicator>, bool, bool)
565 {
566     notImplemented();
567 }
568
569 #if !OS(TIZEN)
570 #if USE(ACCELERATED_COMPOSITING)
571 void PageClientImpl::enterAcceleratedCompositingMode(const LayerTreeContext&)
572 {
573     m_viewImpl->enterAcceleratedCompositingMode();
574 }
575
576 void PageClientImpl::exitAcceleratedCompositingMode()
577 {
578     m_viewImpl->exitAcceleratedCompositingMode();
579 }
580
581 void PageClientImpl::updateAcceleratedCompositingMode(const LayerTreeContext&)
582 {
583     notImplemented();
584 }
585 #endif // USE(ACCELERATED_COMPOSITING)
586 #endif
587
588 void PageClientImpl::initializeAcceleratedCompositingMode()
589 {
590 }
591
592 #if ENABLE(TIZEN_WEBKIT2_TILED_AC)
593 void PageClientImpl::updateAcceleratedCompositingMode(const LayerTreeContext&)
594 {
595     notImplemented();
596 }
597 #endif // ENABLE(TIZEN_WEBKIT2_TILED_AC)
598
599 void PageClientImpl::setBackgroundColor(double red, double green, double blue, double alpha)
600 {
601     WebCore::RGBA32 rgba= WebCore::makeRGBA32FromFloats((float)red, (float)green, (float)blue, (float)alpha);
602     m_bgColor.setRGB(rgba);
603 }
604
605 void PageClientImpl::didChangeScrollbarsForMainFrame() const
606 {
607     notImplemented();
608 }
609
610 #if OS(TIZEN)
611 void PageClientImpl::didFirstVisuallyNonEmptyLayoutForMainFrame()
612 {
613 #if ENABLE(TIZEN_WEBKIT2_TILED_AC_SHARED_PLATFORM_SURFACE_BACKUP_IMAGE)
614     m_initialViewRect.setSize(viewSize());
615 #endif
616 }
617
618 void PageClientImpl::didChangeContentsSize(const WebCore::IntSize size)
619 {
620 #if USE(TILED_BACKING_STORE)
621     if (size.isEmpty())
622         return;
623
624 #if ENABLE(TIZEN_WEBKIT2_TILED_AC)
625     if (drawingArea()->layerTreeCoordinatorProxy())
626         drawingArea()->layerTreeCoordinatorProxy()->setContentsSize(WebCore::FloatSize(size.width(), size.height()));
627 #endif
628
629     // if minimum scale factor is changed, update minimumScale.
630     if (m_viewportConstraints.userScalable) {
631         double minimumScale = availableMinimumScale();
632
633         // Sometimes initializeVisibleContentRect can be called after content size change.
634         // So, if initialScale is not set explicitly in content's meta viewport tag and is same to minimumScale, update initialScale too.
635         if (!m_viewportConstraints.contentsDefinedInitialScale
636             && fabs(m_viewportConstraints.initialScale - m_viewportConstraints.minimumScale) < numeric_limits<float>::epsilon())
637             m_viewportConstraints.initialScale = minimumScale;
638         m_viewportConstraints.minimumScale = minimumScale;
639     }
640 #else
641     m_viewImpl->informContentsSizeChange(size);
642 #endif
643     if (!m_pageDidRendered || m_viewImpl->page()->estimatedProgress() <= 0.1)
644         return;
645
646     // FIXME: Do we really need to adjust visible content rect at here?
647     // if contents size is changed smaller and visible content rect is outside of content area,
648     // adjust visible content rect
649     IntRect adjustedVisibleContentRect = adjustVisibleContentRect(m_visibleContentRect, scaleFactor());
650     if (adjustedVisibleContentRect != m_visibleContentRect)
651         setVisibleContentRect(m_visibleContentRect, scaleFactor());
652 }
653
654 void PageClientImpl::pageScaleFactorDidChange()
655 {
656     ewk_view_focused_node_adjust(m_viewImpl->view());
657 }
658 #endif // #if OS(TIZEN)
659
660 void PageClientImpl::didCommitLoadForMainFrame(bool)
661 {
662 #if OS(TIZEN)
663     m_pageDidRendered = false;
664     m_viewportFitsToContent = false;
665 #if ENABLE(TIZEN_WEBKIT2_HISTORICAL_RESTORE_VISIBLE_CONTENT_RECT)
666     m_restoredScaleFactor = 0;
667 #endif
668     return;
669 #endif
670     notImplemented();
671 }
672
673 void PageClientImpl::didFinishLoadingDataForCustomRepresentation(const String&, const CoreIPC::DataReference&)
674 {
675     notImplemented();
676 }
677
678 double PageClientImpl::customRepresentationZoomFactor()
679 {
680     notImplemented();
681     return 0;
682 }
683
684 void PageClientImpl::setCustomRepresentationZoomFactor(double)
685 {
686     notImplemented();
687 }
688
689 void PageClientImpl::flashBackingStoreUpdates(const Vector<IntRect>&)
690 {
691     notImplemented();
692 }
693
694 void PageClientImpl::findStringInCustomRepresentation(const String&, FindOptions, unsigned)
695 {
696     notImplemented();
697 }
698
699 void PageClientImpl::countStringMatchesInCustomRepresentation(const String&, FindOptions, unsigned)
700 {
701     notImplemented();
702 }
703
704 void PageClientImpl::updateTextInputState()
705 {
706     InputMethodContextEfl* inputMethodContext = m_viewImpl->inputMethodContext();
707     if (inputMethodContext)
708         inputMethodContext->updateTextInputState();
709
710 #if ENABLE(TIZEN_WEBKIT2_TEXT_SELECTION)
711     m_textSelection->update();
712 #endif
713 }
714
715 void PageClientImpl::handleDownloadRequest(DownloadProxy* download)
716 {
717     Ewk_Context* context = m_viewImpl->ewkContext();
718     context->downloadManager()->registerDownload(download, m_viewImpl);
719 }
720
721 #if USE(TILED_BACKING_STORE)
722 void PageClientImpl::pageDidRequestScroll(const IntPoint& point)
723 {
724 #if ENABLE(TIZEN_WEBKIT2_FORM_DATABASE)
725     Ewk_View_Smart_Data* smartData = static_cast<Ewk_View_Smart_Data*>(evas_object_smart_data_get(m_viewImpl->view()));
726     if (smartData->api->formdata_candidate_is_showing(smartData))
727         return;
728 #endif
729 #if ENABLE(TIZEN_WEBKIT2_TILED_BACKING_STORE)
730     IntPoint newPoint = point;
731     newPoint.scale(scaleFactor(), scaleFactor());
732     setVisibleContentRect(IntRect(newPoint, m_visibleContentRect.size()), scaleFactor());
733 #endif
734 }
735 #endif
736
737 #if OS(TIZEN)
738 #if ENABLE(TIZEN_WEBKIT2_HISTORICAL_RESTORE_VISIBLE_CONTENT_RECT)
739 void PageClientImpl::pageDidRequestRestoreVisibleContentRect(const IntPoint& point, float scale)
740 {
741     m_restoredScrollPosition = point;
742     m_restoredScrollPosition.scale(scale, scale);
743     m_restoredScaleFactor = scale;
744
745     // Before contents size is fixed, just update visible content rect's position
746     m_visibleContentRect.setLocation(m_restoredScrollPosition);
747 }
748 #endif
749
750 #if ENABLE(TIZEN_WEBKIT2_FORM_DATABASE)
751 void PageClientImpl::textChangeInTextField(const String& name, const String& value)
752 {
753     if (value == m_formDataCandidate->getCandidateValue()) {
754         m_formDataCandidate->updateCandidateValue(emptyString());
755         return;
756     }
757
758     m_formDataCandidate->updateCandidateValue(value);
759     ewk_view_text_change_in_textfield(m_viewImpl->view(), name, value);
760 }
761 #endif
762
763 void PageClientImpl::updateFormNavigation(int length, int offset)
764 {
765     notImplemented();
766 }
767
768 #if ENABLE(TIZEN_WEBKIT2_TILED_BACKING_STORE)
769 #if ENABLE(TIZEN_WEBKIT2_TILED_AC)
770 DrawingAreaProxy* PageClientImpl::drawingArea() const
771 {
772     return m_viewImpl->page()->drawingArea();
773 }
774 #endif
775
776 // Before rendering, scale factor and scroll position is different from m_viewImpl.
777 float PageClientImpl::scaleFactor()
778 {
779     return m_pageDidRendered ? m_viewImpl->scaleFactor() : (m_restoredScaleFactor ? m_restoredScaleFactor : m_viewportConstraints.initialScale);
780 }
781
782 const IntPoint PageClientImpl::scrollPosition()
783 {
784     return m_pageDidRendered ? m_viewImpl->scrollPosition() : (m_restoredScaleFactor ? m_restoredScrollPosition : IntPoint());
785 }
786
787 IntRect PageClientImpl::adjustVisibleContentRect(IntRect visibleContentRect, float targetScale)
788 {
789     IntSize contentsSize = m_viewImpl->page()->contentsSize();
790     contentsSize.scale(targetScale);
791     if (contentsSize.width() < visibleContentRect.width())
792         visibleContentRect.setX(0);
793     else
794         visibleContentRect.setX(clampTo(visibleContentRect.x(), 0, contentsSize.width() - visibleContentRect.width()));
795
796     if (contentsSize.height() < visibleContentRect.height())
797         visibleContentRect.setY(0);
798     else
799         visibleContentRect.setY(clampTo(visibleContentRect.y(), 0, contentsSize.height() - visibleContentRect.height()));
800     return visibleContentRect;
801 }
802
803 void PageClientImpl::setVisibleContentRect(const IntRect& newRect, float newScale, const FloatPoint& trajectory)
804 {
805 #if ENABLE(TIZEN_SCREEN_READER)
806     IntPoint previousScrollPosition(scrollPosition());
807     float previousScale = m_scaleFactor;
808 #endif
809
810     m_scaleFactor = adjustScaleWithViewport(newScale);
811     m_viewportFitsToContent = fabs(m_scaleFactor - m_viewportConstraints.minimumScale) < numeric_limits<float>::epsilon();
812     m_visibleContentRect.setLocation(newRect.location());
813     m_visibleContentRect = adjustVisibleContentRect(m_visibleContentRect, m_scaleFactor);
814
815     // update both drawing scale factor and scroll position after page is rendered
816     if (m_pageDidRendered) {
817         if (!m_hasSuspendedContent) {
818             // FIXME: We have to update EwkViewImpl's scale and position here because we use them to draw contents.
819             // PageViewport's values are updated when resuming content in the webkit opensource,
820             // but we have to update viewImpl's values here to sync with PageClient's values.
821             // However, We should not update them when hasSuspendedContent is true in order to maintain last values.
822             // The values will be updated when resuming content.
823             // Below codes should be refactored when PageViewportController codes are merged into Tizen.
824             m_viewImpl->setScaleFactor(m_scaleFactor);
825             m_viewImpl->setScrollPosition(m_visibleContentRect.location());
826         }
827     }
828
829     // enclosingIntRect produces inconsistent width and height when scale factor is not 1.
830     // So we removed enclosingIntRect and replaced with floorf and ceilf.
831     IntRect mapToContentsVisibleContentRect = IntRect(floorf(m_visibleContentRect.x() / m_scaleFactor),
832                                                       floorf(m_visibleContentRect.y() / m_scaleFactor),
833                                                       ceilf(m_visibleContentRect.width() / m_scaleFactor),
834                                                       ceilf(m_visibleContentRect.height() / m_scaleFactor));
835     if (!drawingArea())
836         return;
837     drawingArea()->setVisibleContentsRect(mapToContentsVisibleContentRect, m_scaleFactor, trajectory, FloatPoint(m_viewImpl->scrollPosition()));
838 #if ENABLE(TIZEN_CSS_OVERFLOW_SCROLL_ACCELERATION_ON_UI_SIDE)
839     // FIXME: We need to calculate exact visibleRect size here instead of mapToContentsVisibleContentRect.
840     drawingArea()->setVisibleContentsRectForScrollingContentsLayers(mapToContentsVisibleContentRect);
841 #endif
842     displayViewport();
843
844 #if ENABLE(TIZEN_SCREEN_READER)
845     if (ScreenReaderProxy::screenReader().isEnabled()
846         && (scrollPosition() != previousScrollPosition || m_scaleFactor != previousScale))
847         ewkViewGetFocusRing(m_viewImpl->view())->updateScrollAndScale(previousScrollPosition, previousScale);
848 #endif
849
850 #if ENABLE(TIZEN_WEBKIT2_TEXT_SELECTION)
851     if (!isClipboardWindowOpened())
852         updateTextSelectionHandlesAndContextMenu(true);
853 #endif
854 }
855
856 void PageClientImpl::displayViewport()
857 {
858     setViewNeedsDisplay(IntRect(IntPoint(), viewSize()));
859
860 #if ENABLE(TIZEN_WEBKIT2_TILED_SCROLLBAR)
861     updateScrollbar();
862 #endif
863
864 #if ENABLE(TIZEN_SCREEN_READER)
865     m_viewImpl->page()->recalcScreenReaderFocusRect();
866 #endif
867 }
868
869 void PageClientImpl::drawContents()
870 {
871 }
872
873 void PageClientImpl::drawContents(BackingStore::PlatformGraphicsContext context)
874 {
875     cairo_save(context);
876     const cairo_matrix_t matrix = cairo_matrix_t(m_viewImpl->transformToView());
877     cairo_transform(context, &matrix);
878
879     if (drawingArea()) {
880         if (drawingArea()->layerTreeCoordinatorProxy()) {
881             WebLayerTreeRenderer* renderer = drawingArea()->layerTreeCoordinatorProxy()->layerTreeRenderer();
882             renderer->paintToGraphicsContext(context, m_bgColor);
883         }
884     }
885
886     cairo_restore(context);
887 }
888
889 void PageClientImpl::scaleImage(double scaleFactor, IntPoint scrollPosition)
890 {
891 #if OS(TIZEN) && ENABLE(FULLSCREEN_API)
892     // We don't want to process scaling in the FullScreen mode.
893     if (m_viewImpl->page()->fullScreenManager()->isFullScreen())
894         return;
895 #endif
896
897 #if ENABLE(TIZEN_WEBKIT2_TEXT_SELECTION)
898     m_textSelection->hideHandlers();
899 #endif
900
901     // Adjust scaleFactor.
902 #if ENABLE(TIZEN_WEBKIT2_TEXT_ZOOM)
903     if (!m_viewImpl->page()->pageGroup()->preferences()->textZoomEnabled())
904         scaleFactor = adjustScaleWithViewport(scaleFactor);
905 #else
906     scaleFactor = adjustScaleWithViewport(scaleFactor);
907 #endif
908
909     scaleContents(scaleFactor, scrollPosition);
910 }
911
912 void PageClientImpl::scaleContents(double scaleFactor, const IntPoint& origin)
913 {
914 #if OS(TIZEN) && ENABLE(FULLSCREEN_API)
915     // We don't want to process scaling in the FullScreen mode.
916     if (m_viewImpl->page()->fullScreenManager()->isFullScreen())
917         return;
918 #endif
919     scaleFactor = adjustScaleWithViewport(scaleFactor);
920
921     setVisibleContentRect(IntRect(origin, m_visibleContentRect.size()), scaleFactor);
922 }
923
924 // FIXME: The concept of suspending content comes from webkit opensource's PageViewportController,
925 // so below code should be replaced when PageViewportController codes are merged.
926 // Please do not use below codes. They are only for scaling contents.
927 void PageClientImpl::suspendContent()
928 {
929     if (m_hasSuspendedContent)
930         return;
931
932     m_hasSuspendedContent = true;
933 }
934
935 void PageClientImpl::resumeContent()
936 {
937     if (!m_hasSuspendedContent)
938         return;
939
940     // FIXME: Update visibleContentRect with m_viewImpl after resuming content.
941     // The concept is that the values of EwkViewImpl and PageClient can be different
942     // during suspending content and they become same when content is resumed.
943     // Below codes should be refactored when PageViewportController codes are merged into Tizen.
944     setVisibleContentRect(IntRect(m_viewImpl->scrollPosition(), m_visibleContentRect.size()), m_viewImpl->scaleFactor());
945     m_hasSuspendedContent = false;
946 }
947
948 FloatPoint PageClientImpl::boundContentsPositionAtScale(const FloatPoint& framePosition, float scale)
949 {
950     // We need to floor the viewport here as to allow aligning the content in device units. If not,
951     // it might not be possible to scroll the last pixel and that affects fixed position elements.
952     FloatRect bounds;
953     const IntSize& contentsSize = m_viewImpl->page()->contentsSize();
954     bounds.setWidth(std::max(0.f, contentsSize.width() - floorf(viewSize().width() / scale)));
955     bounds.setHeight(std::max(0.f, contentsSize.height() - floorf(viewSize().height() / scale)));
956
957     FloatPoint position;
958     // Unfortunately it doesn't seem to be enough, so just always allow one pixel more.
959     position.setX(clampTo(framePosition.x(), bounds.x(), bounds.width() + 1));
960     position.setY(clampTo(framePosition.y(), bounds.y(), bounds.height() + 1));
961
962     return position;
963 }
964
965 #if ENABLE(TIZEN_WEBKIT2_TILED_SCROLLBAR)
966 void PageClientImpl::createScrollbarIfNeeded(bool horizontalBar, bool verticalBar)
967 {
968     // create if needed.
969     if (horizontalBar && !m_horizontalScrollbar) {
970         m_horizontalScrollbar = MainFrameScrollbarTizen::createNativeScrollbar(m_viewImpl->view(), HorizontalScrollbar);
971         IntRect hBarRect(0, viewSize().height(), viewSize().width(), 0);
972         m_horizontalScrollbar->setFrameRect(hBarRect);
973     } else if (!horizontalBar && m_horizontalScrollbar)
974         m_horizontalScrollbar = 0;
975
976     if (verticalBar && !m_verticalScrollbar) {
977         m_verticalScrollbar = MainFrameScrollbarTizen::createNativeScrollbar(m_viewImpl->view(), VerticalScrollbar);
978         IntRect vBarRect(viewSize().width(), 0, 0, viewSize().height());
979         m_verticalScrollbar->setFrameRect(vBarRect);
980     } else if (!verticalBar && m_verticalScrollbar)
981         m_verticalScrollbar = 0;
982 }
983
984 void PageClientImpl::updateScrollbar()
985 {
986     IntSize scaledContentsSize = m_viewImpl->page()->contentsSize();
987     scaledContentsSize.scale(scaleFactor());
988
989     bool newHasHorizontalScrollbar = false;
990     bool newVerticalScrollbar = false;
991     if (viewSize().width() < scaledContentsSize.width())
992         newHasHorizontalScrollbar = true;
993     if (viewSize().height() < scaledContentsSize.height())
994         newVerticalScrollbar = true;
995     createScrollbarIfNeeded(newHasHorizontalScrollbar, newVerticalScrollbar);
996
997     if (m_horizontalScrollbar) {
998         m_horizontalScrollbar->setProportion(viewSize().width(), scaledContentsSize.width());
999         m_horizontalScrollbar->setPosition(m_viewImpl->scrollPosition().x());
1000     }
1001     if (m_verticalScrollbar) {
1002         m_verticalScrollbar->setProportion(viewSize().height(), scaledContentsSize.height());
1003         m_verticalScrollbar->setPosition(m_viewImpl->scrollPosition().y());
1004     }
1005 }
1006
1007 void PageClientImpl::frameRectChanged()
1008 {
1009     if (m_horizontalScrollbar) {
1010         IntRect hBarRect(0, viewSize().height(), viewSize().width(), 0);
1011         m_horizontalScrollbar->setFrameRect(hBarRect);
1012     }
1013     if (m_verticalScrollbar) {
1014         IntRect vBarRect(viewSize().width(), 0, 0, viewSize().height());
1015         m_verticalScrollbar->setFrameRect(vBarRect);
1016     }
1017 }
1018
1019 void PageClientImpl::updateVisibility()
1020 {
1021     if (m_horizontalScrollbar)
1022         m_horizontalScrollbar->updateVisibility();
1023     if (m_verticalScrollbar)
1024         m_verticalScrollbar->updateVisibility();
1025 }
1026 #endif
1027 #endif // ENABLE(TIZEN_WEBKIT2_TILED_BACKING_STORE)
1028
1029 #if ENABLE(TIZEN_WEBKIT2_TEXT_SELECTION)
1030 bool PageClientImpl::isTextSelectionDowned()
1031 {
1032     return m_textSelection->isTextSelectionDowned();
1033 }
1034
1035 bool PageClientImpl::isTextSelectionMode()
1036 {
1037     return m_textSelection->isTextSelectionMode();
1038 }
1039
1040 void PageClientImpl::setIsTextSelectionMode(bool isTextSelectionMode)
1041 {
1042     m_textSelection->setIsTextSelectionMode(isTextSelectionMode);
1043 }
1044
1045 void PageClientImpl::updateTextSelectionHandlesAndContextMenu(bool isShow, bool isScrolling)
1046 {
1047     if (m_textSelection->isTextSelectionMode() && evas_object_focus_get(m_viewImpl->view()))
1048         m_textSelection->updateHandlesAndContextMenu(isShow, isScrolling);
1049 }
1050
1051 bool PageClientImpl::textSelectionDown(const WebCore::IntPoint& point, bool isStartedTextSelectionFromOutside)
1052 {
1053     if (!evas_object_focus_get(m_viewImpl->view())) {
1054         InputMethodContextEfl* inputMethodContext = m_viewImpl->inputMethodContext();
1055         if (inputMethodContext)
1056             inputMethodContext->hideIMFContext();
1057
1058         evas_object_focus_set(m_viewImpl->view(), true);
1059     }
1060
1061     return m_textSelection->textSelectionDown(point, isStartedTextSelectionFromOutside);
1062 }
1063
1064 void PageClientImpl::textSelectionMove(const WebCore::IntPoint& point, bool isStartedTextSelectionFromOutside)
1065 {
1066     m_textSelection->textSelectionMove(point, isStartedTextSelectionFromOutside);
1067 }
1068
1069 void PageClientImpl::textSelectionUp(const WebCore::IntPoint& point, bool isStartedTextSelectionFromOutside)
1070 {
1071     m_textSelection->textSelectionUp(point, isStartedTextSelectionFromOutside);
1072 }
1073
1074 bool PageClientImpl::isTextSelectionHandleDowned()
1075 {
1076     return m_textSelection->isTextSelectionHandleDowned();
1077 }
1078
1079 #if ENABLE(TIZEN_WEBKIT2_FOR_MOVING_TEXT_SELECTION_HANDLE_FROM_OSP)
1080 void PageClientImpl::textSelectonHandleDown(const WebCore::IntPoint& point)
1081 {
1082     m_textSelection->textSelectionHandleDown(point);
1083 }
1084
1085 void PageClientImpl::textSelectonHandleMove(const WebCore::IntPoint& point)
1086 {
1087     m_textSelection->textSelectionHandleMove(point);
1088 }
1089
1090 void PageClientImpl::textSelectonHandleUp()
1091 {
1092     m_textSelection->textSelectionHandleUp();
1093 }
1094 #endif
1095
1096 #if ENABLE(TIZEN_WEBKIT2_TEXT_SELECTION)
1097 void PageClientImpl::requestToShowTextSelectionHandlesAndContextMenu()
1098 {
1099     m_textSelection->requestToShow();
1100 }
1101 #endif
1102 #endif
1103
1104 #if ENABLE(TIZEN_OFFLINE_PAGE_SAVE)
1105 void PageClientImpl::saveSerializedHTMLDataForMainPage(const String& serializedData, const String& fileName)
1106 {
1107     m_offlinePageSave->saveSerializedHTMLDataForMainPage(serializedData, fileName);
1108 }
1109
1110 void PageClientImpl::saveSubresourcesData(Vector<WebSubresourceTizen>& subresourceData)
1111 {
1112     m_offlinePageSave->saveSubresourcesData(subresourceData);
1113 }
1114
1115 void PageClientImpl::startOfflinePageSave(String& path, String& url, String& title)
1116 {
1117     m_offlinePageSave->startOfflinePageSave(path, url, title);
1118 }
1119 #endif
1120
1121 #if ENABLE(TIZEN_WEBKIT2_CLIPBOARD_HELPER)
1122 void PageClientImpl::pasteContextMenuSelected()
1123 {
1124     m_clipboardHelper->pasteClipboardLastItem(m_viewImpl->page()->editorState().isContentRichlyEditable);
1125 }
1126 #endif
1127
1128 #if ENABLE(TIZEN_CLIPBOARD) || ENABLE(TIZEN_PASTEBOARD)
1129 void PageClientImpl::setClipboardData(const String& data, const String& type)
1130 {
1131 #if ENABLE(TIZEN_WEBKIT2_CLIPBOARD_HELPER)
1132     m_clipboardHelper->setData(data, type);
1133 #endif
1134 }
1135
1136 #if ENABLE(TIZEN_WEBKIT2_CONTEXT_MENU_CLIPBOARD)
1137 void PageClientImpl::clipboardContextMenuSelected()
1138 {
1139     m_clipboardHelper->openClipboardWindow(m_viewImpl->page()->editorState().isContentRichlyEditable);
1140 }
1141
1142 bool PageClientImpl::isClipboardWindowOpened()
1143 {
1144     return m_clipboardHelper->isClipboardWindowOpened();
1145 }
1146
1147 void PageClientImpl::closeClipboardWindow()
1148 {
1149     m_clipboardHelper->closeClipboardWindow();
1150 }
1151 #endif
1152
1153 void PageClientImpl::clearClipboardData()
1154 {
1155 #if ENABLE(TIZEN_WEBKIT2_CLIPBOARD_HELPER)
1156     m_clipboardHelper->clear();
1157 #endif
1158 }
1159 #endif
1160
1161 #if ENABLE(TIZEN_WEBKIT2_VIEW_VISIBILITY)
1162 void PageClientImpl::setIsVisible(bool isVisible)
1163 {
1164 #if ENABLE(TIZEN_WEBKIT2_TILED_AC_SHARED_PLATFORM_SURFACE_BACKUP_IMAGE)
1165     if (m_isVisible != isVisible && m_viewImpl->view() && m_pageDidRendered) {
1166         if (!isVisible && (drawingArea() && drawingArea()->layerTreeCoordinatorProxy()) && !m_shouldShowBackupTexture) {
1167             Ecore_Evas* ee = ecore_evas_ecore_evas_get(evas_object_evas_get(m_viewImpl->view()));
1168             int angle = ecore_evas_rotation_get(ee);
1169             if (angle == 0 || angle == 180) {
1170                 m_shouldMakeBackupTexture = true;
1171                 m_shouldShowBackupTexture = true;
1172                 drawContents();
1173             }
1174         }
1175     }
1176 #endif
1177
1178     m_isVisible = isVisible;
1179
1180     WebPageProxy* pageProxy = m_viewImpl->page();
1181     if (pageProxy)
1182         pageProxy->viewStateDidChange(WebPageProxy::ViewIsVisible);
1183
1184 #if ENABLE(TIZEN_CACHE_MEMORY_OPTIMIZATION)
1185     if (!m_isVisible)
1186         ewk_view_context_get(m_viewImpl->view())->clearAllDecodedData();
1187 #endif
1188 }
1189 #endif
1190
1191 #if ENABLE(TIZEN_DRAG_SUPPORT)
1192 void PageClientImpl::setDragPoint(const WebCore::IntPoint& point)
1193 {
1194     m_drag->setDragPoint(point);
1195 }
1196 bool PageClientImpl::isDragMode()
1197 {
1198     return m_drag->isDragMode();
1199 }
1200 void PageClientImpl::setDragMode(bool isDragMode)
1201 {
1202     m_drag->setDragMode(isDragMode);
1203 }
1204 void PageClientImpl::startDrag(const DragData& dragData, PassRefPtr<ShareableBitmap> dragImage)
1205 {
1206     DragData* dragInfo = new DragData(dragData.platformData(), m_drag->getDragPoint(),
1207         m_drag->getDragPoint(), dragData.draggingSourceOperationMask(), dragData.flags());
1208
1209     String dragStorageName("Drag");
1210     m_viewImpl->page()->dragEntered(dragInfo, dragStorageName);
1211     setDragMode(true);
1212     m_drag->setDragData(dragInfo);
1213     m_drag->Show();
1214 }
1215 #endif
1216
1217 #if ENABLE(TIZEN_WEBKIT2_FORM_DATABASE)
1218 bool PageClientImpl::isShowingFormDataCandidate()
1219 {
1220     return m_formDataCandidate->isShowing();
1221 }
1222
1223 void PageClientImpl::updateFormDataCandidate(const Vector<String>& data)
1224 {
1225     m_formDataCandidate->updateFormData(data);
1226 }
1227
1228 void PageClientImpl::hideFormDataCandidate()
1229 {
1230     m_formDataCandidate->hide();
1231 }
1232
1233 void PageClientImpl::showFormDataCandidate(const WebCore::IntRect& rect)
1234 {
1235     m_formDataCandidate->show(rect);
1236 }
1237 #endif
1238
1239 #if ENABLE(TIZEN_REGISTER_PROTOCOL_HANDLER)
1240 void PageClientImpl::registerProtocolHandler(const String& scheme, const String& baseURL, const String& url, const String& title)
1241 {
1242     ewkViewRegisterProtocolHandlers(m_viewImpl->view(), scheme.utf8().data(), baseURL.utf8().data(), url.utf8().data(), title.utf8().data());
1243 }
1244 #endif
1245
1246 #if ENABLE(TIZEN_CUSTOM_SCHEME_HANDLER)
1247 unsigned int PageClientImpl::isProtocolHandlerRegistered(const String& scheme, const String& baseURL, const String& url)
1248 {
1249     return ewkViewIsProtocolHandlerRegistered(m_viewImpl->view(), scheme.utf8().data(), baseURL.utf8().data(), url.utf8().data());
1250 }
1251
1252 void PageClientImpl::unregisterProtocolHandler(const String& scheme, const String& baseURL, const String& url)
1253 {
1254     ewkViewUnregisterProtocolHandlers(m_viewImpl->view(), scheme.utf8().data(), baseURL.utf8().data(), url.utf8().data());
1255 }
1256 #endif
1257
1258 #if ENABLE(TIZEN_REGISTER_CONTENT_HANDLER)
1259 void PageClientImpl::registerContentHandler(const String& mimeType, const String& baseURL, const String& url, const String& title)
1260 {
1261     ewkViewRegisterContentHandlers(m_viewImpl->view(), mimeType.utf8().data(), baseURL.utf8().data(), url.utf8().data(), title.utf8().data());
1262 }
1263
1264 unsigned int PageClientImpl::isContentHandlerRegistered(const String& mimeType, const String& baseURL, const String& url)
1265 {
1266     return ewkViewIsContentHandlerRegistered(m_viewImpl->view(), mimeType.utf8().data(), baseURL.utf8().data(), url.utf8().data());
1267 }
1268
1269 void PageClientImpl::unregisterContentHandler(const String& mimeType, const String& baseURL, const String& url)
1270 {
1271     ewkViewUnregisterContentHandlers(m_viewImpl->view(), mimeType.utf8().data(), baseURL.utf8().data(), url.utf8().data());
1272 }
1273 #endif
1274
1275 #if ENABLE(TIZEN_SEARCH_PROVIDER)
1276 void PageClientImpl::addSearchProvider(const String& baseURL, const String& engineURL)
1277 {
1278     ewkViewAddSearchProvider(m_viewImpl->view(), baseURL.utf8().data(), engineURL.utf8().data());
1279 }
1280
1281 unsigned long PageClientImpl::isSearchProviderInstalled(const String& baseURL, const String& engineURL)
1282 {
1283     return ewkViewIsSearchProviderInstalled(m_viewImpl->view(), baseURL.utf8().data(), engineURL.utf8().data());
1284 }
1285 #endif
1286
1287 #if ENABLE(TIZEN_SUPPORT_WEBAPP_META_TAG)
1288 bool PageClientImpl::getStandaloneStatus()
1289 {
1290     return ewkViewGetStandaloneStatus(m_viewImpl->view());
1291 }
1292 #endif
1293
1294 #if ENABLE(SCREEN_ORIENTATION_SUPPORT) && ENABLE(TIZEN_SCREEN_ORIENTATION_SUPPORT)
1295 bool PageClientImpl::lockOrientation(int willLockOrientation)
1296 {
1297     return ewk_view_orientation_lock(m_viewImpl->view(), willLockOrientation);
1298 }
1299
1300 void PageClientImpl::unlockOrientation()
1301 {
1302     ewk_view_orientation_unlock(m_viewImpl->view());
1303 }
1304 #endif
1305
1306 void PageClientImpl::didRenderFrame()
1307 {
1308 #if ENABLE(TIZEN_WEBKIT2_TILED_AC_SHARED_PLATFORM_SURFACE_BACKUP_IMAGE)
1309     if (m_shouldShowBackupTexture && m_isVisible)
1310         m_shouldShowBackupTexture = false;
1311 #endif
1312     if (!m_pageDidRendered) {
1313         m_pageDidRendered = true;
1314         initializeVisibleContentRect();
1315     }
1316
1317 #if ENABLE(TIZEN_PRERENDERING_FOR_ROTATION)
1318     if (m_waitFrameOfNewViewortSize) {
1319         m_waitFrameOfNewViewortSize = false;
1320         ewkViewRotatePrepared(m_viewImpl->view());
1321     }
1322 #endif
1323 }
1324
1325 #if ENABLE(TIZEN_CSS_OVERFLOW_SCROLL_ACCELERATION)
1326 void PageClientImpl::setOverflowResult(bool pressed, WebLayerID webLayerID)
1327 {
1328     setIsScrollableLayerFocused(false);
1329     setIsScrollableNodeFocused(false);
1330
1331     if (pressed) {
1332         if (webLayerID) {
1333             setIsScrollableLayerFocused(true);
1334             m_viewImpl->page()->drawingArea()->layerTreeCoordinatorProxy()->layerTreeRenderer()->setFocusedLayerID(webLayerID);
1335         } else {
1336             setIsScrollableNodeFocused(true);
1337         }
1338     }
1339 }
1340
1341 void PageClientImpl::findScrollableNode(const IntPoint& point)
1342 {
1343     WebPageProxy* pageProxy = m_viewImpl->page();
1344     if (pageProxy && pageProxy->isLoadingFinished() && pageProxy->askOverflow()) {
1345         IntPoint pointForPress(m_viewImpl->transformFromScene().mapPoint(point));
1346         WebLayerID webLayerID = 0;
1347         bool checkOverflowLayer = false;
1348 #if ENABLE(TIZEN_CSS_OVERFLOW_SCROLL_ACCELERATION_ON_UI_SIDE)
1349         DrawingAreaProxy* drawingArea = pageProxy->drawingArea();
1350         checkOverflowLayer = drawingArea && drawingArea->layerTreeCoordinatorProxy() && drawingArea->layerTreeCoordinatorProxy()->hasOverflowLayer();
1351 #endif
1352         setOverflowResult(pageProxy->setPressedNodeAtPoint(pointForPress, checkOverflowLayer, webLayerID), webLayerID);
1353     }
1354 }
1355 #endif
1356
1357 #if ENABLE(TIZEN_WEBKIT2_GET_TEXT_STYLE_FOR_SELECTION)
1358 void PageClientImpl::didGetTextStyleStateForSelection(int underlineState, int italicState, int boldState)
1359 {
1360     WebCore::IntPoint startPoint, endPoint;
1361     WebCore::IntRect leftRect, rightRect;
1362
1363     WebCore::IntRect caretRect;
1364     m_viewImpl->page()->getCaretPosition(caretRect);
1365     if (!caretRect.isEmpty()) {
1366         startPoint.setX(caretRect.x());
1367         startPoint.setY(caretRect.y() + caretRect.height());
1368
1369         endPoint.setX(caretRect.x() + caretRect.width());
1370         endPoint.setY(caretRect.y() + caretRect.height());
1371     }
1372 #if ENABLE(TIZEN_WEBKIT2_TEXT_SELECTION)
1373     else if (m_viewImpl->page()->getSelectionHandlers(leftRect, rightRect)) {
1374         startPoint.setX(leftRect.x());
1375         startPoint.setY(leftRect.y() + leftRect.height());
1376
1377         endPoint.setX(rightRect.x() + rightRect.width());
1378         endPoint.setY(rightRect.y() + rightRect.height());
1379     }
1380 #endif
1381
1382     startPoint.scale(scaleFactor(), scaleFactor());
1383     endPoint.scale(scaleFactor(), scaleFactor());
1384
1385     int viewPositionX, viewPositionY;
1386     evas_object_geometry_get(m_viewImpl->view(), &viewPositionX, &viewPositionY, NULL, NULL);
1387
1388     startPoint.move(-scrollPosition().x(),  -scrollPosition().y());
1389     startPoint.move(viewPositionX, viewPositionY);
1390
1391     endPoint.move(-scrollPosition().x(),  -scrollPosition().y());
1392     endPoint.move(viewPositionX, viewPositionY);
1393
1394     ewkViewDidGetTextStyleStateForSelection(m_viewImpl->view(), underlineState, italicState, boldState, startPoint, endPoint);
1395 }
1396 #endif
1397
1398 void PageClientImpl::didFindZoomableArea(const IntPoint& target, const IntRect& area)
1399 {
1400     ewk_view_zoomable_area_set(m_viewImpl->view(), target, area);
1401 }
1402
1403 #if ENABLE(TIZEN_ICON_DATABASE)
1404 void PageClientImpl::didReceiveIcon()
1405 {
1406     ewkViewIconReceived(m_viewImpl->view());
1407 }
1408 #endif
1409
1410 #if ENABLE(TIZEN_WEBKIT2_FOCUS_RING)
1411 void PageClientImpl::hideFocusRing()
1412 {
1413     ewkViewFocusRingHide(m_viewImpl->view());
1414 }
1415 #endif
1416 #endif // #if OS(TIZEN)
1417
1418
1419 #if ENABLE(TIZEN_WEBKIT2_TILED_AC) && ENABLE(TIZEN_RUNTIME_BACKEND_SELECTION)
1420 PageClientEvasGL::PageClientEvasGL(EwkViewImpl* viewImpl)
1421     : PageClientImpl(viewImpl)
1422     , m_evasGL(0)
1423     , m_evasGlApi(0)
1424     , m_context(0)
1425     , m_surface(0)
1426     , m_config(0)
1427 #if ENABLE(TIZEN_WEBKIT2_DIRECT_RENDERING)
1428     , m_angle(0)
1429 #endif
1430     , m_isAcceleratedCompositingModeInitialized(false)
1431 {
1432     initializeAcceleratedCompositingMode();
1433 }
1434
1435 PageClientEvasGL::~PageClientEvasGL()
1436 {
1437     m_viewImpl->page()->close();
1438 }
1439
1440 void PageClientEvasGL::updateViewportSize(const WebCore::IntSize& viewportSize, const int angle)
1441 {
1442     if (m_surface) {
1443         evas_gl_surface_destroy(m_evasGL, m_surface);
1444         m_surface = 0;
1445     }
1446     setTargetSurface();
1447
1448     PageClientImpl::updateViewportSize(viewportSize, angle);
1449 }
1450
1451 void PageClientEvasGL::setViewNeedsDisplay(const WebCore::IntRect& rect)
1452 {
1453 #if !ENABLE(TIZEN_WEBKIT2_DIRECT_RENDERING)
1454     drawContents();
1455 #endif
1456     m_viewImpl->redrawRegion(rect);
1457
1458 #if ENABLE(TIZEN_SCREEN_READER)
1459     if (rect.intersects(ewkViewGetFocusRing(m_viewImpl->view())->rect()))
1460         m_viewImpl->page()->recalcScreenReaderFocusRect();
1461 #endif
1462 }
1463
1464 void PageClientEvasGL::displayViewport()
1465 {
1466 #if ENABLE(TIZEN_WEBKIT2_DIRECT_RENDERING)
1467     // We should not draw here when Direct Rendering is enabled.
1468     // Because we will draw directly when evas is updated - on_pixels_for_accelerated_compositing().
1469     ewk_view_mark_for_sync(m_viewImpl->view());
1470 #else
1471     setViewNeedsDisplay(IntRect(IntPoint(), viewSize()));
1472 #endif
1473
1474 #if ENABLE(TIZEN_WEBKIT2_TILED_SCROLLBAR)
1475     updateScrollbar();
1476 #endif
1477
1478 #if ENABLE(TIZEN_SCREEN_READER)
1479     m_viewImpl->page()->recalcScreenReaderFocusRect();
1480 #endif
1481 }
1482
1483 void PageClientEvasGL::drawContents()
1484 {
1485     if (evas_gl_make_current(m_evasGL, m_surface, m_context) != EINA_TRUE)
1486         return;
1487
1488     WebCore::TransformationMatrix matrix;
1489     IntRect clipRect;
1490     IntSize ewkViewSize = viewSize();
1491
1492 #if ENABLE(TIZEN_WEBKIT2_DIRECT_RENDERING)
1493     Ecore_Evas* ee = ecore_evas_ecore_evas_get(evas_object_evas_get(m_viewImpl->view()));
1494     m_angle = ecore_evas_rotation_get(ee);
1495     if (drawingArea())
1496         drawingArea()->setAngle(m_angle);
1497     matrix.rotate3d(0.0, 0.0, 1.0, 360 - m_angle);
1498
1499     if (m_angle == 90 || m_angle == 270) {
1500         glViewport(0, 0, ewkViewSize.height(), ewkViewSize.width());
1501         if (m_angle == 90)
1502             matrix.translate(-ewkViewSize.width(), 0);
1503         else if (m_angle == 270)
1504             matrix.translate(0, -ewkViewSize.height());
1505         clipRect = IntRect(IntPoint(), ewkViewSize.transposedSize());
1506     } else {
1507         glViewport(0, 0, ewkViewSize.width(), ewkViewSize.height());
1508         if (m_angle == 180)
1509             matrix.translate(-ewkViewSize.width(), -ewkViewSize.height());
1510         clipRect = IntRect(IntPoint(), ewkViewSize);
1511     }
1512 #else
1513     glViewport(0, 0, ewkViewSize.width(), ewkViewSize.height());
1514     clipRect = IntRect(IntPoint(), ewkViewSize);
1515 #endif
1516     matrix *= m_viewImpl->transformToView().toTransformationMatrix();
1517
1518     if (drawingArea()) {
1519         if (drawingArea()->layerTreeCoordinatorProxy()) {
1520             WebLayerTreeRenderer* renderer = drawingArea()->layerTreeCoordinatorProxy()->layerTreeRenderer();
1521 #if ENABLE(TIZEN_WEBKIT2_TILED_AC_SHARED_PLATFORM_SURFACE_BACKUP_IMAGE)
1522             if (m_shouldMakeBackupTexture) {
1523                 glViewport(0, 0, m_initialViewRect.width(), m_initialViewRect.height());
1524                 glClearColor(1, 1, 1, 1);
1525                 glClear(GL_COLOR_BUFFER_BIT);
1526                 renderer->paintToBackupTexture(matrix, 1.0f, m_initialViewRect, m_bgColor);
1527                 m_shouldMakeBackupTexture = false;
1528             } else if (m_shouldShowBackupTexture) {
1529                 matrix.makeIdentity();
1530                 glViewport(0, 0, m_initialViewRect.width(), m_initialViewRect.height());
1531                 renderer->showBackupTexture(matrix, 1.0f, m_initialViewRect);
1532             } else
1533 #endif
1534             renderer->paintToCurrentGLContext(matrix, 1.0f, clipRect, m_bgColor);
1535         }
1536     }
1537 }
1538
1539 void PageClientEvasGL::didRenderFrame()
1540 {
1541     ewkViewFrameRendered(m_viewImpl->view());
1542     PageClientImpl::didRenderFrame();
1543 }
1544
1545 bool PageClientEvasGL::makeContextCurrent()
1546 {
1547     return evas_gl_make_current(m_evasGL, m_surface, m_context);
1548 }
1549
1550 void PageClientEvasGL::initializeAcceleratedCompositingMode()
1551 {
1552     Evas* evas = evas_object_evas_get(m_viewImpl->view());
1553
1554     m_config = evas_gl_config_new();
1555 #if ENABLE(TIZEN_WEBKIT2_DIRECT_RENDERING)
1556     setenv("EVAS_GL_DIRECT_OVERRIDE", "1", 1);
1557     m_config->options_bits = EVAS_GL_OPTIONS_DIRECT;
1558 #endif
1559     m_config->color_format = EVAS_GL_RGBA_8888;
1560     m_config->depth_bits = EVAS_GL_DEPTH_BIT_24;
1561     m_config->stencil_bits = EVAS_GL_STENCIL_BIT_8;
1562
1563     m_evasGL = evas_gl_new(evas);
1564     if (!m_evasGL) {
1565         evas_gl_config_free(m_config);
1566         m_config = 0;
1567         TIZEN_LOGE("failed to create evas_gl");
1568         return;
1569     }
1570
1571     Evas_GL_API* evasGlApi = evas_gl_api_get(m_evasGL);
1572     if (!evasGlApi) {
1573         evas_gl_free(m_evasGL);
1574         m_evasGL = 0;
1575         evas_gl_config_free(m_config);
1576         m_config = 0;
1577         TIZEN_LOGE("failed to get evas_gl_api");
1578         return;
1579     }
1580     WebCore::EvasGlApiInterface::shared().initialize(evasGlApi);
1581
1582     m_context = evas_gl_context_create(m_evasGL, 0);
1583     if (!m_context) {
1584         evas_gl_free(m_evasGL);
1585         m_evasGL = 0;
1586         evas_gl_config_free(m_config);
1587         m_config = 0;
1588         TIZEN_LOGE("failed to create evas_gl_context");
1589         return;
1590     }
1591
1592     setTargetSurface();
1593     m_isAcceleratedCompositingModeInitialized =  true;
1594 }
1595
1596 void PageClientEvasGL::finalizeAcceleratedCompositingMode()
1597 {
1598     if (m_evasGL) {
1599         if (m_surface) {
1600             evas_gl_surface_destroy(m_evasGL, m_surface);
1601             m_surface = 0;
1602         }
1603         if (m_context) {
1604             evas_gl_context_destroy(m_evasGL, m_context);
1605             m_context = 0;
1606         }
1607         if (m_config) {
1608             evas_gl_config_free(m_config);
1609             m_config = 0;
1610         }
1611         evas_gl_free(m_evasGL);
1612         m_evasGL = 0;
1613     }
1614
1615 #if ENABLE(TIZEN_WEBKIT2_DIRECT_RENDERING)
1616     setenv("EVAS_GL_DIRECT_OVERRIDE", "0", 1);
1617 #endif
1618     m_isAcceleratedCompositingModeInitialized = false;
1619 }
1620
1621 void PageClientEvasGL::enterAcceleratedCompositingMode(const LayerTreeContext&)
1622 {
1623     if (!m_isAcceleratedCompositingModeInitialized)
1624         initializeAcceleratedCompositingMode();
1625 }
1626
1627 void PageClientEvasGL::exitAcceleratedCompositingMode()
1628 {
1629     if (m_isAcceleratedCompositingModeInitialized)
1630         finalizeAcceleratedCompositingMode();
1631 }
1632
1633 void PageClientEvasGL::setTargetSurface()
1634 {
1635     if (!m_evasGL)
1636         return;
1637
1638     int width, height;
1639     evas_object_geometry_get(m_viewImpl->view(), 0, 0, &width, &height);
1640     if (width == 0 || height == 0)
1641         return;
1642
1643     m_surface = evas_gl_surface_create(m_evasGL, m_config, width, height);
1644     if (!m_surface) {
1645         TIZEN_LOGE("failed to create Evas_GL_Surface");
1646         return;
1647     }
1648
1649 #if ENABLE(TIZEN_WEBKIT2_DIRECT_RENDERING)
1650     makeContextCurrent();
1651 #else
1652     if (makeContextCurrent()) {
1653         glViewport(0, 0, width, height);
1654         glClearColor(1.0, 1.0, 1.0, 1.0);
1655         glClear(GL_COLOR_BUFFER_BIT);
1656         glFinish();
1657     }
1658 #endif
1659
1660     Evas_Native_Surface nativeSurface;
1661     if (evas_gl_native_surface_get(m_evasGL, m_surface, &nativeSurface))
1662         ewk_view_image_native_surface_set(m_viewImpl->view(), &nativeSurface);
1663 }
1664 #endif
1665
1666 } // namespace WebKit