Skip to content

Commit 3680c2c

Browse files
committed
Initial commit
0 parents  commit 3680c2c

33 files changed

+3985
-0
lines changed

.classpath

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<classpath>
3+
<classpathentry kind="src" path="src"/>
4+
<classpathentry kind="src" path="test"/>
5+
<classpathentry kind="con" path="org.scala-ide.sdt.launching.SCALA_CONTAINER"/>
6+
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>
7+
<classpathentry kind="con" path="org.eclipse.jdt.junit.JUNIT_CONTAINER/4"/>
8+
<classpathentry kind="lib" path="lib/scalatest-1.2.1-SNAPSHOT.jar"/>
9+
<classpathentry kind="lib" path="lib/joda-time-2.0.jar"/>
10+
<classpathentry kind="lib" path="lib/joda-convert-1.2.jar"/>
11+
<classpathentry kind="output" path="bin"/>
12+
</classpath>

.project

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<projectDescription>
3+
<name>scala-react-2</name>
4+
<comment></comment>
5+
<projects>
6+
</projects>
7+
<buildSpec>
8+
<buildCommand>
9+
<name>org.scala-ide.sdt.core.scalabuilder</name>
10+
<arguments>
11+
</arguments>
12+
</buildCommand>
13+
</buildSpec>
14+
<natures>
15+
<nature>org.scala-ide.sdt.core.scalanature</nature>
16+
<nature>org.eclipse.jdt.core.javanature</nature>
17+
</natures>
18+
</projectDescription>

README.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
# scala.react
2+
3+
Scala.react is a reactive programming library for Scala.

lib/hamcrest.jar

26 KB
Binary file not shown.

lib/joda-convert-1.2.jar

37.6 KB
Binary file not shown.

lib/joda-time-2.0-sources.jar

678 KB
Binary file not shown.

lib/joda-time-2.0.jar

556 KB
Binary file not shown.

lib/jsr166y.jar

54.6 KB
Binary file not shown.

lib/junit.jar

191 KB
Binary file not shown.

lib/scalatest-1.2.1-SNAPSHOT.jar

1.65 MB
Binary file not shown.

src/scala/react/Debug.scala

Lines changed: 93 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,93 @@
1+
package scala.react
2+
3+
import java.util.WeakHashMap
4+
import java.text.SimpleDateFormat
5+
import scala.annotation.elidable
6+
import scala.collection.mutable.ArrayBuffer
7+
8+
abstract class Debug[D <: Domain](val domain: D) {
9+
import domain._
10+
11+
def setName(node: Node, name: String)
12+
def getName(node: Node): String
13+
14+
15+
// The thread on which this engine is currently running, `null` if not in a turn.
16+
@volatile private var thread: Thread = null
17+
18+
/**
19+
* Returns `true` if the current thread is the thread the engine is running on.
20+
*/
21+
@elidable(800) protected def isInTurn = Thread.currentThread == thread
22+
@elidable(800) protected def isInTurn_=(b: Boolean) {
23+
thread = if (b) Thread.currentThread else null
24+
}
25+
26+
@elidable(800) def enterTurn(id: Long) {
27+
assert(!isInTurn, "Tried to run a turn before the previous one was finished.")
28+
logEnterTurn(id)
29+
isInTurn = true
30+
}
31+
@elidable(800) def leaveTurn(id: Long) {
32+
assert(isInTurn)
33+
logLeaveTurn(id)
34+
isInTurn = false
35+
}
36+
37+
@elidable(800) def assertInTurn() = assert(isInTurn, "This method must be run on its domain " + this)
38+
39+
@elidable(800) def logStart()
40+
@elidable(800) def logEnterTurn(id: Long)
41+
@elidable(800) def logLeaveTurn(id: Long)
42+
@elidable(800) def logTock(n: Node)
43+
@elidable(800) def logLevelMismatch(accessor: Node, accessed: Node)
44+
@elidable(800) def logTodo(t: Any)
45+
}
46+
47+
class NilDebug[D <: Domain](dom: D) extends Debug(dom) {
48+
import domain._
49+
50+
def setName(node: Node, name: String) { }
51+
def getName(node: Node): String = ""
52+
53+
def logStart() {}
54+
def logEnterTurn(id: Long) {}
55+
def logLeaveTurn(id: Long) {}
56+
def logTock(n: Node) {}
57+
def logLevelMismatch(accessor: Node, accessed: Node) {}
58+
def logTodo(t: Any) {}
59+
}
60+
61+
abstract class AbstractDebug[D <: Domain](dom: D) extends Debug(dom) {
62+
import domain._
63+
private val names = new WeakHashMap[Node, String]
64+
def setName(node: Node, name: String) { names.put(node, name) }
65+
def getName(node: Node): String = names.get(node)
66+
}
67+
68+
abstract class PrintDebug[D <: Domain](dom: D) extends AbstractDebug(dom) {
69+
import domain._
70+
71+
private val dateFormat = new SimpleDateFormat("d MMM yyyy HH:mm:ss.SSS")
72+
73+
def log(s: String)
74+
75+
private def time() = System.currentTimeMillis()
76+
private def timePrefix = "+" + (time()-startTime) + "ms: "
77+
private var startTime = 0L
78+
79+
def logStart() {
80+
startTime = time()
81+
log("Start domain " + domain + " at " + dateFormat.format(startTime))
82+
}
83+
def logEnterTurn(id: Long) = log(timePrefix + "enter turn " + id)
84+
def logLeaveTurn(id: Long) = log(timePrefix + "leave turn " + id)
85+
def logTock(n: Node) = log("Tock " + n)
86+
def logLevelMismatch(accessor: Node, accessed: Node) = log("Level mismatch when " + accessor + " accessed " + accessed)
87+
def logTodo(t: Any) = log("Todo " + t)
88+
}
89+
90+
91+
class ConsoleDebug[D <: Domain](dom: D) extends PrintDebug(dom) {
92+
def log(s: String) = println(s)
93+
}

src/scala/react/Domain.scala

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
package scala.react
2+
import scala.annotation.elidable
3+
4+
/**
5+
* Defines all reactive classes by mixing in all reactive modules.
6+
*
7+
* Clients usually create an 'object myDomain extends Domain' and import it.
8+
*
9+
* Except the scheduler interface, no method in neither class is guaranteed to be thread-safe.
10+
*/
11+
abstract class Domain extends ReactiveModule
12+
with SignalModule
13+
with EventModule
14+
with FlowModule
15+
with SchedulerModule { domain =>
16+
17+
protected val scheduler: Scheduler
18+
protected def engine: Engine
19+
20+
val debug: Debug[this.type] =
21+
System.getProperty("scala.react.debug", "no").toLowerCase match {
22+
case "no" => new NilDebug[this.type](domain)
23+
case "print" => new ConsoleDebug[this.type](this)
24+
case "log" => new monitor.LogDebug[this.type](this)
25+
}
26+
27+
/**
28+
* A reactive version of `scala.App`, running all initialization code on this domain.
29+
* Automatically starts the domain in the main method.
30+
*
31+
* @see scala.App
32+
* @see scala.DelayedInit
33+
*/
34+
trait ReactiveApp extends App {
35+
def main() {}
36+
37+
override def main(args: Array[String]) {
38+
domain schedule { super.main(args) }
39+
domain.start()
40+
main()
41+
}
42+
}
43+
44+
/**
45+
* Starts processing events. Thread-safe.
46+
*/
47+
def start() {
48+
debug.logStart()
49+
scheduler.start()
50+
}
51+
}
52+

0 commit comments

Comments
 (0)