# tk_Basic_Optimizations_Demo.py import tkinter as tk canvas_width = 600 canvas_height = 600 pan_offset_x = 0 scene_objects = [ [50, 50, 50, 0, 0], [150, 70, 40, 1, 0], [250, 60, 60, 0, 1], [350, 80, 30, 1, 1], [450, 90, 55, 0, 2], [550, 100, 45, 1, 2], [100, 250, 70, 0, 0], [200, 270, 50, 1, 0], [300, 260, 80, 0, 1], [400, 280, 35, 1, 1], [500, 290, 65, 0, 2], [50, 450, 60, 0, 0], [150, 470, 45, 1, 0], [250, 460, 75, 0, 1], [350, 480, 38, 1, 1], [450, 490, 60, 0, 2], [550, 500, 50, 1, 2] ] zsort_triangles = [ [60, 50, 50, 2, 0], [80, 150, 50, 2, 0], [220, 120, 60, 2, 1], [400, 70, 70, 2, 2], [520, 150, 80, 2, 3], [100, 350, 90, 2, 4], [300, 450, 100, 2, 5], [580, 300, 70, 2, 6], [180, 270, 60, 2, 7], [480, 370, 80, 2, 8], [360, 240, 90, 2, 9], [60, 50, 15, 2, 0], [100, 70, 10, 2, 1], [140, 90, 12, 2, 2], [180, 110, 8, 2, 3], [220, 130, 14, 2, 4], [260, 150, 9, 2, 5], [300, 170, 13, 2, 6], [340, 190, 11, 2, 7], [380, 210, 10, 2, 8], [420, 230, 12, 2, 9], [460, 250, 14, 2, 10], [500, 270, 9, 2, 11], [540, 290, 13, 2, 12], [580, 310, 11, 2, 13], [100, 350, 10, 2, 14], [140, 370, 12, 2, 15], [180, 390, 8, 2, 16], [220, 410, 14, 2, 17], [260, 430, 9, 2, 18], [300, 450, 13, 2, 19] ] occluder = [200, 200, 200, "gray"] frustum = [120, 120, 480, 480] def get_wrapped_x(x): return (x + pan_offset_x) % canvas_width def get_bounding_box(x, y, size): return (x, y, x + size, y + size) def is_inside_frustum(x, y, size): left, top, right, bottom = get_bounding_box(get_wrapped_x(x), y, size) return not (right < frustum[0] or left > frustum[2] or bottom < frustum[1] or top > frustum[3]) def is_occluded(x, y, size): left, top, right, bottom = get_bounding_box(get_wrapped_x(x), y, size) return (left >= occluder[0] and top >= occluder[1] and right <= occluder[0] + occluder[2] and bottom <= occluder[1] + occluder[2]) def draw_object(x, y, size, shape_type, dashed=False, stationary=False): x = x if stationary else get_wrapped_x(x) dash = (2, 2) if dashed else None outline = "black" if shape_type == 0: # Rectangle fill = "blue" canvas.create_rectangle(x, y, x + size, y + size, fill=fill if not dashed else "", outline=outline, dash=dash) elif shape_type == 1: # Oval fill = "red" canvas.create_oval(x, y, x + size, y + size, fill=fill if not dashed else "", outline=outline, dash=dash) elif shape_type == 2: # Triangle fill = "green" points = [ x + size / 2, y, x, y + size, x + size, y + size ] canvas.create_polygon(points, fill=fill, outline=outline,) def draw_square(x, y, size, fill_color="blue"): canvas.create_rectangle(x, y, x + size, y + size, fill=fill_color, outline="black") def render_scene(): canvas.delete("all") canvas.create_text(300, 20, text="Basic Optimizations Demo", fill="black", font=("Arial", 12)) draw_square(occluder[0], occluder[1], occluder[2], occluder[3]) canvas.create_text(occluder[0], occluder[1], text="Occluder", fill="black", anchor="s") canvas.create_rectangle(frustum[0], frustum[1], frustum[2], frustum[3], outline="cyan", width=2) canvas.create_text(frustum[0], frustum[1], text="Frustum", fill="cyan", anchor="s") all_objects = scene_objects + zsort_triangles if enable_zsort.get(): all_objects = sorted(all_objects, key=lambda o: o[2]) # ascending else: all_objects = sorted(all_objects, key=lambda o: -o[2]) # descending for obj in all_objects: x, y, size, shape_type, _ = obj stationary = (shape_type == 2) frustum_culled = enable_frustum.get() and not is_inside_frustum(x, y, size) occlusion_culled = enable_occlusion.get() and is_occluded(x, y, size) dashed = frustum_culled or occlusion_culled draw_object(x, y, size, shape_type, dashed=dashed, stationary=stationary) def auto_pan(): global pan_offset_x pan_offset_x -= 2 render_scene() root.after(20, auto_pan) root = tk.Tk() root.title("Basic Optimizations Demo") root.geometry("800x600+0+0") canvas = tk.Canvas(root, width=canvas_width, height=canvas_height, bg="white") canvas.pack(side=tk.LEFT, fill=tk.BOTH, expand=True) control_frame = tk.Frame(root) control_frame.pack(side=tk.RIGHT, fill=tk.Y) enable_frustum = tk.BooleanVar() enable_occlusion = tk.BooleanVar() enable_zsort = tk.BooleanVar() tk.Checkbutton(control_frame, text="Frustum Culling", variable=enable_frustum, command=render_scene).pack(anchor="w", padx=10, pady=5) tk.Checkbutton(control_frame, text="Occlusion Culling", variable=enable_occlusion, command=render_scene).pack(anchor="w", padx=10, pady=5) tk.Checkbutton(control_frame, text="Z-Index Sorting", variable=enable_zsort, command=render_scene).pack(anchor="w", padx=10, pady=5) render_scene() auto_pan() root.mainloop()