Remove non-redistributable art from the repo; record licence terms
ci / verify (push) Successful in 46s
ci / verify (push) Successful in 46s
Researched the licence at each of the four itch.io sources. Two of the four
forbid redistribution, and publishing a repository containing them is exactly
that, so they are out of the tree.
0x72 DungeonTileset II CC0 1.0 commercial ok, no credit required
Helton Yan Pixel Combat CC BY 4.0 commercial ok, CREDIT REQUIRED
Fire Pixel Bullet 16x16 custom non-commercial, NO REDISTRIBUTION
750+ Effect and FX Pixel custom non-commercial, NO REDISTRIBUTION
Both bdragon1727 packs state verbatim: "You cannot do: Resell / redistribute
this asset." The FX pack's paid tier is no better for this purpose -- "You can
NOT re-distribute the file, no matter how much you modify it" -- so paying does
not unlock it and neither does editing the art.
bullets.png and impact.png therefore move to assets/local/, gitignored.
Art.bullets_texture() / impact_texture() load them at runtime and return null
when absent; the bullet renderer falls back to the generated dot it used before,
tinted per kind so bullet types stay distinguishable. Nothing there may be
preload()ed -- preload resolves at compile time and would fail the build on
every machine without the files, which is every clone.
Verified both ways rather than assumed: with the files present the game uses
them and no fallback triggers; with them moved aside, 156/156 tests pass and the
game runs clean on the generated dots.
Added CREDITS.md, because Helton Yan's CC BY 4.0 makes attribution a licence
obligation rather than a courtesy. A file in the source tree does not discharge
it once the game ships -- an in-game credits screen is now a tracked todo, and
flagged as a licence requirement rather than polish.
NOT addressed here, and it needs a decision: these files remain in git history
at 4a41ccb. Removing them from the tip does not remove them from a clone. If
this repo is ever made public, history has to be rewritten (git filter-repo)
and force-pushed. Also, both bdragon packs are non-commercial in their free
tier, which conflicts with the stated Steam goal -- either contribute for the
commercial tier (still no redistribution) or replace with CC0 art, which would
solve both problems and let the assets back into the repo.
This commit is contained in:
@@ -1,5 +1,13 @@
|
||||
# Godot's import cache and editor state. Regenerated by `godot --import`.
|
||||
.godot/
|
||||
# Assets whose licence forbids redistribution. bdragon1727's packs say
|
||||
# plainly: "You cannot do: Resell / redistribute this asset." Publishing a repo
|
||||
# containing them IS redistribution, so they stay local-only. The game loads
|
||||
# them if present and falls back to generated placeholders if not, so a clone
|
||||
# without them still runs. See docs/ASSETS.md.
|
||||
/assets/local/*
|
||||
!/assets/local/README.md
|
||||
|
||||
# Raw asset packs: gigabytes of source artwork and audio. Redistributable
|
||||
# third-party material belongs where it was bought or downloaded, not in a code
|
||||
# repo. The directory itself and its guards stay tracked, so a fresh clone has
|
||||
|
||||
+30
@@ -0,0 +1,30 @@
|
||||
# Credits
|
||||
|
||||
Third-party assets used in Transcience, with the attribution their licences
|
||||
require.
|
||||
|
||||
## Audio
|
||||
|
||||
**Pixel Combat SFX** — [Helton Yan](https://heltonyan.itch.io/pixelcombat)
|
||||
Licensed under [CC BY 4.0](https://creativecommons.org/licenses/by/4.0/).
|
||||
Converted to 16-bit / 44.1 kHz mono and trimmed for use in game.
|
||||
|
||||
> Attribution is **required** by this licence, not optional. It has to appear
|
||||
> somewhere a player can reach — this file is not enough on its own once the
|
||||
> game ships. See docs/ROADMAP.md.
|
||||
|
||||
## Art
|
||||
|
||||
**16x16 DungeonTileset II** — [0x72 (Robert Norenberg)](https://0x72.itch.io/dungeontileset-ii)
|
||||
Released under [CC0 1.0](https://creativecommons.org/publicdomain/zero/1.0/)
|
||||
(public domain). Credit is not required; it is here because the work deserves
|
||||
it.
|
||||
|
||||
## Not distributed with this repository
|
||||
|
||||
Two packs are used locally but deliberately **excluded** from the repository,
|
||||
because their licences forbid redistribution. They are not part of any build
|
||||
made from this source alone. See [docs/ASSETS.md](docs/ASSETS.md).
|
||||
|
||||
- Fire Pixel Bullet 16x16 — [bdragon1727](https://bdragon1727.itch.io/fire-pixel-bullet-16x16)
|
||||
- 750+ Effect and FX Pixel All — [bdragon1727](https://bdragon1727.itch.io/750-effect-and-fx-pixel-all)
|
||||
@@ -42,6 +42,7 @@ will otherwise cost an afternoon.
|
||||
|
||||
- [docs/ROADMAP.md](docs/ROADMAP.md) — what is built, what is next, where each feature lives
|
||||
- [docs/DECISIONS.md](docs/DECISIONS.md) — settled design decisions and their reasoning
|
||||
- [CREDITS.md](CREDITS.md) — third-party asset attribution
|
||||
- [CLAUDE.md](CLAUDE.md) — commands, invariants, Godot CLI gotchas
|
||||
- [docs/WORKFLOW.md](docs/WORKFLOW.md) — agent-assisted Godot development, and why the setup looks like this
|
||||
- [docs/ARCHITECTURE.md](docs/ARCHITECTURE.md) — code map and the node-free simulation
|
||||
|
||||
@@ -0,0 +1,24 @@
|
||||
# Local-only assets
|
||||
|
||||
Files here are **deliberately not in git**, because their licences forbid
|
||||
redistribution — and publishing a repository containing them is redistribution.
|
||||
|
||||
Currently:
|
||||
|
||||
| File | Pack | Restriction |
|
||||
| --- | --- | --- |
|
||||
| `bullets.png` | [Fire Pixel Bullet 16x16](https://bdragon1727.itch.io/fire-pixel-bullet-16x16) | "You cannot do: Resell / redistribute this asset." Free tier is non-commercial only. |
|
||||
| `impact.png` | [750 Effect and FX Pixel All](https://bdragon1727.itch.io/750-effect-and-fx-pixel-all) | Same wording. Even the paid tier: "You can NOT re-distribute the file, no matter how much you modify it." |
|
||||
|
||||
The game degrades rather than breaks without them: `Art.bullets_texture()`
|
||||
returns null and the renderer falls back to a generated dot. That fallback is
|
||||
what a fresh clone gets, and it is why nothing here may be `preload()`ed —
|
||||
`preload` is resolved at compile time and would fail the whole build on a
|
||||
machine that does not have these files.
|
||||
|
||||
To restore them locally, copy from `assetpacks/` (also untracked):
|
||||
|
||||
```
|
||||
cp "assetpacks/New_All_Fire_Bullet_Pixel_16x16/All_Fire_Bullet_Pixel_16x16_00.png" assets/local/bullets.png
|
||||
cp "assetpacks/Effect and FX Pixel All Free/Part 1/03.png" assets/local/impact.png
|
||||
```
|
||||
Binary file not shown.
|
Before Width: | Height: | Size: 47 KiB |
@@ -1,40 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://j0ouktqmynvo"
|
||||
path="res://.godot/imported/bullets.png-95be159865e32af815661d75740444b7.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/sprites/bullets.png"
|
||||
dest_files=["res://.godot/imported/bullets.png-95be159865e32af815661d75740444b7.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.7
|
||||
compress/uastc_level=0
|
||||
compress/rdo_quality_loss=0.0
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=false
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/channel_remap/red=0
|
||||
process/channel_remap/green=1
|
||||
process/channel_remap/blue=2
|
||||
process/channel_remap/alpha=3
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=1
|
||||
Binary file not shown.
|
Before Width: | Height: | Size: 198 KiB |
@@ -1,40 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://bspcicxeqn4bq"
|
||||
path="res://.godot/imported/impact.png-e86888071ed584ee489f2674e4500cf8.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/sprites/impact.png"
|
||||
dest_files=["res://.godot/imported/impact.png-e86888071ed584ee489f2674e4500cf8.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.7
|
||||
compress/uastc_level=0
|
||||
compress/rdo_quality_loss=0.0
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=false
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/channel_remap/red=0
|
||||
process/channel_remap/green=1
|
||||
process/channel_remap/blue=2
|
||||
process/channel_remap/alpha=3
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=1
|
||||
+52
-21
@@ -18,32 +18,63 @@ place, [src/view/art.gd](../src/view/art.gd), and
|
||||
`tests/unit/test_art.gd` asserts every rect lands inside its texture — a wrong
|
||||
atlas coordinate does not error, it silently draws the wrong pixels.
|
||||
|
||||
## Packs
|
||||
## Licence findings
|
||||
|
||||
All four are the **free** versions. Source URLs are recorded because the packs
|
||||
themselves are gitignored, so their bundled licence files are not in the repo.
|
||||
Checked against each pack's itch.io page. **Two of the four forbid
|
||||
redistribution**, which is what publishing a repository containing them would
|
||||
be — so they are not in the repository.
|
||||
|
||||
| Pack | Source | In use | Licence |
|
||||
| --- | --- | --- | --- |
|
||||
| 0x72 Dungeon Tileset II v1.7 | https://0x72.itch.io/dungeontileset-ii | Terrain, player, enemies, boss → `assets/sprites/dungeon_tileset.png` | Confirm at source. Widely distributed as CC0 by Robert Norenberg (0x72); the bundled README is technical, not legal. |
|
||||
| Fire Pixel Bullet 16x16 | https://bdragon1727.itch.io/fire-pixel-bullet-16x16 | Bullets → `assets/sprites/bullets.png` | Confirm at source (free version). |
|
||||
| 750+ Effect and FX Pixel All | https://bdragon1727.itch.io/750-effect-and-fx-pixel-all | Impact effect → `assets/sprites/impact.png` | Confirm at source (free version). |
|
||||
| Helton Yan — Pixel Combat | https://heltonyan.itch.io/pixelcombat | SFX → `assets/audio/sfx/*.wav` | Confirm at source (free version). |
|
||||
| Pack | Licence | Commercial | Credit | In this repo? |
|
||||
| --- | --- | --- | --- | --- |
|
||||
| [0x72 DungeonTileset II](https://0x72.itch.io/dungeontileset-ii) | **CC0 1.0** (public domain) | Yes | Not required | **Yes** — `assets/sprites/dungeon_tileset.png` |
|
||||
| [Helton Yan Pixel Combat](https://heltonyan.itch.io/pixelcombat) | **CC BY 4.0** | Yes | **Required** | **Yes** — `assets/audio/sfx/` |
|
||||
| [Fire Pixel Bullet 16x16](https://bdragon1727.itch.io/fire-pixel-bullet-16x16) | Custom | **Non-commercial only** unless you contribute | Encouraged | **No** — local only |
|
||||
| [750+ Effect and FX Pixel All](https://bdragon1727.itch.io/750-effect-and-fx-pixel-all) | Custom | **Non-commercial only** unless you contribute | Encouraged | **No** — local only |
|
||||
|
||||
### The blocking clause
|
||||
|
||||
Both bdragon1727 packs state, verbatim:
|
||||
|
||||
> **You cannot do:** Resell / redistribute this asset.
|
||||
|
||||
And the paid tier of the FX pack is no better for this purpose:
|
||||
|
||||
> You can NOT re-distribute the file, no matter how much you modify it you can
|
||||
> use it but not share or re-sell it.
|
||||
|
||||
Putting those files in a public repository distributes them to everyone who
|
||||
clones it, which is squarely what that forbids. Paying for the commercial tier
|
||||
does **not** unlock it — the restriction survives payment and survives
|
||||
modification.
|
||||
|
||||
So they live in `assets/local/`, which is gitignored. `Art.bullets_texture()`
|
||||
and `Art.impact_texture()` load them at runtime if present and return null if
|
||||
not; the bullet renderer falls back to a generated dot. Verified both ways: with
|
||||
the files present the game uses them, and with them hidden the suite still
|
||||
passes 156/156 and the game runs.
|
||||
|
||||
This is also why nothing there may be `preload()`ed — `preload` resolves at
|
||||
compile time and would fail the build on every machine that lacks the files.
|
||||
|
||||
### Two obligations this creates
|
||||
|
||||
1. **Helton Yan's CC BY 4.0 requires attribution**, and it is not satisfied by
|
||||
a file in the source tree once the game ships. Players need to be able to
|
||||
see it. [CREDITS.md](../CREDITS.md) records it for now; an in-game credits
|
||||
screen is a todo.
|
||||
2. **Both bdragon packs are non-commercial in their free tier.** The stated
|
||||
goal is a Steam release. Before that happens they need either a paid
|
||||
contribution to bdragon1727 (which permits commercial use but still not
|
||||
redistribution) or replacement with CC0 art. A CC0 replacement solves both
|
||||
problems at once and lets the assets go back in the repo.
|
||||
|
||||
### Not in use
|
||||
|
||||
`assetpacks/considering_dont_use_yet/` is the user's own "not chosen" marker and
|
||||
nothing there is referenced by the game. It contains RF Catacombs v1.0 (public
|
||||
domain per its bundled `public-license.txt` — free for personal or commercial
|
||||
use, credit appreciated, no reselling; artwork by Szadi art), plus Tiny RPG
|
||||
Character Pack 02 and neo_zero demos, whose terms are unrecorded.
|
||||
|
||||
### Still to confirm
|
||||
|
||||
Free itch.io packs vary: some are CC0, some require credit, some restrict
|
||||
commercial use, and "free version" often carries different terms from the paid
|
||||
one. Four rows above say *confirm at source* — do that before a public build,
|
||||
and if any require attribution, the credits screen does not exist yet.
|
||||
`assetpacks/considering_dont_use_yet/` is the "not chosen" marker and nothing
|
||||
there is referenced. It contains RF Catacombs v1.0 (public domain per its
|
||||
bundled `public-license.txt` — free for personal or commercial use, credit
|
||||
appreciated, no reselling; artwork by Szadi art), plus Tiny RPG Character Pack
|
||||
02 and neo_zero demos, whose terms are unrecorded.
|
||||
|
||||
## Converting audio before use
|
||||
|
||||
|
||||
@@ -68,6 +68,8 @@ play off server events. Enough to prove the pipeline, not a finished look.
|
||||
| Impact/death VFX animation | todo | `Art.IMPACT` is loaded and validated but nothing plays it yet |
|
||||
| Directional sprites, hit flashes, screen shake | todo | |
|
||||
| Audio buses and a volume setting | todo | Everything plays on Master at hardcoded dB |
|
||||
| **In-game credits screen** | **todo** | Not cosmetic: the SFX are CC BY 4.0 and attribution is a licence *requirement*. [CREDITS.md](../CREDITS.md) is not reachable by a player. |
|
||||
| Replace the two non-redistributable packs | todo | Bullet and FX art is local-only and non-commercial. CC0 replacements would let them into the repo and unblock a commercial release. See [ASSETS.md](ASSETS.md). |
|
||||
|
||||
## Stage 2 — Characters, persistence, levels · *todo, next*
|
||||
|
||||
|
||||
+36
-2
@@ -10,9 +10,43 @@ extends RefCounted
|
||||
## Everything in this file is view-only. Nothing under src/sim/ may reference it:
|
||||
## the simulation has no idea the game has art.
|
||||
|
||||
## Redistributable, so committed and safe to preload.
|
||||
const TILESET := preload("res://assets/sprites/dungeon_tileset.png")
|
||||
const BULLETS := preload("res://assets/sprites/bullets.png")
|
||||
const IMPACT := preload("res://assets/sprites/impact.png")
|
||||
|
||||
## NOT redistributable: bdragon1727's licence says "You cannot do: Resell /
|
||||
## redistribute this asset", and shipping them in a public repo would be exactly
|
||||
## that. They live in the untracked assets/local/ and are loaded at RUNTIME.
|
||||
##
|
||||
## preload() would be resolved at compile time and would fail the entire build
|
||||
## on any machine that does not have them -- which is every fresh clone. Hence
|
||||
## load() behind an existence check, and a generated fallback in the renderer.
|
||||
const LOCAL_BULLETS := "res://assets/local/bullets.png"
|
||||
const LOCAL_IMPACT := "res://assets/local/impact.png"
|
||||
|
||||
static var _bullets: Texture2D = null
|
||||
static var _impact: Texture2D = null
|
||||
static var _optional_loaded: bool = false
|
||||
|
||||
|
||||
static func _load_optional() -> void:
|
||||
if _optional_loaded:
|
||||
return
|
||||
_optional_loaded = true
|
||||
if ResourceLoader.exists(LOCAL_BULLETS):
|
||||
_bullets = load(LOCAL_BULLETS)
|
||||
if ResourceLoader.exists(LOCAL_IMPACT):
|
||||
_impact = load(LOCAL_IMPACT)
|
||||
|
||||
|
||||
## Null when the licence-restricted art is not present. Callers must cope.
|
||||
static func bullets_texture() -> Texture2D:
|
||||
_load_optional()
|
||||
return _bullets
|
||||
|
||||
|
||||
static func impact_texture() -> Texture2D:
|
||||
_load_optional()
|
||||
return _impact
|
||||
|
||||
## Source art is 16px; the world's tiles are 32. Drawn at 2x with nearest
|
||||
## filtering (project-wide `default_texture_filter=0`) so it stays crisp.
|
||||
|
||||
@@ -10,17 +10,34 @@ extends Node2D
|
||||
## sheet. Four kinds means four draw calls, which is nothing, and it avoids a
|
||||
## custom shader passing UV offsets through per-instance custom data.
|
||||
|
||||
## Used only in fallback mode, where every bullet is the same generated dot and
|
||||
## colour is the only thing distinguishing a kind.
|
||||
const _FALLBACK_COLOURS: Array[Color] = [
|
||||
Color(0.45, 0.95, 1.0), # KIND_PLAYER_SHOT
|
||||
Color(1.0, 0.35, 0.75), # KIND_ORB
|
||||
Color(1.0, 0.85, 0.3), # KIND_NEEDLE
|
||||
Color(1.0, 0.45, 0.2), # KIND_HEAVY
|
||||
]
|
||||
|
||||
var _layers: Array[MultiMeshInstance2D] = []
|
||||
## Advances the bullets' own animation, independent of the simulation.
|
||||
var _anim_tick: int = 0
|
||||
## True when the licence-restricted bullet sheet is absent and we are drawing
|
||||
## generated dots instead. See Art.bullets_texture().
|
||||
var _fallback: bool = false
|
||||
|
||||
|
||||
func _ready() -> void:
|
||||
var sheet := Art.bullets_texture()
|
||||
_fallback = sheet == null
|
||||
var art: Texture2D = sheet if sheet != null else _make_dot_texture()
|
||||
if _fallback:
|
||||
GameLog.info("view", "bullet sheet absent, drawing generated dots")
|
||||
var quad := QuadMesh.new()
|
||||
quad.size = Vector2.ONE
|
||||
for kind in SimConfig.KIND_HEAVY + 1:
|
||||
var layer := MultiMeshInstance2D.new()
|
||||
layer.texture = Art.BULLETS
|
||||
layer.texture = art
|
||||
var mm := MultiMesh.new()
|
||||
mm.transform_format = MultiMesh.TRANSFORM_2D
|
||||
mm.use_colors = true
|
||||
@@ -34,7 +51,24 @@ func _ready() -> void:
|
||||
|
||||
func _process(_delta: float) -> void:
|
||||
_anim_tick += 1
|
||||
_apply_frame()
|
||||
if not _fallback:
|
||||
_apply_frame()
|
||||
|
||||
|
||||
## A soft-edged disc with a bright core, generated at runtime. This is what the
|
||||
## game draws when the bullet sheet is not present, which is the case for any
|
||||
## clone of the repository -- the sheet's licence forbids redistributing it.
|
||||
func _make_dot_texture() -> ImageTexture:
|
||||
var size := 32
|
||||
var img := Image.create(size, size, false, Image.FORMAT_RGBA8)
|
||||
var centre := Vector2(size, size) * 0.5
|
||||
for y in size:
|
||||
for x in size:
|
||||
var d := Vector2(x + 0.5, y + 0.5).distance_to(centre) / (size * 0.5)
|
||||
var alpha := pow(clampf(1.0 - d, 0.0, 1.0), 0.6)
|
||||
var core := clampf(1.0 - d * 1.9, 0.0, 1.0)
|
||||
img.set_pixel(x, y, Color(1.0, 1.0, 1.0, alpha).lerp(Color.WHITE, core * 0.8))
|
||||
return ImageTexture.create_from_image(img)
|
||||
|
||||
|
||||
## Point each layer's texture at this frame's cell in the sheet. Every bullet in
|
||||
@@ -50,7 +84,7 @@ func _apply_frame() -> void:
|
||||
var atlas := _layers[kind].texture as AtlasTexture
|
||||
if atlas == null:
|
||||
atlas = AtlasTexture.new()
|
||||
atlas.atlas = Art.BULLETS
|
||||
atlas.atlas = Art.bullets_texture()
|
||||
_layers[kind].texture = atlas
|
||||
atlas.region = region
|
||||
|
||||
@@ -73,7 +107,8 @@ func render_pool(pool: BulletPool) -> void:
|
||||
var angle: float = (pool.vel[i] as Vector2).angle()
|
||||
_layers[kind].multimesh.set_instance_transform_2d(
|
||||
n, Transform2D(angle, Vector2(d, d), 0.0, pool.pos[i]))
|
||||
_layers[kind].multimesh.set_instance_color(n, Color.WHITE)
|
||||
_layers[kind].multimesh.set_instance_color(n,
|
||||
_FALLBACK_COLOURS[kind] if _fallback else Color.WHITE)
|
||||
counts[kind] = n + 1
|
||||
for kind in _layers.size():
|
||||
_layers[kind].multimesh.visible_instance_count = counts[kind]
|
||||
|
||||
+24
-6
@@ -12,10 +12,20 @@ func _fits(tex: Texture2D, r: Rect2) -> bool:
|
||||
and r.end.x <= size.x and r.end.y <= size.y
|
||||
|
||||
|
||||
func test_every_texture_loaded() -> void:
|
||||
for tex in [Art.TILESET, Art.BULLETS, Art.IMPACT]:
|
||||
assert_not_null(tex)
|
||||
assert_gt(tex.get_width(), 0)
|
||||
func test_the_committed_texture_loads() -> void:
|
||||
assert_not_null(Art.TILESET)
|
||||
assert_gt(Art.TILESET.get_width(), 0)
|
||||
|
||||
|
||||
## The licence-restricted sheets are absent from a clean clone by design, so
|
||||
## their absence must be a supported state rather than a failure. When they are
|
||||
## present locally, the rect tests below still validate them.
|
||||
func test_the_game_runs_without_the_restricted_art() -> void:
|
||||
var bullets := Art.bullets_texture()
|
||||
if bullets == null:
|
||||
assert_true(true, "no bullet sheet: renderer falls back to generated dots")
|
||||
else:
|
||||
assert_gt(bullets.get_width(), 0)
|
||||
|
||||
|
||||
func test_terrain_rects_are_inside_the_tileset() -> void:
|
||||
@@ -38,13 +48,17 @@ func test_every_animation_frame_is_inside_the_tileset() -> void:
|
||||
|
||||
|
||||
func test_every_bullet_frame_is_inside_the_sheet() -> void:
|
||||
var sheet := Art.bullets_texture()
|
||||
if sheet == null:
|
||||
pass_test("bullet sheet not present locally; nothing to validate")
|
||||
return
|
||||
for kind in Art.BULLET_CELLS.size():
|
||||
var cell: Vector2i = Art.BULLET_CELLS[kind]
|
||||
for n in Art.BULLET_FRAMES:
|
||||
var r := Rect2(
|
||||
Vector2(float(cell.x + n), float(cell.y)) * Art.BULLET_CELL,
|
||||
Vector2(Art.BULLET_CELL, Art.BULLET_CELL))
|
||||
assert_true(_fits(Art.BULLETS, r),
|
||||
assert_true(_fits(sheet, r),
|
||||
"bullet kind %d frame %d is outside the sheet at %s" % [kind, n, r])
|
||||
|
||||
|
||||
@@ -63,10 +77,14 @@ func test_there_is_a_sprite_for_every_enemy_visual() -> void:
|
||||
|
||||
|
||||
func test_impact_sheet_covers_its_declared_frames() -> void:
|
||||
var impact := Art.impact_texture()
|
||||
if impact == null:
|
||||
pass_test("impact sheet not present locally; nothing to validate")
|
||||
return
|
||||
var last := Rect2(
|
||||
Vector2(float((Art.IMPACT_FRAMES - 1) % Art.IMPACT_COLUMNS), 0.0) * Art.IMPACT_CELL,
|
||||
Vector2(Art.IMPACT_CELL, Art.IMPACT_CELL))
|
||||
assert_true(_fits(Art.IMPACT, last))
|
||||
assert_true(_fits(impact, last))
|
||||
|
||||
|
||||
func test_every_sound_loaded_and_is_short_enough_to_be_a_sound_effect() -> void:
|
||||
|
||||
Reference in New Issue
Block a user