Small animation inside NSCell (progress bar)
Small animation inside NSCell (progress bar)
- Subject: Small animation inside NSCell (progress bar)
- From: malcom <email@hidden>
- Date: Sun, 22 Feb 2009 19:18:53 +0100
Hello,
I'm working on a subclass of NSCell that draws a custom style progress bar.
Everything works fine, it draws correctly and I've made the code to
make indeterminate animation (the method should be called by a timer).
So I've created a NSTimer in my NSCell subclass, but when I try to run
the program itself it only animates the last row of the table. In fact
seems only a timer is created (while I'm pretty sure that each NSCell
displayed is a different subclass because it display correctly
different data).
What's the problem in here?
... However my big question is another. If I can get this method
working I'll have n timers for n cell istances that draw a short
portion of the entire tableview. It seems to be pretty expensive... so
what? What's the correct way to update only "indeterminate" cells with
a single timer? Is there a better way.
The code below is my class.
#define DEFAULT_PROGRESSBAR_LEN 100
#define DEFAULT_PROGRESSBAR_HEG 12
@implementation WGUICell_ProgressBar
- (id) init
{
self = [super init];
if (self != nil) {
[self setIndeterminate: YES];
_bar_width = DEFAULT_PROGRESSBAR_LEN;
_bar_height = DEFAULT_PROGRESSBAR_HEG;
_bar_includeCloseButton = YES;
_bar_maxValue = 100.0;
_bar_currentValue = 75.0;
}
return self;
}
- (void) setDoubleValue:(double) _val {
if (_val > _bar_maxValue) _val = _bar_maxValue;
_bar_currentValue = _val;
}
- (void) setMaxValue:(double) _max {
_bar_maxValue = _max;
}
- (BOOL) isIndetermimate {
return _indeterminate;
}
- (void) setIndeterminate:(BOOL) _ind {
_indeterminate = _ind;
if (!_ind) {
[_timer invalidate];
} else {
_stepOfIndeterminate = 0;
_timer = [[NSTimer scheduledTimerWithTimeInterval:2
target:self
selector:@selector(_updateIndeterminateProgress)
userInfo:nil repeats:YES] retain];
[ ((WGUITorrents_Table*)[self controlView]) _changeProgressBarsStyle];
}
}
#define BAR_WIDTH 100
- (NSRect) progressBarRect {
return _barRect;
}
- (void) _updateIndeterminateProgress {
NSLog(@"refresh %@",self);
[[self controlView] setNeedsDisplayInRect: _barRect];
// [[self controlView] setNeedsDisplay: YES];
_stepOfIndeterminate++;
}
- (void) setRepresentedObject:(id) _obj forColumn:(NSTableColumn *) _col {
[_representedObj release];
_representedObj = [_obj retain];
}
- (void)drawWithFrame:(NSRect)cellFrame inView:(NSView *)controlView {
// the point where the progress bar starts
NSPoint originBar = NSMakePoint(cellFrame.origin.x+75, cellFrame.origin.y+19);
// draw bar itself
NSImage *backgroundStructure = [self _createProgressBarStructure];
NSRect barRect = NSMakeRect(originBar.x, originBar.y, BAR_WIDTH, 12);
_barRect = barRect;
[backgroundStructure drawInRect: barRect fromRect:NSZeroRect
operation:NSCompositeSourceOver fraction:1.0];
if (!_indeterminate) {
NSImage *progression_value = [self _drawDeterminateProgressBarValue: barRect];
NSRect _fillRect = NSMakeRect(originBar.x, originBar.y,
[progression_value size].width, _bar_height);
[progression_value setFlipped:YES];
[progression_value drawInRect: _fillRect
fromRect:NSZeroRect operation:NSCompositeSourceOver fraction:1.0];
} else {
NSImage *indeterminateProgression = [self _drawIndetermination];
NSRect _fillRect = NSMakeRect(originBar.x+1, originBar.y+1,
[indeterminateProgression size].width, [indeterminateProgression
size].height);
[indeterminateProgression setFlipped:YES];
[indeterminateProgression drawInRect: _fillRect
fromRect:NSZeroRect operation:NSCompositeSourceOver fraction:1.0];
}
}
- (NSImage *) _drawIndetermination {
NSImage *_double_prog = [[NSImage alloc] initWithSize: NSMakeSize(
(_bar_width*2)-2, _bar_height-2)];
[_double_prog lockFocus];
[[NSColor colorWithPatternImage: [NSImage
imageNamed:@"ind_progressbar.png"]] set];
NSBezierPath *p =[NSBezierPath bezierPathWithRect: NSMakeRect(0, 0,
(_bar_width*2)-2, _bar_height-2)];
[p fill];
[_double_prog unlockFocus];
NSImage *_portionVisible = [[NSImage alloc]
initWithSize:NSMakeSize(_bar_width-2, _bar_height-2)];
[_portionVisible lockFocus];
// back to the start of animation
if (_stepOfIndeterminate == _bar_width)
_stepOfIndeterminate = 0;
NSRect _portionsToPutInVisible = NSMakeRect(_stepOfIndeterminate, 0,
_bar_width-2, _bar_height-2);
[_double_prog setFlipped:YES];
[_double_prog drawInRect: NSMakeRect(0, 0, _bar_width-2, _bar_height-2)
fromRect:_portionsToPutInVisible operation:NSCompositeSourceOver
fraction:1.0];
[_portionVisible unlockFocus];
[_double_prog release];
return [_portionVisible autorelease];
/*
NSImage *prog = [[NSImage alloc]
initWithSize:NSMakeSize(_bar_width-2, _bar_height-2)];
[prog lockFocus];
NSColor *c = [NSColor colorWithPatternImage:[NSImage
imageNamed:@"ProgressIndeterminate.png"]];
[c set];
NSBezierPath *p =[NSBezierPath bezierPathWithRect:
NSMakeRect(0, 0, _bar_width, _bar_height)];
[p fill];
[prog unlockFocus];
return [prog autorelease];*/
}
- (NSImage *) _drawDeterminateProgressBarValue:(NSRect ) _barRect {
// x = (valore / valore max) * lungh barra
// x = (_bar_currentValue / _bar_maxValue)*_bar_width
double x_progressWidth = (_bar_currentValue/_bar_maxValue)*_bar_width;
NSImage *prog = [[NSImage alloc]
initWithSize:NSMakeSize(x_progressWidth, _bar_height)];
[prog lockFocus];
[[NSColor colorWithPatternImage:[NSImage
imageNamed:@"ProgressBlue12.png"]] set];
NSBezierPath *p = [NSBezierPath bezierPathWithRect:NSMakeRect(0, 0,
x_progressWidth, _bar_height)];
[p fill];
[prog unlockFocus];
return [prog autorelease];
}
-copyWithZone:(NSZone *)zone
{
WGUICell_ProgressBar *cell = (WGUICell_ProgressBar *)[super copyWithZone:zone];
cell->_representedObj = [_representedObj retain];
cell->_timer = [_timer retain];
cell->_closeButtonRect = _closeButtonRect;
cell->_bar_currentValue = _bar_currentValue;
cell->_bar_maxValue =_bar_maxValue;
cell->_bar_width =_bar_width;
cell->_bar_height =_bar_height;
cell->_bar_includeCloseButton =_bar_includeCloseButton;
// cell->_indeterminate =_indeterminate;
//cell->_barRect =_barRect;
// cell->_stepOfIndeterminate =_stepOfIndeterminate;
return cell;
}
- (NSImage *) _createProgressBarStructure {
// create offscreen structure
NSImage *back = [[NSImage alloc] initWithSize:NSMakeSize(_bar_width,
_bar_height)];
[back lockFocus];
// draw background in the middle
NSColor *middle_progressbarImg = [NSColor
colorWithPatternImage:[NSImage imageNamed:@"middle_progressbar.png"]];
[middle_progressbarImg set];
NSBezierPath *p = [NSBezierPath bezierPathWithRect: NSMakeRect(1, 0,
_bar_width-1, _bar_height)];
[p fill];
NSImage *lbar = [NSImage imageNamed:@"end_progressbar.png"];
// left start part
[lbar setFlipped:YES];
[lbar drawInRect: NSMakeRect(0,0, 1, _bar_height)
fromRect:NSZeroRect operation:NSCompositeSourceOver fraction:1.0];
// right end part
[lbar setFlipped:NO];
[lbar drawInRect: NSMakeRect(_bar_width-1, 0, 1, _bar_height)
fromRect:NSZeroRect operation:NSCompositeSourceOver fraction:1.0];
[back unlockFocus];
return [back autorelease];
}
@end
_______________________________________________
Cocoa-dev mailing list (email@hidden)
Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden