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
|
package io.dico.dicore.task;
import org.bukkit.Bukkit;
import org.bukkit.plugin.Plugin;
import java.util.NoSuchElementException;
public abstract class BaseTask<T> {
private boolean running = false;
private Integer taskId = null;
private long workTime = 5L;
private int workCount;
public void start(Plugin plugin, int delay, int period, long workTime) {
doStartChecks();
this.workTime = workTime;
workCount = 0;
running = true;
if (delay == -1) {
run();
if (!running) {
return;
}
delay = period;
}
taskId = plugin.getServer().getScheduler().scheduleSyncRepeatingTask(plugin, this::run, delay, period);
}
public void startImmediately(Plugin plugin, int period, long workTime) {
start(plugin, -1, period, workTime);
}
protected void doStartChecks() {
if (isRunning()) {
throw new IllegalStateException("Can't start when already running");
}
}
public void start(Plugin plugin) {
start(plugin, -1, 20, 5L);
}
protected void onFinish(boolean early) {
}
protected long getWorkTime() {
return workTime;
}
protected abstract boolean process(T object);
private void run() {
workCount++;
final long stop = System.currentTimeMillis() + getWorkTime();
do {
if (!processNext()) {
return;
}
} while (System.currentTimeMillis() < stop);
}
public int getTaskId() {
return running ? taskId : -1;
}
public int getWorkCount() {
return workCount;
}
public boolean isRunning() {
return running;
}
protected abstract T supply() throws NoSuchElementException;
private void cancelTask(boolean early) {
if (taskId != null) {
Bukkit.getScheduler().cancelTask(taskId);
}
running = false;
taskId = null;
onFinish(early);
}
private boolean processNext() {
T object;
try {
object = supply();
} catch (NoSuchElementException e) {
cancelTask(false);
return false;
}
try {
if (process(object)) {
return true;
}
} catch (RuntimeException e) {
e.printStackTrace();
}
cancelTask(true);
return false;
}
}
|