Skip to content
Closed
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
4 changes: 3 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
@@ -1 +1,3 @@
.DS_Store
.DS_Store
.vitepress/cache/
node_modules/
27 changes: 27 additions & 0 deletions .vitepress/config.mts
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import { defineConfig } from "vitepress";

// https://vitepress.dev/reference/site-config
export default defineConfig({
title: "Scratch Specification",
themeConfig: {
// https://vitepress.dev/reference/default-theme-config
sidebar: [
{
items: [
{ text: "Contents", link: "/" },
{ text: "Introduction", link: "/intro" },
{ text: "FAQ", link: "faq" },
{ text: "TODO", link: "/todo" },
],
},
{
text: "Concepts",
items: [
{ text: "Capabilities", link: "/concepts/capabilities" },
{ text: "Constants", link: "/concepts/constants" },
{ text: "Ideas", link: "/concepts/ideas" },
],
},
],
},
});
345 changes: 345 additions & 0 deletions bun.lock

Large diffs are not rendered by default.

19 changes: 19 additions & 0 deletions concepts/capabilities.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
# Capabilities

At its core, Scratch should be able to:

* Run scripts dynamically; multithreading, looping, timing, etc.
* Show images on a screen; position, size, turn + draw graphics.
* Play sounds on speakers; several audio files can play at once.

In an ideal situation, it should also be able to:

* Apply effects to images and sounds
* Detect loudness via microphone
* Interact with linked devices
* Draw graphics dynamically
* Make requests to the web
* Know the current time
* Receive user input

A fully functional implementation of Scratch should be capable of all these things, and if not handle it gracefully, this document detailing how to deal with everything.
69 changes: 69 additions & 0 deletions concepts/constants.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
# Constants

These constant values will show up a lot throughout this specification. They can be changed to one's liking, however for true accuracy to Scratch, they should all have their "**Standard Scratch**:" values.

## Stage Bounds

### Stage Width

The horizontal size of the stage. This is an arbitrary positive [integer](#integer).

**Standard Scratch**: `480`

**Widescreen** (via unofficial modification): `640`

### Stage Height

The vertical size of the stage. This is an arbitrary positive [integer](#integer).

**Standard Scratch**: `360`

### Left Edge

The horizontal position of the left edge. This is derived from the [stage width](#stage-width).

**Formula**: `stage width / -2`

**Standard Scratch**: `-240`

### Right Edge

The horizontal position of the right edge. This is derived from the [stage width](#stage-width).

**Formula**: `stage width / 2`

**Standard Scratch**: `240`

### Top Edge

The vertical position of the top edge. This is derived from the [stage height](#stage-height).

**Formula**: `stage height / 2`

**Standard Scratch**: `180`

### Bottom Edge

The vertical position of the bottom edge. This is derived from the [stage height](#stage-height).

**Formula**: `stage height / -2`

**Standard Scratch**: `-180`

## Limits

### Max Items

The maximum [length](#length) of a [list](#list), aka the most items that one list can hold. This limit is imposed to prevent excessive memory usage by [projects](#project). This is an arbitrary positive [integer](#integer).

**Standard Scratch**: `200000`

**Modified Scratch**: None (many Scratch mods do not enforce this limit, though memory overflow may eventually occur)

### Max Clones

The maximum number of [clones](#clone) that can exist at one time. If this limit is reached, another clone cannot be created until one is deleted. This limit is imposed to prevent excessive memory usage by [projects](#project). This is an arbitrary positive [integer](#integer).

**Standard Scratch**: `300`

**Modified Scratch**: None (many Scratch mods do not enforce this limit, though memory overflow may eventually occur)
116 changes: 116 additions & 0 deletions concepts/ideas.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,116 @@
# Ideas

The following ideas are referenced throughout this specification:

## Asset

A [costume](#costume) or [sound](#sound).

### Costume

A costume is an [image file](https://en.wikipedia.org/wiki/Digital_image) and a type of [asset](#asset) that can be graphically rendered to represent a [target](#target). It can be identified by its [name](#name) or [number](#integer). Costumes can either be [bitmap](https://en.wikipedia.org/wiki/Raster_graphics) or [vector](https://en.wikipedia.org/wiki/Vector_graphics).

### Sound

A sound is an [audio file](https://en.wikipedia.org/wiki/Digital_audio) and a type of [asset](#asset) that can be audibly played to the user via [blocks](#block). It can be identified by its [name](#name).

## Block

The fundamental component of Scratch as a programming language. In fact, they are similar to function calls in other programming languages. Every block:

* Accepts values or blocks as arguments
* Has a specific pre-defined operation that it performs
* Can be run and reports (i.e. outputs, returns) a single value (or [none at all](#undefined))

Blocks can be run, meaning that its operation is performed using the arguments it is given and the value resulting from the operation is reported, if any. When put together, blocks create [scripts](#script).

### Standard Blocks

[Blocks](#block) that are officially supported in Scratch 3.0. They are the most commonly used blocks in [scripts](#script) by far.

### Hidden Blocks

[Blocks](#block) that exist in Scratch 3.0 but are not actively supported or used on their own, either being kept for compatibility with projects created in older versions of Scratch or being used internally. Some are functional, some are not. [Scripts](#script) may use them on occasion, but they are found less often than [standard blocks](#standard-blocks) due to their obscurity.

## Clone

A copy created of a [sprite](#sprite) that has all of the original sprite's code, images, and sounds, but operates independently of it. Unlike sprites, clones cannot be directly referenced via existing blocks (e.g. you cannot [glide to](#glide-to-block) it directly without knowing its position ahead of time, as it cannot be selected in the sprite dropdown menu), and exist as their own thing. They are deleted every time the [flag](#flag) is clicked, and can also be deleted manually using the [`delete this clone` block](#delete-clone-block).

Clones can be created with the [create clone block](#create-clone-block) so long as the [maximum number of clones](#max-clones) has not been reached. Code can be written specifically for the clones of a sprite via the use of the [when I start as a clone block](#when-i-start-as-a-clone-block). The [stage](#stage) is the [target](#target) which cannot be cloned, whereas both sprites *and clones* can themselves be cloned.

## Edge

Refers to the bounds that restrict the graphics of a [project](#project) from exceeding its designated region on the user's screen.

## Flag

> The usefulness of defining "Flag" is up for debate. Feel free to offer insight!

The button that is intended to run scripts that start a project. It is also known as the green flag in official Scratch. It is meant to make the project `Go`, as it is labelled in its title text on the Scratch website. When clicked, it runs any scripts under [when flag clicked blocks](#when-flag-clicked-block).

## JavaScript

> Definitions for general terms indirectly related to Scratch may be put into their own section instead, however this is up for debate. Feel free to offer insight!

The programming language that Scratch 3.0 runs in. The logic it uses is largely similar to the logic Scratch uses due to Scratch's dependence on JavaScript for performing operations and manipulating values. In fact, this is where the type of value [undefined](#undefined) is taken from; it is a type of value in JavaScript for representing what is not defined or known. Thanks to the quirks of Scratch and [no-op hidden reporter blocks](#hidden-blocks), we can obtain this type of value.

## List

A series of [items](#item) stored together in sequence. Each item is referenced by its numerical index (aka item #), a positive [integer](#integer) ranging from `1` to the [length](#length) of the list (inclusive). Lists can be empty, meaning that they have a length of `0` and contain no items. There is also a [maximum number of items](#max-items) that a list can hold, aka a limit to its length.

## Mod

A modification (altered version) of the Scratch 3.0 [runtime](#runtime) that is nonstandard and may introduce new blocks, features, or changes not present in standard Scratch. The majority of this spec will be documenting standard Scratch behavior. For information on nonstandard blocks and behaviors in mods, see the [relevant appendix](#nonstandard-blocks).

## Opcode

A [name](#name) unique to every [block](#block) in the Scratch programming language. It tells blocks what to do. For example, if the opcode of a block is [`motion_movesteps`](#motion_movesteps), it attempts to move steps.

## Project

A stage and optionally some sprites packaged together to do something. They can be loaded into a [runtime](#runtime) and executed. They can also be saved as [project files](#file-format).

## Runtime

The environment in which a [project](#project) is run. It keeps track of the project's current state and executes its code. [Projects files can be loaded into and saved from runtimes](#file-format).

## Script

A set of [blocks](#block) put together to create code. Here is an example of a script:

```sb
when flag clicked
ask [What's your name?] and wait
say (join [Hello, ] (join (answer) [!]))
stop [this script v]
```

Blocks are put together in the following ways:

* TODO :D

## Sprite

A kind of [target](#target) that can exist on its own, have [variables](#variable) only it can set, and be moved, pointed, scaled, and hidden, all of which are things that the [stage](#stage) cannot do.

## Stage

A special [target](#target), with one and only one existing in every project, that is shown behind all [sprites](#sprite). It is sort of like the [global scope](https://en.wikipedia.org/wiki/Scope_(computer_science)#Global_scope) found in some programming languages, but it also exists as its own entity.

Unlike [sprites](#sprite), it cannot be moved, pointed, scaled, hidden, or have variables that only it can set. However, it can do everything else a sprite can.

## Target

An object that runs blocks, shows images, and plays sounds. It has its own [variables](#variable) (aka properties or fields) that are used by contained [scripts](#script) to perform operations.

Every target exists as its own unit independent of other targets, but they can be interconnected in some ways. There are two kinds of targets * [sprites](#sprite) and [stages](#stage).

## User

The individual who is interacting with the [project](#project) and provides input. They may optionally have a [username](#username) that the project can use to identify them.

## Variable

A container with a [name](#name) that can hold any one [value](#value). Every variable is attached to a [target](#target). If it is attached to a [sprite](#sprite), it can only be set by that sprite. If it is attached to the [stage](#stage), it can be set by any sprite, including the stage.

There are two kinds of variables. Some variables are defined and named by the creator of a [project](#project) on a target-by-target basis and interacted with by [variables blocks](#variables-blocks), while all targets have variables that exist by default and can only be interacted with via their dedicated blocks (not variable blocks). Some examples of user-defined variables would be `(score)` or `(index)` (completely custom), while examples of built-in variables would be `(x position)`, `(direction)`, `(size)`, `(volume)`, and `(tempo)` (exist in every target).
42 changes: 42 additions & 0 deletions faq.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
# FAQ

*Questions that would be frequently asked if someone were to ask them.*

## Where to start?

* If you want a **general understanding** of Scratch's inner workings for whatever reason, find whatever interests you in the [table of contents](#contents) and just gloss over whatever you don't need to know.
* If you want **formal definitions** of Scratch terms, see [concepts](#concepts).
* If you want to accurately **recreate blocks**, see the [palette](#palette).

TODO: Threading and execution behavior will be documented soon!

* If you want to learn about project files, see [file format](#file-format).
* If you want to recreate old blocks, see [obsolete blocks](#obsolete-blocks).
* If you want more blocks, see [nonstandard blocks](#nonstandard-blocks).

## What's the point?

This specification exists to document the behavior of Scratch 3.0 as a programming language. It can open the door to:

* **Accurately porting Scratch to run natively on other platforms**
* It could help efforts to make Scratch available on platforms that aren't web-based (if any).
* @OceanIsEndless, the initial creator of this specification, has a lot of wild ideas on their mind regarding Scratch. Their ideas are likely not at all worth their time, but writing this spec will allow them to try doing interesting things such as creating a Scratch to [Desmos](https://www.desmos.com/calculator) packager, or porting Scratch to the [Wii](https://en.wikipedia.org/wiki/Wii). A bit ambitious, yes, and absolutely crazy—but a specification like this could aid projects like these and more. It can help ensure compatibility and easy coding.
* It could help this super cool rapidly-developing [3DS port](https://github.com/NateXS/Scratch-3DS), though the spec may not be done before contributors over there figure out how Scratch works for themselves anyway. :)
* **Recreating parts of Scratch (blocks, scripts) for demonstration**
* For educational reasons, one might want to recreate the behavior of certain parts of Scratch without the full force of the Scratch editor on hand. This spec will eventually provide information ranging from exact block behaviors to full-on runtime execution, making understanding the way each part of Scratch works simple.
* **Improving Scratch in the future while keeping it 100% compatible**
* It isn't known if this spec will reach a state that the developers of Scratch could use as reference, but if so, it could help ensure that Scratch projects remain functionally the same after code rewrites.
* **Directly citing the workings of Scratch without linking wikis or code**
* Although the [Scratch Wiki](https://scratch-wiki.info/) and code of Scratch work well for showing Scratch concepts and runtime behavior, one of them tends to abstract away particular functionalities while the other offers thousands of lines of pure [JavaScript](#javascript). This specification is meant to serve as one clear and concise document explaining the behaviors, blocks, and quirks of Scratch 3.0 in all its blocky glory.
* **Reimplementing Scratch 3.0 in case of catastrophe**
* This kind of blends together all of the previous points. If the Scratch editor were to magically disappear or break entirely (it won't, but in theory), then the Scratch Wiki could guide you in making a fairly accurate reimplementation of Scratch, but would fall short in exactly reproducing the runtime behavior, procedures, and quirks of Scratch, from scratch (literally). Although the wiki strives to be all-encompassing (and it is indeed very far-reaching), a document solely dedicated to the functionality of Scratch will help preserve its literal, programmatic behavior in one organized doc.
* **"Real" programming languages have them.**
* [Scratch is cool](https://blob.codes/scratch-is-cool/). It is [Turing-complete](https://en.wikipedia.org/wiki/Turing_completeness). Lots of languages far less significant than Scratch have [programming language specifications](https://en.wikipedia.org/wiki/Programming_language_specification). And yet Scratch lacks one. The Scratch Wiki helps document the **ideas** of Scratch, but a singular document dedicated to specifying *exactly* all that Scratch does could help it secure official programming language status.
* **Who knows what?**
* If this spec is made reliable enough, it could be cited (or at least, the underlying sources that it will eventually reference for verifability) in the underdeveloped [Wikipedia page about Scratch ***as a programming language***](https://en.wikipedia.org/wiki/Scratch_(programming_language)).

It could be argued that this specification is reinventing the wheel in some ways. However, if it is ever completed, it could serve as a great resource for Scratch 3.0.

## Why?

Why not?
Loading