import pako from "pako"; import { Color, Matrix4, Scene, Vector2, Vector3 } from "three"; import { Purge } from "../Add-on/Purge"; import { app } from "../ApplicationServices/Application"; import { HostApplicationServices } from "../ApplicationServices/HostApplicationServices"; import { ExtrudeHole } from "../DatabaseServices/3DSolid/ExtrudeHole"; import { CADFiler } from "../DatabaseServices/CADFiler"; import { Database } from "../DatabaseServices/Database"; import { Entity } from "../DatabaseServices/Entity/Entity"; import { Polyline } from "../DatabaseServices/Entity/Polyline"; import { PhysicalMaterialRecord } from "../DatabaseServices/PhysicalMaterialRecord"; import { TemplateParam } from "../DatabaseServices/Template/Param/TemplateParam"; import { TemplateRecord } from "../DatabaseServices/Template/TemplateRecord"; import { AsVector2 } from "../Geometry/GeUtils"; import { RenderType } from "../GraphicsSystem/RenderType"; import { userConfig } from './../Editor/UserConfig'; import { DisposeThreeObj } from "./Dispose"; import { uploadLogo } from "./Request"; import { DuplicateRecordCloning } from "./Status"; import { AAType } from "./SystemEnum"; export function MaterialOut(material: PhysicalMaterialRecord): string { let db = new Database(); db.WblockCloneObejcts( [material], db.MaterialTable, new Map(), DuplicateRecordCloning.Ignore ); return JSON.stringify(db.FileWrite().Data); } export function MaterialIn(fileData: Object[]): PhysicalMaterialRecord { let f = new CADFiler(fileData); let db = new Database().FileRead(f); db.hm.Enable = false; return db.MaterialTable.Symbols.entries().next().value[1]; } export function TemplateOut(template: TemplateRecord, tempDb = new Database(false, false, true)) { template = template.Root; let idMap = new Map(); tempDb.WblockCloneObejcts([template], tempDb.TemplateTable, idMap, DuplicateRecordCloning.Ignore); Purge(tempDb); let scs = template.GetTemplateRealitySpaceCS(); let scsInv = new Matrix4().getInverse(scs); for (let en of tempDb.ModelSpace.Entitys) en.ApplyMatrix(scsInv); for (let l of tempDb.Lights.Entitys) if (l.Id.Index > 99) l.ApplyMatrix(scsInv); return JSON.stringify(tempDb.FileWrite().Data); } export function TemplateIn(fileData: Object[]): TemplateRecord { let f = new CADFiler(fileData); let db = new Database(false, false, true).FileRead(f); return db.TemplateTable.Objects[0].Root; } export function TemplateParamsOut(params: TemplateParam[]) { let dataList = []; for (let par of params) { let filer = new CADFiler(); par.WriteFile(filer); dataList.push(filer.Data); } return JSON.stringify(dataList); } export function TemplateParamsIn(paramsData: Object[][]) { let pars: TemplateParam[] = []; for (let data of paramsData) { let file = new CADFiler(data); let par = new TemplateParam(); par.ReadFile(file); pars.push(par); } return pars; } /**反序列化材质并加入图纸*/ export function MaterialInAndAppendAppData(fileData: Object[], name?: string): PhysicalMaterialRecord { let mtl = MaterialIn(fileData) as PhysicalMaterialRecord; if (name) mtl.Name = name; return app.Database.WblockCloneObejcts( [mtl], app.Database.MaterialTable, new Map(), DuplicateRecordCloning.Rename )[0] as PhysicalMaterialRecord; } export function deflate(data: string) { let binaryString = pako.deflate(data, { to: "string" }); let base64 = btoa(binaryString); return base64; } export function inflate(base64: string) { let binaryString = atob(base64); let data = pako.inflate(binaryString, { to: "string" }); return data; } export function dataURItoBlob(dataURI: string) { // convert base64 to raw binary data held in a string // doesn't handle URLEncoded DataURIs - see SO answer #6850276 for code that does this var byteString = atob(dataURI.split(',')[1]); // separate out the mime component var mimeString = dataURI.split(',')[0].split(':')[1].split(';')[0]; // write the bytes of the string to an ArrayBuffer var ab = new ArrayBuffer(byteString.length); // create a view into the buffer var ia = new Uint8Array(ab); // set the bytes of the buffer to the correct values for (var i = 0; i < byteString.length; i++) { ia[i] = byteString.charCodeAt(i); } // write the ArrayBuffer to a blob, and you're done var blob = new Blob([ab], { type: mimeString }); return blob; } export function toplineFileIn(json: string) { let data = JSON.parse(json); let f = new CADFiler(data); let pl = new Polyline(); pl.ReadFile(f); return pl; } export function getPolylineSVG(en: Polyline) { let pl = en.Clone(); pl.OCS = new Matrix4(); //Y镜像 for (let d of pl.LineData) { d.pt.y = -d.pt.y; d.bul = -d.bul; } let box = pl.BoundingBox; let size = box.getSize(new Vector3()); let maxEdgeLength = Math.max(size.x, size.y); let m = AsVector2(pl.BoundingBox.min);//移动到0点 let scale = 90 / maxEdgeLength;//缩放到90,避免图形和边缘重合 let m2 = new Vector2((100 - scale * size.x) / 2, (100 - scale * size.y) / 2);//居中移动 for (let d of pl.LineData) { d.pt.sub(m);//移动到0 d.pt.multiplyScalar(scale); d.pt.add(m2);//居中 } return pl.SVG; } /** * 获取当前图纸的缩略图(预览图) */ export function GetCurrentViewPreViewImage(restore = true, isBase64 = false): Blob | string { //生成预览图 app.Viewer.OnSize(400, 400); app.Viewer.Render(); let url = app.Viewer.Renderer.domElement.toDataURL(isBase64 ? "image/png" : "image/jpeg"); if (restore) { app.Viewer.OnSize(); app.Viewer.Render(); } if (isBase64) return url; return dataURItoBlob(url); } export function ExtrudeDrillFileIn(data: any[]) { let f = new CADFiler(data); let en = new ExtrudeHole(); en.ReadFile(f); return en; } //返回logo url export async function GetEntitysLogo(ens: Entity[], isConceptual = false, dir = new Vector3(1, 1, -1), isBase64 = false) { //备份视图 let sceneBak = app.Viewer.Scene; let renderTypeBak: RenderType; let clearColorBak: Color; if (isConceptual) { renderTypeBak = userConfig.RenderType; HostApplicationServices._renderType = RenderType.Conceptual; clearColorBak = app.Viewer.Renderer.getClearColor().clone(); app.Viewer.Renderer.setClearColor(new Color()); } let aabak = app.Viewer.AAType; let f = new CADFiler(); app.Viewer.CameraCtrl.WriteFile(f); //设置视图 app.Viewer.Scene = new Scene(); app.Viewer._AAType = AAType.SMAA; app.Viewer.CameraCtrl.LookAt(dir); //绘制 for (let e of ens) app.Viewer.Scene.add(e.DrawObject); app.Viewer.ZoomAll(false); let blob = GetCurrentViewPreViewImage(false, isBase64); //还原视图 [app.Viewer.Scene, sceneBak] = [sceneBak, app.Viewer.Scene]; if (isConceptual) { HostApplicationServices._renderType = renderTypeBak; app.Viewer.Renderer.setClearColor(clearColorBak); } app.Viewer._AAType = aabak; f.Reset(); app.Viewer.CameraCtrl.ReadFile(f); app.Viewer.OnSize(); DisposeThreeObj(sceneBak); if (isBase64) return blob; //上传 let logo = await uploadLogo(blob as Blob); return logo; } export function GroupOut(ens: Entity[]) { let file = new CADFiler(); file.Write(ens.length); for (let e of ens) { file.WriteObject(e); } return JSON.stringify(file.Data); } export function GroupFileIn(fileData: Object[]): Entity[] { let f = new CADFiler(fileData); let count = f.Read(); let ens: Entity[] = []; for (let i = 0; i < count; i++) { let en = f.ReadObject() as Entity; ens.push(en); } return ens; } export function EntitysOut(ens: Entity[], callback?: (en) => void) { let dataList = []; for (let en of ens) { let vf = new CADFiler(); if (callback) callback(en); en.WriteFile(vf); dataList.push(vf.Data); } return JSON.stringify(dataList); } export function EntitysIn(datalist: any[]) { let ens: Entity[] = []; for (let data of datalist) ens.push(ExtrudeDrillFileIn(data)); return ens; }