Skip to content
This repository was archived by the owner on Jun 19, 2018. It is now read-only.

Commit 6360de0

Browse files
author
Amos Blanton
committed
Initial commit.
1 parent dd7f6e2 commit 6360de0

File tree

103 files changed

+4819
-339
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

103 files changed

+4819
-339
lines changed

COPYING

+677
Large diffs are not rendered by default.

LICENSE

-339
This file was deleted.

README

+7
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
Scratch HTML5 Player
2+
3+
This project aims to create a Scratch Player in HTML5. Scratch is currently implemented with Actionscript 3 and requires the Flash Player version 10.2. Since Flash does not run on iOS (iPads, iPods, etc) and newer Android devices, we would like to have an HTML5 version to display (but not edit) projects on mobile devices. Scratch projects played in the HTML5 player should look and behave as closely as possible to the way they look and behave when played by the Flash player. We will not be accepting pull requests for new features that don't already exist in the Flash based Scratch project player.
4+
5+
There are a few github issues created that represent some of the missing features. At this point, the HTML5 player is about 40% complete and can run some simple projects. Running the HTML5 player on your own website, or locally, you will need to have PHP so that the proxy.php file can be used to load assets from the same domain. This is done to be compatible with Javascript security models in today's browsers. To test the HTML5 player against the Flash player you can use the compare.html web page.
6+
7+
More documentation will be added as time permits. Thanks for contributing, and Scratch On!

TRADEMARK_POLICY

+22
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
The Scratch trademarks, including the Scratch name, logo, the Scratch
2+
Cat and Gobo graphics (the "Marks"), are property of MIT, and the
3+
use of the Marks is governed by this policy.
4+
5+
# Use
6+
7+
You may use the Marks to refer to Scratch in Substantially Unmodified
8+
form.
9+
10+
"Substantially Unmodified" means the source code provided by MIT,
11+
possibly with minor modifications including but not limited to: bug
12+
fixes (including security), changing the locations of files for better
13+
integration with the host operating system, adding documentation, and
14+
changes to the dynamic linking of libraries.
15+
16+
A version is not "Substantially Unmodified" if it incorporates
17+
features not present in a release of Scratch by MIT. If you do make a
18+
substantial modification, to avoid confusion with versions of Scratch
19+
produced by MIT you must remove all Marks from your version of the
20+
software and refrain from using any of the Marks to refer to your
21+
version.
22+

compare.html

+115
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,115 @@
1+
<?
2+
header("Cache-Control: no-cache, must-revalidate"); // HTTP/1.1
3+
header("Expires: Sat, 26 Jul 1997 05:00:00 GMT"); // Date in the past
4+
?>
5+
<!DOCTYPE html>
6+
<html>
7+
<head>
8+
<title>Scratch HTML5 vs. Flash</title>
9+
<meta charset="utf-8">
10+
<style type="text/css">
11+
body {
12+
background: #222;
13+
color: #fff;
14+
margin: 0;
15+
}
16+
</style>
17+
<link href="player.css" type="text/css" rel="stylesheet" />
18+
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
19+
<script src="//ajax.googleapis.com/ajax/libs/swfobject/2.2/swfobject.js"></script>
20+
<script src="js/util/Timer.js"></script>
21+
<script src="js/util/OffsetBuffer.js"></script>
22+
<script src="js/util/Color.js"></script>
23+
<script src="js/util/Rectangle.js"></script>
24+
<script src="js/Sprite.js"></script>
25+
<script src="js/Reporter.js"></script>
26+
<script src="js/Stage.js"></script>
27+
<script src="js/sound/WAVFile.js"></script>
28+
<script src="js/sound/SoundDecoder.js"></script>
29+
<script src="js/sound/SoundBank.js"></script>
30+
<script src="js/sound/NotePlayer.js"></script>
31+
<script src="soundbank/Instr.js"></script>
32+
<script src="js/IO.js"></script>
33+
<script src="js/primitives/VarListPrims.js"></script>
34+
<script src="js/primitives/MotionAndPenPrims.js"></script>
35+
<script src="js/primitives/LooksPrims.js"></script>
36+
<script src="js/primitives/SensingPrims.js"></script>
37+
<script src="js/primitives/SoundPrims.js"></script>
38+
<script src="js/primitives/Primitives.js"></script>
39+
<script src="js/Interpreter.js"></script>
40+
<script src="js/Runtime.js"></script>
41+
<script src="js/Scratch.js"></script>
42+
<script type="text/javascript">
43+
if (window.location.hash) {
44+
var project_id = parseInt(window.location.hash.substr(1));
45+
} else {
46+
var project_id = 10000160; // Default project for display
47+
}
48+
</script>
49+
<script>
50+
$(function() {
51+
// The flashvars tell flash about the project data (and autostart=true)
52+
var flashvars = {
53+
server: encodeURIComponent('scratch.mit.edu'),
54+
project_id: project_id
55+
};
56+
57+
// Pass in the cloud token for the project
58+
if(window.getCloudToken)
59+
flashvars.cloud_token = encodeURIComponent(getCloudToken());
60+
61+
var params = {
62+
allowscriptaccess: 'always',
63+
allowfullscreen: 'false',
64+
wmode: 'direct',
65+
menu: 'false'};
66+
67+
var flashPlayer = null;
68+
//var swf_url = "http://cdn.scratch.mit.edu/scratchr2/static/Scratch.swf";
69+
var swf_url = "http://jiggler.media.mit.edu/shanemc/scratchr2/static/Scratch.swf";
70+
swfobject.embedSWF(swf_url, "flashScratch", "480", "400", "10.2.0",
71+
"http://cdn.scratch.mit.edu/scratchr2/static/expressInstall.swf",
72+
flashvars, params, null, function(e) {
73+
$('#flashScratch').css('visibility', 'visible');
74+
if(e.success) flashPlayer = e.ref;
75+
});
76+
77+
$('#trigger_green_flag, #greenSlide').click(function() {
78+
flashPlayer.ASstartRunning();
79+
});
80+
81+
// Stop button behavior
82+
$('#trigger_stop').click(function() {
83+
flashPlayer.ASstopRunning();
84+
});
85+
});
86+
</script>
87+
</head>
88+
<body>
89+
<div style="display: inline-block;">
90+
<div id="up">&nbsp;</div>
91+
<div id="left">&nbsp;</div>
92+
<div id="overContainer">
93+
<div id="greenSlide"><div id="greenSlideFg"><img src="img/greenflag.png"></div></div>
94+
<div id="container"></div>
95+
</div>
96+
<div id="right">&nbsp;</div>
97+
<div id="down">&nbsp;</div>
98+
</div>
99+
<div style="display: inline-block;">
100+
<div id="flashScratch" style="text-align:center;visibility:hidden;">
101+
<p style="color:#aaa;font-size:22px;margin-top:14px;line-height:28px;">Oh Noes! Scratch project cannot display.<br/>Flash player is disabled, missing, or less than version 10.2.</p>
102+
<a href="http://www.adobe.com/go/getflashplayer">
103+
<img src="http://www.adobe.com/images/shared/download_buttons/get_flash_player.gif" alt="Get Adobe Flash player" target="_blank" />
104+
</a>
105+
</div>
106+
</div>
107+
108+
<div id="info">Loading...</div>
109+
110+
<button id="trigger_green_flag">Green flag</button>
111+
<button id="trigger_stop">Stop</button>
112+
113+
<input type="text" name="project_id" id="project_id" /><button id='go_project'>Go!</button>
114+
</body>
115+
</html>

copyright.txt

+15
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
// Copyright (C) 2013 Massachusetts Institute of Technology
2+
//
3+
// This program is free software; you can redistribute it and/or
4+
// modify it under the terms of the GNU General Public License version 2,
5+
// as published by the Free Software Foundation.
6+
//
7+
// This program is distributed in the hope that it will be useful,
8+
// but WITHOUT ANY WARRANTY; without even the implied warranty of
9+
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10+
// GNU General Public License for more details.
11+
//
12+
// You should have received a copy of the GNU General Public License
13+
// along with this program; if not, write to the Free Software
14+
// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15+

img/greenflag.png

7.89 KB
Loading

img/say-bottom.png

4.21 KB
Loading

img/think-bottom.png

4.25 KB
Loading

index.html

+66
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
<!DOCTYPE html>
2+
<html>
3+
<head>
4+
<title>Scratch HTML5</title>
5+
<meta charset="utf-8">
6+
<!-- iPad properties: set width, disable pinch zoom -->
7+
<meta name="apple-mobile-web-app-capable" content="yes">
8+
<meta name="viewport" content="user-scalable=no, width=540" />
9+
<meta name="apple-mobile-web-app-status-bar-style" content="black">
10+
<style type="text/css">
11+
body {
12+
background: #222;
13+
color: #fff;
14+
margin: 0;
15+
}
16+
</style>
17+
<link href="player.css" type="text/css" rel="stylesheet" />
18+
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
19+
<script src="js/util/Timer.js"></script>
20+
<script src="js/util/OffsetBuffer.js"></script>
21+
<script src="js/util/Color.js"></script>
22+
<script src="js/util/Rectangle.js"></script>
23+
<script src="js/Sprite.js"></script>
24+
<script src="js/Reporter.js"></script>
25+
<script src="js/Stage.js"></script>
26+
<script src="js/sound/WAVFile.js"></script>
27+
<script src="js/sound/SoundDecoder.js"></script>
28+
<script src="js/sound/SoundBank.js"></script>
29+
<script src="js/sound/NotePlayer.js"></script>
30+
<script src="soundbank/Instr.js"></script>
31+
<script src="js/IO.js"></script>
32+
<script src="js/primitives/VarListPrims.js"></script>
33+
<script src="js/primitives/MotionAndPenPrims.js"></script>
34+
<script src="js/primitives/LooksPrims.js"></script>
35+
<script src="js/primitives/SensingPrims.js"></script>
36+
<script src="js/primitives/SoundPrims.js"></script>
37+
<script src="js/primitives/Primitives.js"></script>
38+
<script src="js/Interpreter.js"></script>
39+
<script src="js/Runtime.js"></script>
40+
<script src="js/Scratch.js"></script>
41+
<script type="text/javascript">
42+
if (window.location.hash) {
43+
var project_id = parseInt(window.location.hash.substr(1));
44+
} else {
45+
var project_id = 10000160; // Default project for display
46+
}
47+
</script>
48+
</head>
49+
<body>
50+
<div id="up">&nbsp;</div>
51+
<div id="left">&nbsp;</div>
52+
<div id="overContainer">
53+
<div id="greenSlide"><div id="greenSlideFg"><img src="img/greenflag.png"></div></div>
54+
<div id="container"></div>
55+
</div>
56+
<div id="right">&nbsp;</div>
57+
<div id="down">&nbsp;</div>
58+
59+
<div id="info">Loading...</div>
60+
61+
<button id="trigger_green_flag">Green flag</button>
62+
<button id="trigger_stop">Stop</button>
63+
64+
<input type="text" name="project_id" id="project_id" /><button id='go_project'>Go!</button>
65+
</body>
66+
</html>

js/IO.js

+136
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,136 @@
1+
// Copyright (C) 2013 Massachusetts Institute of Technology
2+
//
3+
// This program is free software; you can redistribute it and/or
4+
// modify it under the terms of the GNU General Public License version 2,
5+
// as published by the Free Software Foundation.
6+
//
7+
// This program is distributed in the hope that it will be useful,
8+
// but WITHOUT ANY WARRANTY; without even the implied warranty of
9+
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10+
// GNU General Public License for more details.
11+
//
12+
// You should have received a copy of the GNU General Public License
13+
// along with this program; if not, write to the Free Software
14+
// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15+
16+
// Scratch HTML5 Player
17+
// IO.js
18+
// Tim Mickel, March 2012
19+
20+
// IO handles JSON communication and processing.
21+
// We make the sprites and threads here.
22+
23+
'use strict';
24+
25+
var IO = function() {
26+
this.data = null;
27+
// In production, simply use the local path (no proxy)
28+
// since we won't be hampered by the same-origin policy.
29+
this.base = 'proxy.php?resource=internalapi/';
30+
this.project_base = this.base + 'project/';
31+
this.project_suffix = '/get/';
32+
this.asset_base = this.base + 'asset/';
33+
this.asset_suffix = '/get/';
34+
this.soundbank_base = 'soundbank/';
35+
this.spriteLayerCount = 0;
36+
}
37+
38+
IO.prototype.loadProject = function(project_id) {
39+
var runningIO = this;
40+
$.getJSON(this.project_base + project_id + this.project_suffix,
41+
function(data) {
42+
runningIO.data = data;
43+
runningIO.makeObjects();
44+
runningIO.loadThreads();
45+
runningIO.loadNotesDrums();
46+
runtime.loadStart(); // Try to run the project.
47+
}
48+
);
49+
}
50+
51+
IO.prototype.soundRequest = function(sound, sprite) {
52+
var request = new XMLHttpRequest();
53+
request.open('GET', this.asset_base + sound['md5'] + this.asset_suffix, true);
54+
request.responseType = 'arraybuffer';
55+
request.onload = function() {
56+
var waveData = request.response;
57+
// Decode the waveData and populate a buffer channel with the samples
58+
var snd = new SoundDecoder(waveData);
59+
var samples = snd.getAllSamples();
60+
sound.buffer = runtime.audioContext.createBuffer(1, samples.length, runtime.audioContext.sampleRate);
61+
var data = sound.buffer.getChannelData(0);
62+
for (var i = 0; i < data.length; i++) {
63+
data[i] = samples[i];
64+
}
65+
sprite.soundsLoaded++;
66+
}
67+
request.send();
68+
}
69+
70+
IO.prototype.loadNotesDrums = function() {
71+
var self = this;
72+
$.each(Instr.wavs, function(name, file) {
73+
var request = new XMLHttpRequest();
74+
request.open('GET', self.soundbank_base + escape(file), true);
75+
request.responseType = 'arraybuffer';
76+
request.onload = function() {
77+
var waveData = new OffsetBuffer(request.response);
78+
// Decode the waveData and populate a buffer channel with the samples
79+
var info = WAVFile.decode(request.response);
80+
waveData.offset = info.sampleDataStart;
81+
var soundBuffer = waveData.readBytes(2 * info.sampleCount);
82+
Instr.samples[name] = soundBuffer;
83+
Instr.wavsLoaded++;
84+
}
85+
request.send();
86+
});
87+
}
88+
89+
IO.prototype.makeObjects = function() {
90+
// Create the stage
91+
runtime.stage = new Stage(this.data);
92+
runtime.stage.attach(runtime.scene);
93+
runtime.stage.attachPenLayer(runtime.scene);
94+
runtime.stage.loadSounds();
95+
96+
// Create the sprites
97+
$.each(this.data.children, function(index, obj) {
98+
var newSprite;
99+
if(!obj.cmd) {
100+
newSprite = new Sprite(obj);
101+
} else {
102+
newSprite = new Reporter(obj);
103+
runtime.reporters.push(newSprite);
104+
}
105+
runtime.sprites.push(newSprite);
106+
newSprite.attach(runtime.scene);
107+
if (!obj.cmd)
108+
newSprite.loadSounds();
109+
});
110+
}
111+
112+
IO.prototype.loadThreads = function() {
113+
var target = runtime.stage;
114+
var scripts = target.data.scripts;
115+
if (scripts) {
116+
for (var s in scripts) {
117+
target.stacks.push(interp.makeBlockList(scripts[s][2]));
118+
}
119+
}
120+
$.each(this.data.children, function(index, obj) {
121+
target = runtime.sprites[index];
122+
if (typeof(target) != 'undefined' && target.data && target.data.scripts) {
123+
$.each(target.data.scripts, function(j, s) {
124+
target.stacks.push(interp.makeBlockList(s[2]));
125+
});
126+
}
127+
});
128+
}
129+
130+
// Returns the number sprite we are rendering
131+
// used for initial layering assignment
132+
IO.prototype.getCount = function() {
133+
var rv = this.spriteLayerCount;
134+
this.spriteLayerCount++;
135+
return rv;
136+
}

0 commit comments

Comments
 (0)