Skip to content

docs: update docs for typescript #6

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Sep 27, 2024
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
6 changes: 5 additions & 1 deletion docs/css/extra.css

Large diffs are not rendered by default.

42 changes: 25 additions & 17 deletions docs/documentation/getting-started.md
Original file line number Diff line number Diff line change
@@ -1,40 +1,48 @@
### How to export script class to Godot
[Download the editor](https://github.com/godotjs/javascript/releases) and start the application

Recommended for TypeScript:

- Rename the downloaded file to `godot` and [add Godot to your path](https://docs.godotengine.org/en/stable/tutorials/editor/command_line_tutorial.html#path)
- Open a terminal
- Test if you can use Godot via terminal and run `godot --version`

## How to export script class to Godot

1. Define your JavaScript class and inherit from a Godot class, then export it as the **default** entry:

```javascript title="my-sprite.mjs"
// The default export entry is treated as an exported class to Godot
export default class MySprite extends godot.Sprite {
// this is _init() in GDScript
constructor() {
super();
}
// this is _init() in GDScript
constructor() {
super();
}

_ready() {}
_ready() {}

_process(delta) {}
_process(delta) {}
}
```

2. Save the script with extension `.mjs`
3. Attach the script file to the node or resource object like you do with GDScript

### How to export signals
## How to export signals

```javascript title="my-sprite.mjs"
export default class MySprite extends godot.Sprite {}
// register game_over signal to MySprite class
godot.register_signal(MySprite, "game_over");
```

### How to export properties
## How to export properties

```javascript title="my-sprite.mjs"
export default class MySprite extends godot.Sprite {
_process(delta) {
// Yes! We can use operators in JavaScript like GDScript
this.position += this.direction * delta;
}
_process(delta) {
// Yes! We can use operators in JavaScript like GDScript
this.position += this.direction * delta;
}
}
// export 'direction' properties to MySprite Godot inspector
godot.register_property(MySprite, "direction", new godot.Vector2(1, 0));
Expand All @@ -57,10 +65,10 @@ Is the simplified version of:

```js
godot.register_property(MyClass, "number_value", {
type: godot.TYPE_REAL,
hint: godot.PropertyHint.PROPERTY_HINT_NONE,
hint_string: "",
default: 3.14,
type: godot.TYPE_REAL,
hint: godot.PropertyHint.PROPERTY_HINT_NONE,
hint_string: "",
default: 3.14,
});
```

Expand Down
30 changes: 2 additions & 28 deletions docs/documentation/gotchas.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,31 +2,6 @@

Some common mistakes and limitations.

## Import dependency from `node_modules`

If you use `TypeScript` you may encounter the problem where dependencies from `node_modules` are not bundled correctly.

As a workaround you can create a new file `npm-modules.bundle.ts`:

```ts title="npm-modules.bundle.ts"
import { default as dayjs } from "dayjs";
export default { dayjs };
```

In your class you can use the dependency like this:

```ts title="main.ts"
import npm from "./npm-modules.bundle";

export default class Main extends godot.Node {
_ready(): void {
console.log(npm.dayjs().toString());
}
}
```

With a bundler like `esbuild` you should build the `npm-modules.bundle.ts` with the `--bundle` option, but all the other classes like `main.ts` without it.

## Position.x is immutable

You cannot change `this.position.x` try to change `this.position`:
Expand All @@ -46,13 +21,12 @@ export default class Player extends godot.KinematicBody2D {
godot.register_property(Player, "direction", new godot.Vector2(1, 0));
```

## ``register_property`` has to be a target
## `register_property` has to be a target

You cannot change `this.position.x` try to change `this.position`:

```javascript title="player.mjs"
export default class Player extends godot.KinematicBody2D {
}
export default class Player extends godot.KinematicBody2D {}
// This works
godot.register_property(Player, "directionWorks", new godot.Vector2(1, 0));
// This breaks because `player` isn't a correct target
Expand Down
84 changes: 0 additions & 84 deletions docs/documentation/typescript.md

This file was deleted.

74 changes: 74 additions & 0 deletions docs/documentation/typescript/decorators.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
One feature of GodotTS is that your can use decorators for adding `register` functions to your class like [signals](../getting-started.md#how-to-export-signals).

Most of the `register` functions are available as various decorators as seen below. Check the decorators in `src/decorators.bundle` generated in [intro](intro.md).

```ts
import { signal, property, tool, onready, node } from "./decorators.bundle";

@tool // make the script runnable in godot editor
export default class InputLine extends godot.HBoxContainer {
// define a signal
@signal
static readonly OnTextChanged: string;

// expose a node property
@node
icon: godot.Sprite;

// register offset property with the godot inspector with default value of Vector2(0, 0)
@property({ default: godot.Vector2.ZERO })
offset: godot.Vector2;

// register properties for godot editor inspector
@property({ type: godot.VariantType.TYPE_STRING })
get title() {
return this._title;
}
set title(v: string) {
this._title = v;
if (this._label) {
this._label.text = v;
}
}
private _title: string;

@property({ default: "Input text here" })
get hint() {
return this._hint;
}
set hint(v: string) {
this._hint = v;
if (this.edit) {
this.edit.hint_tooltip = v;
this.edit.placeholder_text = v;
}
}
private _hint: string;

get label(): godot.Label {
return this._label;
}
protected _label: godot.Label;

// call get_node('LineEdit') and assign the returned value to 'this.edit' automatically when the node is ready
@onready("LineEdit")
edit: godot.LineEdit;

get text(): string {
return this.edit?.text;
}

_ready() {
// get first child with the type of godot.Label
this._label = this.get_node(godot.Label);

// Apply the inspector filled values with property setters
this.title = this.title;
this.hint = this.hint;

this.edit.connect(godot.LineEdit.text_changed, (text: string) => {
this.emit_signal(InputLine.OnTextChanged, text);
});
}
}
```
16 changes: 16 additions & 0 deletions docs/documentation/typescript/godot-ts.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
[`godot-ts`](https://github.com/godotjs/godot-ts) is a cli tool for using GodotJS with Typescript.

See the [Intro](intro.md) how you initialize a new GodotTS project.

Afterward, you can run ``godot-ts --help`` to see additional helping.

## Further information

The cli tool handles the compilation of `.ts` files into `.mjs` files.

There are two commands `godot-ts build` & `godot-ts watch` which compile those files. Use `build` to compile your files once for production (with minification) and `watch` for developing.

Both commands will compile every `*.ts` file as it is (without bundling), to remain the required class structures for GodotJS.

Sometimes you require to bundle a `*.ts` file e.g. if you need something from `node_modules` ([example](npm-modules.md)).
In this case name your file `*.bundle.ts`, this won't generate a `.mjs` file, instead it generates a `.js` file as bundled code.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
37 changes: 37 additions & 0 deletions docs/documentation/typescript/intro.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
1. [Download the editor](https://github.com/godotjs/javascript/releases)
2. Rename the downloaded file to `godot` and [add Godot to your path](https://docs.godotengine.org/en/stable/tutorials/editor/command_line_tutorial.html#path)
3. Open a terminal
4. Test if you can use Godot via CLI and run `godot --version`
5. Run `npx -y @godot-js/godot-ts init` (new project will be crated at your current terminal path)
6. Follow the prompts
7. Run `cd <your-project>`
8. Run `npm i`
9. Run `npm run dev` - this will enable typescript watch mode and opens the editor
10. Run the menu command inside the editor `Project > Tools > JavaScript > Generate TypeScript Declaration File` and overwrite file `godot.d.ts`

## Features

- By running `npm run dev` you compile your `.ts` files into `.mjs` automatically
- Use the generated `.mjs` files inside your editor
- To open the `.ts` origin file for a `.mjs` file you need to enable [External Editor](#open-scripts-from-the-editor)
- If you want to start the game without editor run `npm run start`
- For more information check out [`godot-ts`](godot-ts.md)

## Open scripts from the editor

Inside the editor you are normally able to open a script inside the build in text editor.

![Open script](images/open-script.png)

But we use a compiled `.mjs` file for our scripts.
`.ts` files can't be open in the editor.

So we need to open the `.ts` files inside an external editor:

1. Goto `Editor/Editor Settings/Text Editor/External`
2. Check the `Use External Editor`
3. Add your path your desired editor to `Exec Path` - Check [this](https://docs.godotengine.org/en/stable/tutorials/editor/external_editor.html) for more information
4. Paste `{project} --line {line} {file}` (JetBrains products) to `Exec Flags`
5. If you click on a `.mjs` script it should read the `banner` on top of the file like `//generatedPath=<absolute-path>.ts` and opens this file

![enable external editor](images/enable-external-editor.png)
31 changes: 31 additions & 0 deletions docs/documentation/typescript/npm-modules.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
You can import ES5/ES6 modules installed from e.g. `npm`. But you need to bundle them first.

We recommend that you create a `npm.bundle.ts` file where you locate all of your dependencies.

## Example

Install dependency:

```shell title="terminal"
npm i dayjs
```

Export the dependency from your `npm.bundle.ts` file.

```ts title="npm.bundle.ts"
export { default as dayjs } from "dayjs";
```

Import the dependency in another class

```ts title="my-class.ts"
import { dayjs } from "./npm-modules.bundle";

export default class MyClass extends Node {
_ready(): void {
console.log(dayjs().toString());
}
}
```

> **Note:** If you use `godot-ts build/watch` the `npm.bundle.ts` file will be bundled with every dependency from `node_modules`, while regular `*.ts` files will preserve their imports. This is required for GodotJS to work.
12 changes: 8 additions & 4 deletions mkdocs.yml
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,14 @@ extra_css:
nav:
- Home: index.md
- Docs:
- Getting Started: documentation/getting-started.md
- API: documentation/api.md
- TypeScript: documentation/typescript.md
- Gotchas: documentation/gotchas.md
- Getting Started: documentation/getting-started.md
- API: documentation/api.md
- TypeScript:
- Intro: documentation/typescript/intro.md
- GodotTS: documentation/typescript/godot-ts.md
- Decorators: documentation/typescript/decorators.md
- NPM Modules: documentation/typescript/npm-modules.md
- Gotchas: documentation/gotchas.md
- Examples:
- Load JSON in Singleton: examples/load-json-in-singleton.md
- Read file local: examples/read-file-local.md
Expand Down
Loading