Files
taiko-editor/ui_utils.py

107 lines
3.6 KiB
Python

import pygame
import pygame.gfxdraw
import sys
# --- Colors (Bcut / Dark Theme) ---
COLOR_BG_ROOT = (19, 19, 19) # #131313
COLOR_BG_PANEL = (30, 30, 30) # #1E1E1E
COLOR_BORDER = (44, 44, 44) # #2C2C2C
COLOR_ACCENT = (255, 71, 87) # #FF4757 (Pinkish Red)
COLOR_ACCENT_HOVER = (255, 107, 129)
COLOR_TEXT_MAIN = (224, 224, 224) # #E0E0E0
COLOR_TEXT_DIM = (128, 128, 128) # #808080
COLOR_TIMELINE_BG = (25, 25, 25)
COLOR_TRACK_BG = (35, 35, 35)
class FontManager:
def __init__(self):
self.fonts = {}
# Try to find a good Chinese font
self.font_names = ['Microsoft YaHei', 'SimHei', 'PingFang SC', 'Segoe UI', 'Arial']
def get_font(self, size, bold=False):
key = (size, bold)
if key in self.fonts:
return self.fonts[key]
font = pygame.font.SysFont(self.font_names, size, bold=bold)
self.fonts[key] = font
return font
def draw_rounded_rect(surface, rect, color, radius=0.4, border_width=0):
"""
Draw a rectangle with rounded corners.
rect: tuple (x, y, w, h)
radius: float (0.0 to 1.0) or int (pixels)
"""
rect = pygame.Rect(rect)
color = pygame.Color(*color)
alpha = color.a
color.a = 0
pos = rect.topleft
rect.topleft = 0,0
rectangle = pygame.Surface(rect.size,pygame.SRCALPHA)
circle = pygame.Surface([min(rect.size)*3]*2,pygame.SRCALPHA)
pygame.draw.ellipse(circle,(0,0,0),circle.get_rect(),0)
circle = pygame.transform.smoothscale(circle,[int(min(rect.size)*radius)]*2)
radius = rectangle.blit(circle,(0,0))
radius.bottomright = rect.bottomright
rectangle.blit(circle,radius)
radius.topright = rect.topright
rectangle.blit(circle,radius)
radius.bottomleft = rect.bottomleft
rectangle.blit(circle,radius)
rectangle.fill((0,0,0),rect.inflate(-radius.w,0))
rectangle.fill((0,0,0),rect.inflate(0,-radius.h))
rectangle.fill(color, special_flags=pygame.BLEND_RGBA_MAX)
rectangle.fill((255, 255, 255, alpha), special_flags=pygame.BLEND_RGBA_MIN)
if border_width > 0:
# Simple border support (not perfect for rounded)
pygame.draw.rect(surface, color, pos, width=border_width) # Fallback
return surface.blit(rectangle, pos)
def draw_pill_btn(surface, text, rect, is_active, font_mgr):
color = COLOR_ACCENT if is_active else (60, 60, 60)
text_color = (255, 255, 255) if is_active else COLOR_TEXT_DIM
# Draw pill background
r = rect[3] // 2
# Left circle
pygame.gfxdraw.aacircle(surface, rect[0] + r, rect[1] + r, r, color)
pygame.gfxdraw.filled_circle(surface, rect[0] + r, rect[1] + r, r, color)
# Right circle
pygame.gfxdraw.aacircle(surface, rect[0] + rect[2] - r, rect[1] + r, r, color)
pygame.gfxdraw.filled_circle(surface, rect[0] + rect[2] - r, rect[1] + r, r, color)
# Center rect
pygame.draw.rect(surface, color, (rect[0] + r, rect[1], rect[2] - 2*r, rect[3]))
# Text
font = font_mgr.get_font(12, bold=True)
txt_surf = font.render(text, True, text_color)
text_rect = txt_surf.get_rect(center=(rect[0] + rect[2]//2, rect[1] + rect[3]//2))
surface.blit(txt_surf, text_rect)
def draw_icon_play(surface, center, size, color):
x, y = center
points = [
(x - size//3, y - size//2),
(x - size//3, y + size//2),
(x + size//2, y)
]
pygame.draw.polygon(surface, color, points)
def draw_icon_pause(surface, center, size, color):
x, y = center
w = size // 3
h = size
pygame.draw.rect(surface, color, (x - w - 2, y - h//2, w, h))
pygame.draw.rect(surface, color, (x + 2, y - h//2, w, h))