This is NetTalkThinker.IconAnim.m in view mode; [Download] [Up]
#import "NetTalkThinker.h"
#import <appkit/appkit.h>
#import <dpsclient/dpsNeXT.h>
#define _PATTERN_END 15
static int newClientPattern[_PATTERN_END]
= {0, 1, 2, 1, 2, 1, 2, 1, 2, 1, 2, 1, 2, 1, 0};
static int newRequestPattern[_PATTERN_END]
= {0, 1, 2, 3, 2, 1, 2, 3, 2, 1, 2, 3, 2, 1, 2};
static int *animationPattern;
static int patternIterator;
static int loopCount;
@implementation NetTalkThinker(IconAnimation)
- _display: anImage
{
// NXAppTile is composited first at 0,0 of the icon window's content view
// (this is required in order to maintain the NeXT icon look). 'anImage' is
// then composited at center (centering is also a requirement).
NXPoint contentViewOrigin = { 0.0, 0.0 };
NXPoint centerPoint = { 8.0, 8.0 };
[appIconContentView lockFocus];
[appTile composite:NX_SOVER toPoint:&contentViewOrigin];
[anImage composite:NX_SOVER toPoint:¢erPoint];
[appIconContentView unlockFocus];
[appIconContentView display];
return self;
}
- _animate
{
// This contains logic for the icon animation (image sequencing). Three
// images are used (contained in imageList). The animationPattern
// provides an index into that list, giving us the right image at the right
// time. The icon will 'ring' twice, and leave the phone off-hook to indicate
// unanswered calls.
static int offset;
[self _display: [imageList objectAt: animationPattern[patternIterator++]]];
if (patternIterator == (_PATTERN_END - offset))
{
[self removeTimedEntry];
patternIterator = 0;
loopCount++;
if (loopCount < 2)
{
offset = 1;
if (animationPattern == newClientPattern)
[self perform: @selector(newClient:) with:self
afterDelay:500 cancelPrevious:YES];
else
[self perform: @selector(newRequest:) with:self
afterDelay:500 cancelPrevious:YES];
}
else
{
loopCount = offset = 0;
if (animationPattern == newClientPattern)
[self _display:[imageList objectAt:0]];
else
if ([requestList count] == 0)
[self _display:[imageList objectAt:0]];
else
[self _display:[imageList objectAt:3]];
}
}
return self;
}
void Animate (DPSTimedEntry timedEntry, double now, id self)
{
[(id)self _animate];
}
- removeTimedEntry
{
if (timedEntry)
{
DPSRemoveTimedEntry (timedEntry);
timedEntry = 0;
}
return self;
}
- newClient:sender
{
if (timedEntry) return self;
animationPattern = newClientPattern;
timedEntry = DPSAddTimedEntry(0.2,
(DPSTimedEntryProc)Animate, (void*)self, NX_MODALRESPTHRESHOLD);
return self;
}
- newRequest:sender
{
if (timedEntry)
[self removeTimedEntry];
if (strcmp(NXGetDefaultValue(APPNAME, NTD_MUTEALARM), NTD_NO) == 0)
[[[[Sound alloc]
initFromSoundfile:NXGetDefaultValue(APPNAME, NTD_SOUNDNAME)]
play: nil] free];
animationPattern = newRequestPattern;
timedEntry = DPSAddTimedEntry(0.2,
(DPSTimedEntryProc)Animate, (void*)self, NX_MODALRESPTHRESHOLD);
return self;
}
@end
These are the contents of the former NiCE NeXT User Group NeXTSTEP/OpenStep software archive, currently hosted by Netfuture.ch.