mirror of https://gitee.com/cf-fz/WebCAD.git
!1938 重构:标注样式 标注板件(AutoDimBrs,FastDim)
parent
5ad2c7251f
commit
808351edd5
@ -0,0 +1,59 @@
|
|||||||
|
import { Euler, Matrix4, Vector3 } from "three";
|
||||||
|
import { equaln } from "../../src/Geometry/GeUtils";
|
||||||
|
|
||||||
|
// file.only
|
||||||
|
|
||||||
|
|
||||||
|
//证明 EU和旋转矩阵复合的转换
|
||||||
|
test('Euler', () =>
|
||||||
|
{
|
||||||
|
let x = 0.5,
|
||||||
|
y = 2,
|
||||||
|
z = 1;
|
||||||
|
|
||||||
|
let eu = new Euler(x, y, z, "ZYX");
|
||||||
|
let mtxEu = new Matrix4().makeRotationFromEuler(eu);//Eu旋转矩阵
|
||||||
|
|
||||||
|
let mtxx = new Matrix4().makeRotationX(x);
|
||||||
|
let mtxy = new Matrix4().makeRotationY(y);
|
||||||
|
let mtxz = new Matrix4().makeRotationZ(z);
|
||||||
|
|
||||||
|
|
||||||
|
let mtxCom = mtxx.clone().premultiply(mtxy).premultiply(mtxz);//复合矩阵 z * y * x
|
||||||
|
|
||||||
|
for (let i = 0; i < mtxEu.elements.length; i++)
|
||||||
|
expect(equaln(mtxEu.elements[i], mtxCom.elements[i])).toBeTruthy();//证明 z*y*x =Euler("ZYX")
|
||||||
|
|
||||||
|
let p = new Vector3(1, 2, 3);
|
||||||
|
p.clone().applyMatrix4(mtxCom);//?
|
||||||
|
p.clone().applyMatrix4(mtxx).applyMatrix4(mtxy).applyMatrix4(mtxz);//?
|
||||||
|
|
||||||
|
//证明了EU角度不可逆转
|
||||||
|
new Euler(0, 0, 0, "ZYX").setFromRotationMatrix(mtxCom);//?
|
||||||
|
|
||||||
|
//证明了这个不能逆转..
|
||||||
|
let euT = new Euler(Math.PI / 2, Math.PI / 2, 0, "ZYX");
|
||||||
|
euT.setFromRotationMatrix(new Matrix4().makeRotationFromEuler(euT));//?
|
||||||
|
});
|
||||||
|
|
||||||
|
//证明 mtxa * mtxb = p.apply(mtxb).apply(mtxa)
|
||||||
|
test('mtx a*b', () =>
|
||||||
|
{
|
||||||
|
let mtx1 = new Matrix4().setPosition(100, 0, 0);
|
||||||
|
let mtx2 = new Matrix4().makeRotationZ(Math.PI / 2);//旋转90度
|
||||||
|
let p = new Vector3(100, 0, 0);
|
||||||
|
mtx1.multiply(mtx2);
|
||||||
|
p.applyMatrix4(mtx1);
|
||||||
|
p; //?
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
test('mtx a*b2', () =>
|
||||||
|
{
|
||||||
|
let mtx1 = new Matrix4().setPosition(100, 0, 0);
|
||||||
|
let mtx2 = new Matrix4().makeRotationZ(Math.PI / 2);
|
||||||
|
mtx1.premultiply(mtx2);
|
||||||
|
let p = new Vector3(100, 0, 0);
|
||||||
|
p.applyMatrix4(mtx1);
|
||||||
|
p; //?
|
||||||
|
});
|
@ -0,0 +1,60 @@
|
|||||||
|
import { observable, toJS } from "mobx";
|
||||||
|
import { DefaultAutoDimBrsOption } from "../../Editor/DefaultConfig";
|
||||||
|
import { BoardModalType } from "../../UI/Components/Board/BoardModalType";
|
||||||
|
import { IConfigOption } from "../../UI/Components/Board/UserConfig";
|
||||||
|
import { IAutoDimBrsOption } from "../../UI/Store/BoardInterface";
|
||||||
|
import { IConfigStore } from "../../UI/Store/BoardStore";
|
||||||
|
import { userConfigStore } from "../../UI/Store/UserConfigStore";
|
||||||
|
|
||||||
|
export class AutoDimBrsStore implements IConfigStore
|
||||||
|
{
|
||||||
|
@observable configName = "默认";
|
||||||
|
@observable configsNames: string[] = [];
|
||||||
|
@observable m_Option: IAutoDimBrsOption = { ...DefaultAutoDimBrsOption };
|
||||||
|
|
||||||
|
InitOption()
|
||||||
|
{
|
||||||
|
Object.assign(this.m_Option, DefaultAutoDimBrsOption);
|
||||||
|
}
|
||||||
|
|
||||||
|
InitConfigs()
|
||||||
|
{
|
||||||
|
let config: IConfigOption = {};
|
||||||
|
config.option = toJS(this.m_Option);
|
||||||
|
let configs: { [key: string]: IConfigOption; } = {};
|
||||||
|
configs["默认"] = config;
|
||||||
|
|
||||||
|
return configs;
|
||||||
|
}
|
||||||
|
|
||||||
|
SaveConfig()
|
||||||
|
{
|
||||||
|
//新的配置
|
||||||
|
let newConfig: IConfigOption = {};
|
||||||
|
newConfig.option = toJS(this.m_Option);
|
||||||
|
return newConfig;
|
||||||
|
};
|
||||||
|
|
||||||
|
UpdateOption(conf: IConfigOption<any>)
|
||||||
|
{
|
||||||
|
if (!conf.option)
|
||||||
|
{
|
||||||
|
this.InitOption();
|
||||||
|
let config = this.InitConfigs();
|
||||||
|
userConfigStore.InitConfigs(config, BoardModalType.AutoDimBrs);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Object.assign(this.m_Option, conf.option);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static _SingleInstance: AutoDimBrsStore;
|
||||||
|
static GetInstance(): AutoDimBrsStore
|
||||||
|
{
|
||||||
|
if (this._SingleInstance) return this._SingleInstance;
|
||||||
|
this._SingleInstance = new AutoDimBrsStore;
|
||||||
|
return this._SingleInstance;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export const autoDimBrsStore = AutoDimBrsStore.GetInstance();
|
@ -0,0 +1,27 @@
|
|||||||
|
import { CADFiler } from "../CADFiler";
|
||||||
|
import { ObjectId } from "../ObjectId";
|
||||||
|
import { Factory } from "./../CADFactory";
|
||||||
|
import { SymbolTable } from "./../SymbolTable";
|
||||||
|
|
||||||
|
|
||||||
|
@Factory
|
||||||
|
export class DimStyleTable extends SymbolTable
|
||||||
|
{
|
||||||
|
Current: ObjectId;
|
||||||
|
//#region -------------------------File-------------------------
|
||||||
|
//对象从文件中读取数据,初始化自身
|
||||||
|
override ReadFile(file: CADFiler)
|
||||||
|
{
|
||||||
|
let ver = file.Read();
|
||||||
|
super.ReadFile(file);
|
||||||
|
this.Current = file.ReadObjectId();
|
||||||
|
}
|
||||||
|
//对象将自身数据写入到文件.
|
||||||
|
override WriteFile(file: CADFiler)
|
||||||
|
{
|
||||||
|
file.Write(1);
|
||||||
|
super.WriteFile(file);
|
||||||
|
file.WriteObjectId(this.Current);
|
||||||
|
}
|
||||||
|
//#endregion
|
||||||
|
}
|
@ -0,0 +1,179 @@
|
|||||||
|
import { Intent, Position, Slider, Tooltip } from "@blueprintjs/core";
|
||||||
|
import { observable } from "mobx";
|
||||||
|
import { observer } from "mobx-react";
|
||||||
|
import React from "react";
|
||||||
|
import { app } from "../../../ApplicationServices/Application";
|
||||||
|
import { safeEval } from "../../../Common/eval";
|
||||||
|
import { KeyBoard } from "../../../Common/KeyEnum";
|
||||||
|
import { FixedNotZero } from "../../../Common/Utils";
|
||||||
|
import { AlignedDimension } from "../../../DatabaseServices/Dimension/AlignedDimension";
|
||||||
|
import { Dimension } from "../../../DatabaseServices/Dimension/Dimension";
|
||||||
|
import { DimStyleKeyCode } from "../../../DatabaseServices/DimStyle/DimstyleKeyCodeEnum";
|
||||||
|
import { commandMachine, CommandWrap } from "../../../Editor/CommandMachine";
|
||||||
|
import { CommandState } from "../../../Editor/CommandState";
|
||||||
|
import { AppToaster } from "../Toaster";
|
||||||
|
import { DimParamsList } from "./Properties_Dim";
|
||||||
|
|
||||||
|
interface DimParamsPanelProps
|
||||||
|
{
|
||||||
|
dims: Dimension[];
|
||||||
|
dimParam: [string, string];
|
||||||
|
changeFunction: (dim: AlignedDimension, length: number, keys: string[]) => void;
|
||||||
|
}
|
||||||
|
|
||||||
|
@observer
|
||||||
|
export class DimParamsPanel extends React.Component<DimParamsPanelProps, {}>
|
||||||
|
{
|
||||||
|
@observable _ParamValue: number = 0;
|
||||||
|
@observable _MinValue: number = 0;
|
||||||
|
@observable _MaxValue: number = 0;
|
||||||
|
@observable _IsPopoverOpen: boolean = false;
|
||||||
|
@observable _StepSize: number = 1;
|
||||||
|
_InputRef: React.RefObject<HTMLInputElement> = React.createRef<HTMLInputElement>();;
|
||||||
|
_SilderRef: React.RefObject<Slider> = React.createRef<Slider>();;
|
||||||
|
|
||||||
|
constructor(props)
|
||||||
|
{
|
||||||
|
super(props);
|
||||||
|
let dim = (this.props.dims[0] as AlignedDimension);
|
||||||
|
switch (this.props.dimParam[0])
|
||||||
|
{
|
||||||
|
case DimParamsList.FootLineLength:
|
||||||
|
this._ParamValue = dim.GetDimStyleValue(DimStyleKeyCode.DIMFXL);
|
||||||
|
this._MaxValue = 500;
|
||||||
|
this._StepSize = 1;
|
||||||
|
break;
|
||||||
|
case DimParamsList.ArrowSize:
|
||||||
|
this._ParamValue = dim.GetDimStyleValue(DimStyleKeyCode.DIMASZ);
|
||||||
|
this._MaxValue = 20;
|
||||||
|
this._StepSize = 1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
changeElValue(value: number)
|
||||||
|
{
|
||||||
|
this._ParamValue = value;
|
||||||
|
this._InputRef.current.value = FixedNotZero(value, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
render()
|
||||||
|
{
|
||||||
|
return (
|
||||||
|
<div className="paramPanel">
|
||||||
|
<div className="input_group">
|
||||||
|
<span>{this.props.dimParam[1]}: </span>
|
||||||
|
<div className="numeric_input" >
|
||||||
|
<Tooltip
|
||||||
|
content={"仅限" + this._MinValue + "-" + this._MaxValue + "间的数字!"}
|
||||||
|
position={Position.TOP}
|
||||||
|
intent={Intent.WARNING}
|
||||||
|
isOpen={this._IsPopoverOpen}
|
||||||
|
>
|
||||||
|
<input
|
||||||
|
ref={this._InputRef}
|
||||||
|
defaultValue={this._ParamValue}
|
||||||
|
style={{ width: "100%" }}
|
||||||
|
onChange={(e) =>
|
||||||
|
{
|
||||||
|
let val = safeEval(e.target.value);
|
||||||
|
if (!isNaN(val))
|
||||||
|
{
|
||||||
|
if (val < this._MinValue || val > this._MaxValue)
|
||||||
|
this._IsPopoverOpen = true;
|
||||||
|
else
|
||||||
|
this._IsPopoverOpen = false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
this._IsPopoverOpen = true;
|
||||||
|
}}
|
||||||
|
onKeyDown={(e) =>
|
||||||
|
{
|
||||||
|
if (e.keyCode === KeyBoard.Escape)
|
||||||
|
{
|
||||||
|
this._InputRef.current.value = this._ParamValue.toString();
|
||||||
|
//@ts-ignore
|
||||||
|
e.target.blur();
|
||||||
|
}
|
||||||
|
else if (e.keyCode === KeyBoard.Enter || e.keyCode === KeyBoard.Space)
|
||||||
|
{
|
||||||
|
if (!this._IsPopoverOpen)
|
||||||
|
//@ts-ignore
|
||||||
|
e.target.blur();
|
||||||
|
e.preventDefault();
|
||||||
|
}
|
||||||
|
e.stopPropagation();
|
||||||
|
}}
|
||||||
|
onFocus={(e) =>
|
||||||
|
{
|
||||||
|
this._InputRef.current.setSelectionRange(0, this._InputRef.current.value.length);
|
||||||
|
}}
|
||||||
|
onBlur={(e) =>
|
||||||
|
{
|
||||||
|
if (!this._IsPopoverOpen)
|
||||||
|
{
|
||||||
|
let val = safeEval(e.target.value);
|
||||||
|
if (val === this._ParamValue) return;
|
||||||
|
CommandWrap(() =>
|
||||||
|
{
|
||||||
|
for (let dim of this.props.dims)
|
||||||
|
{
|
||||||
|
if (dim instanceof AlignedDimension)
|
||||||
|
{
|
||||||
|
this.props.changeFunction(dim, val, [this.props.dimParam[0]]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}, "修改标注" + this.props.dimParam[1]);
|
||||||
|
this._ParamValue = val;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
e.target.value = FixedNotZero(this._ParamValue, 1);
|
||||||
|
this._IsPopoverOpen = false;
|
||||||
|
}
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
</Tooltip>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<Slider
|
||||||
|
min={this._MinValue}
|
||||||
|
max={this._MaxValue}
|
||||||
|
stepSize={this._StepSize}
|
||||||
|
ref={this._SilderRef}
|
||||||
|
labelRenderer={false}
|
||||||
|
onChange={(value) =>
|
||||||
|
{
|
||||||
|
if (!CommandState.CommandIng)
|
||||||
|
commandMachine.CommandStart("更改标注" + this.props.dimParam[1]);
|
||||||
|
else
|
||||||
|
if (app.Database.hm.UndoData.CommandName !== "更改标注" + this.props.dimParam[1])
|
||||||
|
{
|
||||||
|
AppToaster.show({
|
||||||
|
message: "命令执行中,无法修改标注" + this.props.dimParam[1],
|
||||||
|
timeout: 5000,
|
||||||
|
intent: Intent.WARNING,
|
||||||
|
}, "change_dim_text");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
this._InputRef.current.value = FixedNotZero(value, 1);
|
||||||
|
this._ParamValue = value;
|
||||||
|
for (let dim of this.props.dims)
|
||||||
|
{
|
||||||
|
if (dim instanceof AlignedDimension)
|
||||||
|
this.props.changeFunction(dim, value, [this.props.dimParam[0]]);
|
||||||
|
}
|
||||||
|
}}
|
||||||
|
value={this._ParamValue > this._MaxValue ? this._MaxValue : this._ParamValue}
|
||||||
|
onRelease={() =>
|
||||||
|
{
|
||||||
|
if (CommandState.CommandIng && app.Database.hm.UndoData.CommandName === "更改标注" + this.props.dimParam[1])
|
||||||
|
commandMachine.CommandEnd();
|
||||||
|
}}
|
||||||
|
vertical={false}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in new issue