From 3e589f233790e646e06a9a15b77f2692b2fd028a Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Wed, 5 Aug 2026 21:34:30 -0700 Subject: [PATCH 01/24] Add .gitattributes file to configure text handling and language detection for .absp files --- .gitattributes | 3 +++ 1 file changed, 3 insertions(+) create mode 100644 .gitattributes diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..0372651 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,3 @@ +* text=auto eol=lf + +*.absp text linguist-language=JSON linguist-detectable=true diff=json From 021fe67ff3a85173a8058f892abe76260a47af75 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Wed, 5 Aug 2026 21:46:56 -0700 Subject: [PATCH 02/24] Fix import order and ensure console compatibility in logger.py --- engine/logger.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/engine/logger.py b/engine/logger.py index d447805..5d2d3c7 100644 --- a/engine/logger.py +++ b/engine/logger.py @@ -9,7 +9,9 @@ from enum import Enum from typing import Any -from colorama import Fore, Style +from colorama import Fore, Style, just_fix_windows_console + +just_fix_windows_console() class Status(Enum): From a3bea89689de44ae35e633ab4c5f0246b755b979 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Wed, 5 Aug 2026 21:49:59 -0700 Subject: [PATCH 03/24] Move just_fix_windows_console() call to __init__.py and clean up imports in logger.py --- engine/__init__.py | 4 ++++ engine/logger.py | 4 +--- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/engine/__init__.py b/engine/__init__.py index a06b83c..f24109c 100644 --- a/engine/__init__.py +++ b/engine/__init__.py @@ -4,3 +4,7 @@ """ Core engine package """ + +from colorama import just_fix_windows_console + +just_fix_windows_console() diff --git a/engine/logger.py b/engine/logger.py index 5d2d3c7..d447805 100644 --- a/engine/logger.py +++ b/engine/logger.py @@ -9,9 +9,7 @@ from enum import Enum from typing import Any -from colorama import Fore, Style, just_fix_windows_console - -just_fix_windows_console() +from colorama import Fore, Style class Status(Enum): From 30fdb76a20c4eb747dacb6f2b6c9610e4880040b Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Thu, 6 Aug 2026 10:51:17 -0700 Subject: [PATCH 04/24] Refactor import of just_fix_windows_console() to improve clarity in __init__.py --- engine/__init__.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/engine/__init__.py b/engine/__init__.py index f24109c..d6beb19 100644 --- a/engine/__init__.py +++ b/engine/__init__.py @@ -5,6 +5,6 @@ Core engine package """ -from colorama import just_fix_windows_console +import colorama -just_fix_windows_console() +colorama.just_fix_windows_console() From 4fb16b3ba8c93603e31688452269df5cc67b48e5 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Thu, 6 Aug 2026 11:01:48 -0700 Subject: [PATCH 05/24] Refactor RGBType definition to include pygame.Color for improved type compatibility --- engine/core/types.py | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/engine/core/types.py b/engine/core/types.py index 49ece87..7ab6767 100644 --- a/engine/core/types.py +++ b/engine/core/types.py @@ -7,11 +7,14 @@ import pygame -from typing import Protocol +from typing import Union, Protocol from .image import EntityImage -RGBType = tuple[int, int, int] +RGBType = Union[ + tuple[int, int, int], + pygame.Color # For type checkers +] EntityImageType = EntityImage From 47cae412746f717a989a2f1fa7a9de7a46730be6 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Thu, 6 Aug 2026 11:53:34 -0700 Subject: [PATCH 06/24] Add destructor to Entity class for proper resource management --- engine/core/__init__.py | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/engine/core/__init__.py b/engine/core/__init__.py index 0b5ca1f..5d2a24b 100644 --- a/engine/core/__init__.py +++ b/engine/core/__init__.py @@ -139,6 +139,16 @@ def __repr__(self) -> str: return f"<{self.__class__.__name__} at {hex(id(self))} with id {self.id}>" + def __del__(self) -> None: + """ + Destructor for the entity. + """ + + try: + self.destroy() + except ValueError: + logger("Failed to destroy entity", status=LoggerStatus.WARNING) + def _collides_with(self, other: "Entity") -> bool: """ Check if this entity collides with another entity using AABB collision detection. @@ -241,8 +251,8 @@ def destroy(self) -> None: if self.parent is not None: try: self.parent.remove(self) - except ValueError: - logger("Invalid target for destruction", status=LoggerStatus.WARNING) + except ValueError as e: + raise ValueError("Invalid target for destruction") from e self.parent = None From cd6c84c75a94b0864319774fce8f519f496c7e6a Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Thu, 6 Aug 2026 18:37:29 -0700 Subject: [PATCH 07/24] Fix formatting in RGBType --- engine/core/types.py | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/engine/core/types.py b/engine/core/types.py index 7ab6767..281b591 100644 --- a/engine/core/types.py +++ b/engine/core/types.py @@ -12,8 +12,7 @@ from .image import EntityImage RGBType = Union[ - tuple[int, int, int], - pygame.Color # For type checkers + tuple[int, int, int], pygame.Color # Add pygame.Color for type checkers ] EntityImageType = EntityImage From 6b347d936a0a0d4d811498af743e8fade131f8a3 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Thu, 6 Aug 2026 22:02:33 -0700 Subject: [PATCH 08/24] Enhance destroy method documentation in Entity class to include error handling --- engine/core/__init__.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/engine/core/__init__.py b/engine/core/__init__.py index 5d2a24b..873f69a 100644 --- a/engine/core/__init__.py +++ b/engine/core/__init__.py @@ -245,7 +245,10 @@ def get_colliding_entities(self) -> list["Entity"]: def destroy(self) -> None: """ - Destroy this entity + Destroy this entity. + + Raises: + ValueError: If the entity cannot be removed from its parent. """ if self.parent is not None: From 6e2ae6b4e74076a4dd65e05066581580c0a62dc4 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Thu, 6 Aug 2026 22:03:56 -0700 Subject: [PATCH 09/24] Rephrase AI policy statement for clarity in AGENTS.md --- AGENTS.md | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/AGENTS.md b/AGENTS.md index a436b65..fb40327 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -1,4 +1,6 @@ -See ABS Engine's [AI Policy](CONTRIBUTING.md#ai-policy) for more information on +ABS Engine has a strict AI policy. + +See [the AI Policy](CONTRIBUTING.md#ai-policy) for more information on how AI may be used. From 7a7500545200e0cf1f430f319da3ff65767e427b Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 08:27:17 -0700 Subject: [PATCH 10/24] Add 'visible' property to Entity class for rendering control --- docs/scripting.md | 1 + engine/core/__init__.py | 11 +++++++---- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/docs/scripting.md b/docs/scripting.md index a695bc7..c73219d 100644 --- a/docs/scripting.md +++ b/docs/scripting.md @@ -88,6 +88,7 @@ The `engine.core.Entity` class has the following properties: | `id` | Unique entity UUID | `str` | | `get_colliding_entities` | Return a list of colliding entities | `Callable[[], list[Entity]]` | | `destroy` | Destroy the entity | `Callable[[], None]` | +| `visible` | Weather to draw the entity or not | `bool` | ## Script Functions diff --git a/engine/core/__init__.py b/engine/core/__init__.py index 873f69a..37a8ae1 100644 --- a/engine/core/__init__.py +++ b/engine/core/__init__.py @@ -55,6 +55,8 @@ def __init__( image (Optional[str]): Path to optional image file. Defaults to None. """ + self.visible = True + self.x: int = x self.y: int = y self.width: int = width @@ -225,10 +227,11 @@ def draw(self, surface: pygame.Surface) -> None: surface (pygame.Surface): The surface to draw the entity on. """ - if self.image is not None: - self.image.draw(surface, self.rect) - else: - pygame.draw.rect(surface, self.color, self.rect) + if self.visible: + if self.image is not None: + self.image.draw(surface, self.rect) + else: + pygame.draw.rect(surface, self.color, self.rect) def get_colliding_entities(self) -> list["Entity"]: """ From 818d6b0bfcae2a298ee7391335cd7f146d68c98a Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 08:41:00 -0700 Subject: [PATCH 11/24] Add visibility check to Text draw method for conditional rendering --- engine/core/text.py | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/engine/core/text.py b/engine/core/text.py index de990aa..7de535e 100644 --- a/engine/core/text.py +++ b/engine/core/text.py @@ -87,7 +87,8 @@ def draw(self, surface: pygame.Surface) -> None: surface (pygame.Surface): The surface to draw the text on. """ - if self.dynamic: - self._update_text_surface() + if self.visible: + if self.dynamic: + self._update_text_surface() - surface.blit(self.text_surface, self.text_rect) + surface.blit(self.text_surface, self.text_rect) From 805cf491d3dbb5f8c2c99e04b87202e39f03c52d Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 10:04:51 -0700 Subject: [PATCH 12/24] Add center() method to Text entity Add Text.center(pos) to reposition text so it's centered on a given point, offsetting by half the rendered width/height and refreshing the text surface to keep text_rect in sync. --- engine/core/text.py | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/engine/core/text.py b/engine/core/text.py index 7de535e..502492e 100644 --- a/engine/core/text.py +++ b/engine/core/text.py @@ -79,6 +79,11 @@ def _update_text_surface(self) -> None: ) self.text_rect = self.text_surface.get_rect(x=self.x, y=self.y) + def center(self, pos: tuple[int, int]) -> None: + self.x = pos[0] - self.width // 2 + self.y = pos[1] - self.height // 2 + self._update_text_surface() + def draw(self, surface: pygame.Surface) -> None: """ Draw the rendered text onto the given surface. From 4341820ce0528dcc24acde7e67650a7df6b667f5 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 11:22:22 -0700 Subject: [PATCH 13/24] Hoist center() into Entity base class Move the centering math into Entity.center() so all entities get it, and have Text.center() delegate via super() before rebuilding its text surface. Removes the duplicated positioning logic. --- engine/core/__init__.py | 5 +++++ engine/core/text.py | 3 +-- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/engine/core/__init__.py b/engine/core/__init__.py index 37a8ae1..f62c45c 100644 --- a/engine/core/__init__.py +++ b/engine/core/__init__.py @@ -173,6 +173,11 @@ def _setparent(self, parent: "Scene") -> None: """ self.parent = parent + def center(self, pos: tuple[int, int]) -> None: + self.x = pos[0] - self.width // 2 + self.y = pos[1] - self.height // 2 + self._update_rect() + def init(self) -> None: """ Call the init function in the script file if it exists. diff --git a/engine/core/text.py b/engine/core/text.py index 502492e..e537220 100644 --- a/engine/core/text.py +++ b/engine/core/text.py @@ -80,8 +80,7 @@ def _update_text_surface(self) -> None: self.text_rect = self.text_surface.get_rect(x=self.x, y=self.y) def center(self, pos: tuple[int, int]) -> None: - self.x = pos[0] - self.width // 2 - self.y = pos[1] - self.height // 2 + super().center(pos) self._update_text_surface() def draw(self, surface: pygame.Surface) -> None: From 8f78bb51c8f788935131887ee14e2a13899c8358 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 21:35:35 -0700 Subject: [PATCH 14/24] Add colorama for terminal title support in Game class --- engine/core/__init__.py | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/engine/core/__init__.py b/engine/core/__init__.py index f62c45c..32ab198 100644 --- a/engine/core/__init__.py +++ b/engine/core/__init__.py @@ -14,6 +14,7 @@ import tkinter.messagebox import uuid import os +import colorama from typing import Optional, Any, Union @@ -419,6 +420,9 @@ def __init__( self.screen: pygame.Surface = pygame.display.set_mode(self.wsize, display_flags) pygame.display.set_caption(title) + if sys.stdout.isatty(): + print(colorama.ansi.set_title(title)) + self.set_icon(icon_path) pygame.mouse.set_visible(cursor_visible) From 342b10a778e65ccb2256547797df7bf3370d8dcf Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 21:37:16 -0700 Subject: [PATCH 15/24] Add docstrings to center() methods in Entity and Text classes --- engine/core/__init__.py | 7 +++++++ engine/core/text.py | 7 +++++++ 2 files changed, 14 insertions(+) diff --git a/engine/core/__init__.py b/engine/core/__init__.py index 32ab198..8d629fe 100644 --- a/engine/core/__init__.py +++ b/engine/core/__init__.py @@ -175,6 +175,13 @@ def _setparent(self, parent: "Scene") -> None: self.parent = parent def center(self, pos: tuple[int, int]) -> None: + """ + Center the entity on a position. + + Args: + pos (tuple[int, int]): The (x, y) point to center the entity on. + """ + self.x = pos[0] - self.width // 2 self.y = pos[1] - self.height // 2 self._update_rect() diff --git a/engine/core/text.py b/engine/core/text.py index e537220..83db965 100644 --- a/engine/core/text.py +++ b/engine/core/text.py @@ -80,6 +80,13 @@ def _update_text_surface(self) -> None: self.text_rect = self.text_surface.get_rect(x=self.x, y=self.y) def center(self, pos: tuple[int, int]) -> None: + """ + Center the text on a position and rebuild its rendered surface. + + Args: + pos (tuple[int, int]): The (x, y) point to center the text on. + """ + super().center(pos) self._update_text_surface() From ea1eaec70143b9a106fd2b9336bb5d15c34d68a0 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 21:46:10 -0700 Subject: [PATCH 16/24] Refactor logger function to improve readability and maintainability --- engine/logger.py | 18 +++++++++++++----- 1 file changed, 13 insertions(+), 5 deletions(-) diff --git a/engine/logger.py b/engine/logger.py index d447805..8028cae 100644 --- a/engine/logger.py +++ b/engine/logger.py @@ -6,6 +6,7 @@ """ import inspect +import sys from enum import Enum from typing import Any @@ -52,10 +53,17 @@ def logger(message: str, *, status: Status = Status.INFO) -> None: """ source = _get_caller_module().upper() + is_tty: bool = sys.stdout.isatty() - if status == Status.CRITICAL: - print(Fore.RED, end="") - elif status == Status.WARNING: - print(Fore.YELLOW, end="") + if is_tty: + if status == Status.CRITICAL: + print(Fore.RED, end="") + elif status == Status.WARNING: + print(Fore.YELLOW, end="") - print(f"({status.value}) {source}: {message}{Style.RESET_ALL}") + print(f"({status.value}) {source}: {message}", end="") + + if is_tty: + print(Style.RESET_ALL, end="") + + print() From 7463def9388eb8e9817037b96cb045280dc3785d Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 21:58:02 -0700 Subject: [PATCH 17/24] Use positional args for Font.render for pygame compatibility Font.render only accepts keyword arguments on pygame-ce, not upstream pygame, causing a TypeError on systems with vanilla pygame installed. Switch to positional arguments, which are valid on both variants. Note that upstream pygame compatibility is not a requirement. The engine targets pygame-ce. This change is a low-cost portability improvement, not a supported configuration. (See #6) --- engine/core/text.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/engine/core/text.py b/engine/core/text.py index 83db965..687a1d7 100644 --- a/engine/core/text.py +++ b/engine/core/text.py @@ -75,7 +75,7 @@ def _update_text_surface(self) -> None: """ self.text_surface = self.font.render( - self.text, antialias=self.antialias, color=self.color, bgcolor=self.bgcolor + self.text, self.antialias, self.color, self.bgcolor ) self.text_rect = self.text_surface.get_rect(x=self.x, y=self.y) From 692b05a293b877ea3611c08c651c31a076fad39c Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 22:01:40 -0700 Subject: [PATCH 18/24] Fix terminal title printing in Game class to avoid newline --- engine/core/__init__.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/engine/core/__init__.py b/engine/core/__init__.py index 8d629fe..7e6d73f 100644 --- a/engine/core/__init__.py +++ b/engine/core/__init__.py @@ -428,7 +428,10 @@ def __init__( pygame.display.set_caption(title) if sys.stdout.isatty(): - print(colorama.ansi.set_title(title)) + print( + colorama.ansi.set_title(title), + end="" + ) self.set_icon(icon_path) From adb051f656fee796d70e27c88c768d64749b31fd Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 22:03:00 -0700 Subject: [PATCH 19/24] Add newline after ABS Engine version line to separate it from logs --- engine/core/__init__.py | 1 + 1 file changed, 1 insertion(+) diff --git a/engine/core/__init__.py b/engine/core/__init__.py index 7e6d73f..5909237 100644 --- a/engine/core/__init__.py +++ b/engine/core/__init__.py @@ -25,6 +25,7 @@ print( f"ABS Engine v{version} (Python {sys.version_info.major}.{sys.version_info.minor}.{sys.version_info.micro}, pygame {pygame.ver})" + "\n" ) From 939cb4693ac779e14c71f5906390560e77bc35d6 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 22:18:40 -0700 Subject: [PATCH 20/24] Add Release Version Guard workflow to enforce version bump on release PRs --- .github/workflows/release-version-guard.yml | 83 +++++++++++++++++++++ 1 file changed, 83 insertions(+) create mode 100644 .github/workflows/release-version-guard.yml diff --git a/.github/workflows/release-version-guard.yml b/.github/workflows/release-version-guard.yml new file mode 100644 index 0000000..a5f9bfb --- /dev/null +++ b/.github/workflows/release-version-guard.yml @@ -0,0 +1,83 @@ +name: Release Version Guard + +on: + pull_request: + types: [opened, reopened, synchronize, edited, labeled, unlabeled] + +permissions: + contents: read + pull-requests: read + issues: write + +jobs: + check-version-bump: + name: Check Version Bump + runs-on: ubuntu-latest + if: github.event.pull_request.base.ref == 'main' + + steps: + - name: Determine release label + id: label + run: | + HAS_RELEASE_LABEL=false + + for label in ${{ join(github.event.pull_request.labels.*.name, ' ') }}; do + if [ "$label" = "release" ]; then + HAS_RELEASE_LABEL=true + fi + done + + echo "Has release label: $HAS_RELEASE_LABEL" + echo "release=$HAS_RELEASE_LABEL" >> "$GITHUB_OUTPUT" + + - name: Checkout code + if: steps.label.outputs.release == 'true' + uses: actions/checkout@v5 + with: + fetch-depth: 0 + + - name: Compare versions + if: steps.label.outputs.release == 'true' + id: compare + run: | + get_version() { + git show "$1:engine/version.py" \ + | sed -n 's/^__version__[[:space:]]*=[[:space:]]*["'"'"']\(.*\)["'"'"'].*/\1/p' + } + + OLD_VERSION=$(get_version "${{ github.event.pull_request.base.sha }}") + NEW_VERSION=$(get_version HEAD) + + echo "Base (main) version: '$OLD_VERSION'" + echo "PR version: '$NEW_VERSION'" + + if [ -z "$NEW_VERSION" ]; then + echo "Could not read __version__ from engine/version.py" + exit 1 + fi + + if [ "$NEW_VERSION" = "$OLD_VERSION" ]; then + echo "bumped=false" >> "$GITHUB_OUTPUT" + else + echo "bumped=true" >> "$GITHUB_OUTPUT" + fi + + echo "old_version=$OLD_VERSION" >> "$GITHUB_OUTPUT" + + - name: Comment if version not bumped + if: steps.label.outputs.release == 'true' && steps.compare.outputs.bumped == 'false' + uses: actions/github-script@v7 + with: + script: | + await github.rest.issues.createComment({ + owner: context.repo.owner, + repo: context.repo.repo, + issue_number: context.payload.pull_request.number, + body: "@${{ github.event.pull_request.user.login }} This **release** PR does not bump `engine/version.py` (still `${{ steps.compare.outputs.old_version }}`). Update `__version__` before merging." + }); + + - name: Fail if version not bumped + if: steps.label.outputs.release == 'true' && steps.compare.outputs.bumped == 'false' + run: | + echo "Release PR must bump engine/version.py before merging." + exit 1 From f5560b0b1c2fb1830c887208fccdde038a220698 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 22:21:59 -0700 Subject: [PATCH 21/24] Fix formatting --- engine/core/__init__.py | 5 +---- engine/core/text.py | 4 +--- 2 files changed, 2 insertions(+), 7 deletions(-) diff --git a/engine/core/__init__.py b/engine/core/__init__.py index 5909237..cd7a6ba 100644 --- a/engine/core/__init__.py +++ b/engine/core/__init__.py @@ -429,10 +429,7 @@ def __init__( pygame.display.set_caption(title) if sys.stdout.isatty(): - print( - colorama.ansi.set_title(title), - end="" - ) + print(colorama.ansi.set_title(title), end="") self.set_icon(icon_path) diff --git a/engine/core/text.py b/engine/core/text.py index 687a1d7..cd129c9 100644 --- a/engine/core/text.py +++ b/engine/core/text.py @@ -74,9 +74,7 @@ def _update_text_surface(self) -> None: text, color, bgcolor, antialias, and position. """ - self.text_surface = self.font.render( - self.text, self.antialias, self.color, self.bgcolor - ) + self.text_surface = self.font.render(self.text, self.antialias, self.color, self.bgcolor) self.text_rect = self.text_surface.get_rect(x=self.x, y=self.y) def center(self, pos: tuple[int, int]) -> None: From 8441ad4d16431c12f9a13abdd46351a74c353a18 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 22:27:54 -0700 Subject: [PATCH 22/24] Upgrade github-script action to v8 in PR and release version guard workflows --- .github/workflows/pr-target-guard.yml | 2 +- .github/workflows/release-version-guard.yml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/pr-target-guard.yml b/.github/workflows/pr-target-guard.yml index 0b5eaf7..136717a 100644 --- a/.github/workflows/pr-target-guard.yml +++ b/.github/workflows/pr-target-guard.yml @@ -38,7 +38,7 @@ jobs: - name: Comment warning on PR if: steps.check.outputs.WARN == 'true' - uses: actions/github-script@v7 + uses: actions/github-script@v8 with: script: | await github.rest.issues.createComment({ diff --git a/.github/workflows/release-version-guard.yml b/.github/workflows/release-version-guard.yml index a5f9bfb..4d6535b 100644 --- a/.github/workflows/release-version-guard.yml +++ b/.github/workflows/release-version-guard.yml @@ -66,7 +66,7 @@ jobs: - name: Comment if version not bumped if: steps.label.outputs.release == 'true' && steps.compare.outputs.bumped == 'false' - uses: actions/github-script@v7 + uses: actions/github-script@v8 with: script: | await github.rest.issues.createComment({ From 93150a363cfe68a6fc59767a27670c0f535e8795 Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 22:32:18 -0700 Subject: [PATCH 23/24] Update pull request permissions from read to write in workflow files --- .github/workflows/pr-target-guard.yml | 2 +- .github/workflows/release-version-guard.yml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/pr-target-guard.yml b/.github/workflows/pr-target-guard.yml index 136717a..359c825 100644 --- a/.github/workflows/pr-target-guard.yml +++ b/.github/workflows/pr-target-guard.yml @@ -6,7 +6,7 @@ on: permissions: contents: read - pull-requests: read + pull-requests: write issues: write jobs: diff --git a/.github/workflows/release-version-guard.yml b/.github/workflows/release-version-guard.yml index 4d6535b..9e18536 100644 --- a/.github/workflows/release-version-guard.yml +++ b/.github/workflows/release-version-guard.yml @@ -6,7 +6,7 @@ on: permissions: contents: read - pull-requests: read + pull-requests: write issues: write jobs: From 3578ae8736d19054e29de11977c80f21857f9cbb Mon Sep 17 00:00:00 2001 From: "Nathan C." <149914029+Natuworkguy@users.noreply.github.com> Date: Fri, 7 Aug 2026 22:39:49 -0700 Subject: [PATCH 24/24] Enhance Release Version Guard to request changes and dismiss prior reviews if version not bumped --- .github/workflows/release-version-guard.yml | 33 +++++++++++++++++++-- 1 file changed, 30 insertions(+), 3 deletions(-) diff --git a/.github/workflows/release-version-guard.yml b/.github/workflows/release-version-guard.yml index 9e18536..84504a6 100644 --- a/.github/workflows/release-version-guard.yml +++ b/.github/workflows/release-version-guard.yml @@ -64,18 +64,45 @@ jobs: echo "old_version=$OLD_VERSION" >> "$GITHUB_OUTPUT" - - name: Comment if version not bumped + - name: Request changes if version not bumped if: steps.label.outputs.release == 'true' && steps.compare.outputs.bumped == 'false' uses: actions/github-script@v8 with: script: | - await github.rest.issues.createComment({ + await github.rest.pulls.createReview({ owner: context.repo.owner, repo: context.repo.repo, - issue_number: context.payload.pull_request.number, + pull_number: context.payload.pull_request.number, + event: "REQUEST_CHANGES", body: "@${{ github.event.pull_request.user.login }} This **release** PR does not bump `engine/version.py` (still `${{ steps.compare.outputs.old_version }}`). Update `__version__` before merging." }); + - name: Dismiss prior request-changes review once bumped + if: steps.label.outputs.release == 'true' && steps.compare.outputs.bumped == 'true' + uses: actions/github-script@v8 + with: + script: | + const pull_number = context.payload.pull_request.number; + const { data: reviews } = await github.rest.pulls.listReviews({ + owner: context.repo.owner, + repo: context.repo.repo, + pull_number, + }); + for (const review of reviews) { + if ( + review.user.login === "github-actions[bot]" && + review.state === "CHANGES_REQUESTED" + ) { + await github.rest.pulls.dismissReview({ + owner: context.repo.owner, + repo: context.repo.repo, + pull_number, + review_id: review.id, + message: "`engine/version.py` bumped — clearing the version guard.", + }); + } + } + - name: Fail if version not bumped if: steps.label.outputs.release == 'true' && steps.compare.outputs.bumped == 'false' run: |