from ursina import *
import random
R = 30
SPAWN_INTERVAL = 0.5
START_BATCH = 10
BATCH_GROWTH = 5
MIN_FPS = 10
app = Ursina(vsync=False, borderless=False, title='3D stress test')
window.fps_counter.enabled = False
window.color = color.black
pivot = Entity()
camera.parent = pivot
camera.position = (0, 10, -70)
camera.rotation_x = 10
info = Text(text='', origin=(-.5, .5), position=window.top_left + Vec2(.01, -.01), scale=1.3)
Text(text='SPACE - pause | R - reset | ESC - exit', origin=(-.5, -.5),
position=window.bottom_left + Vec2(.01, .01), scale=1)
cubes = []
fps = 60
batch = START_BATCH
spawning = True
spawn_timer = 0
text_timer = 0
def spawn():
e = Entity(
model=random.choice(('cube', 'sphere')),
color=color.random_color(),
position=Vec3(random.uniform(-R, R), random.uniform(-R, R), random.uniform(-R, R)),
scale=random.uniform(0.5, 2),
rotation=Vec3(random.uniform(0, 360), random.uniform(0, 360), random.uniform(0, 360))
)
cubes.append(e)
def update():
global fps, batch, spawning, spawn_timer, text_timer
if time.dt > 0:
fps = fps * 0.9 + (1 / time.dt) * 0.1
pivot.rotation_y += 15 * time.dt
for c in cubes:
c.rotation_y += 90 * time.dt
c.rotation_x += 45 * time.dt
if spawning:
spawn_timer += time.dt
if spawn_timer >= SPAWN_INTERVAL:
spawn_timer = 0
for _ in range(batch):
spawn()
batch += BATCH_GROWTH
if fps < MIN_FPS and len(cubes) > 100:
spawning = False
text_timer += time.dt
if text_timer >= 0.2:
text_timer = 0
info.text = f'FPS: {fps:.0f}\nObjects: {len(cubes)}\nNext batch: {batch}'
if not spawning:
info.text += '\nSpawn: STOPPED'
if fps >= 50:
info.color = color.green
elif fps >= 30:
info.color = color.yellow
else:
info.color = color.red
def input(key):
global spawning, batch
if key == 'space':
spawning = not spawning
elif key == 'r':
for c in cubes:
destroy(c)
cubes.clear()
batch = START_BATCH
spawning = True
elif key == 'escape':
application.quit()
app.run()