Files
Grovewright/game/scripts/figures.gd
T
Steven Wroblewski d2da661452 Startmenü, fremde Figuren und Statuszeile
Das Startmenü fragt nach dem Namen und bietet allein spielen, die Welt
öffnen oder beitreten. Die Figuren der anderen Spieler gleiten zu ihrer
neuesten Position und tragen ihren Namen. Die Anzeige füllt Werte in
Meldungen ein und hat eine Statuszeile. Die Texte für Menü und Netzwerk
gibt es auf Deutsch und Englisch.

Co-Authored-By: Claude Haiku 4.5 <noreply@anthropic.com>
2026-10-01 21:40:57 +02:00

64 lines
1.7 KiB
GDScript

class_name Figures
extends Node2D
## The figures of the other players, with their names. A new position comes
## over the network about ten times a second; in between, each figure glides
## toward the latest one.
## How quickly a figure closes the gap to its latest position, per second.
const GLIDE := 15.0
const COLOR := Color(0.55, 0.8, 0.95)
const OUTLINE := Color(0.05, 0.1, 0.15)
const NAME_SIZE := 8
const NAME_WIDTH := 80.0
var session: GwSession
var _shown: Dictionary[int, Vector2] = {}
var _latest: Dictionary[int, Vector2] = {}
## Moves the figure of `player` toward `position`. A figure that was not
## shown yet appears there at once.
func place(player: int, position: Vector2) -> void:
if not _shown.has(player):
_shown[player] = position
_latest[player] = position
queue_redraw()
## Removes the figure of `player`.
func forget(player: int) -> void:
_shown.erase(player)
_latest.erase(player)
queue_redraw()
func clear() -> void:
_shown.clear()
_latest.clear()
queue_redraw()
## Where the figure of `player` is shown, or Vector2.INF if it is not.
func shown_at(player: int) -> Vector2:
return _shown.get(player, Vector2.INF)
func _process(delta: float) -> void:
if _shown.is_empty():
return
var weight := minf(1.0, GLIDE * delta)
for player in _shown:
_shown[player] = _shown[player].lerp(_latest[player], weight)
queue_redraw()
func _draw() -> void:
var font := ThemeDB.fallback_font
for player in _shown:
var at := _shown[player]
draw_circle(at, Avatar.RADIUS + 1.0, OUTLINE)
draw_circle(at, Avatar.RADIUS, COLOR)
if session != null:
var label := Vector2(at.x - NAME_WIDTH / 2.0, at.y - Avatar.RADIUS - 3.0)
draw_string(font, label, session.player_name(player), HORIZONTAL_ALIGNMENT_CENTER, NAME_WIDTH, NAME_SIZE)