Skip to content

Commit

Permalink
Use local rate limiting to remove need for the rate limiting class
Browse files Browse the repository at this point in the history
  • Loading branch information
ultraq committed Feb 2, 2024
1 parent fd2baaa commit d308f19
Show file tree
Hide file tree
Showing 3 changed files with 64 additions and 41 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -34,4 +34,23 @@ abstract class EngineSystem implements Runnable, EventTarget {

this.scene = scene
}

/**
* Execute an action and optionally wait, such that, if repeated, it would run
* no faster than the given frequency.
*
* @param frequency
* The number of times per second the action could be repeated.
* @param action
* @return
*/
protected static void rateLimit(float frequency, Closure action) {

var maxExecTime = 1000f / frequency
var execTime = time(action)
var waitTime = maxExecTime - execTime
if (waitTime > 0) {
Thread.sleep((long)waitTime)
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -44,8 +44,10 @@ class AudioSystem extends EngineSystem {
final AudioConfiguration config

// For object lifecycles
// TODO: Move to using the 'request' system from the scripting branch to remove these
private final CopyOnWriteArrayList<SceneElement> addedElements = new CopyOnWriteArrayList<>()
private final CopyOnWriteArrayList<SceneElement> removedElements = new CopyOnWriteArrayList<>()
private final Set<AudioElement> initialized = new HashSet<>()

/**
* Constructor, build a new engine for rendering audio.
Expand Down Expand Up @@ -87,39 +89,40 @@ class AudioSystem extends EngineSystem {
logger.debug('Audio system in render loop...')
while (!Thread.interrupted()) {
try {

// Initialize or delete objects which have been added/removed to/from the scene
if (addedElements) {
def elementsToInit = new ArrayList<SceneElement>(addedElements)
elementsToInit.each { elementToInit ->
elementToInit.accept { element ->
if (element instanceof AudioElement) {
element.init(renderer)
rateLimit(100) { ->

// Initialize or delete objects which have been added/removed to/from the scene
if (addedElements) {
def elementsToInit = new ArrayList<SceneElement>(addedElements)
elementsToInit.each { elementToInit ->
elementToInit.accept { element ->
if (element instanceof AudioElement) {
element.init(renderer)
initialized << element
}
}
}
addedElements.removeAll(elementsToInit)
}
addedElements.removeAll(elementsToInit)
}
if (removedElements) {
def elementsToDelete = new ArrayList<SceneElement>(removedElements)
elementsToDelete.each { elementToInit ->
elementToInit.accept { element ->
if (element instanceof AudioElement) {
element.delete(renderer)
if (removedElements) {
def elementsToDelete = new ArrayList<SceneElement>(removedElements)
elementsToDelete.each { elementToInit ->
elementToInit.accept { element ->
if (element instanceof AudioElement) {
element.delete(renderer)
}
}
}
removedElements.removeAll(elementsToDelete)
}
removedElements.removeAll(elementsToDelete)
}

// Run the audio elements
scene.accept { element ->
if (element instanceof AudioElement) {
element.render(renderer)
// Run the audio elements
scene.accept { element ->
if (element instanceof AudioElement && initialized.contains(element)) {
element.render(renderer)
}
}
}

Thread.sleep(10)
}
catch (InterruptedException ignored) {
break
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -85,27 +85,28 @@ class GameClock extends EngineSystem {
logger.debug('Game clock in update loop')
while (!Thread.interrupted()) {
try {
Thread.sleep(10)
var currentSystemTimeMillis = System.currentTimeMillis()
var delta = currentSystemTimeMillis - lastSystemTimeMillis
rateLimit(100) { ->
var currentSystemTimeMillis = System.currentTimeMillis()
var delta = currentSystemTimeMillis - lastSystemTimeMillis

// Normal flow of time, accumulate ticks at the same rate as system time
if (speed == 1.0f) {
currentTimeMillis += delta
}
// Modified flow, accumulate ticks at system time * flow speed
else {
currentTimeMillis += (delta * speed)
}
// Normal flow of time, accumulate ticks at the same rate as system time
if (speed == 1.0f) {
currentTimeMillis += delta
}
// Modified flow, accumulate ticks at system time * flow speed
else {
currentTimeMillis += (delta * speed)
}

// Update time with scene objects
scene.accept { element ->
if (element instanceof Temporal) {
element.tick(currentTimeMillis)
// Update time with scene objects
scene.accept { element ->
if (element instanceof Temporal) {
element.tick(currentTimeMillis)
}
}
}

lastSystemTimeMillis = currentSystemTimeMillis
lastSystemTimeMillis = currentSystemTimeMillis
}
}
catch (InterruptedException ignored) {
break
Expand Down

0 comments on commit d308f19

Please sign in to comment.