feat: Re-Implemented Unit System Node (+ other fixes)

main
Sofus Albert Høgsbro Rose 2024-03-22 10:12:14 +01:00
parent f54a9031e8
commit 74e79649fb
Signed by: so-rose
GPG Key ID: AD901CB0F3701434
5 changed files with 79 additions and 96 deletions

View File

@ -1,21 +1,22 @@
from . import wave_constant
# from . import unit_system
from . import (
constants,
unit_system,
wave_constant,
web_importers,
)
from . import constants
from . import web_importers
# from . import file_importers
BL_REGISTER = [
*wave_constant.BL_REGISTER,
# *unit_system.BL_REGISTER,
*unit_system.BL_REGISTER,
*constants.BL_REGISTER,
*web_importers.BL_REGISTER,
# *file_importers.BL_REGISTER,
]
BL_NODES = {
**wave_constant.BL_NODES,
# **unit_system.BL_NODES,
**unit_system.BL_NODES,
**constants.BL_NODES,
**web_importers.BL_NODES,
# *file_importers.BL_REGISTER,

View File

@ -1,11 +1,7 @@
import bpy
import sympy as sp
from ... import contracts as ct
from ... import sockets
from .. import base
class PhysicalUnitSystemNode(base.MaxwellSimNode):
node_type = ct.NodeType.UnitSystem
bl_label = 'Unit System'
@ -26,7 +22,7 @@ class PhysicalUnitSystemNode(base.MaxwellSimNode):
'Unit System',
input_sockets={'Unit System'},
)
def compute_value(self, input_sockets) -> dict:
def compute_unit_system(self, input_sockets) -> dict:
return input_sockets['Unit System']

View File

@ -1,16 +1,14 @@
import typing as typ
import bpy
import sympy as sp
import sympy.physics.units as spu
import pydantic as pyd
from .....utils.pydantic_sympy import SympyExpr
from .. import base
from ... import contracts as ct
from .. import base
ST = ct.SocketType
SU = lambda socket_type: ct.SOCKET_UNITS[socket_type]['values']
def SU(socket_type): # noqa: N802, D103
return ct.SOCKET_UNITS[socket_type]['values']
####################
@ -195,58 +193,69 @@ class PhysicalUnitSystemBLSocket(base.MaxwellSimSocket):
def draw_value(self, col: bpy.types.UILayout) -> None:
if self.show_definition:
# TODO: We need panels instead of rows!!
col_row = col.row(align=False)
col_row.alignment = 'EXPAND'
col_row.prop(self, 'unit_time', text='')
col_row.prop(self, 'unit_angle', text='')
row = col.row()
row.alignment = 'CENTER'
row.label(text='Time | Angle')
col.prop(self, 'unit_time', text='t')
col.prop(self, 'unit_angle', text='θ')
col.separator(factor=1.0)
col_row = col.row(align=False)
col_row.alignment = 'EXPAND'
col_row.prop(self, 'unit_length', text='')
col_row.prop(self, 'unit_area', text='')
col_row.prop(self, 'unit_volume', text='')
row = col.row()
row.alignment = 'CENTER'
row.label(text='Len | Area | Vol')
col.prop(self, 'unit_length', text='l')
col.prop(self, 'unit_area', text='')
col.prop(self, 'unit_volume', text='')
col.separator(factor=1.0)
col_row = col.row(align=True)
col_row.alignment = 'EXPAND'
col_row.label(text='Point')
col_row.prop(self, 'unit_point_2d', text='')
col_row.prop(self, 'unit_point_3d', text='')
row = col.row()
row.alignment = 'CENTER'
row.label(text='Point')
col.prop(self, 'unit_point_2d', text='P₂')
col.prop(self, 'unit_point_3d', text='P₃')
col.separator(factor=1.0)
col_row = col.row(align=True)
col_row.alignment = 'EXPAND'
col_row.label(text='Size')
col_row.prop(self, 'unit_size_2d', text='')
col_row.prop(self, 'unit_size_3d', text='')
row = col.row()
row.alignment = 'CENTER'
row.label(text='Size')
col.prop(self, 'unit_size_2d', text='S₂')
col.prop(self, 'unit_size_3d', text='S₃')
col.separator(factor=1.0)
col_row = col.row(align=True)
col_row.alignment = 'EXPAND'
col_row.label(text='Mass')
col_row.prop(self, 'unit_mass', text='')
row = col.row()
row.alignment = 'CENTER'
row.label(text='Mass')
col.prop(self, 'unit_mass', text='M')
col.separator(factor=1.0)
col_row = col.row(align=True)
col_row.alignment = 'EXPAND'
col_row.label(text='Vel')
col_row.prop(self, 'unit_speed', text='')
# col_row.prop(self, "unit_vel_2d_vector", text="")
# col_row.prop(self, "unit_vel_3d_vector", text="")
row = col.row()
row.alignment = 'CENTER'
row.label(text='Vel')
col.prop(self, 'unit_speed', text='|v|')
# col.prop(self, "unit_vel_2d_vector", text="")
# col.prop(self, "unit_vel_3d_vector", text="")
col.separator(factor=1.0)
col_row = col.row(align=True)
col_row.label(text='Accel')
col_row.prop(self, 'unit_accel_scalar', text='')
# col_row.prop(self, "unit_accel_2d_vector", text="")
col_row.prop(self, 'unit_accel_3d', text='')
row = col.row()
row.alignment = 'CENTER'
row.label(text='Accel')
col.prop(self, 'unit_accel_scalar', text='|a|')
# col.prop(self, "unit_accel_2d_vector", text="")
col.prop(self, 'unit_accel_3d', text='a₃')
col.separator(factor=1.0)
col_row = col.row(align=True)
col_row.label(text='Force')
col_row.prop(self, 'unit_force_scalar', text='')
# col_row.prop(self, "unit_force_2d_vector", text="")
col_row.prop(self, 'unit_force_3d', text='')
row = col.row()
row.alignment = 'CENTER'
row.label(text='Force')
col.prop(self, 'unit_force_scalar', text='|F|')
# col.prop(self, "unit_force_2d_vector", text="")
col.prop(self, 'unit_force_3d', text='F₃')
col.separator(factor=1.0)
col_row = col.row(align=True)
col_row.alignment = 'EXPAND'
col_row.label(text='Freq')
col_row.prop(self, 'unit_freq', text='')
row = col.row()
row.alignment = 'CENTER'
row.label(text='Freq')
col.prop(self, 'unit_freq', text='t⁽⁻¹⁾')
####################
# - Default Value

View File

@ -17,8 +17,8 @@ log = simple_logger.get(__name__)
# - Preferences
####################
class BLMaxwellAddonPrefs(bpy.types.AddonPreferences):
"""Manages user preferences and settings for the Blender Maxwell addon.
"""
"""Manages user preferences and settings for the Blender Maxwell addon."""
bl_idname = info.ADDON_NAME ## MUST match addon package name
####################

View File

@ -29,10 +29,6 @@ IS_ONLINE = False
IS_AUTHENTICATED = False
def is_online():
return IS_ONLINE
def set_online():
global IS_ONLINE # noqa: PLW0603
IS_ONLINE = True
@ -99,8 +95,7 @@ class TidyCloudFolders:
raise RuntimeError(msg) from ex
folders = {
cloud_folder.folder_id: cloud_folder
for cloud_folder in cloud_folders
cloud_folder.folder_id: cloud_folder for cloud_folder in cloud_folders
}
cls.cache_folders = folders
return folders
@ -117,9 +112,7 @@ class TidyCloudFolders:
set_online()
except td.exceptions.WebError as ex:
set_offline()
msg = (
'Tried to create cloud folder, but cannot connect to cloud'
)
msg = 'Tried to create cloud folder, but cannot connect to cloud'
raise RuntimeError(msg) from ex
if cls.cache_folders is None:
@ -184,9 +177,7 @@ class TidyCloudTasks:
"""
cache_tasks: typ.ClassVar[dict[CloudTaskID, CloudTask]] = {}
cache_folder_tasks: typ.ClassVar[
dict[CloudFolderID, set[CloudTaskID]]
] = {}
cache_folder_tasks: typ.ClassVar[dict[CloudFolderID, set[CloudTaskID]]] = {}
cache_task_info: typ.ClassVar[dict[CloudTaskID, CloudTaskInfo]] = {}
@classmethod
@ -208,9 +199,7 @@ class TidyCloudTasks:
def tasks(cls, cloud_folder: CloudFolder) -> dict[CloudTaskID, CloudTask]:
"""Get all cloud tasks within a particular cloud folder as a set."""
# Retrieve Cached Tasks
if (
task_ids := cls.cache_folder_tasks.get(cloud_folder.folder_id)
) is not None:
if (task_ids := cls.cache_folder_tasks.get(cloud_folder.folder_id)) is not None:
return {task_id: cls.cache_tasks[task_id] for task_id in task_ids}
# Retrieve Tasks by-Folder
@ -219,9 +208,7 @@ class TidyCloudTasks:
set_online()
except td.exceptions.WebError as ex:
set_offline()
msg = (
'Tried to get tasks of a cloud folder, but cannot access cloud'
)
msg = 'Tried to get tasks of a cloud folder, but cannot access cloud'
raise RuntimeError(msg) from ex
# No Tasks: Empty Set
@ -231,9 +218,7 @@ class TidyCloudTasks:
# Populate Caches
## Direct Task Cache
cloud_tasks = {
cloud_task.task_id: cloud_task for cloud_task in folder_tasks
}
cloud_tasks = {cloud_task.task_id: cloud_task for cloud_task in folder_tasks}
cls.cache_tasks |= cloud_tasks
## Task Info Cache
@ -242,9 +227,7 @@ class TidyCloudTasks:
task_name=cloud_task.taskName,
status=cloud_task.status,
created_at=cloud_task.created_at,
cost_est=functools.partial(
td_web.estimate_cost, cloud_task.task_id
),
cost_est=functools.partial(td_web.estimate_cost, cloud_task.task_id),
run_info=cloud_task.get_running_info,
callback_url=cloud_task.callback_url,
)
@ -314,18 +297,14 @@ class TidyCloudTasks:
task_name=cloud_task.taskName,
status=cloud_task.status,
created_at=cloud_task.created_at,
cost_est=functools.partial(
td_web.estimate_cost, cloud_task.task_id
),
cost_est=functools.partial(td_web.estimate_cost, cloud_task.task_id),
run_info=cloud_task.get_running_info,
callback_url=cloud_task.callback_url,
)
## Task by-Folder Cache
if cls.cache_folder_tasks.get(cloud_task.folder_id):
cls.cache_folder_tasks[cloud_task.folder_id].add(
cloud_task.task_id
)
cls.cache_folder_tasks[cloud_task.folder_id].add(cloud_task.task_id)
else:
cls.cache_folder_tasks[cloud_task.folder_id] = {cloud_task.task_id}
@ -379,9 +358,7 @@ class TidyCloudTasks:
return cls.tasks(cloud_folder)[task_id]
@classmethod
def update_tasks(
cls, folder_id: CloudFolderID
) -> dict[CloudTaskID, CloudTask]:
def update_tasks(cls, folder_id: CloudFolderID) -> dict[CloudTaskID, CloudTask]:
"""Updates the CloudTask to the latest ex. status attributes."""
# BUG: td_web.core.task_core.SimulationTask.get(task_id) doesn't return the `created_at` field.
## Therefore, we unfortunately need to get all tasks for the folder ID just to update one.