/
util.kt
56 lines (42 loc) · 1.7 KB
/
util.kt
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
package net.aquadc.properties.executor
import android.os.Handler
import android.os.Looper
import javafx.application.Platform
import java.util.concurrent.*
internal object ScheduledDaemonHolder {
internal val scheduledDaemon =
ScheduledThreadPoolExecutor(1, ThreadFactory { Thread(it).also { it.isDaemon = true } })
}
internal object PlatformExecutors {
private val executors = ConcurrentHashMap<Thread, Executor>(4)
private val executorFactories: Array<() -> Executor?>
init {
val facs = ArrayList<() -> Executor?>(2)
try {
Looper.myLooper() // ensure class available
facs.add {
Looper.myLooper()?.let { myLooper -> HandlerAsExecutor(Handler(myLooper)) }
}
} catch (ignored: NoClassDefFoundError) {}
try {
Platform.isFxApplicationThread() // ensure class available
facs.add {
if (Platform.isFxApplicationThread()) FxApplicationThreadExecutor else null
}
} catch (ignored: NoClassDefFoundError) {}
executorFactories = facs.toTypedArray()
}
internal fun executorForCurrentThread(): Executor {
val thread = Thread.currentThread()
val ex = executors[thread]
if (ex != null) return ex
val newEx = createForCurrentThread()
// if putIfAbsent returns non-null value, the executor was set concurrently,
// use it and throw away our then
return executors.putIfAbsent(thread, newEx) ?: newEx
}
private fun createForCurrentThread(): Executor {
executorFactories.forEach { it()?.let { return it } }
throw UnsupportedOperationException("Can't execute task on $this")
}
}