refactor menu to use helpers, add hot key display
This commit is contained in:
parent
f451308bb8
commit
0346393f7c
4 changed files with 180 additions and 174 deletions
179
src/mesh/api.js
179
src/mesh/api.js
|
|
@ -297,7 +297,7 @@ const pattern = {
|
|||
* @param {int} count number of entities
|
||||
* @param {float[]} center [x,y,z]
|
||||
*/
|
||||
circle(count, center) {
|
||||
circle() {
|
||||
async function doit(count = 3, center = [0,0], zdelta = 0) {
|
||||
api.modal.hide();
|
||||
let models = selection.models();
|
||||
|
|
@ -319,33 +319,29 @@ const pattern = {
|
|||
await api.tool.regroup(modnu);
|
||||
}
|
||||
}
|
||||
if (!count) {
|
||||
api.modal.dialog({
|
||||
title: "circle pattern",
|
||||
body: [ h.div({ class: "addgear" }, [
|
||||
h.label('total count'),
|
||||
h.input({ value: 3, size: 5, id: "_count" }),
|
||||
h.label('center x,y'),
|
||||
h.input({ value: "0,0", size: 5, id: "_center" }),
|
||||
// h.label('z delta'),
|
||||
// h.input({ value: "0", size: 5, id: "_zdelta" }),
|
||||
h.button({ _: "create", onclick() {
|
||||
let { _count, _center, _zdelta } = api.modal.bound;
|
||||
doit(
|
||||
parseInt(_count.value),
|
||||
_center.value.split(',').map(v => parseFloat(v)),
|
||||
// parseFloat(_zdelta.value)
|
||||
);
|
||||
} })
|
||||
]) ]
|
||||
});
|
||||
api.modal.bound._count.focus();
|
||||
} else {
|
||||
doit(count, origin);
|
||||
}
|
||||
api.modal.dialog({
|
||||
title: "circle pattern",
|
||||
body: [ h.div({ class: "addgear" }, [
|
||||
h.label('total count'),
|
||||
h.input({ value: 3, size: 5, id: "_count" }),
|
||||
h.label('center x,y'),
|
||||
h.input({ value: "0,0", size: 5, id: "_center" }),
|
||||
// h.label('z delta'),
|
||||
// h.input({ value: "0", size: 5, id: "_zdelta" }),
|
||||
h.button({ _: "create", onclick() {
|
||||
let { _count, _center, _zdelta } = api.modal.bound;
|
||||
doit(
|
||||
parseInt(_count.value),
|
||||
_center.value.split(',').map(v => parseFloat(v)),
|
||||
// parseFloat(_zdelta.value)
|
||||
);
|
||||
} })
|
||||
]) ]
|
||||
});
|
||||
api.modal.bound._count.focus();
|
||||
},
|
||||
|
||||
grid(x, y, xs, ys) {
|
||||
grid() {
|
||||
async function doit(x = 3, y = 3, xs = 10, ys = 10) {
|
||||
api.modal.hide();
|
||||
let models = selection.models();
|
||||
|
|
@ -364,32 +360,28 @@ const pattern = {
|
|||
await api.tool.regroup(modnu);
|
||||
}
|
||||
}
|
||||
if (!(x && y)) {
|
||||
api.modal.dialog({
|
||||
title: "grid pattern",
|
||||
body: [ h.div({ class: "addgear" }, [
|
||||
h.label('x count'),
|
||||
h.input({ value: 3, size: 5, id: "_x" }),
|
||||
h.label('y count'),
|
||||
h.input({ value: 3, size: 5, id: "_y" }),
|
||||
h.label('x spacing'),
|
||||
h.input({ value: 20, size: 5, id: "_xs" }),
|
||||
h.label('y spacing'),
|
||||
h.input({ value: 20, size: 5, id: "_ys" }),
|
||||
h.button({ _: "create", onclick() {
|
||||
doit(
|
||||
parseInt(api.modal.bound._x.value) || 3,
|
||||
parseInt(api.modal.bound._y.value) || 3,
|
||||
parseFloat(api.modal.bound._xs.value) || 3,
|
||||
parseFloat(api.modal.bound._ys.value) || 3,
|
||||
);
|
||||
} })
|
||||
]) ]
|
||||
});
|
||||
api.modal.bound._x.focus();
|
||||
} else {
|
||||
doit(x, y, xs, ys);
|
||||
}
|
||||
api.modal.dialog({
|
||||
title: "grid pattern",
|
||||
body: [ h.div({ class: "addgear" }, [
|
||||
h.label('x count'),
|
||||
h.input({ value: 3, size: 5, id: "_x" }),
|
||||
h.label('y count'),
|
||||
h.input({ value: 3, size: 5, id: "_y" }),
|
||||
h.label('x spacing'),
|
||||
h.input({ value: 20, size: 5, id: "_xs" }),
|
||||
h.label('y spacing'),
|
||||
h.input({ value: 20, size: 5, id: "_ys" }),
|
||||
h.button({ _: "create", onclick() {
|
||||
doit(
|
||||
parseInt(api.modal.bound._x.value) || 3,
|
||||
parseInt(api.modal.bound._y.value) || 3,
|
||||
parseFloat(api.modal.bound._xs.value) || 3,
|
||||
parseFloat(api.modal.bound._ys.value) || 3,
|
||||
);
|
||||
} })
|
||||
]) ]
|
||||
});
|
||||
api.modal.bound._x.focus();
|
||||
}
|
||||
};
|
||||
|
||||
|
|
@ -706,7 +698,7 @@ let add = {
|
|||
api.modal.dialog({
|
||||
title: "vertices",
|
||||
body: [ h.div({ class: "addact" }, [
|
||||
h.textarea({ value: '', size: 5, id: "genvrt" }),
|
||||
h.textarea({ value: '', cols:30, rows:4, id: "genvrt" }),
|
||||
h.button({ _: "create", onclick() {
|
||||
const vert = (api.modal.bound.genvrt.value)
|
||||
.split(',').map(v => parseFloat(v)).toFloat32();
|
||||
|
|
@ -725,10 +717,11 @@ let add = {
|
|||
const nmdl = new mesh.model({ file: "box", mesh: vert });
|
||||
const ngrp = group.new([ nmdl ]);
|
||||
ngrp.scale(10, 10, 10).floor();
|
||||
selection.set([ nmdl ]);
|
||||
return ngrp;
|
||||
},
|
||||
|
||||
cylinder(opt = {}) {
|
||||
cylinder() {
|
||||
function gencyl(opt = {}) {
|
||||
let { diameter, height, facets, chamfer, bore } = opt;
|
||||
api.modal.hide();
|
||||
|
|
@ -743,43 +736,40 @@ let add = {
|
|||
const vert = cyl.extrude(height, { chamfer }).toFloat32();
|
||||
const nmdl = new mesh.model({ file: "cylinder", mesh: vert });
|
||||
const ngrp = group.new([ nmdl ]);
|
||||
selection.set([ nmdl ]);
|
||||
ngrp.floor();
|
||||
}
|
||||
}
|
||||
if (opt.facets && opt.diameter && opt.height) {
|
||||
return gencyl(opt.diameter, opt.height, opt.facets);
|
||||
} else {
|
||||
api.modal.dialog({
|
||||
title: "cylinder",
|
||||
body: [ h.div({ class: "addgear" }, [
|
||||
h.label('diameter'),
|
||||
h.input({ value: opt.diameter || 20, size: 5, id: "_diameter" }),
|
||||
h.label('height'),
|
||||
h.input({ value: opt.height || 10, size: 5, id: "_height" }),
|
||||
h.hr(),
|
||||
h.label('bore'),
|
||||
h.input({ value: opt.facets || 0, size: 5, id: "_bore" }),
|
||||
h.label('facets'),
|
||||
h.input({ value: opt.facets || 0, size: 5, id: "_facets" }),
|
||||
h.label('chamfer'),
|
||||
h.input({ value: opt.chamfer || 0, size: 5, id: "_chamfer" }),
|
||||
h.button({ _: "create", onclick() {
|
||||
const { _diameter, _facets, _height, _chamfer, _bore } = api.modal.bound;
|
||||
gencyl({
|
||||
diameter: parseFloat(_diameter.value),
|
||||
height: parseFloat(_height.value),
|
||||
facets: parseInt(_facets.value),
|
||||
bore: parseFloat(_bore.value),
|
||||
chamfer: parseFloat(_chamfer.value),
|
||||
});
|
||||
} })
|
||||
]) ]
|
||||
});
|
||||
api.modal.bound._diameter.focus();
|
||||
}
|
||||
api.modal.dialog({
|
||||
title: "cylinder",
|
||||
body: [ h.div({ class: "addgear" }, [
|
||||
h.label('diameter'),
|
||||
h.input({ value: 20, size: 5, id: "_diameter" }),
|
||||
h.label('height'),
|
||||
h.input({ value: 10, size: 5, id: "_height" }),
|
||||
h.hr(),
|
||||
h.label('bore'),
|
||||
h.input({ value: 0, size: 5, id: "_bore" }),
|
||||
h.label('facets'),
|
||||
h.input({ value: 0, size: 5, id: "_facets" }),
|
||||
h.label('chamfer'),
|
||||
h.input({ value: 0, size: 5, id: "_chamfer" }),
|
||||
h.button({ _: "create", onclick() {
|
||||
const { _diameter, _facets, _height, _chamfer, _bore } = api.modal.bound;
|
||||
gencyl({
|
||||
diameter: parseFloat(_diameter.value),
|
||||
height: parseFloat(_height.value),
|
||||
facets: parseInt(_facets.value),
|
||||
bore: parseFloat(_bore.value),
|
||||
chamfer: parseFloat(_chamfer.value),
|
||||
});
|
||||
} })
|
||||
]) ]
|
||||
});
|
||||
api.modal.bound._diameter.focus();
|
||||
},
|
||||
|
||||
gear(opt = {}) {
|
||||
gear() {
|
||||
function gengear(bound) {
|
||||
const { _teeth, _module, _angle, _twist, _shaft, _offset, _height, _chamfer } = bound;
|
||||
api.modal.hide();
|
||||
|
|
@ -796,6 +786,7 @@ let add = {
|
|||
}).then(gear => {
|
||||
const nmdl = new mesh.model({ file: "gear", mesh: gear.toFloat32() });
|
||||
const ngrp = group.new([ nmdl ]);
|
||||
selection.set([ nmdl ]);
|
||||
ngrp.floor();
|
||||
Object.assign(last, params);
|
||||
api.prefs.save();
|
||||
|
|
@ -806,25 +797,25 @@ let add = {
|
|||
title: "gear generator",
|
||||
body: [ h.div({ class: "addgear" }, [
|
||||
h.label('number of teeth'),
|
||||
h.input({ value: opt.teeth || last.teeth || 20, size: 5, id: "_teeth" }),
|
||||
h.input({ value: last.teeth || 20, size: 5, id: "_teeth" }),
|
||||
h.label('shaft diameter'),
|
||||
h.input({ value: opt.shaft || last.shaft || 5, size: 5, id: "_shaft" }),
|
||||
h.input({ value: last.shaft || 5, size: 5, id: "_shaft" }),
|
||||
h.label('z height'),
|
||||
h.input({ value: opt.height || last.height || 15, size: 5, id: "_height" }),
|
||||
h.input({ value: last.height || 15, size: 5, id: "_height" }),
|
||||
h.label({ _:'chamfer', title:"negative values apply chamfer to the bottom only" }),
|
||||
h.input({ value: opt.chamfer || last.chamfer || 0, size: 5, id: "_chamfer" }),
|
||||
h.input({ value: last.chamfer || 0, size: 5, id: "_chamfer" }),
|
||||
h.hr(),
|
||||
h.code("all other settings must"),
|
||||
h.code("match for gears to mesh"),
|
||||
h.hr(),
|
||||
h.label('module (diam / teeth)'),
|
||||
h.input({ value: opt.module || last.module || 3, size: 5, id: "_module" }),
|
||||
h.input({ value: last.module || 3, size: 5, id: "_module" }),
|
||||
h.label('pressure angle'),
|
||||
h.input({ value: opt.angle || last.angle || 20, size: 5, id: "_angle" }),
|
||||
h.input({ value: last.angle || 20, size: 5, id: "_angle" }),
|
||||
h.label('twist angle (helix)'),
|
||||
h.input({ value: opt.twist || last.twist || 0, size: 5, id: "_twist" }),
|
||||
h.input({ value: last.twist || 0, size: 5, id: "_twist" }),
|
||||
h.label('tooth offset (play)'),
|
||||
h.input({ value: opt.offset || last.offset || 0.1, size: 5, id: "_offset" }),
|
||||
h.input({ value: last.offset || 0.1, size: 5, id: "_offset" }),
|
||||
h.button({ _: "create", onclick() { gengear(api.modal.bound) } })
|
||||
]) ]
|
||||
});
|
||||
|
|
|
|||
|
|
@ -8,8 +8,9 @@
|
|||
gapp.register("mesh.build", [], (root, exports) => {
|
||||
|
||||
const { broker } = gapp;
|
||||
const { mesh } = root;
|
||||
const { mesh, moto } = root;
|
||||
const { api, util } = mesh;
|
||||
const { space } = moto;
|
||||
const devel = api.isDebug;
|
||||
|
||||
let call = broker.send;
|
||||
|
|
@ -339,6 +340,20 @@ api.settings = function() {
|
|||
] ));
|
||||
}
|
||||
|
||||
function menu_item(text, fn, short) {
|
||||
if (short) {
|
||||
short = Array.isArray(short) ? short : [ short ];
|
||||
short = h.div({ class: "short" }, short.map(s => s.startsWith('bi-') ?
|
||||
h.i({ class: ["bi", s ]}) :
|
||||
h.div(s)
|
||||
));
|
||||
}
|
||||
return h.div({ onclick: fn }, [
|
||||
h.div({ _: text, class: "grow" }),
|
||||
short
|
||||
].filter(o => o));
|
||||
}
|
||||
|
||||
// create html elements
|
||||
function ui_build() {
|
||||
let { file, selection, mode, tool, sketch, prefs, add } = api;
|
||||
|
|
@ -351,52 +366,54 @@ function ui_build() {
|
|||
h.div({ class: "menu" }, [
|
||||
h.div('File'),
|
||||
h.div({ class: "menu-items" }, [
|
||||
h.div({ _: 'Import', onclick: file.import }, [
|
||||
h.input({
|
||||
id: "import", type: "file", class: ["hide"], multiple: true,
|
||||
onchange(evt) { broker.send.load_files(evt.target.files) }
|
||||
})
|
||||
]),
|
||||
h.div({ _: 'Export', onclick: file.export }),
|
||||
h.input({
|
||||
id: "import", type: "file", class: ["hide"], multiple: true,
|
||||
onchange(evt) { broker.send.load_files(evt.target.files) }
|
||||
}),
|
||||
menu_item('Import', file.import, 'I'),
|
||||
menu_item('Export', file.export, 'X'),
|
||||
h.hr(),
|
||||
h.div({ _: "Slicer", onclick: api.kirimoto }),
|
||||
menu_item('Slicer', api.kirimoto),
|
||||
h.hr(),
|
||||
h.div({ _: 'Close', onclick: window.close }),
|
||||
menu_item('Close', window.close),
|
||||
])
|
||||
]),
|
||||
h.div({ class: "menu sketch-on" }, [
|
||||
h.div('Edit'),
|
||||
h.div({ class: "menu-items" }, [
|
||||
h.div({ _: 'Add Circle', onclick() { sketch.selected.one?.add.circle() } }),
|
||||
h.div({ _: 'Add Rectangle', onclick() { sketch.selected.one?.add.rectangle() } }),
|
||||
menu_item('Add Circle', () => { sketch.selected.one?.add.circle() }),
|
||||
menu_item('Add Rectangle', () => { sketch.selected.one?.add.rectangle() }),
|
||||
h.hr(),
|
||||
h.div({ _: 'Add Sketch', onclick: add.sketch }),
|
||||
menu_item('Add Sketch', add.sketch),
|
||||
h.hr(),
|
||||
h.div({ _: 'Delete', onclick: api.selection.delete }),
|
||||
menu_item('Delete', api.selection.delete, 'bi-backspace'),
|
||||
])
|
||||
]),
|
||||
h.div({ class: "menu sketch-off" }, [
|
||||
h.div('Edit'),
|
||||
h.div({ class: "menu-items" }, [
|
||||
h.div({ _: 'Add Cylinder', onclick() { add.cylinder() } }),
|
||||
h.div({ _: 'Add Cube', onclick() { add.cube() } }),
|
||||
h.div({ _: 'Add Gear', onclick() { add.gear() } }),
|
||||
menu_item('Add Cylinder', add.cylinder),
|
||||
menu_item('Add Cube', add.cube),
|
||||
menu_item('Add Gear', add.gear),
|
||||
h.hr(),
|
||||
h.div({ _: 'Add Sketch', onclick: add.sketch }),
|
||||
devel ? h.div({ _: 'Add Vertices', onclick: add.input }) : undefined,
|
||||
menu_item('Add Sketch', add.sketch),
|
||||
devel ? menu_item('Add Vertices', add.input) : undefined,
|
||||
h.hr(),
|
||||
h.div({ _: 'Delete', onclick: api.selection.delete }),
|
||||
menu_item('Delete', api.selection.delete, 'bi-backspace'),
|
||||
])
|
||||
]),
|
||||
h.div({ class: "menu" }, [
|
||||
h.div('View'),
|
||||
h.div({ class: "menu-items" }, [
|
||||
h.div({ _: 'Bounds', onclick() { selection.boundsBox({ toggle: true }) } }),
|
||||
h.div({ _: 'Normals', onclick() { api.normals() } }),
|
||||
h.div({ _: 'Wireframes', onclick() { api.wireframe() } }),
|
||||
menu_item('Bounds', () => { selection.boundsBox({ toggle: true }) }, 'B'),
|
||||
menu_item('Normals', () => { api.normals() }, 'N'),
|
||||
menu_item('Wireframes', () => { api.wireframe() }, 'W'),
|
||||
h.hr(),
|
||||
h.div({ _: 'Gridlines', onclick() { api.grid() } }),
|
||||
h.div({ _: 'Messages', onclick() { api.log.toggle({ spinner: false }) } }),
|
||||
menu_item('Gridlines', () => { api.grid() }, 'G'),
|
||||
menu_item('Messages', () => { api.log.toggle({ spinner: false }) }, 'L'),
|
||||
h.hr(),
|
||||
menu_item('Home', space.view.home, 'H'),
|
||||
menu_item('Top', space.view.top, 'T'),
|
||||
])
|
||||
]),
|
||||
h.div({ class: "menu" }, [
|
||||
|
|
@ -415,75 +432,75 @@ function ui_build() {
|
|||
h.div({ class: "menu sketch-on" }, [
|
||||
h.div('Object'),
|
||||
h.div({ class: "menu-items" }, [
|
||||
h.div({ _: 'Group', onclick: sketch.arrange.group }),
|
||||
h.div({ _: 'Ungroup', onclick: sketch.arrange.ungroup }),
|
||||
menu_item('Group', sketch.arrange.group),
|
||||
menu_item('Ungroup', sketch.arrange.ungroup),
|
||||
h.hr(),
|
||||
h.div({ _: 'Center', onclick: sketch.arrange.center }),
|
||||
menu_item('Center', sketch.arrange.center),
|
||||
h.hr(),
|
||||
h.div({ _: 'Flip Horizontal', onclick: sketch.arrange.fliph }),
|
||||
h.div({ _: 'Flip Vertical', onclick: sketch.arrange.flipv }),
|
||||
menu_item('Flip Horizontal', sketch.arrange.fliph),
|
||||
menu_item('Flip Vertical', sketch.arrange.flipv),
|
||||
h.hr(),
|
||||
h.div({ _: 'Raise', onclick: sketch.arrange.up }),
|
||||
h.div({ _: 'Lower', onclick: sketch.arrange.down }),
|
||||
h.div({ _: 'Raise to Top', onclick: sketch.arrange.top }),
|
||||
h.div({ _: 'Lower to Bottom', onclick: sketch.arrange.bottom }),
|
||||
menu_item('Raise', sketch.arrange.up),
|
||||
menu_item('Lower', sketch.arrange.down),
|
||||
menu_item('To Top', sketch.arrange.top),
|
||||
menu_item('To Bottom', sketch.arrange.bottom),
|
||||
])
|
||||
]),
|
||||
h.div({ class: "menu sketch-off" }, [
|
||||
h.div('Object'),
|
||||
h.div({ class: "menu-items" }, [
|
||||
h.div({ _: 'Regroup', onclick: tool.regroup }),
|
||||
h.div({ _: 'Isolate', onclick: tool.isolate }),
|
||||
menu_item('Regroup', tool.regroup),
|
||||
menu_item('Isolate', tool.isolate),
|
||||
h.hr(),
|
||||
h.div({ _: 'Duplicate', onclick: tool.duplicate }),
|
||||
h.div({ _: 'Mirror', onclick: tool.mirror }),
|
||||
h.div({ _: 'Merge', onclick: tool.merge }),
|
||||
h.div({ _: 'Split', onclick: call.edit_split }),
|
||||
menu_item('Duplicate', tool.duplicate, ['bi-shift','D']),
|
||||
menu_item('Mirror', tool.mirror, 'M'),
|
||||
menu_item('Merge', tool.merge),
|
||||
menu_item('Split', mesh.split.start, 'S'),
|
||||
h.hr(),
|
||||
h.div({ _: 'Union', onclick: tool.union }),
|
||||
h.div({ _: 'Subtract', onclick: tool.subtract }),
|
||||
h.div({ _: 'Intersect', onclick: tool.intersect }),
|
||||
h.div({ _: 'Difference', onclick: tool.difference }),
|
||||
menu_item('Union', tool.union),
|
||||
menu_item('Subtract', tool.subtract),
|
||||
menu_item('Intersect', tool.intersect),
|
||||
menu_item('Difference', tool.difference),
|
||||
h.hr(),
|
||||
h.div({ _: 'Copy Circle', onclick: api.pattern.circle }),
|
||||
h.div({ _: 'Copy Grid', onclick: api.pattern.grid }),
|
||||
menu_item('Copy Circle', api.pattern.circle),
|
||||
menu_item('Copy Grid', api.pattern.grid),
|
||||
])
|
||||
]),
|
||||
h.div({ class: "menu sketch-off" }, [
|
||||
h.div('Faces'),
|
||||
h.div({ class: "menu-items" }, [
|
||||
h.div({ _: 'Flip Normals', onclick: tool.invert }),
|
||||
h.div({ _: 'Analyze', onclick: tool.analyze }),
|
||||
menu_item('Flip Normals', tool.invert),
|
||||
menu_item('Analyze', tool.analyze),
|
||||
// h.div({ _: 'Patch', onclick: tool.repair }),
|
||||
// h.div({ _: 'rebuild', onclick: tool.rebuild }),
|
||||
h.div({ _: 'Clean', onclick: tool.clean }),
|
||||
menu_item('Clean', tool.clean),
|
||||
])
|
||||
]),
|
||||
h.div({ class: "menu sketch-on" }, [
|
||||
h.div('Shape'),
|
||||
h.div({ class: "menu-items" }, [
|
||||
h.div({ _: 'Duplicate', onclick: api.tool.duplicate }),
|
||||
h.div({ _: 'Extrude', onclick: sketch.extrude }),
|
||||
menu_item('Duplicate', tool.duplicate, ['bi-shift','D']),
|
||||
menu_item('Extrude', sketch.extrude, ['bi-shift','E']),
|
||||
h.hr(),
|
||||
h.div({ _: 'Union', onclick: sketch.boolean.union }),
|
||||
h.div({ _: 'Intersect', onclick: sketch.boolean.intersect }),
|
||||
h.div({ _: 'Difference', onclick: sketch.boolean.difference }),
|
||||
menu_item('Union', sketch.boolean.union),
|
||||
menu_item('Intersect', sketch.boolean.intersect),
|
||||
menu_item('Difference', sketch.boolean.difference),
|
||||
h.hr(),
|
||||
h.div({ _: 'Nest', onclick: sketch.boolean.nest }),
|
||||
h.div({ _: 'Flatten', onclick: sketch.boolean.flatten }),
|
||||
h.div({ _: 'Even Odd', onclick: sketch.boolean.evenodd }),
|
||||
menu_item('Nest', sketch.boolean.nest),
|
||||
menu_item('Flatten', sketch.boolean.flatten),
|
||||
menu_item('Even Odd', sketch.boolean.evenodd),
|
||||
])
|
||||
]),
|
||||
h.div({ class: "menu" }, [
|
||||
h.div('Help'),
|
||||
h.div({ class: "menu-items" }, [
|
||||
h.div({ _: 'About', onclick() { api.welcome(mesh.version) } }),
|
||||
menu_item('About', () => { api.welcome(mesh.version) }),
|
||||
h.hr(),
|
||||
h.div({ _: 'Documentation', onclick: api.help }),
|
||||
h.div({ _: 'Official Site', onclick: api.gridspace }),
|
||||
h.div({ _: "Donate", onclick: api.donate }),
|
||||
menu_item('Documentation', api.help),
|
||||
menu_item('Official Site', api.gridspace),
|
||||
menu_item('Donate', api.donate),
|
||||
h.hr(),
|
||||
h.div({ _: 'Versions', onclick: api.version }),
|
||||
menu_item('Versions', api.version),
|
||||
])
|
||||
]),
|
||||
]);
|
||||
|
|
|
|||
|
|
@ -28,9 +28,6 @@ let split = {
|
|||
return;
|
||||
}
|
||||
let { api, util } = mesh;
|
||||
// highlight button
|
||||
let button = event.target;
|
||||
button.classList.add('selected');
|
||||
// create split plane visual
|
||||
let geo, mat, obj = new Mesh(
|
||||
geo = new PlaneGeometry(1,1),
|
||||
|
|
@ -45,7 +42,7 @@ let split = {
|
|||
// hide until first hover
|
||||
obj.visible = false;
|
||||
// enable temp mode
|
||||
let state = split.state = { button, obj };
|
||||
let state = split.state = { obj };
|
||||
let models = state.models = api.selection.models();
|
||||
let meshes = models.map(m => m.mesh);
|
||||
// for split and lay flat modes
|
||||
|
|
@ -92,8 +89,7 @@ let split = {
|
|||
return;
|
||||
}
|
||||
let space = moto.space;
|
||||
let { button, obj } = split.state;
|
||||
button.classList.remove('selected');
|
||||
let { obj } = split.state;
|
||||
space.scene.remove(obj);
|
||||
space.mouse.onHover(undefined);
|
||||
isActive = split.state = undefined;
|
||||
|
|
|
|||
|
|
@ -173,11 +173,11 @@ button:hover {
|
|||
padding: 0 !important;
|
||||
}
|
||||
|
||||
.menu {
|
||||
.menu, #top-right > div {
|
||||
cursor: default;
|
||||
align-self: stretch;
|
||||
align-items: center;
|
||||
padding: 5px 12px 5px 12px;
|
||||
padding: 6px 12px 6px 12px;
|
||||
border-radius: 6px;
|
||||
white-space: nowrap;
|
||||
user-select: none;
|
||||
|
|
@ -214,10 +214,19 @@ button:hover {
|
|||
}
|
||||
|
||||
.menu-items > div {
|
||||
gap: 15px;
|
||||
border-radius: 6px;
|
||||
padding: 4px 8px 4px 8px;
|
||||
}
|
||||
|
||||
.menu-items .grow {
|
||||
flex-grow: 1;
|
||||
}
|
||||
|
||||
.menu-items .short {
|
||||
gap: 1px;
|
||||
}
|
||||
|
||||
#top-mid {
|
||||
flex-grow: 1;
|
||||
}
|
||||
|
|
@ -230,13 +239,6 @@ button:hover {
|
|||
|
||||
#top-right > div {
|
||||
gap: 8px;
|
||||
align-self: stretch;
|
||||
align-items: center;
|
||||
padding: 5px 12px 5px 12px;
|
||||
border-radius: 6px;
|
||||
cursor: default;
|
||||
user-select: none;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
/** specific modal dialogs */
|
||||
|
|
@ -357,11 +359,11 @@ button:hover {
|
|||
/** welcome dialog **/
|
||||
|
||||
.welcome {
|
||||
font-size: smaller;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
padding: 5px;
|
||||
gap: 5px;
|
||||
font-size: smaller;
|
||||
}
|
||||
|
||||
.welcome a {
|
||||
|
|
@ -469,9 +471,9 @@ button:hover {
|
|||
background-color: rgba(0,255,0,0.8);
|
||||
}
|
||||
|
||||
.dark .head {
|
||||
/* .dark .head {
|
||||
color: #000 !important;
|
||||
}
|
||||
} */
|
||||
|
||||
/** slide in/out logging window **/
|
||||
|
||||
|
|
|
|||
Loading…
Reference in a new issue