summaryrefslogtreecommitdiff
path: root/frontends/cocoa/schedule.m
blob: 0fc55efbda43e47ce386b95a8c685af73a5bc59c (plain)
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
/*
 * Copyright 2011 Sven Weidauer <sven.weidauer@gmail.com>
 *
 * This file is part of NetSurf, http://www.netsurf-browser.org/
 *
 * NetSurf is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; version 2 of the License.
 *
 * NetSurf is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

#import <Cocoa/Cocoa.h>

#import "utils/errors.h"

#import "cocoa/schedule.h"

@interface ScheduledCallback : NSObject {
    void (*callback)(void *userData);
    void *userData;
}

- (instancetype)initWithCallback:(void (*)(void *))cb userData:(void *)ud;
- (void)schedule:(NSTimeInterval)ti;

@end

@implementation ScheduledCallback

- (instancetype)initWithCallback:(void (*)(void *))cb userData:(void *)ud
{
    callback = cb;
    userData = ud;

    return self;
}

static NSMutableSet *timerSet = nil;

- (void)schedule:(NSTimeInterval)ti
{
    if (nil == timerSet) {
        timerSet = [[NSMutableSet alloc] init];
    }

    [self performSelector:@selector(timerFired) withObject:nil afterDelay:ti];
    [timerSet addObject:self];
}

- (void)timerFired
{
    if ([timerSet containsObject:self]) {
        [timerSet removeObject:self];
        callback(userData);
    }
}

- (BOOL)isEqual:(id)object
{
    if (object == self)
        return YES;
    if ([object class] != [self class])
        return NO;
    return ((ScheduledCallback *)object)->callback == callback && ((ScheduledCallback *)object)->userData == userData;
}

- (NSUInteger)hash
{
    return (NSUInteger)callback + (NSUInteger)userData;
}

@end

/* exported interface documented in cocoa/schedule.h */
nserror cocoa_schedule(int t, void (*callback)(void *p), void *p)
{
    ScheduledCallback *cb = [[ScheduledCallback alloc] initWithCallback:callback userData:p];
    [timerSet removeObject:cb];
    if (t >= 0) {
        [cb schedule:(NSTimeInterval)t / 1000];
    }

    return NSERROR_OK;
}