From 645f0e100d892604968a6ce1835dd61db3693e78 Mon Sep 17 00:00:00 2001 From: march3 Date: Sat, 18 Mar 2023 12:51:31 +0800 Subject: [PATCH] =?UTF-8?q?=E5=A4=AA=E9=98=B3=E7=B3=BB=E4=B8=89=E4=BD=93?= =?UTF-8?q?=E6=A8=A1=E6=8B=9F=E5=99=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- scenes/func.py | 25 ++++++++++++---- scenes/solar_system_1.py | 3 +- scenes/solar_system_2.py | 5 ++-- scenes/sun_earth.py | 5 ++-- scenes/sun_earth_jupiter.py | 5 ++-- scenes/sun_earth_moon.py | 19 +++++++++--- scenes/three_body_01.py | 5 ++-- ...ee_body_chatgpt_01.py => three_body_03.py} | 5 ++-- scenes/two_body_01.py | 10 +++++-- simulators/ursina/ursina_config.py | 29 +++++++++++++++---- simulators/ursina/ursina_ui.py | 6 ++-- simulators/ursina_simulator.py | 8 +++-- simulators/views/ursina_view.py | 26 +++++++++++------ 13 files changed, 107 insertions(+), 44 deletions(-) rename scenes/{three_body_chatgpt_01.py => three_body_03.py} (94%) diff --git a/scenes/func.py b/scenes/func.py index bba9931..81b51bb 100644 --- a/scenes/func.py +++ b/scenes/func.py @@ -55,22 +55,37 @@ def mayavi_run(bodies, dt=SECONDS_PER_WEEK, def ursina_run(bodies, dt=SECONDS_PER_HALF_DAY, position=(4000000, 800000000, 4000000), + # view_azimuth=0, light=True, cosmic_bg=None, show_grid=True): """ - :param bodies: - :param dt: + :param bodies: 天体 + :param dt: 单位:秒,按时间差进行演变,值越小越精确,但演变速度会慢。 + :param position: 摄像头位置 + :param view_azimuth: 摄像头观测方位角,可选,float类型(以度为单位,0-360) + :param light: 使用灯光效果 + :param cosmic_bg: 宇宙背景图片 + :param show_grid: 是否显示空间网格 :return: """ from simulators.ursina_simulator import UrsinaSimulator, UrsinaPlayer - from ursina import application, Sequence, camera, held_keys, time, clamp,Entity,Text + from ursina import application, Sequence, camera, held_keys, time, clamp, Entity, Text, color + from ursina.prefabs.first_person_controller import FirstPersonController body_sys = System(bodies) simulator = UrsinaSimulator(body_sys) - - player = UrsinaPlayer(position, simulator.ursina_views) + view_azimuth = 0 # 暂时未用 + player = UrsinaPlayer(position, view_azimuth, simulator.ursina_views) + # # player = FirstPersonController(model='cube', y=-1e20, color=color.orange, origin_y=-5000, speed=8) + # # player.on_disable() + # # player.position = position + # + # player = FirstPersonController() + # cube = Entity(model='cube', color=color.red, scale=2) + # player.parent = cube # 设置 FirstPersonController 的父实体为 cube + # cube.position = position # 修改父实体的位置,从而间接地修改 FirstPersonController 的位置 # # 创建一个实体(在屏幕中央)和一个摄像机 # TODO: 未使用 diff --git a/scenes/solar_system_1.py b/scenes/solar_system_1.py index a343e69..981bc20 100644 --- a/scenes/solar_system_1.py +++ b/scenes/solar_system_1.py @@ -39,4 +39,5 @@ if __name__ == '__main__': # mayavi_run(bodies, SECONDS_PER_WEEK, view_azimuth=-45) # 使用 ursina 查看的运行效果 - ursina_run(bodies, SECONDS_PER_YEAR, position=(0, 5 * AU, -10 * AU)) # position=左-右+、上+下-、前+后- + # position = 左-右+、上+下-、前+后- + ursina_run(bodies, SECONDS_PER_YEAR, position=(0, 2 * AU, -11 * AU)) diff --git a/scenes/solar_system_2.py b/scenes/solar_system_2.py index a268c18..c6923a5 100644 --- a/scenes/solar_system_2.py +++ b/scenes/solar_system_2.py @@ -7,7 +7,7 @@ # python_version :3.8 # ============================================================================== from bodies import Sun, Mercury, Venus, Earth, Mars, Jupiter, Saturn, Uranus, Neptune, Pluto, Asteroids -from common.consts import SECONDS_PER_WEEK, SECONDS_PER_DAY, SECONDS_PER_MONTH, SECONDS_PER_YEAR +from common.consts import SECONDS_PER_WEEK, SECONDS_PER_DAY, SECONDS_PER_MONTH, SECONDS_PER_YEAR, AU from scenes.func import mayavi_run, ursina_run if __name__ == '__main__': @@ -42,4 +42,5 @@ if __name__ == '__main__': # mayavi_run(bodies, SECONDS_PER_WEEK, view_azimuth=-45, view_distance=3e9, view_focalpoint=[5e2, 5e2, 5e2]) # 使用 ursina 查看的运行效果 - ursina_run(bodies, SECONDS_PER_YEAR, position=(0, 0, 0)) \ No newline at end of file + # position = 左-右+、上+下-、前+后- + ursina_run(bodies, SECONDS_PER_YEAR, position=(0, 2 * AU, -11 * AU)) diff --git a/scenes/sun_earth.py b/scenes/sun_earth.py index ab50342..62266f3 100644 --- a/scenes/sun_earth.py +++ b/scenes/sun_earth.py @@ -7,7 +7,7 @@ # python_version :3.8 # ============================================================================== from bodies import Sun, Earth -from common.consts import SECONDS_PER_WEEK, SECONDS_PER_DAY +from common.consts import SECONDS_PER_WEEK, SECONDS_PER_DAY, AU from scenes.func import mayavi_run, ursina_run if __name__ == '__main__': @@ -23,4 +23,5 @@ if __name__ == '__main__': # mayavi_run(bodies, SECONDS_PER_WEEK, view_azimuth=-45) # 使用 ursina 查看的运行效果 - ursina_run(bodies, SECONDS_PER_WEEK, position=(0, 0, 0)) + # position = 左-右+、上+下-、前+后- + ursina_run(bodies, SECONDS_PER_WEEK, position=(0, AU, -3 * AU)) diff --git a/scenes/sun_earth_jupiter.py b/scenes/sun_earth_jupiter.py index 68da821..5a8f480 100644 --- a/scenes/sun_earth_jupiter.py +++ b/scenes/sun_earth_jupiter.py @@ -7,7 +7,7 @@ # python_version :3.8 # ============================================================================== from bodies import Sun, Earth, Jupiter -from common.consts import SECONDS_PER_WEEK +from common.consts import SECONDS_PER_WEEK, AU from scenes.func import mayavi_run, ursina_run if __name__ == '__main__': @@ -24,4 +24,5 @@ if __name__ == '__main__': # mayavi_run(bodies, SECONDS_PER_WEEK, view_azimuth=-45) # 使用 ursina 查看的运行效果 - ursina_run(bodies, SECONDS_PER_WEEK, position=(0, 0, 0)) + # position = 左-右+、上+下-、前+后- + ursina_run(bodies, SECONDS_PER_WEEK, position=(0, AU, -3 * AU)) diff --git a/scenes/sun_earth_moon.py b/scenes/sun_earth_moon.py index d91c0d4..85c46bd 100644 --- a/scenes/sun_earth_moon.py +++ b/scenes/sun_earth_moon.py @@ -20,17 +20,28 @@ if __name__ == '__main__': sun = Sun(init_position=[AU, 0, 0], size_scale=2e1) # 太阳放大 20 倍 # 忽略质量的引力 sun.ignore_mass = True + + # 观看月相变化的过程:分别是 新月、蛾眉月、上弦月、盈凸、满月、亏凸、下弦月、残月 + # TODO: 月球在摄像机的前方(从 “新月” 开始) + moon_pos, moon_vel = [384400, 0, 0], [0, EARTH_INIT_VELOCITY + 1.023, 0] + # TODO: 月球在摄像机的右方(从 “下弦月” 开始),将会出现 + # moon_pos, moon_vel = [0, -384400, 0], [1.023, EARTH_INIT_VELOCITY, 0] + # TODO: 月月球在摄像机的左方(从 “上弦月” 开始) + # moon_pos, moon_vel = [0, 384400, 0], [-1.023, EARTH_INIT_VELOCITY, 0] + bodies = [ sun, Earth(init_position=[0, 0, 0], init_velocity=[0, EARTH_INIT_VELOCITY, 0], - size_scale=1e1), # 地球放大 10 倍,距离保持不变 - Moon(init_position=[0, 384400, 0], # 距地距离约: 363104 至 405696 km - init_velocity=[-1.023, EARTH_INIT_VELOCITY, 0], - size_scale=2e1) # 月球放大 20 倍,距离保持不变 + size_scale=1e1), # 地球放大 10 倍,距离保持不变 + Moon(init_position=moon_pos, # 距地距离约: 363104 至 405696 km + init_velocity=moon_vel, + size_scale=2e1) # 月球放大 20 倍,距离保持不变 ] # 使用 mayavi 查看的运行效果 # mayavi_run(bodies, SECONDS_PER_HALF_DAY / 2, view_azimuth=-45) # 使用 ursina 查看的运行效果 + # position = 左-右+、上+下-、前+后- + # position=(0, 0, 0) 的位置是站在地球视角,可以观看月相变化的过程 ursina_run(bodies, SECONDS_PER_DAY, position=(0, 0, 0)) diff --git a/scenes/three_body_01.py b/scenes/three_body_01.py index ed17267..9c19a41 100644 --- a/scenes/three_body_01.py +++ b/scenes/three_body_01.py @@ -7,7 +7,7 @@ # python_version :3.8 # ============================================================================== from bodies import Sun, Earth -from common.consts import SECONDS_PER_WEEK, SECONDS_PER_DAY +from common.consts import SECONDS_PER_WEEK, SECONDS_PER_DAY, AU from scenes.func import mayavi_run, ursina_run if __name__ == '__main__': @@ -32,4 +32,5 @@ if __name__ == '__main__': # mayavi_run(bodies, SECONDS_PER_WEEK, view_azimuth=0) # 使用 ursina 查看的运行效果 - ursina_run(bodies, SECONDS_PER_DAY, position=(0, 0, 0)) \ No newline at end of file + # position = 左-右+、上+下-、前+后- + ursina_run(bodies, SECONDS_PER_DAY, position=(3 * AU, AU, -4 * AU)) \ No newline at end of file diff --git a/scenes/three_body_chatgpt_01.py b/scenes/three_body_03.py similarity index 94% rename from scenes/three_body_chatgpt_01.py rename to scenes/three_body_03.py index 5222e4d..72d4644 100644 --- a/scenes/three_body_chatgpt_01.py +++ b/scenes/three_body_03.py @@ -7,7 +7,7 @@ # python_version :3.8 # ============================================================================== from bodies import Sun, Earth -from common.consts import SECONDS_PER_DAY, SECONDS_PER_WEEK, SECONDS_PER_YEAR +from common.consts import SECONDS_PER_DAY, SECONDS_PER_WEEK, SECONDS_PER_YEAR, AU from scenes.func import mayavi_run, mpl_run, ursina_run if __name__ == '__main__': @@ -57,4 +57,5 @@ if __name__ == '__main__': # mpl_run(bodies, SECONDS_PER_WEEK) # 使用 ursina 查看的运行效果 - ursina_run(bodies, SECONDS_PER_YEAR, position=(0, 0, 0)) + # position = 左-右+、上+下-、前+后- + ursina_run(bodies, SECONDS_PER_YEAR, position=(3 * AU, 3 * AU, -20 * AU)) diff --git a/scenes/two_body_01.py b/scenes/two_body_01.py index f11a9b2..03f1f78 100644 --- a/scenes/two_body_01.py +++ b/scenes/two_body_01.py @@ -7,8 +7,8 @@ # python_version :3.8 # ============================================================================== from bodies import Sun, Earth -from common.consts import SECONDS_PER_WEEK -from scenes.func import mayavi_run +from common.consts import SECONDS_PER_WEEK, SECONDS_PER_YEAR, AU +from scenes.func import mayavi_run, mpl_run, ursina_run if __name__ == '__main__': """ @@ -28,4 +28,8 @@ if __name__ == '__main__': ] # 使用 mayavi 查看的运行效果 - mayavi_run(bodies, SECONDS_PER_WEEK, view_azimuth=0) + # mayavi_run(bodies, SECONDS_PER_WEEK, view_azimuth=0) + + # 使用 ursina 查看的运行效果 + # position = 左-右+、上+下-、前+后- + ursina_run(bodies, SECONDS_PER_YEAR, position=(0, 2 * AU, -5 * AU)) \ No newline at end of file diff --git a/simulators/ursina/ursina_config.py b/simulators/ursina/ursina_config.py index e73270b..6c255f1 100644 --- a/simulators/ursina/ursina_config.py +++ b/simulators/ursina/ursina_config.py @@ -12,7 +12,8 @@ class UrsinaConfig: # 常量定义 # 天体缩放的因子(不能太大,否则无法容得下大数量级的天体)调整 5e-7 最佳 - SCALE_FACTOR = 5e-7 + __SCALE_FACTOR = 5e-7 + auto_scale_factor = 1.0 # __SCALE_FACTOR 不能满足,需要自动进行调整 # 旋转因子为1,则为正常的转速 ROTATION_SPEED_FACTOR = 1.0 # ROTATION_SPEED_FACTOR = 0.01 @@ -34,7 +35,7 @@ class UrsinaConfig: show_trail = False # 拖尾球体的数量 - trail_length = 200 + trail_length = 100 # 默认秒数(0表示默认) seconds_per = 0 # # 控制摄像机动作速度(天体越大,速度越快,天体越小,速度越慢) @@ -42,6 +43,25 @@ class UrsinaConfig: __body_size_factor = 1.0 + @classmethod + def init(cls): + # 初始化 + cls.run_speed_factor = 1.0 + cls.body_spin_factor = 1.0 + cls.body_size_factor = 1.0 + # 天体缩放的因子(不能太大,否则无法容得下大数量级的天体)调整 5e-7 最佳 + cls.SCALE_FACTOR = 5e-7 + + @property + @classmethod + def SCALE_FACTOR(cls): + return cls.__SCALE_FACTOR * cls.auto_scale_factor + + @SCALE_FACTOR.setter + @classmethod + def SCALE_FACTOR(cls, value): + cls.__SCALE_FACTOR = value + @property @classmethod def run_speed_factor(cls): @@ -82,10 +102,7 @@ class UrsinaConfig: f() -# 初始化 -UrsinaConfig.run_speed_factor = 1.0 -UrsinaConfig.body_spin_factor = 1.0 -UrsinaConfig.body_size_factor = 1.0 +UrsinaConfig.init() if __name__ == '__main__': UrsinaConfig.run_speed_factor = 2.0 diff --git a/simulators/ursina/ursina_ui.py b/simulators/ursina/ursina_ui.py index 1c5112c..3914119 100644 --- a/simulators/ursina/ursina_ui.py +++ b/simulators/ursina/ursina_ui.py @@ -29,9 +29,9 @@ class UrsinaUI: # application.time_scale = 0.5 self.slider_body_spin_factor = UiSlider(text='自转速度', min=0.01, max=30, default=1) - self.slider_body_size_factor = UiSlider(text='天体缩放', min=0.1, max=100, default=1) + self.slider_body_size_factor = UiSlider(text='天体缩放', min=0.1, max=100, step=0.1, default=1) self.slider_run_speed_factor = UiSlider(text="运行速度", min=0.01, max=80, default=1) - self.slider_control_speed_factor = UiSlider(text="控制速度", min=0.01, max=50, default=application.time_scale) + self.slider_control_speed_factor = UiSlider(text="控制速度", min=0.01, max=20, default=application.time_scale) self.slider_trail_length = UiSlider(text="拖尾长度", min=30, max=500, step=10, default=UrsinaConfig.trail_length) self.slider_body_size_factor.on_value_changed = self.on_slider_body_size_changed @@ -98,7 +98,7 @@ class UrsinaUI: ) self.sec_per_time_switch.x = -0.4 self.on_off_switch.x = 0.2 - self.on_off_trail.x = -0.4 + self.on_off_trail.x = 0.2 # -0.4 wp.y = 0.5 # wp.panel.scale_y / 2 * wp.scale_y # center the window panel wp.x = 0.6 # wp.scale_x + 0.1 # wp.x = 0#wp.panel.scale_x / 2 * wp.scale_x diff --git a/simulators/ursina_simulator.py b/simulators/ursina_simulator.py index 69012e9..1526148 100644 --- a/simulators/ursina_simulator.py +++ b/simulators/ursina_simulator.py @@ -57,10 +57,10 @@ class UrsinaSimulator(Simulator): self.ursina_views.append(view) # planets.append(newPlanet) # x += cp[i] * 10 - self.adj_application_time_scale() + self.adj_run_params() UrsinaEvent.on_searching_bodies_subscription(type(self).__name__, self.on_searching_bodies) - def adj_application_time_scale(self): + def adj_run_params(self): max_distance = 0 for b1 in self.body_views: for b2 in self.body_views: @@ -71,10 +71,12 @@ class UrsinaSimulator(Simulator): max_distance = d # UrsinaConfig.control_camera_speed = round(max_distance * 10, 2) - time_scale = round(pow(max_distance, 1 / 3), 2) + time_scale = round(pow(max_distance, 1 / 4), 2) if time_scale < 0.01: time_scale = 0.01 + application.time_scale = time_scale + # UrsinaConfig.auto_scale_factor = 1.0e-9 def on_searching_bodies(self, **kwargs): views = [] diff --git a/simulators/views/ursina_view.py b/simulators/views/ursina_view.py index f191f1f..f2a0928 100644 --- a/simulators/views/ursina_view.py +++ b/simulators/views/ursina_view.py @@ -28,9 +28,9 @@ class UrsinaPlayer(FirstPersonController): """ """ - body_rotation_speed_control = 1.0 + # body_rotation_speed_control = 1.0 - def __init__(self, position, targets=None): + def __init__(self, position, view_azimuth=0, targets=None): super().__init__() # camera.fov = 2000 # 100 # camera.rotation_y = 90 @@ -50,18 +50,21 @@ class UrsinaPlayer(FirstPersonController): self.position = Vec3(pos[0], pos[1], pos[2]) # 将摄像机位置设置为 x=0、y=1、z=0 的位置 camera.position = Vec3(pos[0], pos[1], pos[2]) + # self.x = 90 # self.position = Vec3(pos[0], pos[1], pos[2]) # 将摄像机的观察角度绕 x 轴旋转 45 度,绕 y 轴旋转 0 度,绕 z 轴旋转 0 度 - # camera.rotation = Vec3(45, 90, 0) - camera.rotation = Vec3(0, 0, 0) - + # self.rotation = Vec3(45, 90, 0) + # camera.look_at(Vec3(0, 0, 0)) + # camera.world_rotation = Vec3(0, 190, 190) + # camera.enabled = True # self.gravity = 0 # self.vspeed = 400 # self.speed = 1000 # self.mouse_sensitivity = Vec2(160, 160) # self.on_enable() # self.rotation_speed = 80 - self.on_disable() + + self.on_disable() # 防止鼠标被窗口锁定 # def input(self, key): # if key == "escape": @@ -95,7 +98,7 @@ class Planet(Entity): if hasattr(self.body_view.body, "torus_stars"): # 创建一个星环小天体群(主要模拟小行星群,非一个天体) - model = create_torus(0.75, 1.10, 64, 1) + model = create_torus(0.83, 1.05, 64, 1) rotation = (90, 0, 0) else: # 创建一个天体 @@ -112,11 +115,12 @@ class Planet(Entity): color=color.white, position=pos, rotation=rotation # ,double_sided=True - ) + ) if hasattr(self.body_view.body, "torus_stars"): # 星环小天体群(主要模拟小行星群,非一个天体) self.set_light_off() + self.double_sided = True else: # 一个天体 # 拖尾球体的初始化 @@ -195,8 +199,12 @@ class Planet(Entity): :param pos: :return: """ - trail = Entity(model="sphere", color=self.trail_color, scale=self.trail_scale, position=pos) + # sphere = create_sphere(1,6) diamond sphere + trail = Entity(model='sphere', color=self.trail_color, scale=self.trail_scale, position=pos) trail.set_light_off() + # trail.set_color_off() + # trail.set_color_scale_off() + # trail.enabled = False return trail def turn(self): -- GitLab