2c8b17ed9799e1bbfdfaf90e3b6a2089a4ee97ae
[WebKit-https.git] / Source / WebCore / platform / ios / wak / WKView.mm
1 /*
2  * Copyright (C) 2005, 2006, 2007, 2008, 2009 Apple Inc. All rights reserved.
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 #import "config.h"
27 #import "WKViewPrivate.h"
28
29 #if PLATFORM(IOS)
30
31 #import "WAKViewInternal.h"
32 #import "WAKWindow.h"
33 #import "WKUtilities.h"
34 #import <wtf/Assertions.h>
35
36 void _WKViewSetSuperview (WKViewRef view, WKViewRef superview)
37 {
38     // Not retained.
39     view->superview = superview;
40 }
41
42 void _WKViewWillRemoveSubview(WKViewRef view, WKViewRef subview)
43 {
44     if (view->context && view->context->willRemoveSubviewCallback)
45         view->context->willRemoveSubviewCallback(view, subview);
46 }
47
48 void _WKViewSetWindow (WKViewRef view, WAKWindow *window)
49 {
50     if (view->window == window)
51         return;
52
53     [window retain];
54     [view->window release];
55
56     view->window = window;
57
58     // Set the window on all subviews.
59     WKViewRef firstChild = WKViewFirstChild(view);
60     if (firstChild) {
61         _WKViewSetWindow (firstChild, window);
62         WKViewRef nextSibling = WKViewNextSibling(firstChild);
63         while (nextSibling) {
64             _WKViewSetWindow (nextSibling, window);
65             nextSibling = WKViewNextSibling(nextSibling);
66         }
67     }
68
69     if (view->context && view->context->notificationCallback)
70         view->context->notificationCallback (view, WKViewNotificationViewDidMoveToWindow, view->context->notificationUserInfo);
71 }
72
73 static void _WKViewClearSuperview(const void *value, void *context)
74 {
75     UNUSED_PARAM(context);
76     _WKViewSetSuperview((WKViewRef)value, 0);
77 }
78
79 static void _WKViewDealloc (WKObjectRef v)
80 {
81     WKViewRef view = (WKViewRef)v;
82     
83     if (view->subviews) {
84         CFArrayApplyFunction(view->subviews, CFRangeMake(0, CFArrayGetCount(view->subviews)), _WKViewClearSuperview, NULL);
85         CFRelease (view->subviews);
86         view->subviews = 0;
87     }
88
89     [view->window release];
90     view->window = nil;
91 }
92
93 void WKViewInitialize (WKViewRef view, CGRect frame, WKViewContext *context)
94 {
95     view->origin = frame.origin;
96     view->bounds.origin = CGPointZero;
97     view->bounds.size = frame.size;
98     
99     view->context = context;
100     view->autoresizingMask = NSViewNotSizable;
101     view->scale = 1.0f;
102 }
103
104 WKClassInfo WKViewClassInfo = { &WKObjectClass, "WKView", _WKViewDealloc };
105
106 WKViewRef WKViewCreateWithFrame (CGRect frame, WKViewContext *context)
107 {
108     WKViewRef view = (WKViewRef)WKCreateObjectWithSize (sizeof(struct _WKView), &WKViewClassInfo);
109     if (!view)
110         return 0;
111     
112     WKViewInitialize (view, frame, context);
113     
114     return view;
115 }
116
117 void _WKViewSetViewContext (WKViewRef view, WKViewContext *context)
118 {
119     if (!view) {
120         WKError("invalid parameter");
121         return;
122     }
123     view->context = context;
124 }
125
126 CGRect WKViewGetBounds (WKViewRef view)
127 {
128     if (!view) {
129         WKError("invalid parameter");
130         return CGRectZero;
131     }
132     
133     return view->bounds;
134 }
135
136 CGRect WKViewGetFrame (WKViewRef view)
137 {
138     if (!view) {
139         WKError("invalid parameter");
140         return CGRectZero;
141     }
142     
143     return WKViewConvertRectToSuperview(view, view->bounds);
144 }
145
146 CGPoint WKViewGetOrigin(WKViewRef view)
147 {
148     if (!view) {
149         WKError("invalid parameter");
150         return CGPointZero;
151     }
152
153     return view->origin;
154 }
155
156 static void _WKViewRecursivelyInvalidateGState(WKViewRef view)
157 {
158     if (!view) {
159         WKError("invalid parameter");
160         return;
161     }
162
163     if (view->context && view->context->invalidateGStateCallback)
164         view->context->invalidateGStateCallback(view);
165     
166     WKViewRef subview = WKViewFirstChild(view);
167     while (subview) {
168         _WKViewRecursivelyInvalidateGState(subview);
169         subview = WKViewNextSibling(subview);
170     }
171 }
172
173 void WKViewSetFrameOrigin (WKViewRef view, CGPoint newOrigin)
174 {
175     if (!view) {
176         WKError("invalid parameter");
177         return;
178     }
179     
180     ASSERT(!isinf(newOrigin.x));
181     ASSERT(!isnan(newOrigin.x));
182     ASSERT(!isinf(newOrigin.y));
183     ASSERT(!isnan(newOrigin.y));
184     
185     if (!CGPointEqualToPoint(view->origin, newOrigin)) {
186         view->origin = newOrigin;
187         _WKViewRecursivelyInvalidateGState(view);
188     }
189 }
190
191 #define XSIZING_BITS(mask)      ((mask) & 7)
192 #define YSIZING_BITS(mask)      (((mask) >> 3) & 7)
193
194 static void _WKViewAutoresizeCoord(bool bByHeight, unsigned int sizingMethod, const CGRect *origSuperFrame, const CGRect *newSuperFrame, CGRect *newFrame)
195 {
196     CGFloat origSuperFrameWidthOrHeight;
197     CGFloat newSuperFrameWidthOrHeight;
198     CGFloat *origFrameXorY;
199     CGFloat *origFrameWidthOrHeight;
200     CGFloat prop;
201     CGFloat tmp;
202     CGFloat xOrY;
203     CGFloat widthOrHeight;
204     CGFloat origMarginsTotal;
205     CGFloat origWidthMinusMinMargin;
206     
207     if (bByHeight) {
208         sizingMethod = YSIZING_BITS(sizingMethod);
209         origSuperFrameWidthOrHeight = origSuperFrame->size.height;
210         newSuperFrameWidthOrHeight = newSuperFrame->size.height;
211         origFrameXorY = &newFrame->origin.y;
212         origFrameWidthOrHeight = &newFrame->size.height;
213     } else {
214         sizingMethod = XSIZING_BITS(sizingMethod);
215         origSuperFrameWidthOrHeight = origSuperFrame->size.width;
216         newSuperFrameWidthOrHeight = newSuperFrame->size.width;
217         origFrameXorY = &newFrame->origin.x;
218         origFrameWidthOrHeight = &newFrame->size.width;
219     }
220     
221     xOrY = *origFrameXorY;
222     widthOrHeight = *origFrameWidthOrHeight;
223     
224     switch (sizingMethod) {
225         case NSViewNotSizable:
226         case NSViewMaxXMargin:
227             break;
228         case NSViewWidthSizable:
229             widthOrHeight = newSuperFrameWidthOrHeight - (origSuperFrameWidthOrHeight - widthOrHeight);
230             if (widthOrHeight < 0.0f)
231                 widthOrHeight = 0.0f;
232                 break;
233         case NSViewWidthSizable | NSViewMaxXMargin:
234             origWidthMinusMinMargin = origSuperFrameWidthOrHeight - xOrY;
235             if (widthOrHeight) {
236                 if (origWidthMinusMinMargin != 0.0f) {
237                     prop = widthOrHeight / origWidthMinusMinMargin;
238                 } else {
239                     prop = 0.0f;
240                 }
241             } else {
242                 prop = 1.0f;
243             }
244                 widthOrHeight = ((newSuperFrameWidthOrHeight - xOrY)) * prop;
245             if (widthOrHeight < 0.0f)
246                 widthOrHeight = 0.0f;
247                 break;
248         case NSViewMinXMargin:
249             xOrY = newSuperFrameWidthOrHeight - (origSuperFrameWidthOrHeight - xOrY);
250             if (xOrY < 0.0f)
251                 xOrY = 0.0f;
252             break;
253         case NSViewMinXMargin | NSViewMaxXMargin:
254             origMarginsTotal = origSuperFrameWidthOrHeight - widthOrHeight;
255             if (xOrY && origMarginsTotal != 0.0f) {
256                 prop = xOrY / origMarginsTotal;
257             }
258                 // Do the 50/50 split even if XorY = 0 and the WidthOrHeight is only
259                 // one pixel shorter...
260                 // FIXME: If origMarginsTotal is in the range (0, 1) then we won't do the 50/50 split. Is this right?
261                 else if (origMarginsTotal == 0.0f 
262                     || (abs(static_cast<int>(origMarginsTotal)) == 1)) {
263                     prop = 0.5f;  // Then split it 50:50.
264                 }
265                 else {
266                     prop = 1.0f;
267                 }
268                 xOrY = ((newSuperFrameWidthOrHeight - widthOrHeight)) * prop;
269             if (xOrY < 0.0f)
270                 xOrY = 0.0f;
271                 break;
272         case NSViewMinXMargin | NSViewWidthSizable:
273             tmp = xOrY + widthOrHeight;
274             if (tmp)
275                 prop = xOrY / tmp;
276             else
277                 prop = 0.5f;
278             xOrY = ((newSuperFrameWidthOrHeight - (origSuperFrameWidthOrHeight - tmp))) * prop;
279             widthOrHeight  = newSuperFrameWidthOrHeight - (xOrY + (origSuperFrameWidthOrHeight - tmp));
280             if (xOrY < 0.0f)
281                 xOrY = 0.0f;
282                 if (widthOrHeight < 0.0f)
283                     widthOrHeight = 0.0f;
284                     break;
285         case NSViewMinXMargin | NSViewWidthSizable | NSViewMaxXMargin:
286             if (origSuperFrameWidthOrHeight)
287                 prop = xOrY / origSuperFrameWidthOrHeight;
288             else
289                 prop = 1.0f / 3.0f;
290             xOrY = (newSuperFrameWidthOrHeight * prop);
291             if (origSuperFrameWidthOrHeight)
292                 prop = widthOrHeight / origSuperFrameWidthOrHeight;
293             else
294                 prop = 1.0f / 3.0f;
295             widthOrHeight = (newSuperFrameWidthOrHeight * prop);
296             break;
297     }
298     
299     *origFrameXorY = floorf(xOrY);
300     *origFrameWidthOrHeight = floorf(widthOrHeight);
301 }
302
303 void _WKViewAutoresize(WKViewRef view, const CGRect *oldSuperFrame, const CGRect *newSuperFrame)
304 {
305     if (view->autoresizingMask != NSViewNotSizable) {
306         CGRect newFrame = WKViewGetFrame(view);
307         _WKViewAutoresizeCoord(false, view->autoresizingMask, oldSuperFrame, newSuperFrame, &newFrame);
308         _WKViewAutoresizeCoord(true, view->autoresizingMask, oldSuperFrame, newSuperFrame, &newFrame);
309         WKViewSetFrameOrigin(view, newFrame.origin);
310         WKViewSetFrameSize(view, newFrame.size);
311     }
312 }
313
314 static void _WKViewAutoresizeChildren(WKViewRef view, const CGRect *oldSuperFrame, const CGRect *newSuperFrame)
315 {
316     WKViewRef child;
317     for (child = WKViewFirstChild(view); child != NULL; child = WKViewNextSibling(child)) {
318         _WKViewAutoresize(child, oldSuperFrame, newSuperFrame);
319     }        
320 }
321
322 void WKViewSetFrameSize (WKViewRef view, CGSize newSize)
323 {
324     if (!view) {
325         WKError("invalid parameter");
326         return;
327     }
328     
329     ASSERT(!isinf(newSize.width));
330     ASSERT(!isnan(newSize.width));
331     ASSERT(!isinf(newSize.height));
332     ASSERT(!isnan(newSize.height));
333     
334     CGRect frame;
335     frame.origin = CGPointZero;
336     frame.size = newSize;
337     CGSize boundsSize = WKViewConvertRectFromSuperview(view, frame).size;
338     WKViewSetBoundsSize(view, boundsSize);
339 }
340
341 void WKViewSetBoundsSize (WKViewRef view, CGSize newSize)
342 {
343     if (CGSizeEqualToSize(view->bounds.size, newSize))
344         return;
345     
346     CGRect oldFrame = WKViewGetFrame(view);
347     view->bounds.size = newSize;
348     CGRect newFrame = WKViewGetFrame(view);
349     
350     if (view->context && view->context->notificationCallback)
351         view->context->notificationCallback (view, WKViewNotificationViewFrameSizeChanged, view->context->notificationUserInfo);
352     
353     _WKViewAutoresizeChildren(view, &oldFrame, &newFrame);    
354     _WKViewRecursivelyInvalidateGState(view);
355 }
356
357 void WKViewSetBoundsOrigin(WKViewRef view, CGPoint newOrigin)
358 {
359     if (CGPointEqualToPoint(view->bounds.origin, newOrigin))
360         return;
361
362     view->bounds.origin = newOrigin;
363
364     _WKViewRecursivelyInvalidateGState(view);    
365 }
366
367 void WKViewSetScale(WKViewRef view, float scale)
368 {
369     ASSERT(!isinf(scale));
370     ASSERT(!isnan(scale));
371     
372     if (view->scale == scale)
373         return;
374     
375     view->scale = scale;
376     
377     if (view->context && view->context->notificationCallback)
378         view->context->notificationCallback (view, WKViewNotificationViewFrameSizeChanged, view->context->notificationUserInfo);
379 }
380
381 float WKViewGetScale(WKViewRef view)
382 {
383     return view->scale;
384 }
385
386 WAKWindow *WKViewGetWindow (WKViewRef view)
387 {
388     if (!view) {
389         WKError("invalid parameter");
390         return 0;
391     }
392     
393     return view->window;
394 }
395
396 CFArrayRef WKViewGetSubviews (WKViewRef view)
397 {
398     if (!view) {
399         WKError("invalid parameter");
400         return 0;
401     }
402     
403     return view->subviews;
404 }
405
406 void WKViewAddSubview (WKViewRef view, WKViewRef subview)
407 {
408     if (!view || !subview) {
409         WKError("invalid parameter");
410         return;
411     }
412     
413     if (!view->subviews) {
414         view->subviews = CFArrayCreateMutable(NULL, 0, &WKCollectionArrayCallBacks);
415     }
416     CFArrayAppendValue (view->subviews, subview);
417     _WKViewSetSuperview (subview, view);
418     
419     // Set the window on subview and all it's children.
420     _WKViewSetWindow (subview, view->window);
421 }
422
423 void WKViewRemoveFromSuperview (WKViewRef view)
424 {
425     if (!view) {
426         WKError("invalid parameter");
427         return;
428     }
429
430     _WKViewSetWindow (view, 0);
431
432     if (!view->superview) {
433         return;
434     }
435     
436     CFMutableArrayRef svs = view->superview->subviews;
437     if (!svs) {
438         WKError("superview has no subviews");
439         return;
440     }
441
442     CFIndex index = WKArrayIndexOfValue (svs, view);
443     if (index < 0) {
444         WKError("view not in superview subviews");
445         return;
446     }
447
448     _WKViewWillRemoveSubview(view->superview, view);
449     
450     CFArrayRemoveValueAtIndex (svs, index);
451
452     _WKViewSetSuperview (view, 0);
453 }
454
455 WKViewRef WKViewFirstChild (WKViewRef view)
456 {
457     if (!view) {
458         WKError("invalid parameter");
459         return 0;
460     }
461
462     CFArrayRef sv = view->subviews;
463     
464     if (!sv)
465         return 0;
466         
467     CFIndex count = CFArrayGetCount (sv);
468     if (!count)
469         return 0;
470         
471     return (const WKViewRef)CFArrayGetValueAtIndex (sv, 0);
472 }
473
474 WKViewRef WKViewNextSibling (WKViewRef view)
475 {
476     if (!view) {
477         WKError("invalid parameter");
478         return 0;
479     }
480
481     if (!view->superview)
482         return 0;
483         
484     CFArrayRef svs = view->superview->subviews;
485     if (!svs)
486         return 0;
487         
488     CFIndex thisIndex = WKArrayIndexOfValue (svs, view);
489     if (thisIndex < 0) {
490         WKError("internal error, view is not present in superview subviews");
491         return 0;
492     }
493     
494     CFIndex count = CFArrayGetCount (svs);
495     if (thisIndex+1 >= count)
496         return 0;
497         
498     return (const WKViewRef)CFArrayGetValueAtIndex (svs, thisIndex+1);
499 }
500
501 // To remove, see: <rdar://problem/10360425> Remove WKViewTraverseNext from Skankphone
502 WKViewRef WKViewTraverseNext(WKViewRef view)
503 {
504     if (!view) {
505         WKError("invalid parameter");
506         return 0;
507     }
508
509     WKViewRef firstChild = WKViewFirstChild(view);
510     if (firstChild)
511         return firstChild;
512
513     WKViewRef nextSibling = WKViewNextSibling(view);
514     if (nextSibling)
515         return nextSibling;
516
517     while (view && !WKViewNextSibling(view)) {
518         WAKView *wakView = WAKViewForWKViewRef(view);
519         WAKView *superView = [wakView superview];
520         view = [superView _viewRef];
521     }
522         
523     if (view)
524         return WKViewNextSibling(view);
525     
526     return 0;
527 }
528
529 CGAffineTransform _WKViewGetTransform(WKViewRef view)
530 {
531     CGAffineTransform transform;
532     transform = CGAffineTransformMakeTranslation(view->origin.x, view->origin.y);
533     transform = CGAffineTransformScale(transform, view->scale, view->scale);
534     transform = CGAffineTransformTranslate(transform, -view->bounds.origin.x, -view->bounds.origin.y);
535     return transform;
536 }
537
538 CGRect WKViewGetVisibleRect(WKViewRef viewRef)
539 {
540     if (!viewRef) {
541         WKError("invalid parameter");
542         return CGRectZero;
543     }
544
545     WKViewRef view = viewRef;
546     CGRect rect = WKViewGetBounds(view);
547     WKViewRef superview = view->superview;
548     
549     while (superview != NULL) {
550         rect = WKViewConvertRectToSuperview(view, rect);
551         rect = CGRectIntersection(WKViewGetBounds(superview), rect);
552         view = superview;
553         superview = superview->superview;
554     }
555     
556     if (view != viewRef) {
557         rect = WKViewConvertRectToBase(view, rect);
558         rect = WKViewConvertRectFromBase(viewRef, rect);
559     }
560     
561     return rect;
562 }
563
564 CGRect WKViewConvertRectToSuperview(WKViewRef view, CGRect r)
565 {
566     if (!view) {
567         WKError("invalid parameter");
568         return CGRectZero;
569     }
570     
571     return CGRectApplyAffineTransform(r, _WKViewGetTransform(view));
572 }
573
574 CGRect WKViewConvertRectToBase(WKViewRef view, CGRect r)
575 {
576     if (!view) {
577         WKError("invalid parameter");
578         return CGRectZero;
579     }
580
581     CGRect aRect = r;
582     
583     while (view) {
584         aRect = WKViewConvertRectToSuperview (view, aRect);    
585         view = view->superview;
586     }
587     
588     return aRect;
589 }
590
591 CGPoint WKViewConvertPointToSuperview(WKViewRef view, CGPoint p)
592 {
593     if (!view) {
594         WKError("invalid parameter");
595         return CGPointZero;
596     }
597
598     return CGPointApplyAffineTransform(p, _WKViewGetTransform(view));
599 }
600
601 CGPoint WKViewConvertPointFromSuperview(WKViewRef view, CGPoint p)
602 {
603     if (!view) {
604         WKError("invalid parameter");
605         return CGPointZero;
606     }
607     
608     CGAffineTransform transform = CGAffineTransformInvert(_WKViewGetTransform(view));
609     return CGPointApplyAffineTransform(p, transform);
610 }
611
612 CGPoint WKViewConvertPointToBase(WKViewRef view, CGPoint p)
613 {
614     if (!view) {
615         WKError("invalid parameter");
616         return CGPointZero;
617     }
618
619     CGPoint aPoint = p;
620     
621     while (view) {
622         aPoint = WKViewConvertPointToSuperview (view, aPoint);    
623         view = view->superview;
624     }
625     
626     return aPoint;
627 }
628
629 #define VIEW_ARRAY_SIZE 128
630
631 static void _WKViewGetAncestorViewsIncludingView (WKViewRef view, WKViewRef *views, unsigned maxViews, unsigned *viewCount)
632 {
633     unsigned count = 0;
634     
635     views[count++] = view;
636     WKViewRef superview = view->superview;
637     while (superview) {
638         views[count++] = superview;
639         if (count >= maxViews) {
640             WKError("Exceeded maxViews, use malloc/realloc");
641             *viewCount = 0;
642             return;
643         }
644         superview = superview->superview;
645     }
646     *viewCount = count;
647 }
648
649 CGPoint WKViewConvertPointFromBase(WKViewRef view, CGPoint p)
650 {
651     if (!view) {
652         WKError("invalid parameter");
653         return CGPointZero;
654     }
655
656     WKViewRef views[VIEW_ARRAY_SIZE];
657     unsigned viewCount = 0;
658
659     _WKViewGetAncestorViewsIncludingView (view, views, VIEW_ARRAY_SIZE, &viewCount);
660     if (viewCount == 0)
661         return CGPointZero;
662
663     CGPoint aPoint = p;
664     int i;
665     for (i = viewCount-1; i >= 0; i--) {
666         aPoint = WKViewConvertPointFromSuperview (views[i], aPoint);
667     }
668         
669     return aPoint;
670 }
671
672 CGRect WKViewConvertRectFromSuperview(WKViewRef view, CGRect r)
673 {
674     if (!view) {
675         WKError("invalid parameter");
676         return CGRectZero;
677     }
678     
679     CGAffineTransform transform = CGAffineTransformInvert(_WKViewGetTransform(view));
680     return CGRectApplyAffineTransform(r, transform);
681 }
682
683 CGRect WKViewConvertRectFromBase(WKViewRef view, CGRect r)
684 {
685     if (!view) {
686         WKError("invalid parameter");
687         return CGRectZero;
688     }
689
690     WKViewRef views[VIEW_ARRAY_SIZE];
691     unsigned viewCount = 0;
692
693     _WKViewGetAncestorViewsIncludingView (view, views, VIEW_ARRAY_SIZE, &viewCount);
694     if (viewCount == 0)
695         return CGRectZero;
696     
697     CGRect aRect = r;
698     int i;
699     for (i = viewCount-1; i >= 0; i--) {
700         aRect = WKViewConvertRectFromSuperview (views[i], aRect);
701     }
702         
703     return aRect;
704 }
705
706 bool WKViewAcceptsFirstResponder (WKViewRef view)
707 {
708     bool result = TRUE;
709     if (view && view->context && view->context->responderCallback)
710         result = view->context->responderCallback(view, WKViewResponderAcceptsFirstResponder, view->context->responderUserInfo);
711     return result;
712 }
713
714 bool WKViewBecomeFirstResponder (WKViewRef view)
715 {
716     bool result = TRUE;
717     if (view && view->context && view->context->responderCallback)
718         result = view->context->responderCallback(view, WKViewResponderBecomeFirstResponder, view->context->responderUserInfo);
719     return result;
720 }
721
722 bool WKViewResignFirstResponder (WKViewRef view)
723 {
724     bool result = TRUE;
725     if (view && view->context && view->context->responderCallback)
726         result = view->context->responderCallback(view, WKViewResponderResignFirstResponder, view->context->responderUserInfo);
727     return result;
728 }
729
730 unsigned int WKViewGetAutoresizingMask(WKViewRef view)
731 {
732     if (!view) {
733         WKError("invalid parameter");
734         return 0;
735     }    
736     return view->autoresizingMask;
737 }
738
739 void WKViewSetAutoresizingMask (WKViewRef view, unsigned int mask)
740 {
741     if (!view) {
742         WKError("invalid parameter");
743         return;
744     }    
745     view->autoresizingMask = mask;
746 }
747
748 #endif // PLATFORM(IOS)