Skip to content
This repository was archived by the owner on Sep 3, 2019. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
77 changes: 2 additions & 75 deletions src/Scratch.as
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,7 @@ import watchers.ListWatcher;

public class Scratch extends Sprite {
// Version
public static const versionString:String = 'v460.0.1';
public static const versionString:String = 'v461';
public static var app:Scratch; // static reference to the app, used for debugging

// Display modes
Expand Down Expand Up @@ -734,6 +734,7 @@ public class Scratch extends Sprite {

protected function step(e:Event):void {
// Step the runtime system and all UI components.
CachedTimer.clearCachedTimer();
gh.step();
runtime.stepRuntime();
Transition.step(null);
Expand Down Expand Up @@ -971,10 +972,6 @@ public class Scratch extends Sprite {
scriptsPart.setWidthHeight(contentW, contentH);

if (mediaLibrary) mediaLibrary.setWidthHeight(topBarPart.w, fullH);
if (frameRateGraph) {
frameRateGraph.y = stage.stageHeight - frameRateGraphH;
addChild(frameRateGraph); // put in front
}

SCRATCH::allow3d {
if (isIn3D) render3D.onStageResize();
Expand Down Expand Up @@ -1497,76 +1494,6 @@ public class Scratch extends Sprite {
lp.y = int(p.y + ((stagePane.height - lp.height) / 2));
}

// -----------------------------
// Frame rate readout (for use during development)
//------------------------------

private var frameRateReadout:TextField;
private var firstFrameTime:int;
private var frameCount:int;

protected function addFrameRateReadout(x:int, y:int, color:uint = 0):void {
frameRateReadout = new TextField();
frameRateReadout.autoSize = TextFieldAutoSize.LEFT;
frameRateReadout.selectable = false;
frameRateReadout.background = false;
frameRateReadout.defaultTextFormat = new TextFormat(CSS.font, 12, color);
frameRateReadout.x = x;
frameRateReadout.y = y;
addChild(frameRateReadout);
frameRateReadout.addEventListener(Event.ENTER_FRAME, updateFrameRate);
}

private function updateFrameRate(e:Event):void {
frameCount++;
if (!frameRateReadout) return;
var now:int = getTimer();
var msecs:int = now - firstFrameTime;
if (msecs > 500) {
var fps:Number = Math.round((1000 * frameCount) / msecs);
frameRateReadout.text = fps + ' fps (' + Math.round(msecs / frameCount) + ' msecs)';
firstFrameTime = now;
frameCount = 0;
}
}

// TODO: Remove / no longer used
private const frameRateGraphH:int = 150;
private var frameRateGraph:Shape;
private var nextFrameRateX:int;
private var lastFrameTime:int;

private function addFrameRateGraph():void {
addChild(frameRateGraph = new Shape());
frameRateGraph.y = stage.stageHeight - frameRateGraphH;
clearFrameRateGraph();
stage.addEventListener(Event.ENTER_FRAME, updateFrameRateGraph);
}

public function clearFrameRateGraph():void {
var g:Graphics = frameRateGraph.graphics;
g.clear();
g.beginFill(0xFFFFFF);
g.drawRect(0, 0, stage.stageWidth, frameRateGraphH);
nextFrameRateX = 0;
}

private function updateFrameRateGraph(evt:*):void {
var now:int = getTimer();
var msecs:int = now - lastFrameTime;
lastFrameTime = now;
var c:int = 0x505050;
if (msecs > 40) c = 0xE0E020;
if (msecs > 50) c = 0xA02020;

if (nextFrameRateX > stage.stageWidth) clearFrameRateGraph();
var g:Graphics = frameRateGraph.graphics;
g.beginFill(c);
var barH:int = Math.min(frameRateGraphH, msecs / 2);
g.drawRect(nextFrameRateX, frameRateGraphH - barH, 1, barH);
nextFrameRateX++;
}

// -----------------------------
// Camera Dialog
//------------------------------
Expand Down
4 changes: 2 additions & 2 deletions src/extensions/ExtensionManager.as
Original file line number Diff line number Diff line change
Expand Up @@ -403,7 +403,7 @@ public class ExtensionManager {

public function updateIndicator(indicator:IndicatorLight, ext:ScratchExtension, firstTime:Boolean = false):void {
if(ext.port > 0) {
var msecsSinceLastResponse:uint = getTimer() - ext.lastPollResponseTime;
var msecsSinceLastResponse:uint = CachedTimer.getCachedTimer() - ext.lastPollResponseTime;
if (msecsSinceLastResponse > 500) indicator.setColorAndMsg(0xE00000, 'Cannot find helper app');
else if (ext.problem != '') indicator.setColorAndMsg(0xE0E000, ext.problem);
else indicator.setColorAndMsg(0x00C000, ext.success);
Expand Down Expand Up @@ -724,7 +724,7 @@ public class ExtensionManager {

private function processPollResponse(ext:ScratchExtension, response:String):void {
if (response == null) return;
ext.lastPollResponseTime = getTimer();
ext.lastPollResponseTime = CachedTimer.getCachedTimer();
ext.problem = '';

// clear the busy list unless we just started a command that waits
Expand Down
48 changes: 41 additions & 7 deletions src/interpreter/Interpreter.as
Original file line number Diff line number Diff line change
Expand Up @@ -62,18 +62,19 @@ import extensions.ExtensionManager;

import flash.geom.Point;
import flash.utils.Dictionary;
import flash.utils.getTimer;

import primitives.*;

import scratch.*;

import sound.*;

import util.CachedTimer;

public class Interpreter {

public var activeThread:Thread; // current thread
public var currentMSecs:int = getTimer(); // millisecond clock for the current step
public var activeThread:Thread; // current thread
public var currentMSecs:int; // millisecond clock for the current step
public var turboMode:Boolean = false;

private var app:Scratch;
Expand Down Expand Up @@ -219,12 +220,34 @@ public class Interpreter {
doRedraw = true;
}

private const workTimeCheckIntervalFactor:Number = 1/3.0;
private const maxIterationCountSamples: uint = 10;
private var iterationCountSamples: Vector.<uint> = new <uint>[500]; // initial guess

private function addIterationCountSample(sample:uint):void {
iterationCountSamples.push(sample);
while (iterationCountSamples.length > maxIterationCountSamples) {
iterationCountSamples.shift();
}
}

private function getAverageIterationCount():Number {
var total:uint = 0;
for each (var sample:uint in iterationCountSamples) {
total += sample;
}
return Number(total) / iterationCountSamples.length;
}

public function stepThreads():void {
startTime = getTimer();
var workTime:int = (0.75 * 1000) / app.stage.frameRate; // work for up to 75% of one frame time
doRedraw = false;
currentMSecs = getTimer();
startTime = currentMSecs = CachedTimer.getFreshTimer();
if (threads.length == 0) return;
var currentEstimate:Number = getAverageIterationCount();
var iterationCount:uint = 0;
var checkInterval:uint = Math.round(workTimeCheckIntervalFactor * currentEstimate);
var checkCount:uint = 0;
while ((currentMSecs - startTime) < workTime) {
if (warpThread && (warpThread.block == null)) clearWarpBlock();
var threadStopped:Boolean = false;
Expand All @@ -247,9 +270,18 @@ public class Interpreter {
threads = newThreads;
if (threads.length == 0) return;
}
currentMSecs = getTimer();
if (doRedraw || (runnableCount == 0)) return;
++iterationCount;
++checkCount;
if (checkCount >= checkInterval) {
currentMSecs = CachedTimer.getFreshTimer();
checkCount = 0;
}
}
// if we get here, this was a frame where we needed to check the timer twice or more
// use the elapsed time and actual iteration count to generate an estimate for iterations per step
var newEstimate:uint = Math.round(workTime * iterationCount / Number(currentMSecs - startTime));
addIterationCountSample(newEstimate);
}

private function stepActiveThread():void {
Expand All @@ -264,13 +296,15 @@ public class Interpreter {
}
}
yield = false;
var warpStartTimer:int = CachedTimer.getCachedTimer();
while (true) {
if (activeThread == warpThread) currentMSecs = getTimer();
if (activeThread == warpThread) currentMSecs = warpStartTimer;
evalCmd(activeThread.block);
if (yield) {
if (activeThread == warpThread) {
if ((currentMSecs - startTime) > warpMSecs) return;
yield = false;
warpStartTimer = CachedTimer.getFreshTimer();
continue;
} else return;
}
Expand Down
6 changes: 4 additions & 2 deletions src/logging/LogEntry.as
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@
package logging {
import flash.utils.getTimer;

import util.CachedTimer;

public class LogEntry {
public var timeStamp:Number;
public var severity:int;
Expand Down Expand Up @@ -49,11 +51,11 @@ public class LogEntry {
return [makeTimeStampString(), LogLevel.LEVEL[severity], messageKey].join(' | ');
}

private static const timerOffset:Number = new Date().time - getTimer();
private static const timerOffset:Number = new Date().time - CachedTimer.getFreshTimer();

// Returns approximately the same value as "new Date().time" without GC impact
public static function getCurrentTime():Number {
return getTimer() + timerOffset;
return CachedTimer.getCachedTimer() + timerOffset;
}
}
}
5 changes: 0 additions & 5 deletions src/render3d/DisplayObjectContainerIn3D.as
Original file line number Diff line number Diff line change
Expand Up @@ -1052,12 +1052,8 @@ SCRATCH::allow3d{
currentTexture = null;
}

private var drawCount:uint = 0;
//private var lastTime:int = 0;
public function onRender(e:Event):void {
if (!scratchStage) return;
//trace('frame was '+(getTimer() - lastTime)+'ms.');
//lastTime = getTimer();

if (scratchStage.stage.stage3Ds[0] == null || __context == null || __context.driverInfo == "Disposed") {
if (__context) __context.dispose();
Expand All @@ -1068,7 +1064,6 @@ SCRATCH::allow3d{

draw();
__context.present();
++drawCount;

// Invalidate cached renders
for (var o:Object in cachedOtherRenderBitmaps)
Expand Down
2 changes: 1 addition & 1 deletion src/scratch/ScratchObj.as
Original file line number Diff line number Diff line change
Expand Up @@ -544,7 +544,7 @@ public class ScratchObj extends Sprite {
public function click(evt:MouseEvent):void {
var app:Scratch = root as Scratch;
if (!app) return;
var now:uint = getTimer();
var now:uint = CachedTimer.getCachedTimer();
app.runtime.startClickedHats(this);
if ((now - lastClickTime) < DOUBLE_CLICK_MSECS) {
if (isStage || ScratchSprite(this).isClone) return;
Expand Down
10 changes: 5 additions & 5 deletions src/scratch/ScratchRuntime.as
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,7 @@ public class ScratchRuntime {
return;
}
if (ready==ReadyLabel.COUNTDOWN) {
var tR:Number = getTimer()*.001-videoSeconds;
var tR:Number = CachedTimer.getCachedTimer()*.001-videoSeconds;
while (t>videoSounds.length/videoFramerate+1/videoFramerate) {
saveSound();
}
Expand All @@ -135,7 +135,7 @@ public class ScratchRuntime {
}
}
if (recording) { // Recording a YouTube video?
var t:Number = getTimer()*.001-videoSeconds;
var t:Number = CachedTimer.getCachedTimer()*.001-videoSeconds;
//If, based on time and framerate, the current frame needs to be in the video, capture the frame.
//Will always be true if framerate is 30, as every frame is captured.
if (t>videoSounds.length/videoFramerate+1/videoFramerate) {
Expand Down Expand Up @@ -213,7 +213,7 @@ public class ScratchRuntime {

private function saveFrame():void {
saveSound();
var t:Number = getTimer()*.001-videoSeconds;
var t:Number = CachedTimer.getCachedTimer()*.001-videoSeconds;
while (t>videoSounds.length/videoFramerate+1/videoFramerate) {
saveSound();
}
Expand Down Expand Up @@ -380,7 +380,7 @@ public class ScratchRuntime {
videoHeight = 360;
}
ready=ReadyLabel.COUNTDOWN;
videoSeconds = getTimer()*.001;
videoSeconds = CachedTimer.getCachedTimer()*.001;
baFlvEncoder = new ByteArrayFlvEncoder(videoFramerate);
baFlvEncoder.setVideoProperties(videoWidth, videoHeight);
baFlvEncoder.setAudioProperties(FlvEncoder.SAMPLERATE_44KHZ, true, true, true);
Expand Down Expand Up @@ -433,7 +433,7 @@ public class ScratchRuntime {
ready=ReadyLabel.NOT_READY;
app.refreshStagePart();
var player:ScratchSoundPlayer, length:int;
videoSeconds = getTimer() * 0.001;
videoSeconds = CachedTimer.getCachedTimer() * 0.001;
for each (player in ScratchSoundPlayer.activeSounds) {
length = int((player.soundChannel.position*.001)*videoFramerate);
player.readPosition = Math.max(Math.min(baFlvEncoder.audioFrameSize*length,player.dataBytes.length),0);
Expand Down
6 changes: 4 additions & 2 deletions src/sound/ScratchSoundPlayer.as
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,8 @@ import flash.utils.ByteArray;

import scratch.ScratchSound;

import util.CachedTimer;

public class ScratchSoundPlayer {

static public var activeSounds:Array = [];
Expand Down Expand Up @@ -160,7 +162,7 @@ public class ScratchSoundPlayer {

private function writeSampleData(evt:SampleDataEvent):void {
var i:int;
if ((lastBufferTime != 0) && ((getTimer() - lastBufferTime) > 230)) {
if ((lastBufferTime != 0) && ((CachedTimer.getCachedTimer() - lastBufferTime) > 230)) {
soundChannel = null; // don't explicitly stop the sound channel in this callback; allow it to stop on its own
stopPlaying();
return;
Expand All @@ -174,7 +176,7 @@ public class ScratchSoundPlayer {
}
dataBytes.writeBytes(data);
if ((bytePosition >= endOffset) && (lastBufferTime == 0)) {
lastBufferTime = getTimer();
lastBufferTime = CachedTimer.getCachedTimer();
}
}

Expand Down
6 changes: 4 additions & 2 deletions src/ui/parts/LibraryPart.as
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,8 @@ import ui.media.*;
import ui.SpriteThumbnail;
import uiwidgets.*;

import util.CachedTimer;

public class LibraryPart extends UIPart {

private const smallTextFormat:TextFormat = new TextFormat(CSS.font, 10, CSS.textColor);
Expand Down Expand Up @@ -251,12 +253,12 @@ public class LibraryPart extends UIPart {
public function step():void {
// Update thumbnails and sprite details.
var viewedObj:ScratchObj = app.viewedObj();
var updateThumbnails:Boolean = ((getTimer() - lastUpdate) > updateInterval);
var updateThumbnails:Boolean = ((CachedTimer.getCachedTimer() - lastUpdate) > updateInterval);
for each (var tn:SpriteThumbnail in allThumbnails()) {
if (updateThumbnails) tn.updateThumbnail();
tn.select(tn.targetObj == viewedObj);
}
if (updateThumbnails) lastUpdate = getTimer();
if (updateThumbnails) lastUpdate = CachedTimer.getCachedTimer();
if (spriteDetails.visible) spriteDetails.step();
if (videoButton && videoButton.visible) updateVideoButton();
}
Expand Down
6 changes: 4 additions & 2 deletions src/ui/parts/ScriptsPart.as
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,8 @@ import ui.*;

import uiwidgets.*;

import util.CachedTimer;

public class ScriptsPart extends UIPart {

private var shape:Shape;
Expand Down Expand Up @@ -130,12 +132,12 @@ public class ScriptsPart extends UIPart {
private var lastUpdateTime:uint;

private function updateExtensionIndicators():void {
if ((getTimer() - lastUpdateTime) < 500) return;
if ((CachedTimer.getCachedTimer() - lastUpdateTime) < 500) return;
for (var i:int = 0; i < app.palette.numChildren; i++) {
var indicator:IndicatorLight = app.palette.getChildAt(i) as IndicatorLight;
if (indicator) app.extensionManager.updateIndicator(indicator, indicator.target);
}
lastUpdateTime = getTimer();
lastUpdateTime = CachedTimer.getCachedTimer();
}

public function setWidthHeight(w:int, h:int):void {
Expand Down
Loading