LoafyLemon
93c899cd44
* Implemented wheelmenu for the wardrobe * Implemented hide/show functions for singular items * Implemented quick jumps * Fixed wheelmenu overflowing screen positions (needed a clamp)
164 lines
5.6 KiB
Plaintext
164 lines
5.6 KiB
Plaintext
init python in wheelmenu:
|
|
import math
|
|
|
|
reference_num_buttons = 32
|
|
reference_radius = 0.5
|
|
|
|
def pos(num_buttons):
|
|
num_buttons = max(num_buttons, 2)
|
|
radius = reference_radius * (num_buttons / reference_num_buttons) ** 0.5
|
|
angle_step = 2 * math.pi / num_buttons
|
|
start_angle = angle_step / 2 if num_buttons % 2 else 0
|
|
positions = [(min(max(0.5 + math.cos(start_angle + i * angle_step) * radius, 0.0), 1.0),
|
|
min(max(0.5 + math.sin(start_angle + i * angle_step) * radius, 0.0), 1.0))
|
|
for i in range(num_buttons)]
|
|
return positions
|
|
|
|
def button(displayable, action, condition, disabled, **kwargs):
|
|
"""
|
|
displayable - Ren'Py displayable
|
|
action - Ren'Py screen action
|
|
condition - Boolean
|
|
disabled - Boolean
|
|
"""
|
|
|
|
if condition:
|
|
if action is None or disabled:
|
|
return renpy.store.Button(renpy.store.Transform(displayable, matrixcolor=renpy.store.SaturationMatrix(0)*renpy.store.BrightnessMatrix(-0.25)*renpy.store.OpacityMatrix(0.5)), action=action, style="wheelmenu_disabled_button", **kwargs)
|
|
return renpy.store.Button(displayable, action=action, style="wheelmenu_button", **kwargs)
|
|
else:
|
|
return None
|
|
|
|
def clamp_to_screen(num_buttons, pos):
|
|
num_buttons = max(num_buttons, 2)
|
|
radius = reference_radius * (num_buttons / reference_num_buttons) ** 0.5
|
|
diameter = int(radius * min(renpy.store.config.screen_width, renpy.store.config.screen_height))
|
|
x = max(diameter, min(renpy.store.config.screen_width - diameter, pos[0]))
|
|
y = max(diameter, min(renpy.store.config.screen_height - diameter, pos[1]))
|
|
return (x, y)
|
|
|
|
init python:
|
|
def create_wheelmenu(elements):
|
|
# Proxy function; We cannot evaluate in a named store without side effects.
|
|
|
|
buttons = []
|
|
for name, (displayable, action, *tail) in elements.items():
|
|
if tail:
|
|
condition = eval(tail[0])
|
|
disabled = eval(tail[1]) if len(tail) > 1 else False
|
|
else:
|
|
condition = True
|
|
disabled = False
|
|
|
|
if not condition and disabled:
|
|
continue
|
|
|
|
buttons.append(wheelmenu.button(displayable, action, condition, disabled, tooltip=name))
|
|
|
|
if not buttons:
|
|
return None
|
|
|
|
return None if not buttons else tuple(zip(buttons, wheelmenu.pos(len(buttons)))) # Nonhashable types cannot be used in a screen, so we use a tuple instead.
|
|
|
|
config.per_frame_screens.append("wheelmenu")
|
|
|
|
label wheelmenu(btns, ret, pos=None):
|
|
play sound "sounds/qubodup-click1.ogg"
|
|
call screen wheelmenu(btns, pos)
|
|
|
|
jump expression ret
|
|
|
|
screen wheelmenu(btns, pos=None, close_action=Return("Close")):
|
|
layer "interface"
|
|
tag wheelmenu
|
|
zorder 1
|
|
style_prefix "wheelmenu"
|
|
|
|
$ mpos = renpy.get_mouse_pos()
|
|
default start_pos = wheelmenu.clamp_to_screen(len(btns), pos or mpos)
|
|
|
|
use close_button_background(action=close_action, keysym="game_menu")
|
|
|
|
window at wheelmenu_anim:
|
|
id "wheelmenu"
|
|
pos start_pos
|
|
|
|
for btn, pos in btns:
|
|
add btn pos pos
|
|
|
|
add "wheelmenu_genie" align (0.5, 0.5) at transform:
|
|
subpixel True
|
|
xysize (48, 48)
|
|
yzoom (1 if mpos[0] < start_pos[0] else -1)
|
|
rotate (math.degrees(math.atan2(mpos[1] - start_pos[1], mpos[0] - start_pos[0])) + 360) % 360 - 180
|
|
|
|
style wheelmenu_window is empty:
|
|
background Transform("wheelmenu_gradient", align=(0.5, 0.5), xysize=(200, 200))
|
|
maximum (400, 400)
|
|
anchor (0.5, 0.5)
|
|
|
|
style wheelmenu_button is empty:
|
|
background Transform("wheelmenu_button", xysize=(48,48))
|
|
hover_background At(Transform("wheelmenu_button_opaque", xysize=(48,48)), wheelmenu_hover_anim)
|
|
hover_sound "sounds/qubodup-hover1.ogg"
|
|
activate_sound "sounds/qubodup-click2.ogg"
|
|
xysize (48, 48)
|
|
anchor (0.5, 0.5)
|
|
|
|
style wheelmenu_disabled_button is wheelmenu_button:
|
|
background Transform("wheelmenu_button", xysize=(48,48), matrixcolor=BrightnessMatrix(0.2))
|
|
hover_background At(Transform("wheelmenu_button_opaque", xysize=(48,48), matrixcolor=BrightnessMatrix(0.2)), wheelmenu_hover_anim)
|
|
xysize (48, 48)
|
|
anchor (0.5, 0.5)
|
|
|
|
style wheelmenu_window_text is default:
|
|
anchor (0.5, 0.5)
|
|
color "#fff"
|
|
size 10
|
|
outlines [(1, "#00000080", 1, 0)]
|
|
|
|
style wheelmenu_button_text is wheelmenu_text
|
|
|
|
transform wheelmenu_anim:
|
|
on show:
|
|
zoom 0.0
|
|
alpha 0.0
|
|
easein_back 0.2 zoom 1.0 alpha 1.0
|
|
on hide:
|
|
easeout 0.15 zoom 0.0 alpha 0.0
|
|
|
|
transform wheelmenu_hover_anim(t=2.0, strength=0.2, pause=0.0):
|
|
matrixcolor BrightnessMatrix(value=0.0)
|
|
linear t/2 matrixcolor BrightnessMatrix(value=strength)
|
|
linear t/2 matrixcolor BrightnessMatrix(value=0.0)
|
|
pause pause
|
|
repeat
|
|
|
|
# transform tooltip_follow:
|
|
# events False
|
|
# function tooltip_func
|
|
|
|
# init python:
|
|
|
|
# def tooltip_func(trans, st, at):
|
|
# x, y = renpy.get_mouse_pos()
|
|
|
|
# if trans.pos is not (x, y):
|
|
# cw, ch = trans.child.window_size
|
|
|
|
# xanchor = 1.0 if (x + int(cw)) > (config.screen_width) else 0.0
|
|
# yanchor = 1.0 if (y + int(ch)) > (config.screen_height) else 0.0
|
|
|
|
# xoffset = 18 if xanchor else 0
|
|
# yoffset = 24 if yanchor else 0
|
|
# trans.pos = (x, y)
|
|
# trans.anchor = (xanchor, yanchor)
|
|
# trans.offset = (xoffset, yoffset)
|
|
|
|
# return 0
|
|
|
|
# if not renpy.android:
|
|
|
|
# config.always_shown_screens.append("tooltip")
|
|
# config.per_frame_screens.append("tooltip")
|