API  0.9.10
CPControl.j
Go to the documentation of this file.
1 /*
2  * CPControl.j
3  * AppKit
4  *
5  * Created by Francisco Tolmasky.
6  * Copyright 2008, 280 North, Inc.
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public
10  * License as published by the Free Software Foundation; either
11  * version 2.1 of the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with this library; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
21  */
22 
23 
24 
25 @global CPApp
26 
27 @protocol CPControlTextEditingDelegate <CPObject>
28 
29 @optional
30 - (void)controlTextDidBeginEditing:(CPNotification)aNotification;
31 - (void)controlTextDidChange:(CPNotification)aNotification;
32 - (void)controlTextDidEndEditing:(CPNotification)aNotification;
33 - (void)controlTextDidFocus:(CPNotification)aNotification;
34 - (void)controlTextDidBlur:(CPNotification)aNotification;
35 - (BOOL)control:(CPControl)control didFailToFormatString:(CPString)string errorDescription:(CPString)error;
36 
37 @end
38 
39 @typedef CPControlSize
43 
44 @typedef CPLineBreakMode
51 
52 @typedef CPVerticalTextAlignment
56 
57 // Deprecated for use with images, use the CPImageScale constants
58 @typedef CPImageScaling
62 
67 
68 @typedef CPCellImagePosition
76 
80 
81 CPControlNormalBackgroundColor = "CPControlNormalBackgroundColor";
82 CPControlSelectedBackgroundColor = "CPControlSelectedBackgroundColor";
83 CPControlHighlightedBackgroundColor = "CPControlHighlightedBackgroundColor";
84 CPControlDisabledBackgroundColor = "CPControlDisabledBackgroundColor";
85 
86 CPControlTextDidBeginEditingNotification = "CPControlTextDidBeginEditingNotification";
87 CPControlTextDidChangeNotification = "CPControlTextDidChangeNotification";
88 CPControlTextDidEndEditingNotification = "CPControlTextDidEndEditingNotification";
89 
91 
97 @implementation CPControl : CPView
98 {
99  id _value;
100  CPFormatter _formatter;
101 
102  // Target-Action Support
103  id _target;
104  SEL _action;
105  int _sendActionOn;
106  BOOL _sendsActionOnEndEditing;
107 
108  // Mouse Tracking Support
109  BOOL _continuousTracking;
110  BOOL _trackingWasWithinFrame;
111  unsigned _trackingMouseDownFlags;
112  CGPoint _previousTrackingLocation;
113 
114  CPControlSize _controlSize;
115 
116  CPWritingDirection _baseWritingDirection;
117 }
118 
120 {
121  return @{
122  @"alignment": CPLeftTextAlignment,
123  @"vertical-alignment": CPTopVerticalTextAlignment,
124  @"line-break-mode": CPLineBreakByClipping,
125  @"text-color": [CPColor blackColor],
126  @"font": [CPFont systemFontOfSize:CPFontCurrentSystemSize],
127  @"text-shadow-color": [CPNull null],
128  @"text-shadow-offset": CGSizeMakeZero(),
129  @"image-position": CPImageLeft,
130  @"image-scaling": CPScaleToFit,
131  @"min-size": CGSizeMakeZero(),
132  @"max-size": CGSizeMake(-1.0, -1.0),
133  @"nib2cib-adjustment-frame": CGRectMakeZero()
134  };
135 }
136 
137 + (void)initialize
138 {
139  if (self !== [CPControl class])
140  return;
141 
142  [self exposeBinding:@"value"];
143  [self exposeBinding:@"objectValue"];
144  [self exposeBinding:@"stringValue"];
145  [self exposeBinding:@"integerValue"];
146  [self exposeBinding:@"intValue"];
147  [self exposeBinding:@"doubleValue"];
148  [self exposeBinding:@"floatValue"];
149 
150  [self exposeBinding:@"enabled"];
151 }
152 
153 + (Class)_binderClassForBinding:(CPString)aBinding
154 {
155  if (aBinding === CPValueBinding)
156  return [_CPValueBinder class];
157  else if ([aBinding hasPrefix:CPEnabledBinding])
158  return [CPMultipleValueAndBinding class];
159 
160  return [super _binderClassForBinding:aBinding];
161 }
162 
166 - (void)_continuouslyReverseSetBinding
167 {
168  var binderClass = [[self class] _binderClassForBinding:CPValueBinding],
169  theBinding = [binderClass getBinding:CPValueBinding forObject:self];
170 
171  if ([theBinding continuouslyUpdatesValue])
172  [theBinding reverseSetValueFor:@"objectValue"];
173 }
174 
175 - (void)_reverseSetBinding
176 {
177  var binderClass = [[self class] _binderClassForBinding:CPValueBinding],
178  theBinding = [binderClass getBinding:CPValueBinding forObject:self];
179 
180  [theBinding reverseSetValueFor:@"objectValue"];
181 }
182 
183 - (id)initWithFrame:(CGRect)aFrame
184 {
185  self = [super initWithFrame:aFrame];
186 
187  if (self)
188  {
189  _sendActionOn = CPLeftMouseUpMask;
190  _trackingMouseDownFlags = 0;
191  }
192 
193  return self;
194 }
195 
196 #pragma mark -
197 #pragma mark Control Size
198 
202 - (CPControlSize)controlSize
203 {
204  return _controlSize;
205 }
206 
211 - (void)setControlSize:(CPControlSize)aControlSize
212 {
213  if (_controlSize === aControlSize)
214  return;
215 
216  [self unsetThemeState:[self _controlSizeThemeState]];
217  _controlSize = aControlSize;
218  [self setThemeState:[self _controlSizeThemeState]];
219 
220  [self setNeedsLayout];
221  [self setNeedsDisplay:YES];
222 }
223 
228 - (ThemeState)_controlSizeThemeState
229 {
230  switch (_controlSize)
231  {
232  case CPSmallControlSize:
234 
235  case CPMiniControlSize:
237 
239  default:
241  }
242 }
243 
249 - (void)_sizeToControlSize
250 {
251  var frameSize = [self frameSize],
252  minSize = [self currentValueForThemeAttribute:@"min-size"],
253  maxSize = [self currentValueForThemeAttribute:@"max-size"];
254 
255  if (minSize.width > 0)
256  {
257  frameSize.width = MAX(minSize.width, frameSize.width);
258 
259  if (maxSize.width > 0)
260  frameSize.width = MIN(maxSize.width, frameSize.width);
261  }
262 
263  if (minSize.height > 0)
264  {
265  frameSize.height = MAX(minSize.height, frameSize.height);
266 
267  if (maxSize.height > 0)
268  frameSize.height = MIN(maxSize.height, frameSize.height);
269  }
270 
271  [self setFrameSize:frameSize];
272 }
273 
274 
275 #pragma mark -
276 
282 - (void)setAction:(SEL)anAction
283 {
284  _action = anAction;
285 }
286 
290 - (SEL)action
291 {
292  return _action;
293 }
294 
300 - (void)setTarget:(id)aTarget
301 {
302  _target = aTarget;
303 }
304 
308 - (id)target
309 {
310  return _target;
311 }
312 
319 - (BOOL)sendAction:(SEL)anAction to:(id)anObject
320 {
321  [self _reverseSetBinding];
322 
323  var binding = [CPBinder getBinding:CPTargetBinding forObject:self];
324  [binding invokeAction];
325 
326  return [CPApp sendAction:anAction to:anObject from:self];
327 }
328 
329 - (int)sendActionOn:(int)mask
330 {
331  var previousMask = _sendActionOn;
332 
333  _sendActionOn = mask;
334 
335  return previousMask;
336 }
337 
342 {
343  // Some subclasses should redefine this with CPLeftMouseDraggedMask
344  return (_sendActionOn & CPPeriodicMask) !== 0;
345 }
346 
350 - (void)setContinuous:(BOOL)flag
351 {
352  // Some subclasses should redefine this with CPLeftMouseDraggedMask
353  if (flag)
354  _sendActionOn |= CPPeriodicMask;
355  else
356  _sendActionOn &= ~CPPeriodicMask;
357 }
358 
363 {
364  return NO;
365 }
366 
367 - (void)trackMouse:(CPEvent)anEvent
368 {
369  var type = [anEvent type],
370  currentLocation = [self convertPoint:[anEvent locationInWindow] fromView:nil],
371  isWithinFrame = [self tracksMouseOutsideOfFrame] || CGRectContainsPoint([self bounds], currentLocation);
372 
373  if (type === CPLeftMouseUp)
374  {
375  [self stopTracking:_previousTrackingLocation at:currentLocation mouseIsUp:YES];
376 
377  _trackingMouseDownFlags = 0;
378 
379  if (isWithinFrame)
380  [self setThemeState:CPThemeStateHovered];
381  }
382  else
383  {
384  [self unsetThemeState:CPThemeStateHovered];
385 
386  if (type === CPLeftMouseDown)
387  {
388  _trackingMouseDownFlags = [anEvent modifierFlags];
389  _continuousTracking = [self startTrackingAt:currentLocation];
390  }
391  else if (type === CPLeftMouseDragged)
392  {
393  if (isWithinFrame)
394  {
395  if (!_trackingWasWithinFrame)
396  _continuousTracking = [self startTrackingAt:currentLocation];
397 
398  else if (_continuousTracking)
399  _continuousTracking = [self continueTracking:_previousTrackingLocation at:currentLocation];
400  }
401  else
402  [self stopTracking:_previousTrackingLocation at:currentLocation mouseIsUp:NO];
403  }
404 
405  [CPApp setTarget:self selector:@selector(trackMouse:) forNextEventMatchingMask:CPLeftMouseDraggedMask | CPLeftMouseUpMask untilDate:nil inMode:nil dequeue:YES];
406  }
407 
408  if ((_sendActionOn & (1 << type)) && isWithinFrame)
409  [self sendAction:_action to:_target];
410 
411  _trackingWasWithinFrame = isWithinFrame;
412  _previousTrackingLocation = currentLocation;
413 }
414 
415 - (void)setState:(CPInteger)state
416 {
417 }
418 
419 - (CPInteger)nextState
420 {
421  return 0;
422 }
423 
429 - (void)performClick:(id)sender
430 {
431  if (![self isEnabled])
432  return;
433 
434  [self highlight:YES];
435  [self setState:[self nextState]];
436 
437  try
438  {
439  [self sendAction:[self action] to:[self target]];
440  }
441  catch (e)
442  {
443  throw e;
444  }
445  finally
446  {
448  }
449 }
450 
455 - (void)unhighlightButtonTimerDidFinish:(id)sender
456 {
457  [self highlight:NO];
458 }
459 
463 - (unsigned)mouseDownFlags
464 {
465  return _trackingMouseDownFlags;
466 }
467 
468 - (BOOL)startTrackingAt:(CGPoint)aPoint
469 {
470  [self highlight:YES];
471 
472  return (_sendActionOn & CPPeriodicMask) || (_sendActionOn & CPLeftMouseDraggedMask);
473 }
474 
475 - (BOOL)continueTracking:(CGPoint)lastPoint at:(CGPoint)aPoint
476 {
477  return (_sendActionOn & CPPeriodicMask) || (_sendActionOn & CPLeftMouseDraggedMask);
478 }
479 
480 - (void)stopTracking:(CGPoint)lastPoint at:(CGPoint)aPoint mouseIsUp:(BOOL)mouseIsUp
481 {
482  if (mouseIsUp)
483  [self highlight:NO];
484  else
485  [self highlight:YES];
486 }
487 
491 - (BOOL)acceptsFirstMouse:(CPEvent)anEvent
492 {
493  return [self isEnabled];
494 }
495 
496 - (void)mouseDown:(CPEvent)anEvent
497 {
498  if (![self isEnabled])
499  return;
500 
501  [self trackMouse:anEvent];
502 }
503 
504 - (void)mouseEntered:(CPEvent)anEvent
505 {
506  if (![self isEnabled])
507  return;
508 
509  [self setThemeState:CPThemeStateHovered];
510 }
511 
512 - (void)mouseExited:(CPEvent)anEvent
513 {
514  var currentLocation = [self convertPoint:[anEvent locationInWindow] fromView:nil],
515  isWithinFrame = [self tracksMouseOutsideOfFrame] || CGRectContainsPoint([self bounds], currentLocation);
516 
517  // Make sure we're not still in the frame because Cappuccino will sent mouseExited events
518  // for all of the (ephemeral) subviews of a view as well.
519  if (!isWithinFrame)
520  [self unsetThemeState:CPThemeStateHovered];
521 }
522 
527 {
528  return _value;
529 }
530 
534 - (void)setObjectValue:(id)anObject
535 {
536  _value = anObject;
537 
538  [self setNeedsLayout];
539  [self setNeedsDisplay:YES];
540 }
541 
545 - (float)floatValue
546 {
547  var floatValue = parseFloat(_value, 10);
548  return isNaN(floatValue) ? 0.0 : floatValue;
549 }
550 
554 - (void)setFloatValue:(float)aValue
555 {
556  [self setObjectValue:aValue];
557 }
558 
562 - (double)doubleValue
563 {
564  var doubleValue = parseFloat(_value, 10);
565  return isNaN(doubleValue) ? 0.0 : doubleValue;
566 }
567 
571 - (void)setDoubleValue:(double)anObject
572 {
573  [self setObjectValue:anObject];
574 }
575 
579 - (int)intValue
580 {
581  var intValue = parseInt(_value, 10);
582  return isNaN(intValue) ? 0.0 : intValue;
583 }
584 
588 - (void)setIntValue:(int)anObject
589 {
590  [self setObjectValue:anObject];
591 }
592 
597 {
598  var intValue = parseInt(_value, 10);
599  return isNaN(intValue) ? 0.0 : intValue;
600 }
601 
605 - (void)setIntegerValue:(int)anObject
606 {
607  [self setObjectValue:anObject];
608 }
609 
614 {
615  if (_formatter && _value !== undefined)
616  {
617  var formattedValue = [self hasThemeState:CPThemeStateEditing] ? [_formatter editingStringForObjectValue:_value] : [_formatter stringForObjectValue:_value];
618 
619  if (formattedValue !== nil && formattedValue !== undefined)
620  return formattedValue;
621  }
622 
623  return (_value === undefined || _value === nil) ? @"" : String(_value);
624 }
625 
629 - (void)setStringValue:(CPString)aString
630 {
631  // Cocoa raises an invalid parameter assertion and returns if you pass nil.
632  if (aString === nil || aString === undefined)
633  {
634  CPLog.warn("nil or undefined sent to CPControl -setStringValue");
635  return;
636  }
637 
638  var value;
639 
640  if (_formatter)
641  {
642  value = nil;
643 
644  if ([_formatter getObjectValue:@ref(value) forString:aString errorDescription:nil] === NO)
645  {
646  // If the given string is non-empty and doesn't work, Cocoa tries an empty string.
647  if (!aString || [_formatter getObjectValue:@ref(value) forString:@"" errorDescription:nil] === NO)
648  value = undefined; // Means the value is invalid
649  }
650  }
651  else
652  value = aString;
653 
654  [self setObjectValue:value];
655 }
656 
657 - (void)takeDoubleValueFrom:(id)sender
658 {
659  if ([sender respondsToSelector:@selector(doubleValue)])
660  [self setDoubleValue:[sender doubleValue]];
661 }
662 
663 
664 - (void)takeFloatValueFrom:(id)sender
665 {
666  if ([sender respondsToSelector:@selector(floatValue)])
667  [self setFloatValue:[sender floatValue]];
668 }
669 
670 - (void)takeIntegerValueFrom:(id)sender
671 {
672  if ([sender respondsToSelector:@selector(integerValue)])
673  [self setIntegerValue:[sender integerValue]];
674 }
675 
676 - (void)takeIntValueFrom:(id)sender
677 {
678  if ([sender respondsToSelector:@selector(intValue)])
679  [self setIntValue:[sender intValue]];
680 }
681 
682 - (void)takeObjectValueFrom:(id)sender
683 {
684  if ([sender respondsToSelector:@selector(objectValue)])
685  [self setObjectValue:[sender objectValue]];
686 }
687 
688 - (void)takeStringValueFrom:(id)sender
689 {
690  if ([sender respondsToSelector:@selector(stringValue)])
691  [self setStringValue:[sender stringValue]];
692 }
693 
694 - (void)textDidBeginEditing:(CPNotification)note
695 {
696  //this looks to prevent false propagation of notifications for other objects
697  if ([note object] != self)
698  return;
699 
700  [[CPNotificationCenter defaultCenter] postNotificationName:CPControlTextDidBeginEditingNotification object:self userInfo:@{"CPFieldEditor": [note object]}];
701 }
702 
703 - (void)textDidChange:(CPNotification)note
704 {
705  //this looks to prevent false propagation of notifications for other objects
706  if ([note object] != self)
707  return;
708 
709  [[CPNotificationCenter defaultCenter] postNotificationName:CPControlTextDidChangeNotification object:self userInfo:@{"CPFieldEditor": [note object]}];
710 }
711 
712 - (void)textDidEndEditing:(CPNotification)note
713 {
714  //this looks to prevent false propagation of notifications for other objects
715  if ([note object] != self)
716  return;
717 
718  [self _reverseSetBinding];
719 
720  [[CPNotificationCenter defaultCenter] postNotificationName:CPControlTextDidEndEditingNotification object:self userInfo:[note userInfo]];
721 }
722 
728 - (unsigned)_currentTextMovement
729 {
730  var currentEvent = [CPApp currentEvent],
731  keyCode = [currentEvent keyCode],
732  modifierFlags = [currentEvent modifierFlags];
733 
734  switch (keyCode)
735  {
736  case CPEscapeKeyCode:
737  return CPCancelTextMovement;
738 
739  case CPLeftArrowKeyCode:
740  return CPLeftTextMovement;
741 
742  case CPRightArrowKeyCode:
743  return CPRightTextMovement;
744 
745  case CPUpArrowKeyCode:
746  return CPUpTextMovement;
747 
748  case CPDownArrowKeyCode:
749  return CPDownTextMovement;
750 
751  case CPReturnKeyCode:
752  return CPReturnTextMovement;
753 
754  case CPTabKeyCode:
755  if (modifierFlags & CPShiftKeyMask)
756  return CPBacktabTextMovement;
757 
758  return CPTabTextMovement;
759 
760  default:
761  return CPOtherTextMovement;
762  }
763 }
764 
776 - (void)setAlignment:(CPTextAlignment)alignment
777 {
778  [self setValue:alignment forThemeAttribute:@"alignment"];
779 }
780 
784 - (CPTextAlignment)alignment
785 {
786  return [self valueForThemeAttribute:@"alignment"];
787 }
788 
798 - (void)setVerticalAlignment:(CPTextVerticalAlignment)alignment
799 {
800  [self setValue:alignment forThemeAttribute:@"vertical-alignment"];
801 }
802 
806 - (CPTextVerticalAlignment)verticalAlignment
807 {
808  return [self valueForThemeAttribute:@"vertical-alignment"];
809 }
810 
823 - (void)setLineBreakMode:(CPLineBreakMode)mode
824 {
825  [self setValue:mode forThemeAttribute:@"line-break-mode"];
826 }
827 
831 - (CPLineBreakMode)lineBreakMode
832 {
833  return [self valueForThemeAttribute:@"line-break-mode"];
834 }
835 
841 - (void)setTextColor:(CPColor)aColor
842 {
843  [self setValue:aColor forThemeAttribute:@"text-color"];
844 }
845 
850 {
851  return [self valueForThemeAttribute:@"text-color"];
852 }
853 
857 - (void)setTextShadowColor:(CPColor)aColor
858 {
859  [self setValue:aColor forThemeAttribute:@"text-shadow-color"];
860 }
861 
866 {
867  return [self valueForThemeAttribute:@"text-shadow-color"];
868 }
869 
875 - (void)setTextShadowOffset:(CGSize)offset
876 {
877  [self setValue:offset forThemeAttribute:@"text-shadow-offset"];
878 }
879 
884 {
885  return [self valueForThemeAttribute:@"text-shadow-offset"];
886 }
887 
891 - (void)setFont:(CPFont)aFont
892 {
893  [self setValue:aFont forThemeAttribute:@"font"];
894 }
895 
900 {
901  return [self valueForThemeAttribute:@"font"];
902 }
903 
917 - (void)setImagePosition:(CPCellImagePosition)position
918 {
919  [self setValue:position forThemeAttribute:@"image-position"];
920 }
921 
925 - (CPCellImagePosition)imagePosition
926 {
927  return [self valueForThemeAttribute:@"image-position"];
928 }
929 
940 - (void)setImageScaling:(CPImageScaling)scaling
941 {
942  [self setValue:scaling forThemeAttribute:@"image-scaling"];
943 }
944 
948 - (CPUInteger)imageScaling
949 {
950  return [self valueForThemeAttribute:@"image-scaling"];
951 }
952 
959 - (void)setEnabled:(BOOL)isEnabled
960 {
961  if (isEnabled)
962  [self unsetThemeState:CPThemeStateDisabled];
963  else
964  [self setThemeState:CPThemeStateDisabled];
965 }
966 
970 - (BOOL)isEnabled
971 {
972  return ![self hasThemeState:CPThemeStateDisabled];
973 }
974 
980 - (void)highlight:(BOOL)shouldHighlight
981 {
982  [self setHighlighted:shouldHighlight];
983 }
984 
990 - (void)setHighlighted:(BOOL)isHighlighted
991 {
992  if (isHighlighted)
993  [self setThemeState:CPThemeStateHighlighted];
994  else
995  [self unsetThemeState:CPThemeStateHighlighted];
996 }
997 
1002 {
1003  return [self hasThemeState:CPThemeStateHighlighted];
1004 }
1005 
1006 
1007 #pragma mark -
1008 #pragma mark Base writing direction
1009 
1014 - (void)setBaseWritingDirection:(CPWritingDirection)writingDirection
1015 {
1016  if (writingDirection == _baseWritingDirection)
1017  return;
1018 
1019  [self willChangeValueForKey:@"baseWritingDirection"];
1020  _baseWritingDirection = writingDirection;
1021  [self didChangeValueForKey:@"baseWritingDirection"];
1022 
1023 #if PLATFORM(DOM)
1024 
1025  var style;
1026 
1027  switch (_baseWritingDirection)
1028  {
1030  style = "initial";
1031  break;
1032 
1034  style = "ltr";
1035  break;
1036 
1038  style = "rtl";
1039  break;
1040 
1041  default:
1042  style = "initial";
1043  }
1044 
1045  _DOMElement.style.direction = style;
1046 #endif
1047 }
1048 
1049 @end
1050 
1052 
1054 {
1055  [self removeAllTrackingAreas];
1056  [self addTrackingArea:[[CPTrackingArea alloc] initWithRect:CGRectMakeZero()
1057  options:CPTrackingMouseEnteredAndExited | CPTrackingActiveInKeyWindow | CPTrackingInVisibleRect
1058  owner:self
1059  userInfo:nil]];
1060 }
1061 
1062 @end
1063 
1064 var CPControlActionKey = @"CPControlActionKey",
1065  CPControlControlSizeKey = @"CPControlControlSizeKey",
1066  CPControlControlStateKey = @"CPControlControlStateKey",
1067  CPControlFormatterKey = @"CPControlFormatterKey",
1068  CPControlIsEnabledKey = @"CPControlIsEnabledKey",
1069  CPControlSendActionOnKey = @"CPControlSendActionOnKey",
1070  CPControlSendsActionOnEndEditingKey = @"CPControlSendsActionOnEndEditingKey",
1071  CPControlTargetKey = @"CPControlTargetKey",
1072  CPControlValueKey = @"CPControlValueKey",
1073  CPControlBaseWrittingDirectionKey = @"CPControlBaseWrittingDirectionKey";
1074 
1075  __Deprecated__CPImageViewImageKey = @"CPImageViewImageKey";
1076 
1077 @implementation CPControl (CPCoding)
1078 
1079 /*
1080  Initializes the control by unarchiving it from a coder.
1081 
1082  @param aCoder the coder from which to unarchive the control
1083  @return the initialized control
1084 */
1085 - (id)initWithCoder:(CPCoder)aCoder
1086 {
1087  self = [super initWithCoder:aCoder];
1088 
1089  if (self)
1090  {
1091  [self setObjectValue:[aCoder decodeObjectForKey:CPControlValueKey]];
1092 
1093  [self setTarget:[aCoder decodeObjectForKey:CPControlTargetKey]];
1094  [self setAction:[aCoder decodeObjectForKey:CPControlActionKey]];
1095 
1096  [self sendActionOn:[aCoder decodeIntForKey:CPControlSendActionOnKey]];
1097  [self setSendsActionOnEndEditing:[aCoder decodeBoolForKey:CPControlSendsActionOnEndEditingKey]];
1098 
1099  [self setFormatter:[aCoder decodeObjectForKey:CPControlFormatterKey]];
1100 
1101  [self setControlSize:[aCoder decodeIntForKey:CPControlControlSizeKey]];
1102 
1103  [self setBaseWritingDirection:[aCoder decodeIntForKey:CPControlBaseWrittingDirectionKey]];
1104  }
1105 
1106  return self;
1107 }
1108 
1109 /*
1110  Archives the control to the provided coder.
1111 
1112  @param aCoder the coder to which the control will be archived.
1113 */
1114 - (void)encodeWithCoder:(CPCoder)aCoder
1115 {
1116  [super encodeWithCoder:aCoder];
1117 
1118  if (_sendsActionOnEndEditing)
1119  [aCoder encodeBool:_sendsActionOnEndEditing forKey:CPControlSendsActionOnEndEditingKey];
1120 
1121  var objectValue = [self objectValue];
1122 
1123  if (objectValue !== nil)
1124  [aCoder encodeObject:objectValue forKey:CPControlValueKey];
1125 
1126  if (_target !== nil)
1127  [aCoder encodeConditionalObject:_target forKey:CPControlTargetKey];
1128 
1129  if (_action !== nil)
1130  [aCoder encodeObject:_action forKey:CPControlActionKey];
1131 
1132  [aCoder encodeInt:_sendActionOn forKey:CPControlSendActionOnKey];
1133 
1134  if (_formatter !== nil)
1135  [aCoder encodeObject:_formatter forKey:CPControlFormatterKey];
1136 
1137  [aCoder encodeInt:_controlSize forKey:CPControlControlSizeKey];
1138 
1139  [aCoder encodeInt:_baseWritingDirection forKey:CPControlBaseWrittingDirectionKey];
1140 
1141 }
1142 
1143 @end
1144 
1145 var _CPControlSizeIdentifiers = [],
1146  _CPControlCachedColorWithPatternImages = {},
1147  _CPControlCachedThreePartImagePattern = {};
1148 
1149 _CPControlSizeIdentifiers[CPRegularControlSize] = "Regular";
1150 _CPControlSizeIdentifiers[CPSmallControlSize] = "Small";
1151 _CPControlSizeIdentifiers[CPMiniControlSize] = "Mini";
1152 
1153 function _CPControlIdentifierForControlSize(aControlSize)
1154 {
1155  return _CPControlSizeIdentifiers[aControlSize];
1156 }
1157 
1158 function _CPControlColorWithPatternImage(sizes, aClassName)
1159 {
1160  var index = 1,
1161  count = arguments.length,
1162  identifier = "";
1163 
1164  for (; index < count; ++index)
1165  identifier += arguments[index];
1166 
1167  var color = _CPControlCachedColorWithPatternImages[identifier];
1168 
1169  if (!color)
1170  {
1171  var bundle = [CPBundle bundleForClass:[CPControl class]];
1172 
1173  color = [CPColor colorWithPatternImage:[[CPImage alloc] initWithContentsOfFile:[bundle pathForResource:aClassName + "/" + identifier + ".png"] size:sizes[identifier]]];
1174 
1175  _CPControlCachedColorWithPatternImages[identifier] = color;
1176  }
1177 
1178  return color;
1179 }
1180 
1181 function _CPControlThreePartImagePattern(isVertical, sizes, aClassName)
1182 {
1183  var index = 2,
1184  count = arguments.length,
1185  identifier = "";
1186 
1187  for (; index < count; ++index)
1188  identifier += arguments[index];
1189 
1190  var color = _CPControlCachedThreePartImagePattern[identifier];
1191 
1192  if (!color)
1193  {
1194  var bundle = [CPBundle bundleForClass:[CPControl class]],
1195  path = aClassName + "/" + identifier;
1196 
1197  sizes = sizes[identifier];
1198 
1200  [[CPImage alloc] initWithContentsOfFile:[bundle pathForResource:path + "0.png"] size:sizes[0]],
1201  [[CPImage alloc] initWithContentsOfFile:[bundle pathForResource:path + "1.png"] size:sizes[1]],
1202  [[CPImage alloc] initWithContentsOfFile:[bundle pathForResource:path + "2.png"] size:sizes[2]]
1203  ] isVertical:isVertical]];
1204 
1205  _CPControlCachedThreePartImagePattern[identifier] = color;
1206  }
1207 
1208  return color;
1209 }
1210 
1212 
1217 {
1218  return _formatter;
1219 }
1220 
1224 - (void)setFormatter:(CPFormatter)aValue
1225 {
1226  _formatter = aValue;
1227 }
1228 
1233 {
1234  return _sendsActionOnEndEditing;
1235 }
1236 
1240 - (void)setSendsActionOnEndEditing:(BOOL)aValue
1241 {
1242  _sendsActionOnEndEditing = aValue;
1243 }
1244 
1248 - (CPWritingDirection)baseWritingDirection
1249 {
1250  return _baseWritingDirection;
1251 }
1252 
1256 - (void)setBaseWritingDirection:(CPWritingDirection)aValue
1257 {
1258  _baseWritingDirection = aValue;
1259 }
1260 
1261 @end
id initWithFrame:(CGRect aFrame)
Definition: CPView.j:334
Definition: CPFont.h:2
CPControlSelectedBackgroundColor
Definition: CPControl.j:82
CPControlHighlightedBackgroundColor
Definition: CPControl.j:83
CPControlSize controlSize()
Definition: CPControl.j:202
BOOL isHighlighted()
Definition: CPControl.j:1001
CPPeriodicMask
BOOL tracksMouseOutsideOfFrame()
Definition: CPControl.j:362
CPUpTextMovement
Definition: CPText.j:63
id initWithImageSlices:isVertical:(CPArray imageSlices, [isVertical] BOOL isVertical)
Definition: CPImage.j:533
void setAction:(SEL anAction)
Definition: CPControl.j:282
BOOL isEnabled()
Definition: CPControl.j:970
BOOL setThemeState:(ThemeState aState)
Definition: CPView.j:3214
FrameUpdater prototype identifier
CPThemeStateControlSizeMini
Definition: CPTheme.j:565
CPDictionary themeAttributes()
Definition: CPControl.j:119
void trackMouse:(CPEvent anEvent)
Definition: CPControl.j:367
void postNotificationName:object:userInfo:(CPString aNotificationName, [object] id anObject, [userInfo] CPDictionary aUserInfo)
An object representation of nil.
Definition: CPNull.h:2
id initWithCoder:(CPCoder aCoder)
Definition: CPView.j:3662
CPImageAbove
Definition: CPControl.j:74
CPScaleToFit
Definition: CPControl.j:60
CPFont systemFontOfSize:(CGSize aSize)
Definition: CPFont.j:282
void setTarget:(id aTarget)
Definition: CPControl.j:300
CPColor colorWithPatternImage:(CPImage anImage)
Definition: CPColor.j:481
CPEscapeKeyCode
Definition: CPResponder.j:29
BOOL startTrackingAt:(CGPoint aPoint)
Definition: CPControl.j:468
CPScaleNone
Definition: CPControl.j:61
CPLineBreakByTruncatingHead
Definition: CPControl.j:48
CPWritingDirectionRightToLeft
Definition: CPText.j:70
void setBaseWritingDirection:(CPWritingDirection writingDirection)
Definition: CPControl.j:1014
CPTabTextMovement
Definition: CPText.j:59
unsigned mouseDownFlags()
Definition: CPControl.j:463
CPMiniControlSize
Definition: CPControl.j:42
CPInteger nextState()
Definition: CPControl.j:419
CGPoint locationInWindow()
Definition: CPEvent.j:290
CPFont font()
Definition: CPControl.j:899
CPCellImagePosition imagePosition()
Definition: CPControl.j:925
CPReturnTextMovement
Definition: CPText.j:58
CPLineBreakByCharWrapping
Definition: CPControl.j:46
CPSmallControlSize
Definition: CPControl.j:41
void setIntValue:(int anObject)
Definition: CPControl.j:588
CPLeftMouseUpMask
CGRect bounds()
Definition: CPView.j:1302
CPLeftTextMovement
Definition: CPText.j:61
void setControlSize:(CPControlSize aControlSize)
Definition: CPControl.j:211
CPEventType type()
Definition: CPEvent.j:325
CPColor textShadowColor()
Definition: CPControl.j:865
int sendActionOn:(int mask)
Definition: CPControl.j:329
unsigned modifierFlags()
Definition: CPEvent.j:309
CPImageScaleProportionallyDown
Definition: CPControl.j:63
void setValue:forThemeAttribute:(id aValue, [forThemeAttribute] CPString aName)
Definition: CPView.j:3343
CPNotificationCenter defaultCenter()
void setFormatter:(CPFormatter aValue)
Definition: CPControl.j:1224
A mutable key-value pair collection.
Definition: CPDictionary.h:2
function ThemeState(stateNames)
Definition: CPTheme.j:314
CPImageScaleAxesIndependently
Definition: CPControl.j:64
CPImageScaleNone
Definition: CPControl.j:65
CPEnabledBinding
CPLineBreakByTruncatingMiddle
Definition: CPControl.j:50
CGSize frameSize()
Definition: CPView.j:1032
CPImageLeft
Definition: CPControl.j:71
CPControlTextDidChangeNotification
Definition: CPControl.j:87
CPColor blackColor()
Definition: CPColor.j:283
CPDownTextMovement
Definition: CPText.j:64
CPReturnKeyCode
Definition: CPResponder.j:28
CPMixedState
Definition: CPControl.j:79
An immutable string (collection of characters).
Definition: CPString.h:2
CPNull null()
Definition: CPNull.j:51
CGPoint convertPoint:fromView:(CGPoint aPoint, [fromView] CPView aView)
Definition: CPView.j:2208
CPCellImagePosition CPNoImage
Definition: CPControl.j:69
Definition: CPImage.h:2
var CPControlControlStateKey
Definition: CPControl.j:1066
CPWritingDirection baseWritingDirection()
Definition: CPControl.j:1248
BOOL sendAction:to:(SEL anAction, [to] id anObject)
Definition: CPControl.j:319
SEL action()
Definition: CPControl.j:290
CPLineBreakByClipping
Definition: CPControl.j:47
CGSize textShadowOffset()
Definition: CPControl.j:883
void setFloatValue:(float aValue)
Definition: CPControl.j:554
CPImageOnly
Definition: CPControl.j:70
CPColor textColor()
Definition: CPControl.j:849
var CPControlBlackColor
Definition: CPControl.j:90
id initWithContentsOfFile:size:(CPString aFilename, [size] CGSize aSize)
Definition: CPImage.j:176
var CPControlTargetKey
Definition: CPControl.j:1071
CPFormatter is an abstract class that declares an interface for objects that create, interpret, and validate the textual representation of cell contents. The Foundation framework provides two concrete subclasses of CPFormatter to generate these objects: CPNumberFormatter and CPDateFormatter.
Definition: CPFormatter.h:2
CPControlDisabledBackgroundColor
Definition: CPControl.j:84
CPBinder getBinding:forObject:(CPString aBinding, [forObject] id anObject)
void setNeedsDisplay:(BOOL aFlag)
Definition: CPView.j:2556
CPLeftArrowKeyCode
Definition: CPResponder.j:33
void setObjectValue:(id anObject)
Definition: CPControl.j:534
CPRightArrowKeyCode
Definition: CPResponder.j:35
void encodeWithCoder:(CPCoder aCoder)
Definition: CPView.j:3770
CPTextAlignment alignment()
Definition: CPControl.j:784
CPUpArrowKeyCode
Definition: CPResponder.j:34
CPDownArrowKeyCode
Definition: CPResponder.j:36
CPLeftMouseUp
CPShiftKeyMask
CPVerticalTextAlignment CPTopVerticalTextAlignment
Definition: CPControl.j:53
void setStringValue:(CPString aString)
Definition: CPControl.j:629
int integerValue()
Definition: CPControl.j:596
A notification that can be posted to a CPNotificationCenter.
Definition: CPNotification.h:2
void setHighlighted:(BOOL isHighlighted)
Definition: CPControl.j:990
CPTimer scheduledTimerWithTimeInterval:target:selector:userInfo:repeats:(CPTimeInterval seconds, [target] id aTarget, [selector] SEL aSelector, [userInfo] id userInfo, [repeats] BOOL shouldRepeat)
Definition: CPTimer.j:58
CPLineBreakByTruncatingTail
Definition: CPControl.j:49
CPRightTextMovement
Definition: CPText.j:62
BOOL continueTracking:at:(CGPoint lastPoint, [at] CGPoint aPoint)
Definition: CPControl.j:475
CPUInteger imageScaling()
Definition: CPControl.j:948
void setNeedsLayout()
Definition: CPView.j:2707
CPImageScaling CPScaleProportionally
Definition: CPControl.j:59
id target()
Definition: CPControl.j:308
CPWritingDirectionLeftToRight
Definition: CPText.j:69
var CPControlValueKey
Definition: CPControl.j:1072
void highlight:(BOOL shouldHighlight)
Definition: CPControl.j:980
CPString stringValue()
Definition: CPControl.j:613
CPOtherTextMovement
Definition: CPText.j:57
CPBottomVerticalTextAlignment
Definition: CPControl.j:55
double doubleValue()
Definition: CPControl.j:562
CPImageOverlaps
Definition: CPControl.j:75
var CPControlSendsActionOnEndEditingKey
Definition: CPControl.j:1070
void setSendsActionOnEndEditing:(BOOL aValue)
Definition: CPControl.j:1240
float floatValue()
Definition: CPControl.j:545
CPControlNormalBackgroundColor
Definition: CPControl.j:81
A timer object that can send a message after the given time interval.
Definition: CPTimer.h:2
CPLeftMouseDragged
Defines methods for use when archiving & restoring (enc/decoding).
Definition: CPCoder.h:2
CPLeftMouseDraggedMask
CPDictionary userInfo()
CPControlSize CPRegularControlSize
Definition: CPControl.j:40
BOOL unsetThemeState:(ThemeState aState)
Definition: CPView.j:3227
Sends messages (CPNotification) between objects.
var CPControlSendActionOnKey
Definition: CPControl.j:1069
void addTrackingArea:(CPTrackingArea trackingArea)
Definition: CPView.j:3500
CPImageRight
Definition: CPControl.j:72
CPLineBreakMode lineBreakMode()
Definition: CPControl.j:831
var CPControlFormatterKey
Definition: CPControl.j:1067
CPControlTextDidEndEditingNotification
Definition: CPControl.j:88
var CPControlActionKey
Definition: CPControl.j:1064
CPTextAlignment CPLeftTextAlignment
Definition: CPText.j:73
CPLeftMouseDown
CPControlTextDidBeginEditingNotification
Definition: CPControl.j:86
CPBundle bundleForClass:(Class aClass)
Definition: CPBundle.j:77
CPLineBreakMode CPLineBreakByWordWrapping
Definition: CPControl.j:45
void setFrameSize:(CGSize aSize)
Definition: CPView.j:1100
CPCancelTextMovement
Definition: CPText.j:65
var CPControlBaseWrittingDirectionKey
Definition: CPControl.j:1073
Definition: CPEvent.h:2
CPThemeStateControlSizeSmall
Definition: CPTheme.j:564
CPThemeStateControlSizeRegular
Definition: CPTheme.j:563
CPImageBelow
Definition: CPControl.j:73
void setDoubleValue:(double anObject)
Definition: CPControl.j:571
CPTrackingArea initWithRect:options:owner:userInfo:(CGRect aRect, [options] CPTrackingAreaOptions options, [owner] id owner, [userInfo] CPDictionary userInfo)
BOOL isContinuous()
Definition: CPControl.j:341
void setIntegerValue:(int anObject)
Definition: CPControl.j:605
CPOffState
Definition: CPControl.j:78
void removeAllTrackingAreas()
Definition: CPView.j:3564
CPTabKeyCode
Definition: CPResponder.j:27
int intValue()
Definition: CPControl.j:579
var CPControlIsEnabledKey
Definition: CPControl.j:1068
CPTextVerticalAlignment verticalAlignment()
Definition: CPControl.j:806
CPValueBinding
CPOnState
Definition: CPControl.j:77
void initialize()
Definition: CPControl.j:137
void setState:(CPInteger state)
Definition: CPControl.j:415
CPWritingDirection CPWritingDirectionNatural
Definition: CPText.j:68
var CPControlControlSizeKey
Definition: CPControl.j:1065
CPImageScaleProportionallyUpOrDown
Definition: CPControl.j:66
id objectValue()
Definition: CPControl.j:526
void stopTracking:at:mouseIsUp:(CGPoint lastPoint, [at] CGPoint aPoint, [mouseIsUp] BOOL mouseIsUp)
Definition: CPControl.j:480
CPCenterVerticalTextAlignment
Definition: CPControl.j:54
id alloc()
Definition: CPObject.j:130
CPBacktabTextMovement
Definition: CPText.j:60
Definition: CPView.j:136