Libraryless. Click here for Pure Java version (10477L/58K).
1 | transient sclass ReliableSingleThread implements Runnable { |
2 | O runnable; // usually a Runnable. is allowed to call trigger() itself |
3 | S name = "Single Thread"; |
4 | bool cancelBeforeTrigger; // always cancel running thread and wait for it to end before starting new operation |
5 | bool waitBetweenCancelAndTrigger; // make sure the old thread is actually ended |
6 | F0<AutoCloseable> enter; // optional ownership marker, e.g. for DynModules |
7 | int cancelTimeOut = 10000; |
8 | |
9 | bool trigger; |
10 | Thread thread; |
11 | WeakReference<Thread> threadBeingCancelled; |
12 | L<Runnable> inserts = syncL(); |
13 | |
14 | // If you want to set the action later |
15 | *() {} |
16 | |
17 | // legacy |
18 | *(O *runnable) {} |
19 | |
20 | *(Runnable *runnable) {} |
21 | |
22 | void trigger() { go(); } |
23 | synchronized void go() { |
24 | if (cancelBeforeTrigger) cancelAndPossiblyWait(); |
25 | trigger = true; |
26 | if (!running()) { |
27 | temp callF(enter); |
28 | thread = startThread(name, r { |
29 | temp callF(enter); |
30 | _run(); |
31 | }); |
32 | } |
33 | } |
34 | public void run() { go(); } |
35 | void get() { go(); } // so you can use the ! syntax |
36 | |
37 | synchronized bool running() { ret thread != null; } |
38 | |
39 | // use only if this is the last time you trigger this |
40 | void triggerAndWait() { |
41 | trigger(); |
42 | waitUntilDone(); |
43 | } |
44 | |
45 | void waitUntilDone { |
46 | while (running()) sleep(1); |
47 | } |
48 | |
49 | swappable void preSleep {} |
50 | |
51 | void _run() ctex { |
52 | while licensed { |
53 | preSleep(); |
54 | Thread oldThread; |
55 | synchronized(this) { |
56 | var currentInserts = syncGetAndClear(inserts); |
57 | pcallFAll(currentInserts); |
58 | |
59 | if (!trigger) { |
60 | thread = null; |
61 | break; |
62 | } |
63 | |
64 | oldThread = getWeakRef(threadBeingCancelled); |
65 | trigger = false; |
66 | } |
67 | |
68 | if (oldThread != null && oldThread != currentThread()) |
69 | oldThread.join(cancelTimeOut); |
70 | |
71 | pcallF(runnable); |
72 | } |
73 | } |
74 | |
75 | synchronized void cancel() { |
76 | if (thread == null) ret; |
77 | threadBeingCancelled = new WeakReference(thread); |
78 | cancelAndInterruptThread(thread); |
79 | thread = null; |
80 | } |
81 | |
82 | void cancelAndWait() { |
83 | Thread _thread; |
84 | |
85 | synchronized { |
86 | if (thread == null) ret; |
87 | _thread = thread; |
88 | threadBeingCancelled = new WeakReference(thread); |
89 | thread = null; |
90 | } |
91 | |
92 | cancelAndInterruptThread(_thread); |
93 | } |
94 | |
95 | void cancelAndTrigger() { |
96 | cancelAndPossiblyWait(); |
97 | trigger(); |
98 | } |
99 | |
100 | synchronized bool triggered() { ret trigger; } |
101 | |
102 | void cleanMeUp { cancel(); } |
103 | |
104 | selfType cancelBeforeTrigger() { |
105 | cancelBeforeTrigger = true; |
106 | this; |
107 | } |
108 | |
109 | void cancelAndPossiblyWait() { |
110 | if (waitBetweenCancelAndTrigger) |
111 | cancel(); |
112 | |
113 | } |
114 | |
115 | // TODO: trigger technically not necessary, just notify (I guess) |
116 | void insert(Runnable r) { inserts.add(r); trigger(); } |
117 | |
118 | synchronized bool hasThread() { ret thread != null; } |
119 | |
120 | selfType action(Runnable r) { runnable = r; this; } |
121 | } |
Began life as a copy of #1004705
download show line numbers debug dex old transpilations
Travelled to 19 computer(s): aoiabmzegqzx, bhatertpkbcr, cbybwowwnfue, cfunsshuasjs, gwrvuhgaqvyk, irmadwmeruwu, ishqpsrjomds, lpdgvwnxivlt, mowyntqkapby, mqqgnosmbjvj, omdjrrnzbjjv, onxytkatvevr, pyentgdyhuwx, pzhvpgtvlbxg, tslmcundralx, tvejysmllsmz, vouqrxazstgt, whxojlpjdney, xrpafgyirdlv
No comments. add comment
Snippet ID: | #1006319 |
Snippet name: | class ReliableSingleThread - triggers again reliably when one step is already running |
Eternal ID of this version: | #1006319/31 |
Text MD5: | 734470ef7b4d13d5d71ebbbed6e06b5a |
Transpilation MD5: | 28ec46cfccbb78842e407dc089e62f81 |
Author: | stefan |
Category: | javax |
Type: | JavaX fragment (include) |
Public (visible to everyone): | Yes |
Archived (hidden from active list): | No |
Created/modified: | 2022-12-18 23:42:10 |
Source code size: | 3016 bytes / 121 lines |
Pitched / IR pitched: | No / No |
Views / Downloads: | 898 / 2554 |
Version history: | 30 change(s) |
Referenced in: | [show references] |