Cône de vision
Vingt-huit rayons déployés en éventail vers la souris. Chacun devient rouge là où il touche un mur, c'est la ligne de vue dans sa forme la plus simple.
L'éditeur ci-dessus fait tourner ce projet. Changez une ligne et il se recharge.
Classes Godot utilisées
RayCast2DLine2DStaticBody2D
Le code
scripts/main.gd
extends Node
const RAYS: int = 28
const SPREAD: float = 1.0
const LENGTH: float = 560.0
const CLEAR_COLOR: Color = Color(0.55, 0.65, 0.95, 0.35)
const HIT_COLOR: Color = Color(0.98, 0.5, 0.5, 0.9)
var origin: Vector2
var rays: Array[RayCast2D] = []
var lines: Array[Line2D] = []
func _ready() -> void:
_add_background()
var view: Vector2 = get_viewport().get_visible_rect().size
origin = Vector2(view.x * 0.5, view.y * 0.78)
for at in [Vector2(view.x * 0.25, view.y * 0.4), Vector2(view.x * 0.6, view.y * 0.3), Vector2(view.x * 0.78, view.y * 0.55)]:
_add_wall(at, Vector2(160, 40))
for i in RAYS:
var ray: RayCast2D = RayCast2D.new()
ray.position = origin
add_child(ray)
rays.append(ray)
var line: Line2D = Line2D.new()
line.width = 2.0
add_child(line)
lines.append(line)
add_child(_make_circle(origin, 16.0, Color('#8eef97')))
print('the cone follows the mouse, a ray turns red where it hits a wall')
func _process(_delta: float) -> void:
var aim: float = (get_viewport().get_mouse_position() - origin).angle()
for i in RAYS:
var angle: float = aim + (float(i) / (RAYS - 1) - 0.5) * SPREAD
var direction: Vector2 = Vector2(cos(angle), sin(angle))
rays[i].target_position = direction * LENGTH
rays[i].force_raycast_update()
var hit: bool = rays[i].is_colliding()
var to: Vector2 = rays[i].get_collision_point() if hit else origin + direction * LENGTH
lines[i].points = PackedVector2Array([origin, to])
lines[i].default_color = HIT_COLOR if hit else CLEAR_COLOR
func _add_wall(center: Vector2, size: Vector2) -> void:
var shape: RectangleShape2D = RectangleShape2D.new()
shape.size = size
var collision: CollisionShape2D = CollisionShape2D.new()
collision.shape = shape
var rect: Polygon2D = Polygon2D.new()
rect.polygon = PackedVector2Array([-size * 0.5, Vector2(size.x, -size.y) * 0.5, size * 0.5, Vector2(-size.x, size.y) * 0.5])
rect.color = Color('#2a2f3d')
var wall: StaticBody2D = StaticBody2D.new()
wall.position = center
wall.add_child(rect)
wall.add_child(collision)
add_child(wall)
func _make_circle(at: Vector2, radius: float, color: Color) -> Polygon2D:
var points: PackedVector2Array = PackedVector2Array()
for i in 20:
points.append(Vector2(cos(TAU * i / 20.0), sin(TAU * i / 20.0)) * radius)
var circle: Polygon2D = Polygon2D.new()
circle.polygon = points
circle.color = color
circle.position = at
return circle
func _add_background() -> void:
var background: ColorRect = ColorRect.new()
background.color = Color('#12141a')
add_child(background)
background.set_anchors_and_offsets_preset(Control.PRESET_FULL_RECT)