00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026 @import <Foundation/CPObject.j>
00027
00028 @import "CPPopUpButton.j"
00029 @import "CPToolbarItem.j"
00030
00031
00032
00033
00034
00035
00036 CPToolbarDisplayModeDefault = 0;
00037
00038
00039
00040
00041 CPToolbarDisplayModeIconAndLabel = 1;
00042
00043
00044
00045
00046 CPToolbarDisplayModeIconOnly = 2;
00047
00048
00049
00050
00051 CPToolbarDisplayModeLabelOnly = 3;
00052
00053 var CPToolbarsByIdentifier = nil;
00054 var CPToolbarConfigurationsByIdentifier = nil;
00055
00083 @implementation CPToolbar : CPObject
00084 {
00085 CPString _identifier;
00086 CPToolbarDisplayMode _displayMode;
00087 BOOL _showsBaselineSeparator;
00088 BOOL _allowsUserCustomization;
00089 BOOL _isVisible;
00090
00091 id _delegate;
00092
00093 CPArray _itemIdentifiers;
00094
00095 CPDictionary _identifiedItems;
00096 CPArray _defaultItems;
00097 CPArray _allowedItems;
00098 CPArray _selectableItems;
00099
00100 CPArray _items;
00101 CPArray _itemsSortedByVisibilityPriority;
00102
00103 CPView _toolbarView;
00104 CPWindow _window;
00105 }
00106
00107
00108 + (void)initialize
00109 {
00110 if (self != [CPToolbar class])
00111 return;
00112
00113 CPToolbarsByIdentifier = [CPDictionary dictionary];
00114 CPToolbarConfigurationsByIdentifier = [CPDictionary dictionary];
00115 }
00116
00117
00118 + (void)_addToolbar:(CPToolbar)toolbar forIdentifier:(CPString)identifier
00119 {
00120 var toolbarsSharingIdentifier = [CPToolbarsByIdentifier objectForKey:identifier];
00121
00122 if (!toolbarsSharingIdentifier)
00123 {
00124 toolbarsSharingIdentifier = []
00125 [CPToolbarsByIdentifier setObject:toolbarsSharingIdentifier forKey:identifier];
00126 }
00127
00128 [toolbarsSharingIdentifier addObject:toolbar];
00129 }
00130
00136 - (id)initWithIdentifier:(CPString)anIdentifier
00137 {
00138 self = [super init];
00139
00140 if (self)
00141 {
00142 _items = [];
00143
00144 _identifier = anIdentifier;
00145 _isVisible = YES;
00146
00147 [CPToolbar _addToolbar:self forIdentifier:_identifier];
00148 }
00149
00150 return self;
00151 }
00152
00153
00157 - (void)setDisplayMode:(CPToolbarDisplayMode)aDisplayMode
00158 {
00159
00160 }
00161
00165 - (CPString)identifier
00166 {
00167 return _identifier;
00168 }
00169
00173 - (id)delegate
00174 {
00175 return _delegate;
00176 }
00177
00181 - (BOOL)isVisible
00182 {
00183 return _isVisible;
00184 }
00185
00190 - (void)setVisible:(BOOL)aFlag
00191 {
00192 if (_isVisible === aFlag)
00193 return;
00194
00195 _isVisible = aFlag;
00196
00197 [_window _noteToolbarChanged];
00198 }
00199
00200 - (CPWindow)_window
00201 {
00202 return _window;
00203 }
00204
00205 - (void)_setWindow:(CPWindow)aWindow
00206 {
00207 _window = aWindow;
00208 }
00209
00214 - (void)setDelegate:(id)aDelegate
00215 {
00216 if (_delegate == aDelegate)
00217 return;
00218
00219 _delegate = aDelegate;
00220
00221 [self _reloadToolbarItems];
00222 }
00223
00224
00225 - (void)_loadConfiguration
00226 {
00227
00228 }
00229
00230
00231 - (CPView)_toolbarView
00232 {
00233 if (!_toolbarView)
00234 {
00235 _toolbarView = [[_CPToolbarView alloc] initWithFrame:CPRectMake(0.0, 0.0, 1200.0, 59.0)];
00236
00237 [_toolbarView setToolbar:self];
00238 [_toolbarView setAutoresizingMask:CPViewWidthSizable];
00239 [_toolbarView reloadToolbarItems];
00240 }
00241
00242 return _toolbarView;
00243 }
00244
00245
00246 - (void)_reloadToolbarItems
00247 {
00248 if (!_delegate)
00249 return;
00250
00251 var count = [_itemIdentifiers count];
00252
00253 if (!count)
00254 {
00255 _itemIdentifiers = [[_delegate toolbarDefaultItemIdentifiers:self] mutableCopy];
00256 count = [_itemIdentifiers count];
00257 }
00258
00259 _items = [];
00260
00261 var index = 0;
00262
00263 for (; index < count; ++index)
00264 {
00265 var identifier = _itemIdentifiers[index],
00266 item = [CPToolbarItem _standardItemWithItemIdentifier:identifier];
00267
00268 if (!item)
00269 item = [_delegate toolbar:self itemForItemIdentifier:identifier willBeInsertedIntoToolbar:YES];
00270
00271 item = [item copy];
00272
00273 if (item == nil)
00274 [CPException raise:CPInvalidArgumentException
00275 reason:sprintf(@"_delegate %s returned nil toolbar item returned for identifier %s", _delegate, identifier)];
00276
00277 [_items addObject:item];
00278 }
00279
00280
00281
00282
00283
00284
00285 _itemsSortedByVisibilityPriority = [_items sortedArrayUsingFunction:_CPToolbarItemVisibilityPriorityCompare context:NULL];
00286
00287 [_toolbarView reloadToolbarItems];
00288 }
00289
00293 - (CPArray)items
00294 {
00295 return _items;
00296 }
00297
00301 - (CPArray)visibleItems
00302 {
00303 return [_toolbarView visibleItems];
00304 }
00305
00309 - (CPArray)itemsSortedByVisibilityPriority
00310 {
00311 return _itemsSortedByVisibilityPriority;
00312 }
00313
00314
00315 - (id)_itemForItemIdentifier:(CPString)identifier willBeInsertedIntoToolbar:(BOOL)toolbar
00316 {
00317 var item = [_identifiedItems objectForKey:identifier];
00318 if (!item)
00319 {
00320 item = [CPToolbarItem _standardItemWithItemIdentifier:identifier];
00321 if (_delegate && !item)
00322 {
00323 item = [[_delegate toolbar:self itemForItemIdentifier:identifier willBeInsertedIntoToolbar:toolbar] copy];
00324 if (!item)
00325 [CPException raise:CPInvalidArgumentException
00326 reason:sprintf(@"_delegate %s returned nil toolbar item returned for identifier %s", _delegate, identifier)];
00327 }
00328
00329 [_identifiedItems setObject:item forKey:identifier];
00330 }
00331
00332 return item;
00333 }
00334
00335
00336 - (id)_itemsWithIdentifiers:(CPArray)identifiers
00337 {
00338 var items = [];
00339 for (var i = 0; i < identifiers.length; i++)
00340 [items addObject:[self _itemForItemIdentifier:identifiers[i] willBeInsertedIntoToolbar:NO]];
00341
00342 return items;
00343 }
00344
00345
00346 -(id)_defaultToolbarItems
00347 {
00348 if (!_defaultItems)
00349 if ([_delegate respondsToSelector:@selector(toolbarDefaultItemIdentifiers:)])
00350 _defaultItems = [self _itemsWithIdentifiers:[_delegate toolbarDefaultItemIdentifiers:self]];
00351
00352 return _defaultItems;
00353 }
00354
00355 @end
00356
00357
00358 var CPToolbarIdentifierKey = "CPToolbarIdentifierKey",
00359 CPToolbarDisplayModeKey = "CPToolbarDisplayModeKey",
00360 CPToolbarShowsBaselineSeparatorKey = "CPToolbarShowsBaselineSeparatorKey",
00361 CPToolbarAllowsUserCustomizationKey = "CPToolbarAllowsUserCustomizationKey",
00362 CPToolbarIsVisibleKey = "CPToolbarIsVisibleKey",
00363 CPToolbarDelegateKey = "CPToolbarDelegateKey",
00364 CPToolbarIdentifiedItemsKey = "CPToolbarIdentifiedItemsKey",
00365 CPToolbarDefaultItemsKey = "CPToolbarDefaultItemsKey",
00366 CPToolbarAllowedItemsKey = "CPToolbarAllowedItemsKey",
00367 CPToolbarSelectableItemsKey = "CPToolbarSelectableItemsKey";
00368
00369 @implementation CPToolbar (CPCoding)
00370
00371
00372
00373
00374
00375 - (id)initWithCoder:(CPCoder)aCoder
00376 {
00377 self = [super init];
00378
00379 if (self)
00380 {
00381 _identifier = [aCoder decodeObjectForKey:CPToolbarIdentifierKey];
00382 _displayMode = [aCoder decodeIntForKey:CPToolbarDisplayModeKey];
00383 _showsBaselineSeparator = [aCoder decodeBoolForKey:CPToolbarShowsBaselineSeparatorKey];
00384 _allowsUserCustomization = [aCoder decodeBoolForKey:CPToolbarAllowsUserCustomizationKey];
00385 _isVisible = [aCoder decodeBoolForKey:CPToolbarIsVisibleKey];
00386
00387 _identifiedItems = [aCoder decodeObjectForKey:CPToolbarIdentifiedItemsKey];
00388 _defaultItems = [aCoder decodeObjectForKey:CPToolbarDefaultItemsKey];
00389 _allowedItems = [aCoder decodeObjectForKey:CPToolbarAllowedItemsKey];
00390 _selectableItems = [aCoder decodeObjectForKey:CPToolbarSelectableItemsKey];
00391
00392 _items = [];
00393 [CPToolbar _addToolbar:self forIdentifier:_identifier];
00394
00395 [self setDelegate:[aCoder decodeObjectForKey:CPToolbarDelegateKey]];
00396 }
00397
00398 return self;
00399 }
00400
00401
00402
00403
00404
00405 - (void)encodeWithCoder:(CPCoder)aCoder
00406 {
00407 [aCoder encodeObject:_identifier forKey:CPToolbarIdentifierKey];
00408 [aCoder encodeInt:_displayMode forKey:CPToolbarDisplayModeKey];
00409 [aCoder encodeBool:_showsBaselineSeparator forKey:CPToolbarShowsBaselineSeparatorKey];
00410 [aCoder encodeBool:_allowsUserCustomization forKey:CPToolbarAllowsUserCustomizationKey];
00411 [aCoder encodeBool:_isVisible forKey:CPToolbarIsVisibleKey];
00412
00413 [aCoder encodeObject:_identifiedItems forKey:CPToolbarIdentifiedItemsKey];
00414 [aCoder encodeObject:_defaultItems forKey:CPToolbarDefaultItemsKey];
00415 [aCoder encodeObject:_allowedItems forKey:CPToolbarAllowedItemsKey];
00416 [aCoder encodeObject:_selectableItems forKey:CPToolbarSelectableItemsKey];
00417
00418 [aCoder encodeConditionalObject:_delegate forKey:CPToolbarDelegateKey];
00419 }
00420
00421 @end
00422
00423
00424 var _CPToolbarViewBackgroundColor = nil,
00425 _CPToolbarViewExtraItemsImage = nil,
00426 _CPToolbarViewExtraItemsAlternateImage = nil;
00427
00428 var TOOLBAR_TOP_MARGIN = 5.0,
00429 TOOLBAR_ITEM_MARGIN = 10.0,
00430 TOOLBAR_EXTRA_ITEMS_WIDTH = 20.0;
00431
00432 var _CPToolbarItemInfoMake = function(anIndex, aView, aLabel, aMinWidth)
00433 {
00434 return { index:anIndex, view:aView, label:aLabel, minWidth:aMinWidth };
00435 }
00436
00437
00438 @implementation _CPToolbarView : CPView
00439 {
00440 CPToolbar _toolbar;
00441
00442 CPIndexSet _flexibleWidthIndexes;
00443 CPIndexSet _visibleFlexibleWidthIndexes;
00444
00445 CPDictionary _itemInfos;
00446
00447 CPArray _visibleItems;
00448 CPArray _invisibleItems;
00449
00450 CPPopUpButton _additionalItemsButton;
00451 CPColor _labelColor;
00452 CPColor _labelShadowColor;
00453
00454 float _minWidth;
00455 }
00456
00457 + (void)initialize
00458 {
00459 if (self != [_CPToolbarView class])
00460 return;
00461
00462 var bundle = [CPBundle bundleForClass:self];
00463
00464 _CPToolbarViewExtraItemsImage = [[CPImage alloc] initWithContentsOfFile: [bundle pathForResource:"_CPToolbarView/_CPToolbarViewExtraItemsImage.png"] size: CPSizeMake(10.0, 15.0)];
00465
00466 _CPToolbarViewExtraItemsAlternateImage = [[CPImage alloc] initWithContentsOfFile: [bundle pathForResource:"_CPToolbarView/_CPToolbarViewExtraItemsAlternateImage.png"] size:CGSizeMake(10.0, 15.0)];
00467 }
00468
00469 - (id)initWithFrame:(CGRect)aFrame
00470 {
00471 self = [super initWithFrame:aFrame];
00472
00473 if (self)
00474 {
00475 _minWidth = 0;
00476
00477 _labelColor = [CPColor blackColor];
00478 _labelShadowColor = [CPColor colorWithWhite:1.0 alpha:0.75];
00479
00480 _additionalItemsButton = [[CPPopUpButton alloc] initWithFrame:CGRectMake(0.0, 0.0, 10.0, 15.0) pullsDown:YES];
00481 [_additionalItemsButton setBordered:NO];
00482
00483 [_additionalItemsButton setImagePosition:CPImageOnly];
00484 [[_additionalItemsButton menu] setShowsStateColumn:NO];
00485
00486 [_additionalItemsButton setAlternateImage:_CPToolbarViewExtraItemsAlternateImage];
00487 }
00488
00489 return self;
00490 }
00491
00492 - (void)setToolbar:(CPToolbar)aToolbar
00493 {
00494 _toolbar = aToolbar;
00495 }
00496
00497 - (CPToolbar)toolbar
00498 {
00499 return _toolbar;
00500 }
00501
00502 - (void)setLabelColor:(CPColor)aColor
00503 {
00504 if (_labelColor === aColor)
00505 return;
00506
00507 _labelColor = aColor;
00508
00509 var items = [_toolbar items],
00510 count = [items count];
00511
00512 while (count--)
00513 [[self labelForItem:items[count]] setTextColor:_labelColor];
00514 }
00515
00516 - (void)setLabelShadowColor:(CPColor)aColor
00517 {
00518 if (_labelShadowColor === aColor)
00519 return;
00520
00521 _labelShadowColor = aColor;
00522
00523 var items = [_toolbar items],
00524 count = [items count];
00525
00526 while (count--)
00527 [[self labelForItem:items[count]] setTextShadowColor:_labelShadowColor];
00528 }
00529
00530
00531 - (void)resizeSubviewsWithOldSize:(CGSize)aSize
00532 {
00533 [self layoutSubviews];
00534 }
00535
00536 - (void)layoutSubviews
00537 {
00538
00539 var items = [_toolbar items],
00540 width = CGRectGetWidth([self bounds]),
00541 minWidth = _minWidth,
00542 flexibleItemIndexes = [CPIndexSet indexSet],
00543
00544 invisibleItemsSortedByPriority = [];
00545
00546 _visibleItems = items;
00547
00548
00549
00550 if (width < minWidth)
00551 {
00552 width -= TOOLBAR_EXTRA_ITEMS_WIDTH;
00553
00554 _visibleItems = [_visibleItems copy];
00555
00556 var itemsSortedByVisibilityPriority = [_toolbar itemsSortedByVisibilityPriority],
00557 count = itemsSortedByVisibilityPriority.length;
00558
00559
00560 while (minWidth > width)
00561 {
00562 var item = itemsSortedByVisibilityPriority[count--];
00563
00564 minWidth -= [self minWidthForItem:item] + TOOLBAR_ITEM_MARGIN;
00565
00566 [_visibleItems removeObjectIdenticalTo:item];
00567 [invisibleItemsSortedByPriority addObject:item];
00568
00569 [[self viewForItem:item] setHidden:YES];
00570 [[self labelForItem:item] setHidden:YES];
00571 }
00572 }
00573
00574
00575
00576
00577 var index = _visibleItems.length,
00578 height = 0.0;
00579
00580 while (index--)
00581 {
00582 var item = _visibleItems[index],
00583 minSize = [item minSize],
00584 view = [self viewForItem:item];
00585
00586 if (minSize.width != [item maxSize].width)
00587 [flexibleItemIndexes addIndex:index];
00588
00589
00590
00591 else
00592 [view setFrameSize:CGSizeMake([item minSize].width, CGRectGetHeight([view frame]))];
00593
00594
00595
00596 [view setHidden:NO];
00597 [[self labelForItem:item] setHidden:NO];
00598
00599 if (height < minSize.height)
00600 height = minSize.height;
00601 }
00602
00603 var remainingSpace = width - minWidth,
00604 proportionate = 0.0;
00605
00606
00607
00608
00609 while (remainingSpace && [flexibleItemIndexes count])
00610 {
00611
00612 proportionate += remainingSpace / [flexibleItemIndexes count];
00613
00614
00615 remainingSpace = 0.0;
00616
00617 var index = CPNotFound;
00618
00619 while ((index = [flexibleItemIndexes indexGreaterThanIndex:index]) != CPNotFound)
00620 {
00621 var item = _visibleItems[index];
00622 view = [self viewForItem:item],
00623 viewFrame = [view frame],
00624
00625 proposedWidth = [item minSize].width + proportionate,
00626 constrainedWidth = MIN(proposedWidth, [item maxSize].width);
00627
00628 if (constrainedWidth < proposedWidth)
00629 {
00630 [flexibleItemIndexes removeIndex:index];
00631
00632 remainingSpace += proposedWidth - constrainedWidth;
00633 }
00634
00635 [view setFrameSize:CGSizeMake(constrainedWidth, CGRectGetHeight(viewFrame))];
00636 }
00637 }
00638
00639
00640 var count = _visibleItems.length,
00641 x = TOOLBAR_ITEM_MARGIN,
00642 fullHeightItems = [];
00643
00644 for (index = 0; index < count; ++index)
00645 {
00646 var item = _visibleItems[index],
00647 view = [self viewForItem:item],
00648
00649 viewFrame = [view frame],
00650 viewWidth = CGRectGetWidth(viewFrame),
00651
00652 label = [self labelForItem:item],
00653 labelFrame = [label frame],
00654 labelWidth = CGRectGetWidth(labelFrame),
00655
00656 itemWidth = MAX([self minWidthForItem:item], viewWidth),
00657
00658 viewHeight = CGRectGetHeight(viewFrame);
00659
00660
00661
00662 [view setFrame:CGRectMake(x + (itemWidth - viewWidth) / 2.0, TOOLBAR_TOP_MARGIN + (height - viewHeight) / 2.0, viewWidth, viewHeight)];
00663 [label setFrameOrigin:CGPointMake(x + (itemWidth - labelWidth) / 2.0, TOOLBAR_TOP_MARGIN + height + 2.0)];
00664
00665 x += itemWidth + TOOLBAR_ITEM_MARGIN;
00666
00667 if ([item itemIdentifier] == CPToolbarSeparatorItemIdentifier)
00668 fullHeightItems.push(item);
00669 }
00670
00671 for (index = 0, count = fullHeightItems.length; index < count; ++index)
00672 {
00673 var view = [self viewForItem:fullHeightItems[index]],
00674 viewHeight = 53.0;
00675
00676
00677 [view setFrame:CGRectMake(CGRectGetMinX([view frame]), (59.0 - viewHeight) / 2.0, CGRectGetWidth([view frame]), viewHeight)];
00678 }
00679
00680 if ([invisibleItemsSortedByPriority count])
00681 {
00682 var index = 0,
00683 count = [items count];
00684
00685 _invisibleItems = [];
00686
00687 for (; index < count; ++index)
00688 {
00689 var item = items[index];
00690
00691 if ([invisibleItemsSortedByPriority indexOfObjectIdenticalTo:item] != CPNotFound)
00692 [_invisibleItems addObject:item];
00693 }
00694
00695 [_additionalItemsButton setFrameOrigin:CGPointMake(width + 5.0, (CGRectGetHeight([self bounds]) - CGRectGetHeight([_additionalItemsButton frame])) / 2.0)];
00696
00697 [self addSubview:_additionalItemsButton];
00698
00699 [_additionalItemsButton removeAllItems];
00700
00701 var index = 0,
00702 count = [_invisibleItems count];
00703
00704 [_additionalItemsButton addItemWithTitle:@"Additional Items"];
00705 [[_additionalItemsButton itemArray][0] setImage:_CPToolbarViewExtraItemsImage];
00706
00707 for (; index < count; ++index)
00708 {
00709 var item = _invisibleItems[index];
00710
00711 [_additionalItemsButton addItemWithTitle:[item label]];
00712
00713 var menuItem = [_additionalItemsButton itemArray][index + 1];
00714
00715 [menuItem setImage:[item image]];
00716
00717 [menuItem setTarget:[item target]];
00718 [menuItem setAction:[item action]];
00719 }
00720 }
00721 else
00722 [_additionalItemsButton removeFromSuperview];
00723
00724 }
00725
00726 - (CPView)viewForItem:(CPToolbarItem)anItem
00727 {
00728 var info = [_itemInfos objectForKey:[anItem hash]];
00729
00730 if (!info)
00731 return nil;
00732
00733 return info.view;
00734 }
00735
00736 - (CPTextField)labelForItem:(CPToolbarItem)anItem
00737 {
00738 var info = [_itemInfos objectForKey:[anItem hash]];
00739
00740 if (!info)
00741 return nil;
00742
00743 return info.label;
00744 }
00745
00746 - (float)minWidthForItem:(CPToolbarItem)anItem
00747 {
00748 var info = [_itemInfos objectForKey:[anItem hash]];
00749
00750 if (!info)
00751 return 0;
00752
00753 return info.minWidth;
00754 }
00755
00756 - (void)reloadToolbarItems
00757 {
00758
00759 var subviews = [self subviews],
00760 count = subviews.length;
00761
00762 while (count--)
00763 [subviews[count] removeFromSuperview];
00764
00765
00766 var items = [_toolbar items],
00767 index = 0;
00768
00769 count = items.length;
00770
00771 _itemInfos = [CPDictionary dictionary];
00772 _minWidth = TOOLBAR_ITEM_MARGIN;
00773
00774 for (; index < count; ++index)
00775 {
00776 var item = items[index],
00777 view = [item view];
00778
00779
00780 if (!view)
00781 {
00782 view = [[CPButton alloc] initWithFrame:CGRectMake(0.0, 0.0, 32.0, 32.0)];
00783
00784 [view setBordered:NO];
00785
00786 [view setImage:[item image]];
00787 [view setAlternateImage:[item alternateImage]];
00788
00789 [view setTarget:[item target]];
00790 [view setAction:[item action]];
00791
00792 [view setTag:[item tag]];
00793
00794 [view setImagePosition:CPImageOnly];
00795 }
00796
00797 [self addSubview:view];
00798
00799
00800 var label = [[CPTextField alloc] initWithFrame:CGRectMakeZero()];
00801
00802 [label setStringValue:[item label]];
00803 [label setFont:[CPFont systemFontOfSize:11.0]];
00804 [label setTextColor:_labelColor];
00805 [label setTextShadowColor:_labelShadowColor];
00806 [label setTextShadowOffset:CGSizeMake(0, 1)];
00807 [label sizeToFit];
00808
00809 [label setTarget:[item target]];
00810 [label setAction:[item action]];
00811
00812 [self addSubview:label];
00813
00814 var minSize = [item minSize],
00815 minWidth = MAX(minSize.width, CGRectGetWidth([label frame]));
00816
00817 [_itemInfos setObject:_CPToolbarItemInfoMake(index, view, label, minWidth) forKey:[item hash]];
00818
00819 _minWidth += minWidth + TOOLBAR_ITEM_MARGIN;
00820
00821
00822
00823
00824 }
00825
00826 [self layoutSubviews];
00827 }
00828
00829 @end
00830
00831
00832 var _CPToolbarItemVisibilityPriorityCompare = function(lhs, rhs)
00833 {
00834 var lhsVisibilityPriority = [lhs visibilityPriority],
00835 rhsVisibilityPriority = [rhs visibilityPriority];
00836
00837 if (lhsVisibilityPriority == rhsVisibilityPriority)
00838 return CPOrderedSame;
00839
00840 if (lhsVisibilityPriority > rhsVisibilityPriority)
00841 return CPOrderedAscending;
00842
00843 return CPOrderedDescending;
00844 }