mirror of
https://github.com/Yonokid/PyTaiko.git
synced 2026-02-04 03:30:13 +01:00
3d model experiments
This commit is contained in:
21
PyTaiko.py
21
PyTaiko.py
@@ -2,6 +2,7 @@ import sqlite3
|
|||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
|
|
||||||
import pyray as ray
|
import pyray as ray
|
||||||
|
from raylib import CAMERA_ORTHOGRAPHIC
|
||||||
from raylib.defines import (
|
from raylib.defines import (
|
||||||
RL_FUNC_ADD,
|
RL_FUNC_ADD,
|
||||||
RL_ONE,
|
RL_ONE,
|
||||||
@@ -67,11 +68,18 @@ def main():
|
|||||||
ray.set_config_flags(ray.ConfigFlags.FLAG_MSAA_4X_HINT)
|
ray.set_config_flags(ray.ConfigFlags.FLAG_MSAA_4X_HINT)
|
||||||
ray.set_trace_log_level(ray.TraceLogLevel.LOG_WARNING)
|
ray.set_trace_log_level(ray.TraceLogLevel.LOG_WARNING)
|
||||||
|
|
||||||
|
camera = ray.Camera3D()
|
||||||
|
camera.position = ray.Vector3(0.0, 0.0, 10.0) # Camera position
|
||||||
|
camera.target = ray.Vector3(0.0, 0.0, 0.0) # Camera looking at point
|
||||||
|
camera.up = ray.Vector3(0.0, 1.0, 0.0) # Camera up vector
|
||||||
|
camera.fovy = screen_height # For orthographic, this acts as the view height
|
||||||
|
camera.projection = CAMERA_ORTHOGRAPHIC
|
||||||
|
|
||||||
ray.init_window(screen_width, screen_height, "PyTaiko")
|
ray.init_window(screen_width, screen_height, "PyTaiko")
|
||||||
if global_data.config["video"]["borderless"]:
|
if global_data.config["video"]["borderless"]:
|
||||||
ray.toggle_borderless_windowed()
|
ray.toggle_borderless_windowed()
|
||||||
if global_data.config["video"]["fullscreen"]:
|
if global_data.config["video"]["fullscreen"]:
|
||||||
ray.maximize_window()
|
ray.toggle_fullscreen()
|
||||||
|
|
||||||
current_screen = Screens.LOADING
|
current_screen = Screens.LOADING
|
||||||
|
|
||||||
@@ -104,18 +112,23 @@ def main():
|
|||||||
ray.rl_set_blend_factors_separate(RL_SRC_ALPHA, RL_ONE_MINUS_SRC_ALPHA, RL_ONE, RL_ONE_MINUS_SRC_ALPHA, RL_FUNC_ADD, RL_FUNC_ADD)
|
ray.rl_set_blend_factors_separate(RL_SRC_ALPHA, RL_ONE_MINUS_SRC_ALPHA, RL_ONE, RL_ONE_MINUS_SRC_ALPHA, RL_FUNC_ADD, RL_FUNC_ADD)
|
||||||
ray.set_exit_key(ray.KeyboardKey.KEY_A)
|
ray.set_exit_key(ray.KeyboardKey.KEY_A)
|
||||||
global_data.textures = load_all_textures_from_zip(Path('Graphics/lumendata/intermission.zip'))
|
global_data.textures = load_all_textures_from_zip(Path('Graphics/lumendata/intermission.zip'))
|
||||||
while not ray.window_should_close():
|
|
||||||
|
|
||||||
|
while not ray.window_should_close():
|
||||||
ray.begin_texture_mode(target)
|
ray.begin_texture_mode(target)
|
||||||
ray.begin_blend_mode(ray.BlendMode.BLEND_CUSTOM_SEPARATE)
|
ray.begin_blend_mode(ray.BlendMode.BLEND_CUSTOM_SEPARATE)
|
||||||
|
|
||||||
screen = screen_mapping[current_screen]
|
screen = screen_mapping[current_screen]
|
||||||
|
# Begin 3D mode with orthographic camera
|
||||||
|
|
||||||
if ray.is_key_pressed(ray.KeyboardKey.KEY_F11):
|
if ray.is_key_pressed(ray.KeyboardKey.KEY_F11):
|
||||||
ray.toggle_fullscreen()
|
ray.toggle_borderless_windowed()
|
||||||
|
|
||||||
next_screen = screen.update()
|
next_screen = screen.update()
|
||||||
ray.clear_background(ray.BLACK)
|
ray.clear_background(ray.BLACK)
|
||||||
screen.draw()
|
screen.draw()
|
||||||
|
ray.begin_mode_3d(camera)
|
||||||
|
screen.draw_3d()
|
||||||
|
ray.end_mode_3d()
|
||||||
|
|
||||||
if next_screen is not None:
|
if next_screen is not None:
|
||||||
current_screen = next_screen
|
current_screen = next_screen
|
||||||
@@ -129,7 +142,7 @@ def main():
|
|||||||
ray.draw_texture_pro(
|
ray.draw_texture_pro(
|
||||||
target.texture,
|
target.texture,
|
||||||
ray.Rectangle(0, 0, target.texture.width, -target.texture.height),
|
ray.Rectangle(0, 0, target.texture.width, -target.texture.height),
|
||||||
ray.Rectangle(0, 0, screen_width, screen_height),
|
ray.Rectangle(0, 0, ray.get_screen_width(), ray.get_screen_height()),
|
||||||
ray.Vector2(0,0),
|
ray.Vector2(0,0),
|
||||||
0,
|
0,
|
||||||
ray.WHITE
|
ray.WHITE
|
||||||
|
|||||||
@@ -11,14 +11,14 @@ class Background:
|
|||||||
def __init__(self, screen_width: int, screen_height: int):
|
def __init__(self, screen_width: int, screen_height: int):
|
||||||
self.screen_width = screen_width
|
self.screen_width = screen_width
|
||||||
self.screen_height = screen_height
|
self.screen_height = screen_height
|
||||||
self.donbg = DonBG.create(self.screen_width, self.screen_height, random.randint(6, 6), 1)
|
self.donbg = DonBG.create(self.screen_width, self.screen_height, random.randint(1, 6), 1)
|
||||||
self.bg_normal = BGNormal.create(self.screen_width, self.screen_height, random.randint(1, 5))
|
self.bg_normal = BGNormal.create(self.screen_width, self.screen_height, random.randint(1, 5))
|
||||||
self.bg_fever = BGFever.create(self.screen_width, self.screen_height, 4)
|
self.bg_fever = BGFever.create(self.screen_width, self.screen_height, 4)
|
||||||
self.footer = Footer(self.screen_width, self.screen_height, random.randint(1, 3))
|
self.footer = Footer(self.screen_width, self.screen_height, random.randint(1, 3))
|
||||||
self.is_clear = False
|
self.is_clear = False
|
||||||
def update(self, current_time_ms: float, is_clear: bool):
|
def update(self, current_time_ms: float, is_clear: bool):
|
||||||
self.is_clear = is_clear
|
self.is_clear = is_clear
|
||||||
self.donbg.update(current_time_ms, is_clear)
|
self.donbg.update(current_time_ms, self.is_clear)
|
||||||
self.bg_normal.update(current_time_ms)
|
self.bg_normal.update(current_time_ms)
|
||||||
self.bg_fever.update(current_time_ms)
|
self.bg_fever.update(current_time_ms)
|
||||||
def draw(self):
|
def draw(self):
|
||||||
@@ -38,7 +38,7 @@ class DonBG:
|
|||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def create(screen_width: int, screen_height: int, index: int, player_num: int):
|
def create(screen_width: int, screen_height: int, index: int, player_num: int):
|
||||||
map = [None, DonBG1, DonBG1, DonBG1, DonBG1, DonBG1, DonBG6]
|
map = [None, DonBG1, DonBG2, DonBG3, DonBG4, DonBG5, DonBG6]
|
||||||
selected_obj = map[index]
|
selected_obj = map[index]
|
||||||
return selected_obj(index, screen_width, screen_height, player_num)
|
return selected_obj(index, screen_width, screen_height, player_num)
|
||||||
|
|
||||||
@@ -75,14 +75,123 @@ class DonBG1(DonBGBase):
|
|||||||
def draw(self):
|
def draw(self):
|
||||||
texture_index = 0
|
texture_index = 0
|
||||||
if self.is_clear:
|
if self.is_clear:
|
||||||
texture_index = 2
|
texture_index = 3
|
||||||
top_texture = self.textures[self.name + f'_{self.player_num}p'][0 + texture_index]
|
top_texture = self.textures[self.name + f'_{self.player_num}p'][0 + texture_index]
|
||||||
for i in range(0, self.screen_width + top_texture.width, top_texture.width):
|
for i in range(0, self.screen_width + top_texture.width, top_texture.width):
|
||||||
ray.draw_texture(top_texture, i + int(self.move.attribute), 0, ray.WHITE)
|
ray.draw_texture(top_texture, i + int(self.move.attribute), 0, ray.WHITE)
|
||||||
|
|
||||||
|
wave_texture = self.textures[self.name + f'_{self.player_num}p'][1 + texture_index]
|
||||||
|
for i in range(0, self.screen_width + (wave_texture.width+80), wave_texture.width+80):
|
||||||
|
ray.draw_texture(wave_texture, i + int(self.move.attribute * ((wave_texture.width+80)/top_texture.width)) + 100, int(self.overlay_move.attribute), ray.WHITE)
|
||||||
|
|
||||||
|
texture = self.textures[self.name + f'_{self.player_num}p'][2 + texture_index]
|
||||||
|
for i in range(0, self.screen_width + texture.width + texture.width*5, texture.width):
|
||||||
|
ray.draw_texture(texture, i + int(self.move.attribute * (texture.width/top_texture.width)*3), int(self.overlay_move.attribute) + 105, ray.WHITE)
|
||||||
|
|
||||||
|
class DonBG2(DonBGBase):
|
||||||
|
def __init__(self, index: int, screen_width: int, screen_height: int, player_num: int):
|
||||||
|
super().__init__(index, screen_width, screen_height, player_num)
|
||||||
|
self.overlay_move = Animation.create_move(1500, start_position=0, total_distance=20, reverse_delay=0)
|
||||||
|
def update(self, current_time_ms: float, is_clear: bool):
|
||||||
|
super().update(current_time_ms, is_clear)
|
||||||
|
self.overlay_move.update(current_time_ms)
|
||||||
|
if self.overlay_move.is_finished:
|
||||||
|
self.overlay_move.restart()
|
||||||
|
def draw(self):
|
||||||
|
texture_index = 0
|
||||||
|
if self.is_clear:
|
||||||
|
texture_index = 2
|
||||||
|
top_texture = self.textures[self.name + f'_{self.player_num}p'][texture_index]
|
||||||
|
for i in range(0, self.screen_width + top_texture.width, top_texture.width):
|
||||||
|
ray.draw_texture(top_texture, i + int(self.move.attribute), 0, ray.WHITE)
|
||||||
|
|
||||||
texture = self.textures[self.name + f'_{self.player_num}p'][1 + texture_index]
|
texture = self.textures[self.name + f'_{self.player_num}p'][1 + texture_index]
|
||||||
for i in range(0, self.screen_width + texture.width, texture.width):
|
for i in range(0, self.screen_width + texture.width, texture.width):
|
||||||
ray.draw_texture(texture, i + int(self.move.attribute), int(self.overlay_move.attribute) - 50, ray.WHITE)
|
ray.draw_texture(texture, i + int(self.move.attribute), int(self.overlay_move.attribute) - 25, ray.WHITE)
|
||||||
|
|
||||||
|
class DonBG3(DonBGBase):
|
||||||
|
def __init__(self, index: int, screen_width: int, screen_height: int, player_num: int):
|
||||||
|
super().__init__(index, screen_width, screen_height, player_num)
|
||||||
|
duration = 266
|
||||||
|
bounce_distance = 40
|
||||||
|
self.bounce_up = Animation.create_move(duration, total_distance=-bounce_distance, ease_out='quadratic')
|
||||||
|
self.bounce_down = Animation.create_move(duration, total_distance=-bounce_distance, ease_in='quadratic', delay=self.bounce_up.duration)
|
||||||
|
self.overlay_move = Animation.create_move(duration*3, total_distance=20, reverse_delay=0, ease_in='quadratic', ease_out='quadratic', delay=self.bounce_up.duration+self.bounce_down.duration)
|
||||||
|
self.overlay_move_2 = Animation.create_move(duration*3, total_distance=20, reverse_delay=0, ease_in='quadratic', ease_out='quadratic', delay=self.bounce_up.duration+self.bounce_down.duration+self.overlay_move.duration)
|
||||||
|
|
||||||
|
def update(self, current_time_ms: float, is_clear: bool):
|
||||||
|
super().update(current_time_ms, is_clear)
|
||||||
|
self.bounce_up.update(current_time_ms)
|
||||||
|
self.bounce_down.update(current_time_ms)
|
||||||
|
self.overlay_move.update(current_time_ms)
|
||||||
|
self.overlay_move_2.update(current_time_ms)
|
||||||
|
if self.overlay_move_2.is_finished:
|
||||||
|
self.bounce_up.restart()
|
||||||
|
self.bounce_down.restart()
|
||||||
|
self.overlay_move.restart()
|
||||||
|
self.overlay_move_2.restart()
|
||||||
|
|
||||||
|
def draw(self):
|
||||||
|
texture_index = 0
|
||||||
|
if self.is_clear:
|
||||||
|
texture_index = 2
|
||||||
|
top_texture = self.textures[self.name + f'_{self.player_num}p'][0 + texture_index]
|
||||||
|
for i in range(0, self.screen_width + top_texture.width, top_texture.width):
|
||||||
|
ray.draw_texture(top_texture, i + int(self.move.attribute), 0, ray.WHITE)
|
||||||
|
texture = self.textures[self.name + f'_{self.player_num}p'][1 + texture_index]
|
||||||
|
for i in range(0, self.screen_width + texture.width, texture.width):
|
||||||
|
ray.draw_texture(texture, i + int(self.move.attribute*2), int(self.bounce_up.attribute) - int(self.bounce_down.attribute) - 25 + int(self.overlay_move.attribute) + int(self.overlay_move_2.attribute), ray.WHITE)
|
||||||
|
|
||||||
|
class DonBG4(DonBGBase):
|
||||||
|
def __init__(self, index: int, screen_width: int, screen_height: int, player_num: int):
|
||||||
|
super().__init__(index, screen_width, screen_height, player_num)
|
||||||
|
self.overlay_move = Animation.create_move(1500, start_position=0, total_distance=20, reverse_delay=0)
|
||||||
|
def update(self, current_time_ms: float, is_clear: bool):
|
||||||
|
super().update(current_time_ms, is_clear)
|
||||||
|
self.overlay_move.update(current_time_ms)
|
||||||
|
if self.overlay_move.is_finished:
|
||||||
|
self.overlay_move.restart()
|
||||||
|
def draw(self):
|
||||||
|
texture_index = 0
|
||||||
|
if self.is_clear:
|
||||||
|
texture_index = 2
|
||||||
|
top_texture = self.textures[self.name + f'_{self.player_num}p'][texture_index]
|
||||||
|
for i in range(0, self.screen_width + top_texture.width, top_texture.width):
|
||||||
|
ray.draw_texture(top_texture, i + int(self.move.attribute), 0, ray.WHITE)
|
||||||
|
|
||||||
|
texture = self.textures[self.name + f'_{self.player_num}p'][1 + texture_index]
|
||||||
|
for i in range(0, self.screen_width + texture.width, texture.width):
|
||||||
|
ray.draw_texture(texture, i + int(self.move.attribute), int(self.overlay_move.attribute) - 25, ray.WHITE)
|
||||||
|
|
||||||
|
class DonBG5(DonBGBase):
|
||||||
|
def __init__(self, index: int, screen_width: int, screen_height: int, player_num: int):
|
||||||
|
super().__init__(index, screen_width, screen_height, player_num)
|
||||||
|
duration = 266
|
||||||
|
bounce_distance = 40
|
||||||
|
self.bounce_up = Animation.create_move(duration, total_distance=-bounce_distance, ease_out='quadratic')
|
||||||
|
self.bounce_down = Animation.create_move(duration, total_distance=-bounce_distance, ease_in='quadratic', delay=self.bounce_up.duration)
|
||||||
|
self.adjust = Animation.create_move(1000, total_distance=10, reverse_delay=0, delay=self.bounce_up.duration+self.bounce_down.duration)
|
||||||
|
|
||||||
|
def update(self, current_time_ms: float, is_clear: bool):
|
||||||
|
super().update(current_time_ms, is_clear)
|
||||||
|
self.bounce_up.update(current_time_ms)
|
||||||
|
self.bounce_down.update(current_time_ms)
|
||||||
|
self.adjust.update(current_time_ms)
|
||||||
|
if self.adjust.is_finished:
|
||||||
|
self.bounce_up.restart()
|
||||||
|
self.bounce_down.restart()
|
||||||
|
self.adjust.restart()
|
||||||
|
|
||||||
|
def draw(self):
|
||||||
|
texture_index = 0
|
||||||
|
if self.is_clear:
|
||||||
|
texture_index = 2
|
||||||
|
top_texture = self.textures[self.name + f'_{self.player_num}p'][0 + texture_index]
|
||||||
|
for i in range(0, self.screen_width + top_texture.width, top_texture.width):
|
||||||
|
ray.draw_texture(top_texture, i + int(self.move.attribute), 0, ray.WHITE)
|
||||||
|
texture = self.textures[self.name + f'_{self.player_num}p'][1 + texture_index]
|
||||||
|
for i in range(0, self.screen_width + texture.width + texture.width*2, texture.width*2):
|
||||||
|
ray.draw_texture(texture, i + int((self.move.attribute * (texture.width/top_texture.width))*2), int(self.bounce_up.attribute) - int(self.bounce_down.attribute) - int(self.adjust.attribute), ray.WHITE)
|
||||||
|
|
||||||
class DonBG6(DonBGBase):
|
class DonBG6(DonBGBase):
|
||||||
def __init__(self, index: int, screen_width: int, screen_height: int, player_num: int):
|
def __init__(self, index: int, screen_width: int, screen_height: int, player_num: int):
|
||||||
|
|||||||
@@ -169,6 +169,8 @@ def calculate_base_score(play_note_list: deque[Note | Drumroll | Balloon]) -> in
|
|||||||
balloon_count += note.count
|
balloon_count += note.count
|
||||||
else:
|
else:
|
||||||
total_notes += 1
|
total_notes += 1
|
||||||
|
if total_notes == 0:
|
||||||
|
return 0
|
||||||
total_score = (1000000 - (balloon_count * 100) - (drumroll_sec * 1692.0079999994086)) / total_notes
|
total_score = (1000000 - (balloon_count * 100) - (drumroll_sec * 1692.0079999994086)) / total_notes
|
||||||
return math.ceil(total_score / 10) * 10
|
return math.ceil(total_score / 10) * 10
|
||||||
|
|
||||||
|
|||||||
BIN
model/cos_100000_01.png
Normal file
BIN
model/cos_100000_01.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 163 KiB |
BIN
model/cos_100000_02.png
Normal file
BIN
model/cos_100000_02.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 62 KiB |
76
model/mikudon.mtl
Normal file
76
model/mikudon.mtl
Normal file
@@ -0,0 +1,76 @@
|
|||||||
|
# Blender 4.5.0 MTL File: 'None'
|
||||||
|
# www.blender.org
|
||||||
|
|
||||||
|
newmtl RGB_don_color_S_CUS_0x10000001_
|
||||||
|
Ns 360.000000
|
||||||
|
Ka 1.000000 1.000000 1.000000
|
||||||
|
Kd 0.968627 0.945098 0.882352
|
||||||
|
Ks 0.500000 0.500000 0.500000
|
||||||
|
Ke 0.000000 0.000000 0.000000
|
||||||
|
Ni 1.000000
|
||||||
|
d 1.000000
|
||||||
|
illum 2
|
||||||
|
|
||||||
|
newmtl cos_100000_HEADBODY_01_color_S_CUS_0x10000000__AT_ZERO___CULLNO
|
||||||
|
Ns 360.000000
|
||||||
|
Ka 1.000000 1.000000 1.000000
|
||||||
|
Kd 0.800000 0.800000 0.800000
|
||||||
|
Ks 0.500000 0.500000 0.500000
|
||||||
|
Ke 0.000000 0.000000 0.000000
|
||||||
|
Ni 1.000000
|
||||||
|
d 1.000000
|
||||||
|
map_Kd cos_100000_01.png
|
||||||
|
illum 2
|
||||||
|
|
||||||
|
newmtl cos_100000_HEADBODY_02_color_S_CUS_0x10000000__AT_ZERO___CULLNO
|
||||||
|
Ns 360.000000
|
||||||
|
Ka 1.000000 1.000000 1.000000
|
||||||
|
Kd 0.800000 0.800000 0.800000
|
||||||
|
Ks 0.500000 0.500000 0.500000
|
||||||
|
Ke 0.000000 0.000000 0.000000
|
||||||
|
Ni 1.000000
|
||||||
|
d 1.000000
|
||||||
|
map_Kd cos_100000_02.png
|
||||||
|
illum 2
|
||||||
|
|
||||||
|
newmtl cos_100000_HEADBODY_03_color_S_CUS_0x10000000__A_AB_AA_ADD_AT_O
|
||||||
|
Ns 360.000000
|
||||||
|
Ka 1.000000 1.000000 1.000000
|
||||||
|
Kd 0.800000 0.800000 0.800000
|
||||||
|
Ks 0.500000 0.500000 0.500000
|
||||||
|
Ke 0.000000 0.000000 0.000000
|
||||||
|
Ni 1.000000
|
||||||
|
d 1.000000
|
||||||
|
map_Kd cos_100000_01.png
|
||||||
|
illum 2
|
||||||
|
|
||||||
|
newmtl cos_100000_HEADBODY_04_color_S_CUS_0x10000000__A_AB_AA_ADD_AT_O
|
||||||
|
Ns 360.000000
|
||||||
|
Ka 1.000000 1.000000 1.000000
|
||||||
|
Kd 0.800000 0.800000 0.800000
|
||||||
|
Ks 0.500000 0.500000 0.500000
|
||||||
|
Ke 0.000000 0.000000 0.000000
|
||||||
|
Ni 1.000000
|
||||||
|
d 1.000000
|
||||||
|
map_Kd cos_100000_02.png
|
||||||
|
illum 2
|
||||||
|
|
||||||
|
newmtl don_FACEHIP_color_S_CUS_0x10000001_
|
||||||
|
Ns 360.000000
|
||||||
|
Ka 1.000000 1.000000 1.000000
|
||||||
|
Kd 0.968627 0.945098 0.882352
|
||||||
|
Ks 0.500000 0.500000 0.500000
|
||||||
|
Ke 0.000000 0.000000 0.000000
|
||||||
|
Ni 1.000000
|
||||||
|
d 1.000000
|
||||||
|
illum 2
|
||||||
|
|
||||||
|
newmtl face2_FACIAL_S_CUS_0x10000002_A_AB_AA_ADD
|
||||||
|
Ns 360.000000
|
||||||
|
Ka 1.000000 1.000000 1.000000
|
||||||
|
Kd 0.968627 0.286274 0.156862
|
||||||
|
Ks 0.500000 0.500000 0.500000
|
||||||
|
Ke 0.000000 0.000000 0.000000
|
||||||
|
Ni 1.000000
|
||||||
|
d 1.000000
|
||||||
|
illum 2
|
||||||
16482
model/mikudon.obj
Normal file
16482
model/mikudon.obj
Normal file
File diff suppressed because it is too large
Load Diff
@@ -1,11 +1,16 @@
|
|||||||
import pyray as ray
|
import pyray as ray
|
||||||
|
|
||||||
|
|
||||||
class DevScreen:
|
class DevScreen:
|
||||||
def __init__(self, width: int, height: int):
|
def __init__(self, width: int, height: int):
|
||||||
self.width = width
|
self.width = width
|
||||||
self.height = height
|
self.height = height
|
||||||
self.screen_init = False
|
self.screen_init = False
|
||||||
|
self.model = ray.load_model("model/mikudon.obj")
|
||||||
|
self.model_position = ray.Vector3(-450.0, 100.0, -180.0)
|
||||||
|
self.model_scale = 1000.0
|
||||||
|
self.model_rotation_y = 45.0 # Face towards camera (rotate 180 degrees on Y-axis)
|
||||||
|
self.model_rotation_x = 0.0 # No up/down tilt
|
||||||
|
self.model_rotation_z = 0.0 # No roll
|
||||||
|
|
||||||
def on_screen_start(self):
|
def on_screen_start(self):
|
||||||
if not self.screen_init:
|
if not self.screen_init:
|
||||||
@@ -13,12 +18,26 @@ class DevScreen:
|
|||||||
|
|
||||||
def on_screen_end(self, next_screen: str):
|
def on_screen_end(self, next_screen: str):
|
||||||
self.screen_init = False
|
self.screen_init = False
|
||||||
|
ray.unload_model(self.model)
|
||||||
return next_screen
|
return next_screen
|
||||||
|
|
||||||
def update(self):
|
def update(self):
|
||||||
self.on_screen_start()
|
self.on_screen_start()
|
||||||
|
|
||||||
if ray.is_key_pressed(ray.KeyboardKey.KEY_ENTER):
|
if ray.is_key_pressed(ray.KeyboardKey.KEY_ENTER):
|
||||||
return self.on_screen_end('RESULT')
|
return self.on_screen_end('GAME')
|
||||||
|
|
||||||
def draw(self):
|
def draw(self):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
def draw_3d(self):
|
||||||
|
# Method 1: Using draw_model_ex for full control over rotation
|
||||||
|
rotation_axis = ray.Vector3(0.0, 1.0, 0.0) # Y-axis for horizontal rotation
|
||||||
|
ray.draw_model_ex(
|
||||||
|
self.model,
|
||||||
|
self.model_position,
|
||||||
|
rotation_axis,
|
||||||
|
self.model_rotation_y,
|
||||||
|
ray.Vector3(self.model_scale, self.model_scale, self.model_scale),
|
||||||
|
ray.WHITE
|
||||||
|
)
|
||||||
|
|||||||
@@ -304,3 +304,6 @@ class EntryScreen:
|
|||||||
src = ray.Rectangle(0, 0, self.texture_black.width, self.texture_black.height)
|
src = ray.Rectangle(0, 0, self.texture_black.width, self.texture_black.height)
|
||||||
dest = ray.Rectangle(0, 0, self.width, self.height)
|
dest = ray.Rectangle(0, 0, self.width, self.height)
|
||||||
ray.draw_texture_pro(self.texture_black, src, dest, ray.Vector2(0, 0), 0, ray.WHITE)
|
ray.draw_texture_pro(self.texture_black, src, dest, ray.Vector2(0, 0), 0, ray.WHITE)
|
||||||
|
|
||||||
|
def draw_3d(self):
|
||||||
|
pass
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import bisect
|
import bisect
|
||||||
import math
|
import math
|
||||||
import sqlite3
|
import sqlite3
|
||||||
|
from collections import deque
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import Optional
|
from typing import Optional
|
||||||
|
|
||||||
@@ -103,6 +104,10 @@ class GameScreen:
|
|||||||
self.textures['onp_renda_dai'][0], self.textures['onp_renda_dai'][1],
|
self.textures['onp_renda_dai'][0], self.textures['onp_renda_dai'][1],
|
||||||
self.textures['onp_fusen'][0]]
|
self.textures['onp_fusen'][0]]
|
||||||
|
|
||||||
|
if song == Path(''):
|
||||||
|
self.start_ms = get_current_ms()
|
||||||
|
self.tja = None
|
||||||
|
else:
|
||||||
self.tja = TJAParser(song, start_delay=self.start_delay, distance=self.width - GameScreen.JUDGE_X)
|
self.tja = TJAParser(song, start_delay=self.start_delay, distance=self.width - GameScreen.JUDGE_X)
|
||||||
if self.tja.metadata.bgmovie != Path() and self.tja.metadata.bgmovie.exists():
|
if self.tja.metadata.bgmovie != Path() and self.tja.metadata.bgmovie.exists():
|
||||||
self.movie = VideoPlayer(self.tja.metadata.bgmovie)
|
self.movie = VideoPlayer(self.tja.metadata.bgmovie)
|
||||||
@@ -110,8 +115,6 @@ class GameScreen:
|
|||||||
else:
|
else:
|
||||||
self.movie = None
|
self.movie = None
|
||||||
session_data.song_title = self.tja.metadata.title.get(global_data.config['general']['language'].lower(), self.tja.metadata.title['en'])
|
session_data.song_title = self.tja.metadata.title.get(global_data.config['general']['language'].lower(), self.tja.metadata.title['en'])
|
||||||
|
|
||||||
self.player_1 = Player(self, 1, difficulty)
|
|
||||||
if not hasattr(self, 'song_music'):
|
if not hasattr(self, 'song_music'):
|
||||||
if self.tja.metadata.wave.exists() and self.tja.metadata.wave.is_file():
|
if self.tja.metadata.wave.exists() and self.tja.metadata.wave.is_file():
|
||||||
self.song_music = audio.load_sound(self.tja.metadata.wave)
|
self.song_music = audio.load_sound(self.tja.metadata.wave)
|
||||||
@@ -120,6 +123,8 @@ class GameScreen:
|
|||||||
self.song_music = None
|
self.song_music = None
|
||||||
self.start_ms = (get_current_ms() - self.tja.metadata.offset*1000)
|
self.start_ms = (get_current_ms() - self.tja.metadata.offset*1000)
|
||||||
|
|
||||||
|
self.player_1 = Player(self, 1, difficulty)
|
||||||
|
|
||||||
def on_screen_start(self):
|
def on_screen_start(self):
|
||||||
if not self.screen_init:
|
if not self.screen_init:
|
||||||
self.screen_init = True
|
self.screen_init = True
|
||||||
@@ -146,6 +151,8 @@ class GameScreen:
|
|||||||
return next_screen
|
return next_screen
|
||||||
|
|
||||||
def write_score(self):
|
def write_score(self):
|
||||||
|
if self.tja is None:
|
||||||
|
return
|
||||||
if global_data.config['general']['autoplay']:
|
if global_data.config['general']['autoplay']:
|
||||||
return
|
return
|
||||||
with sqlite3.connect('scores.db') as con:
|
with sqlite3.connect('scores.db') as con:
|
||||||
@@ -173,6 +180,7 @@ class GameScreen:
|
|||||||
if self.transition is not None:
|
if self.transition is not None:
|
||||||
self.transition.update(get_current_ms())
|
self.transition.update(get_current_ms())
|
||||||
self.current_ms = get_current_ms() - self.start_ms
|
self.current_ms = get_current_ms() - self.start_ms
|
||||||
|
if self.tja is not None:
|
||||||
if (self.current_ms >= self.tja.metadata.offset*1000 + self.start_delay - global_data.config["general"]["judge_offset"]) and not self.song_started:
|
if (self.current_ms >= self.tja.metadata.offset*1000 + self.start_delay - global_data.config["general"]["judge_offset"]) and not self.song_started:
|
||||||
if self.song_music is not None:
|
if self.song_music is not None:
|
||||||
if not audio.is_sound_playing(self.song_music):
|
if not audio.is_sound_playing(self.song_music):
|
||||||
@@ -228,6 +236,9 @@ class GameScreen:
|
|||||||
if self.result_transition is not None:
|
if self.result_transition is not None:
|
||||||
self.result_transition.draw(self.width, self.height, global_data.textures['shutter'][0], global_data.textures['shutter'][1])
|
self.result_transition.draw(self.width, self.height, global_data.textures['shutter'][0], global_data.textures['shutter'][1])
|
||||||
|
|
||||||
|
def draw_3d(self):
|
||||||
|
self.player_1.draw_3d(self)
|
||||||
|
|
||||||
class Player:
|
class Player:
|
||||||
TIMING_GOOD = 25.0250015258789
|
TIMING_GOOD = 25.0250015258789
|
||||||
TIMING_OK = 75.0750045776367
|
TIMING_OK = 75.0750045776367
|
||||||
@@ -239,7 +250,10 @@ class Player:
|
|||||||
self.difficulty = difficulty
|
self.difficulty = difficulty
|
||||||
self.visual_offset = global_data.config["general"]["visual_offset"]
|
self.visual_offset = global_data.config["general"]["visual_offset"]
|
||||||
|
|
||||||
|
if game_screen.tja is not None:
|
||||||
self.play_notes, self.draw_note_list, self.draw_bar_list = game_screen.tja.notes_to_position(self.difficulty)
|
self.play_notes, self.draw_note_list, self.draw_bar_list = game_screen.tja.notes_to_position(self.difficulty)
|
||||||
|
else:
|
||||||
|
self.play_notes, self.draw_note_list, self.draw_bar_list = deque(), deque(), deque()
|
||||||
self.total_notes = len([note for note in self.play_notes if 0 < note.type < 5])
|
self.total_notes = len([note for note in self.play_notes if 0 < note.type < 5])
|
||||||
self.base_score = calculate_base_score(self.play_notes)
|
self.base_score = calculate_base_score(self.play_notes)
|
||||||
|
|
||||||
@@ -275,12 +289,23 @@ class Player:
|
|||||||
|
|
||||||
self.input_log: dict[float, tuple] = dict()
|
self.input_log: dict[float, tuple] = dict()
|
||||||
|
|
||||||
self.gauge = Gauge(self.difficulty, game_screen.tja.metadata.course_data[self.difficulty].level, self.total_notes)
|
if game_screen.tja is not None:
|
||||||
|
stars = game_screen.tja.metadata.course_data[self.difficulty].level
|
||||||
|
else:
|
||||||
|
stars = 0
|
||||||
|
self.gauge = Gauge(self.difficulty, stars, self.total_notes)
|
||||||
self.gauge_hit_effect: list[GaugeHitEffect] = []
|
self.gauge_hit_effect: list[GaugeHitEffect] = []
|
||||||
|
|
||||||
self.autoplay_hit_side = 'L'
|
self.autoplay_hit_side = 'L'
|
||||||
self.last_subdivision = -1
|
self.last_subdivision = -1
|
||||||
|
|
||||||
|
self.model = ray.load_model("model/mikudon.obj")
|
||||||
|
self.model_position = ray.Vector3(-475.0, 160.0, -180.0)
|
||||||
|
self.model_scale = 850.0
|
||||||
|
self.model_rotation_y = 30.0 # Face towards camera (rotate 180 degrees on Y-axis)
|
||||||
|
self.model_rotation_x = 0.0 # No up/down tilt
|
||||||
|
self.model_rotation_z = 0.0
|
||||||
|
|
||||||
def get_result_score(self):
|
def get_result_score(self):
|
||||||
return self.score, self.good_count, self.ok_count, self.bad_count, self.total_drumroll, self.max_combo
|
return self.score, self.good_count, self.ok_count, self.bad_count, self.total_drumroll, self.max_combo
|
||||||
|
|
||||||
@@ -383,6 +408,7 @@ class Player:
|
|||||||
else:
|
else:
|
||||||
note_type = game_screen.note_type_list[note.type][0]
|
note_type = game_screen.note_type_list[note.type][0]
|
||||||
|
|
||||||
|
if note.type < 7:
|
||||||
self.combo += 1
|
self.combo += 1
|
||||||
if self.combo > self.max_combo:
|
if self.combo > self.max_combo:
|
||||||
self.max_combo = self.combo
|
self.max_combo = self.combo
|
||||||
@@ -710,6 +736,20 @@ class Player:
|
|||||||
anim.draw(game_screen)
|
anim.draw(game_screen)
|
||||||
#ray.draw_circle(game_screen.width//2, game_screen.height, 300, ray.ORANGE)
|
#ray.draw_circle(game_screen.width//2, game_screen.height, 300, ray.ORANGE)
|
||||||
|
|
||||||
|
def draw_3d(self):
|
||||||
|
'''
|
||||||
|
rotation_axis = ray.Vector3(0.0, 1.0, 0.0) # Y-axis for horizontal rotation
|
||||||
|
ray.draw_model_ex(
|
||||||
|
self.model,
|
||||||
|
self.model_position,
|
||||||
|
rotation_axis,
|
||||||
|
self.model_rotation_y,
|
||||||
|
ray.Vector3(self.model_scale, self.model_scale, self.model_scale),
|
||||||
|
ray.WHITE
|
||||||
|
)
|
||||||
|
'''
|
||||||
|
pass
|
||||||
|
|
||||||
class Judgement:
|
class Judgement:
|
||||||
def __init__(self, type: str, big: bool, ms_display: Optional[float]=None):
|
def __init__(self, type: str, big: bool, ms_display: Optional[float]=None):
|
||||||
self.type = type
|
self.type = type
|
||||||
|
|||||||
@@ -112,3 +112,5 @@ class LoadScreen:
|
|||||||
|
|
||||||
if self.fade_in is not None:
|
if self.fade_in is not None:
|
||||||
ray.draw_rectangle(0, 0, self.width, self.height, ray.fade(ray.WHITE, self.fade_in.attribute))
|
ray.draw_rectangle(0, 0, self.width, self.height, ray.fade(ray.WHITE, self.fade_in.attribute))
|
||||||
|
def draw_3d(self):
|
||||||
|
pass
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
import math
|
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
|
|
||||||
import pyray as ray
|
import pyray as ray
|
||||||
@@ -252,6 +251,9 @@ class ResultScreen:
|
|||||||
if self.fade_out is not None:
|
if self.fade_out is not None:
|
||||||
self.fade_out.draw(self.width, self.height)
|
self.fade_out.draw(self.width, self.height)
|
||||||
|
|
||||||
|
def draw_3d(self):
|
||||||
|
pass
|
||||||
|
|
||||||
class Crown:
|
class Crown:
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
duration = 466
|
duration = 466
|
||||||
|
|||||||
@@ -264,3 +264,5 @@ class SettingsScreen:
|
|||||||
else:
|
else:
|
||||||
# Draw exit instruction
|
# Draw exit instruction
|
||||||
ray.draw_text("Press Don to exit settings", 250, 100, 20, ray.GREEN)
|
ray.draw_text("Press Don to exit settings", 250, 100, 20, ray.GREEN)
|
||||||
|
def draw_3d(self):
|
||||||
|
pass
|
||||||
|
|||||||
@@ -314,6 +314,9 @@ class SongSelectScreen:
|
|||||||
if self.game_transition is not None:
|
if self.game_transition is not None:
|
||||||
self.game_transition.draw(self.screen_height)
|
self.game_transition.draw(self.screen_height)
|
||||||
|
|
||||||
|
def draw_3d(self):
|
||||||
|
pass
|
||||||
|
|
||||||
class SongBox:
|
class SongBox:
|
||||||
OUTLINE_MAP = {
|
OUTLINE_MAP = {
|
||||||
555: ray.Color(0, 77, 104, 255),
|
555: ray.Color(0, 77, 104, 255),
|
||||||
|
|||||||
@@ -127,6 +127,9 @@ class TitleScreen:
|
|||||||
dest = ray.Rectangle(0, 0, self.width, self.height)
|
dest = ray.Rectangle(0, 0, self.width, self.height)
|
||||||
ray.draw_texture_pro(self.texture_black, src, dest, ray.Vector2(0, 0), 0, ray.fade(ray.WHITE, self.fade_out.attribute))
|
ray.draw_texture_pro(self.texture_black, src, dest, ray.Vector2(0, 0), 0, ray.fade(ray.WHITE, self.fade_out.attribute))
|
||||||
|
|
||||||
|
def draw_3d(self):
|
||||||
|
pass
|
||||||
|
|
||||||
class WarningScreen:
|
class WarningScreen:
|
||||||
class X:
|
class X:
|
||||||
DELAY = 4250
|
DELAY = 4250
|
||||||
|
|||||||
Reference in New Issue
Block a user