-
Notifications
You must be signed in to change notification settings - Fork 52
/
IMBImageBrowserCell.m
395 lines (297 loc) · 12.7 KB
/
IMBImageBrowserCell.m
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
/*
iMedia Browser Framework <http://karelia.com/imedia/>
Copyright (c) 2005-2012 by Karelia Software et al.
iMedia Browser is based on code originally developed by Jason Terhorst,
further developed for Sandvox by Greg Hulands, Dan Wood, and Terrence Talbot.
The new architecture for version 2.0 was developed by Peter Baumgartner.
Contributions have also been made by Matt Gough, Martin Wennerberg and others
as indicated in source files.
The iMedia Browser Framework is licensed under the following terms:
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in all or substantial portions of the Software without restriction, including
without limitation the rights to use, copy, modify, merge, publish,
distribute, sublicense, and/or sell copies of the Software, and to permit
persons to whom the Software is furnished to do so, subject to the following
conditions:
Redistributions of source code must retain the original terms stated here,
including this list of conditions, the disclaimer noted below, and the
following copyright notice: Copyright (c) 2005-2012 by Karelia Software et al.
Redistributions in binary form must include, in an end-user-visible manner,
e.g., About window, Acknowledgments window, or similar, either a) the original
terms stated here, including this list of conditions, the disclaimer noted
below, and the aforementioned copyright notice, or b) the aforementioned
copyright notice and a link to karelia.com/imedia.
Neither the name of Karelia Software, nor Sandvox, nor the names of
contributors to iMedia Browser may be used to endorse or promote products
derived from the Software without prior and express written permission from
Karelia Software or individual contributors, as appropriate.
Disclaimer: THE SOFTWARE IS PROVIDED BY THE COPYRIGHT OWNER AND CONTRIBUTORS
"AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT
LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE,
AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
LIABLE FOR ANY CLAIM, DAMAGES, OR OTHER LIABILITY, WHETHER IN AN ACTION OF
CONTRACT, TORT, OR OTHERWISE, ARISING FROM, OUT OF, OR IN CONNECTION WITH, THE
SOFTWARE OR THE USE OF, OR OTHER DEALINGS IN, THE SOFTWARE.
*/
// Author: Peter Baumgartner, Dan Wood
//----------------------------------------------------------------------------------------------------------------------
#pragma mark HEADERS
#import "IMBImageBrowserCell.h"
#import "IMBObject.h"
#import "IMBNode.h"
#import "IMBCommon.h"
#import "IMBObjectViewController.h"
/* weak linking of types for layerForType to ensure 10.5 compatibility: */
extern NSString *const IKImageBrowserCellBackgroundLayer __attribute__((weak_import));
extern NSString *const IKImageBrowserCellForegroundLayer __attribute__((weak_import));
extern NSString *const IKImageBrowserCellSelectionLayer __attribute__((weak_import));
extern NSString *const IKImageBrowserCellPlaceHolderLayer __attribute__((weak_import));
//----------------------------------------------------------------------------------------------------------------------
@interface IKImageBrowserCell (NotPublicSoThisMightBeAProblemForTheMAS)
- (void) setDataSource:(id)inDataSource;
- (void) drawShadow;
- (void) drawImageOutline;
- (NSRect) usedRectInCellFrame:(NSRect)inFrame;
- (NSRect) imageContainerFrame;
- (IKImageBrowserView*) imageBrowserView; // To shut up the compiler when using 10.5.sdk
- (void) drawTitle; // To shut up the compiler when using 10.6.sdk
- (id) parent;
@end
//----------------------------------------------------------------------------------------------------------------------
#pragma mark
@implementation IMBImageBrowserCell
@synthesize imbShouldDrawOutline = _imbShouldDrawOutline;
@synthesize imbShouldDrawShadow = _imbShouldDrawShadow;
@synthesize imbShouldDisableTitle = _imbShouldDisableTitle;
//----------------------------------------------------------------------------------------------------------------------
- (id) init
{
if (self = [super init])
{
_imbShouldDrawOutline = YES;
_imbShouldDrawShadow = YES;
_imbShouldDisableTitle = NO;
}
return self;
}
//----------------------------------------------------------------------------------------------------------------------
// Disable outline and shadow drawing for certain objects...
- (void) setDataSource:(id)inDataSource
{
[super setDataSource:inDataSource];
if ([inDataSource isKindOfClass:[IMBObject class]])
{
IMBObject* object = (IMBObject*)inDataSource;
_imbShouldDrawOutline = object.shouldDrawAdornments;
_imbShouldDrawShadow = object.shouldDrawAdornments;
_imbShouldDisableTitle = object.shouldDisableTitle;
}
}
//----------------------------------------------------------------------------------------------------------------------
// Drawing outlines and shadows should be suppress in some cases (e.g. for IMBNodeObjects which are displayed
// as non-rectangular folder icons)...
- (void) drawShadow
{
if (_imbShouldDrawShadow)
{
[super drawShadow];
}
}
- (void) drawImageOutline
{
if (_imbShouldDrawOutline)
{
[super drawImageOutline];
}
}
// Draw the image itself. In the case of an IMBNodeObject (which is represented as a large folder icon)
// we should draw a small badge icon on top of the large folder icon. This si used to distinguish various
// kinds of subnodes visually (e.g. iPhoto events, albums, etc)...
//- (void) drawImage:(id)inImage
//{
// [super drawImage:inImage];
//
// id datasource = self.dataSource;
//
// if ([datasource isKindOfClass:[IMBNodeObject class]])
// {
// IMBNode* node = (IMBNode*) datasource;
// NSImage* icon = node.icon;
// NSRect frame = [self imageFrame];
// CGFloat x0 = 20; //NSMidX(frame);
// CGFloat y0 = 20; //NSMidY(frame);
// CGFloat dx = 16.0;
// CGFloat dy = 16.0;
// frame = NSMakeRect(x0-0.5*dx,y0-0.5*dy,dx,dy);
// [icon drawInRect:frame fromRect:NSZeroRect operation:NSCompositeSourceOver fraction:1.0];
// }
//}
//----------------------------------------------------------------------------------------------------------------------
- (CGFloat) imbPointSize
{
CGFloat points = 0;
CGFloat width = [((id)self) size].width;
if (width < 60) points = 9;
else if (width < 70) points = 10;
else points = 11;
return points;
}
// Is there any smarter way to do this?
- (void) imbSetTitleColors
{
CGFloat points = [self imbPointSize]; // we need to get the whole font thing since we have to set the whole attributes
NSMutableDictionary *attributes1 = [NSMutableDictionary dictionaryWithObject:[NSFont systemFontOfSize:points] forKey:NSFontAttributeName];
NSMutableDictionary *attributes2 = [NSMutableDictionary dictionaryWithDictionary:attributes1];
// Now set the title color. Try to match what we see in table views.
// Enabled: Black, white if Selected; Disabled: grayed out.
if (_imbShouldDisableTitle)
{
[attributes1 setObject:[NSColor colorWithCalibratedWhite:0.0 alpha:0.4] forKey:NSForegroundColorAttributeName];
[attributes2 setObject:[NSColor colorWithCalibratedWhite:1.0 alpha:0.5] forKey:NSForegroundColorAttributeName];
}
else
{
[attributes1 setObject:[NSColor blackColor] forKey:NSForegroundColorAttributeName];
[attributes2 setObject:[NSColor whiteColor] forKey:NSForegroundColorAttributeName];
}
if (IMBRunningOnSnowLeopardOrNewer())
{
[[self imageBrowserView] setValue:attributes1 forKey:IKImageBrowserCellsTitleAttributesKey];
[[self imageBrowserView] setValue:attributes2 forKey:IKImageBrowserCellsHighlightedTitleAttributesKey];
}
else
{
[[self parent] setValue:attributes1 forKey:IKImageBrowserCellsTitleAttributesKey];
[[self parent] setValue:attributes2 forKey:IKImageBrowserCellsHighlightedTitleAttributesKey];
}
}
- (void) drawTitle
{
[self imbSetTitleColors];
[super drawTitle];
}
//---------------------------------------------------------------------------------
// layerForType:
//
// provides the layers for the given types
//---------------------------------------------------------------------------------
- (CALayer *) layerForType:(NSString*) type
{
CGColorRef color;
//retrieve some usefull rects
NSRect frame = [self frame];
NSRect imageFrame = [self imageFrame];
NSRect relativeImageFrame = NSMakeRect(imageFrame.origin.x - frame.origin.x, imageFrame.origin.y - frame.origin.y, imageFrame.size.width, imageFrame.size.height);
/* place holder layer */
if(type == IKImageBrowserCellPlaceHolderLayer){
//create a place holder layer
CALayer *layer = [CALayer layer];
layer.frame = CGRectMake(0, 0, frame.size.width, frame.size.height);
CALayer *placeHolderLayer = [CALayer layer];
placeHolderLayer.frame = *(CGRect*) &relativeImageFrame;
CGFloat fillComponents[4] = {1.0, 1.0, 1.0, 0.3};
CGFloat strokeComponents[4] = {1.0, 1.0, 1.0, 0.9};
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
//set a background color
color = CGColorCreate(colorSpace, fillComponents);
[placeHolderLayer setBackgroundColor:color];
CFRelease(color);
//set a stroke color
color = CGColorCreate(colorSpace, strokeComponents);
[placeHolderLayer setBorderColor:color];
CFRelease(color);
[placeHolderLayer setBorderWidth:2.0];
[placeHolderLayer setCornerRadius:10];
CFRelease(colorSpace);
[layer addSublayer:placeHolderLayer];
return layer;
}
/* foreground layer */
if(type == IKImageBrowserCellForegroundLayer){
// No foreground layer on place holders
if([self cellState] != IKImageStateReady)
return nil;
// Create a foreground layer that may contain a badge layer
// (i.e. add a badge icon if the host app does provide one)
CALayer *layer = [CALayer layer];
layer.frame = CGRectMake(0, 0, frame.size.width, frame.size.height);
IMBObjectViewController* objectViewController = (IMBObjectViewController*) [[self imageBrowserView] delegate];
IMBObject* item = (IMBObject*) [self representedItem];
id <IMBObjectViewControllerDelegate> delegate = [objectViewController delegate];
if ([delegate respondsToSelector:@selector(objectViewController:badgeForObject:)])
{
CGImageRef badge = [delegate objectViewController:objectViewController badgeForObject:item];
if (badge)
{
CALayer* badgeLayer = [CALayer layer];
[badgeLayer setContents:(id)badge];
badgeLayer.frame = CGRectMake(relativeImageFrame.origin.x + relativeImageFrame.size.width - CGImageGetWidth(badge) - 3,
relativeImageFrame.origin.y + 3,
CGImageGetWidth(badge), CGImageGetHeight(badge));
[layer addSublayer:badgeLayer];
}
}
return layer;
}
/* selection layer */
if(type == IKImageBrowserCellSelectionLayer){
return nil;
//create a selection layer
CALayer *selectionLayer = [CALayer layer];
selectionLayer.frame = CGRectMake(0, 0, frame.size.width, frame.size.height);
CGFloat fillComponents[4] = {1.0, 0, 0.5, 0.3};
CGFloat strokeComponents[4] = {1.0, 0.0, 0.5, 1.0};
//set a background color
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
color = CGColorCreate(colorSpace, fillComponents);
[selectionLayer setBackgroundColor:color];
CFRelease(color);
//set a border color
color = CGColorCreate(colorSpace, strokeComponents);
[selectionLayer setBorderColor:color];
CFRelease(color);
[selectionLayer setBorderWidth:2.0];
[selectionLayer setCornerRadius:5];
return selectionLayer;
}
/* background layer */
if(type == IKImageBrowserCellBackgroundLayer)
{
//return nil;
//no background layer on place holders
if([self cellState] != IKImageStateReady)
return nil;
CALayer *layer = [CALayer layer];
layer.frame = CGRectMake(0, 0, frame.size.width, frame.size.height);
// NSRect backgroundRect = NSMakeRect(0, 0, frame.size.width, frame.size.height);
//
// CALayer *photoBackgroundLayer = [CALayer layer];
// photoBackgroundLayer.frame = *(CGRect*) &backgroundRect;
//
// CGFloat fillComponents[4] = {0.95, 0.95, 0.95, 1.0};
// CGFloat strokeComponents[4] = {0.2, 0.2, 0.2, 0.5};
//
// CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
//
// color = CGColorCreate(colorSpace, fillComponents);
// [photoBackgroundLayer setBackgroundColor:color];
// CFRelease(color);
//
// color = CGColorCreate(colorSpace, strokeComponents);
// [photoBackgroundLayer setBorderColor:color];
// CFRelease(color);
//
// [photoBackgroundLayer setBorderWidth:5.0];
// [photoBackgroundLayer setShadowOpacity:0.5];
// [photoBackgroundLayer setCornerRadius:3];
//
// CFRelease(colorSpace);
//
// [layer addSublayer:photoBackgroundLayer];
return layer;
}
return nil;
}
//----------------------------------------------------------------------------------------------------------------------
@end