有3d gcode预览,基本能按要求切片,但是缩放后切片会失败

This commit is contained in:
2026-04-12 17:09:19 +08:00
parent 3020957367
commit a3f8a31432
3280 changed files with 1433 additions and 634630 deletions

163
app/conf_parse.py Normal file
View File

@@ -0,0 +1,163 @@
import configparser
import json
import copy
import math
class ConfParse:
def __init__(self, config_def_json_files_paths):
self.config_def_json_files_paths = config_def_json_files_paths
self.configs = {}
for file in self.config_def_json_files_paths:
with open(file, 'r') as f:
jf = json.load(f)
if "settings" in jf:
setting_json = jf["settings"]
for key, value in setting_json.items():
# print(key, value)
all_items = self._expend_children(value["children"])
for item_key, item_value in all_items.items():
self.configs[item_key] = item_value
elif "overrides" in jf:
override_json = jf["overrides"]
for key, value in override_json.items():
if key in self.configs:
for item_key, item_value in value.items():
self.configs[key][item_key] = item_value
else:
self.configs[key] = value
def _expend_children(self, config):
tmp_c = {}
for key,val in config.items():
if "children" in val:
tmp_c.update(self._expend_children(val["children"]))
val.pop("children", None)
tmp_c[key] = val
return tmp_c
def add_inst_cfg(self, inst_cfg_files_paths):
copy_settings = copy.deepcopy(self.configs)
config = configparser.ConfigParser()
for file in inst_cfg_files_paths:
config.read(file)
if config.has_section('values'):
for key, val in config.items('values'):
v = str(val)
if key not in copy_settings:
copy_settings[key] = {}
if v.startswith("="):
copy_settings[key]["value"] = v[1:]
else:
copy_settings[key]["value"] = v
return copy_settings
def parse_configs(self, settings):
class ConfigStr(str):
def __mul__(self, other): raise TypeError()
def __rmul__(self, other): raise TypeError()
def __add__(self, other): raise TypeError()
def __radd__(self, other): raise TypeError()
def __sub__(self, other): raise TypeError()
def __rsub__(self, other): raise TypeError()
def __truediv__(self, other): raise TypeError()
def __rtruediv__(self, other): raise TypeError()
def __pow__(self, other): raise TypeError()
def __rpow__(self, other): raise TypeError()
parsed_settings = copy.deepcopy(settings)
last_unparsed = -1
while True:
unparsed = 0
# 构建上下文环境变量上下文用作eval的变量替换
context = {}
for k, v in parsed_settings.items():
# 上下文里的变量取值:优先使用 value如果有否则使用 default_value
if "value" in v:
val = v["value"]
elif "default_value" in v:
val = v["default_value"]
else:
val = None
if isinstance(val, str):
if val.lower() == "true":
val = True
elif val.lower() == "false":
val = False
else:
try:
val = int(val)
except ValueError:
try:
val = float(val)
except ValueError:
val = ConfigStr(val)
context[k] = val
# 自定义函数实现
def resolveOrValue(key):
return context.get(key)
def extruderValues(key):
# 兼容简易的多挤出机查询逻辑,目前单挤出机环境下返回一个单元素列表
return [context.get(key)]
def extruderValue(extruder_position, key):
# 对于单挤出机环境或者全局配置,直接忽略 extruder_position返回指定的 key 对应的值
return context.get(key)
def defaultExtruderPosition():
return 0
# 提供基础的运算函数支持
builtin_funcs = {
"max": max,
"min": min,
"abs": abs,
"round": round,
"int": int,
"float": float,
"bool": bool,
"math": math,
"resolveOrValue": resolveOrValue,
"extruderValues": extruderValues,
"extruderValue": extruderValue,
"defaultExtruderPosition": defaultExtruderPosition
}
for key, val_dict in parsed_settings.items():
for field, field_val in val_dict.items():
# 仅对字符串进行尝试计算
if "type" == field:
continue
if isinstance(field_val, str):
try:
# 如果是一个普通的纯字符串,比如分类名(如"Machine Type" eval可能会抛出SyntaxError或NameError
# 如果它是一个python表达式则会被顺利计算出结果
evaluated = eval(field_val, {"__builtins__": builtin_funcs}, context)
# 避免将原本只是用来作类型声明的 "int"/"float" 纯字符串,被错误求值为内置 Python type class 打断 JSON 序列化
if evaluated != field_val and not isinstance(evaluated, type):
if val_dict.get("type") == "str" and not isinstance(evaluated, str):
if isinstance(evaluated, (list, dict)):
import json
val_dict[field] = json.dumps(evaluated).replace(" ", "")
else:
val_dict[field] = str(evaluated)
else:
val_dict[field] = evaluated
except Exception:
# 解析失败(例如是个普通英文字符串或者依赖还没被解开)则暂不做处理
unparsed += 1
# 如果在这一轮中未解析出的表达式数量不再减少,说明已经到达极限,跳出循环
if unparsed == last_unparsed:
break
last_unparsed = unparsed
return parsed_settings