mirror of
https://github.com/JannisX11/blockbench.git
synced 2025-01-30 15:42:42 +08:00
Add pan tool
Fix panel resizing direction on mobile Remove screen orientation preference Fix error message when changing keybinding on search result
This commit is contained in:
parent
b97fd52f12
commit
8f310a1e0e
@ -244,6 +244,11 @@
|
||||
top: unset;
|
||||
bottom: 0;
|
||||
}
|
||||
|
||||
body.is_mobile #panel_uv,
|
||||
body.is_mobile #panel_color {
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
/*Display*/
|
||||
|
||||
@ -1567,6 +1572,9 @@
|
||||
float: right;
|
||||
pointer-events: none;
|
||||
}
|
||||
body.is_mobile .panel .bar.next_to_title {
|
||||
margin-right: 32px;
|
||||
}
|
||||
.panel .bar.next_to_title > .tool {
|
||||
float: right;
|
||||
pointer-events: initial;
|
||||
|
@ -343,8 +343,15 @@
|
||||
body.is_mobile .toolbar_wrapper.narrow.tools {
|
||||
position: absolute;
|
||||
z-index: 2;
|
||||
top: 0;
|
||||
bottom: 0px;
|
||||
right: 0px;
|
||||
display: flex;
|
||||
align-items: end;
|
||||
}
|
||||
body.is_mobile .toolbar_wrapper.narrow.tools .toolbar {
|
||||
height: auto;
|
||||
max-height: 100%;
|
||||
}
|
||||
body.is_mobile #main_toolbar > div.tool_options {
|
||||
background-color: var(--color-back);
|
||||
|
@ -839,7 +839,9 @@ const Animator = {
|
||||
Animator.timeline_node = Panels.timeline.node;
|
||||
}
|
||||
updateInterface()
|
||||
Toolbars.element_origin.toPlace('bone_origin')
|
||||
if (Panels.element) {
|
||||
Toolbars.element_origin.toPlace('bone_origin')
|
||||
}
|
||||
if (!Timeline.is_setup) {
|
||||
Timeline.setup()
|
||||
}
|
||||
@ -865,8 +867,10 @@ const Animator = {
|
||||
scene.remove(Animator.motion_trail);
|
||||
Animator.resetParticles(true);
|
||||
|
||||
let anchor = Panels.element.node.querySelector('#element_origin_toolbar_anchor');
|
||||
if (anchor) anchor.before(Toolbars.element_origin.node);
|
||||
if (Panels.element) {
|
||||
let anchor = Panels.element.node.querySelector('#element_origin_toolbar_anchor');
|
||||
if (anchor) anchor.before(Toolbars.element_origin.node);
|
||||
}
|
||||
|
||||
Canvas.updateAllBones()
|
||||
},
|
||||
|
@ -1934,6 +1934,7 @@ const BARS = {
|
||||
'pivot_tool',
|
||||
'vertex_snap_tool',
|
||||
'seam_tool',
|
||||
'pan_tool',
|
||||
'brush_tool',
|
||||
'fill_tool',
|
||||
'eraser',
|
||||
@ -1947,6 +1948,7 @@ const BARS = {
|
||||
})
|
||||
Blockbench.onUpdateTo('4.2.0-beta.2', () => {
|
||||
Toolbars.tools.add(BarItems.seam_tool, 5);
|
||||
Toolbars.tools.add(BarItems.pan_tool, 6);
|
||||
})
|
||||
|
||||
Toolbars.element_position = new Toolbar({
|
||||
|
@ -548,8 +548,7 @@ function setZoomLevel(mode) {
|
||||
case 'out': zoom *= 0.66; break;
|
||||
case 'reset': zoom = 1; break;
|
||||
}
|
||||
zoom = limitNumber(zoom, 1, 4)
|
||||
UVEditor.setZoom(zoom)
|
||||
UVEditor.setZoom(zoom);
|
||||
|
||||
} else if (Prop.active_panel == 'timeline') {
|
||||
|
||||
|
@ -665,13 +665,16 @@ function setupMobilePanelSelector() {
|
||||
},
|
||||
select(panel) {
|
||||
this.selected = panel && panel.id;
|
||||
for (let key in Panels) {
|
||||
let panel_b = Panels[key];
|
||||
if (panel_b.slot == 'bottom') {
|
||||
$(panel_b.node).detach();
|
||||
panel_b.slot = 'left_bar';
|
||||
}
|
||||
}
|
||||
if (panel) {
|
||||
panel.moveTo('bottom');
|
||||
} else {
|
||||
let other_panel = Interface.getBottomPanel();
|
||||
if (other_panel) {
|
||||
$(other_panel.node).detach();
|
||||
}
|
||||
resizeWindow();
|
||||
}
|
||||
},
|
||||
|
@ -64,7 +64,10 @@ class Mode extends KeybindItem {
|
||||
}
|
||||
if (Blockbench.isMobile) {
|
||||
Interface.PanelSelectorVue.$forceUpdate();
|
||||
Interface.PanelSelectorVue.select(null);
|
||||
let bottom_panel = Interface.getBottomPanel();
|
||||
if (bottom_panel && !Condition(bottom_panel.display_condition)) {
|
||||
Interface.PanelSelectorVue.select(null);
|
||||
}
|
||||
}
|
||||
|
||||
if (Interface.Panels[Prop.active_panel] && !Condition(Interface.Panels[Prop.active_panel].condition)) {
|
||||
|
@ -2101,7 +2101,8 @@ BARS.defineActions(function() {
|
||||
Preview.all.forEach(preview => {
|
||||
if (!preview.offscreen) {
|
||||
let icon = Blockbench.getIconNode(this.options[this.value].icon);
|
||||
preview.node.querySelector('.preview_view_mode_menu > i').replaceWith(icon);
|
||||
let icon_node = preview.node.querySelector('.preview_view_mode_menu > i');
|
||||
if (icon_node) icon_node.replaceWith(icon);
|
||||
}
|
||||
})
|
||||
//Blockbench.showQuickMessage(tl('action.view_mode') + ': ' + tl('action.view_mode.' + this.value));
|
||||
|
@ -148,14 +148,7 @@ const Painter = {
|
||||
Painter.current.y = y
|
||||
Painter.current.face = data.face
|
||||
Painter.current.element = data.element
|
||||
delete Painter.current.face_matrix;
|
||||
new_face = true
|
||||
if (Painter.current.element instanceof Mesh) {
|
||||
let face = Painter.current.element.faces[Painter.current.face];
|
||||
if (face && face.vertices.length > 2) {
|
||||
Painter.current.face_matrix = face.getOccupationMatrix(true, [0, 0]);
|
||||
}
|
||||
}
|
||||
if (texture !== Painter.current.texture) {
|
||||
Undo.current_save.addTexture(texture)
|
||||
}
|
||||
@ -199,12 +192,6 @@ const Painter = {
|
||||
var is_line = (event.shiftKey || Pressing.overrides.shift) && Painter.current.element == data.element && Painter.current.face == data.face
|
||||
Painter.current.element = data.element;
|
||||
Painter.current.face = data.face;
|
||||
if (Painter.current.element instanceof Mesh) {
|
||||
let face = Painter.current.element.faces[Painter.current.face];
|
||||
if (face && face.vertices.length > 2) {
|
||||
Painter.current.face_matrix = face.getOccupationMatrix(true, [0, 0]);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
//uv editor
|
||||
var is_line = (event.shiftKey || Pressing.overrides.shift);
|
||||
@ -303,9 +290,19 @@ const Painter = {
|
||||
let target = Painter.getMirrorPaintTarget(texture, x, y, uvTag)
|
||||
if (target) {
|
||||
let old_element = Painter.current.element;
|
||||
let old_face = Painter.current.face;
|
||||
Painter.current.element = target.element;
|
||||
Painter.current.face = target.face;
|
||||
Painter.useBrushlike(texture, target.x, target.y, event, target.uv_tag, true, true);
|
||||
Painter.current.element = old_element;
|
||||
Painter.current.face = old_face;
|
||||
}
|
||||
}
|
||||
delete Painter.current.face_matrix;
|
||||
if (Painter.current.element instanceof Mesh) {
|
||||
let face = Painter.current.element.faces[Painter.current.face];
|
||||
if (face && face.vertices.length > 2) {
|
||||
Painter.current.face_matrix = face.getOccupationMatrix(true, [0, 0]);
|
||||
}
|
||||
}
|
||||
|
||||
@ -333,6 +330,13 @@ const Painter = {
|
||||
let tool = Toolbox.selected.id;
|
||||
|
||||
ctx.clip()
|
||||
delete Painter.current.face_matrix;
|
||||
if (Painter.current.element instanceof Mesh) {
|
||||
let face = Painter.current.element.faces[Painter.current.face];
|
||||
if (face && face.vertices.length > 2) {
|
||||
Painter.current.face_matrix = face.getOccupationMatrix(true, [0, 0]);
|
||||
}
|
||||
}
|
||||
if (event.touches && event.touches[0] && event.touches[0].touchType == 'stylus' && event.touches[0].force) {
|
||||
|
||||
// Stylus
|
||||
@ -519,10 +523,10 @@ const Painter = {
|
||||
let uvFactorX = 1 / Project.texture_width * texture.img.naturalWidth;
|
||||
let uvFactorY = 1 / Project.texture_height * texture.img.naturalHeight;
|
||||
|
||||
let face = Painter.current.face;
|
||||
let side_face = (face === 'west' || face === 'east')
|
||||
if (side_face) face = CubeFace.opposite[face];
|
||||
face = mirror_element.faces[face];
|
||||
let fkey = Painter.current.face;
|
||||
let side_face = (fkey === 'west' || fkey === 'east')
|
||||
if (side_face) fkey = CubeFace.opposite[fkey];
|
||||
let face = mirror_element.faces[fkey];
|
||||
|
||||
if (side_face &&
|
||||
uvTag[1] === face.uv[1] && uvTag[3] === face.uv[3] &&
|
||||
@ -552,7 +556,8 @@ const Painter = {
|
||||
element: mirror_element,
|
||||
x: point_on_uv[0],
|
||||
y: point_on_uv[1],
|
||||
uv_tag: face.uv
|
||||
uv_tag: face.uv,
|
||||
face: fkey
|
||||
}
|
||||
|
||||
} else if (mirror_element instanceof Mesh) {
|
||||
@ -564,6 +569,7 @@ const Painter = {
|
||||
let center = clicked_face.getCenter();
|
||||
let e = 0.01;
|
||||
let face;
|
||||
let match_fkey;
|
||||
for (let fkey in mesh.faces) {
|
||||
let normal2 = mesh.faces[fkey].getNormal(true);
|
||||
let center2 = mesh.faces[fkey].getCenter();
|
||||
@ -572,6 +578,7 @@ const Painter = {
|
||||
Math.epsilon(center[0], -center2[0], e) && Math.epsilon(center[1], center2[1], e) && Math.epsilon(center[2], center2[2], e)
|
||||
) {
|
||||
face = mesh.faces[fkey];
|
||||
match_fkey = fkey;
|
||||
}
|
||||
}
|
||||
if (!face) return;
|
||||
@ -594,7 +601,8 @@ const Painter = {
|
||||
element: mesh,
|
||||
x: point_on_uv[0],
|
||||
y: point_on_uv[1],
|
||||
uv_tag: face.uv
|
||||
uv_tag: face.uv,
|
||||
face: match_fkey
|
||||
}
|
||||
}
|
||||
},
|
||||
@ -744,9 +752,12 @@ const Painter = {
|
||||
if (target) {
|
||||
let start_target = Painter.getMirrorPaintTarget(texture, Painter.startPixel[0], Painter.startPixel[1], uvTag);
|
||||
let old_element = Painter.current.element;
|
||||
let old_face = Painter.current.face;
|
||||
Painter.current.element = target.element;
|
||||
Painter.current.face = target.face;
|
||||
drawShape(start_target.x, start_target.y, target.x, target.y, target.uv_tag)
|
||||
Painter.current.element = old_element;
|
||||
Painter.current.face = old_face;
|
||||
}
|
||||
}
|
||||
|
||||
@ -1040,6 +1051,16 @@ const Painter = {
|
||||
|
||||
BARS.defineActions(function() {
|
||||
|
||||
new Tool('pan_tool', {
|
||||
icon: 'pan_tool',
|
||||
category: 'tools',
|
||||
cursor: 'grab',
|
||||
selectFace: false,
|
||||
transformerMode: 'hidden',
|
||||
allowed_view_modes: ['textured'],
|
||||
modes: ['paint'],
|
||||
condition: Blockbench.isMobile && {modes: ['paint']}
|
||||
})
|
||||
new Tool('brush_tool', {
|
||||
icon: 'fa-paint-brush',
|
||||
category: 'tools',
|
||||
|
@ -97,7 +97,7 @@ const UVEditor = {
|
||||
var texture = UVEditor.getTexture()
|
||||
if (!texture) {
|
||||
Blockbench.showQuickMessage('message.untextured')
|
||||
} else {
|
||||
} else if (event.which === 1 || (event.touches && event.touches.length == 1)) {
|
||||
var new_face;
|
||||
var {x, y} = UVEditor.getBrushCoordinates(event, texture);
|
||||
if (texture.img.naturalWidth + texture.img.naturalHeight == 0) return;
|
||||
@ -379,8 +379,12 @@ const UVEditor = {
|
||||
},
|
||||
//Set
|
||||
setZoom(zoom) {
|
||||
zoom = Math.clamp(zoom, 0.5, UVEditor.max_zoom)
|
||||
this.vue.zoom = zoom;
|
||||
Project.uv_viewport.zoom = this.zoom;
|
||||
Vue.nextTick(() => {
|
||||
if (Painter.selection.overlay) UVEditor.updatePastingOverlay()
|
||||
})
|
||||
return this;
|
||||
},
|
||||
setGrid(value) {
|
||||
@ -1906,14 +1910,13 @@ Interface.definePanels(function() {
|
||||
event.preventDefault()
|
||||
|
||||
let original_margin = this.getFrameMargin();
|
||||
let old_zoom = this.zoom;
|
||||
var n = (event.deltaY < 0) ? 0.1 : -0.1;
|
||||
n *= this.zoom
|
||||
var number = Math.clamp(this.zoom + n, 0.5, this.max_zoom)
|
||||
if (number > 0.91 && number < 1.1) number = 1;
|
||||
let old_zoom = this.zoom;
|
||||
|
||||
this.zoom = number;
|
||||
Project.uv_viewport.zoom = this.zoom;
|
||||
let zoom = this.zoom + n;
|
||||
if (zoom > 0.91 && zoom < 1.1) zoom = 1;
|
||||
UVEditor.setZoom(zoom);
|
||||
|
||||
let updateScroll = () => {
|
||||
let {viewport} = this.$refs;
|
||||
@ -1933,7 +1936,7 @@ Interface.definePanels(function() {
|
||||
this.centerView();
|
||||
}
|
||||
this.updateMouseCoords(event)
|
||||
if (Painter.selection.overlay) UVEditor.updatePastingOverlay()
|
||||
//if (Painter.selection.overlay) UVEditor.updatePastingOverlay()
|
||||
}
|
||||
if (n > 0) {
|
||||
Vue.nextTick(updateScroll);
|
||||
@ -1946,7 +1949,13 @@ Interface.definePanels(function() {
|
||||
},
|
||||
onMouseDown(event) {
|
||||
setActivePanel('uv');
|
||||
if (event.which === 2) {
|
||||
let second_touch;
|
||||
let original_zoom = this.zoom;
|
||||
if (event.which === 2 || (event.touches && !Toolbox.selected.paintTool && event.target.id == 'uv_frame')) {
|
||||
if (event.touches) {
|
||||
event.clientX = event.touches[0].clientX;
|
||||
event.clientY = event.touches[0].clientY;
|
||||
}
|
||||
let {viewport} = this.$refs;
|
||||
let margin = this.getFrameMargin();
|
||||
let margin_center = [this.width/2, this.height/2];
|
||||
@ -1955,8 +1964,20 @@ Interface.definePanels(function() {
|
||||
viewport.scrollTop
|
||||
];
|
||||
function dragMouseWheel(e2) {
|
||||
if (e2.touches) {
|
||||
e2.clientX = e2.touches[0].clientX;
|
||||
e2.clientY = e2.touches[0].clientY;
|
||||
}
|
||||
viewport.scrollLeft = Math.snapToValues(original[0] + event.clientX - e2.clientX, [margin[0], margin_center[0]], 10);
|
||||
viewport.scrollTop = Math.snapToValues(original[1] + event.clientY - e2.clientY, [margin[1], margin_center[1]], 10);
|
||||
|
||||
if (!second_touch && e2.touches[1]) second_touch = e2.touches[1];
|
||||
if (second_touch && e2.touches[1]) {
|
||||
let factor = Math.sqrt(Math.pow(e2.touches[0].clientX - e2.touches[1].clientX, 2) + Math.pow(e2.touches[0].clientY - e2.touches[1].clientY, 2))
|
||||
/ Math.sqrt(Math.pow(event.touches[0].clientX - second_touch.clientX, 2) + Math.pow(event.touches[0].clientY - second_touch.clientY, 2));
|
||||
UVEditor.setZoom(original_zoom * factor);
|
||||
}
|
||||
|
||||
UVEditor.vue.centered_view = (viewport.scrollLeft == margin[0] || viewport.scrollLeft == margin_center[0])
|
||||
&& (viewport.scrollTop == margin[1] || viewport.scrollTop == margin_center[1]);
|
||||
}
|
||||
@ -2883,7 +2904,9 @@ Interface.definePanels(function() {
|
||||
}
|
||||
})
|
||||
UVEditor.panel.on('move_to', (data) => {
|
||||
UVEditor.saveViewportOffset();
|
||||
if (!Blockbench.isMobile) {
|
||||
UVEditor.saveViewportOffset();
|
||||
}
|
||||
})
|
||||
UVEditor.panel.on('moved_to', (data) => {
|
||||
Vue.nextTick(() => {
|
||||
|
File diff suppressed because one or more lines are too long
@ -696,7 +696,7 @@
|
||||
|
||||
"settings.autouv": "Auto UV",
|
||||
"settings.autouv.desc": "Enable Auto UV by default",
|
||||
"settings.create_rename": "Rename New Cube",
|
||||
"settings.create_rename": "Rename New Element",
|
||||
"settings.create_rename.desc": "Focus name field when creating new element or group",
|
||||
"settings.show_only_selected_uv": "Show Only Selected UV",
|
||||
"settings.show_only_selected_uv.desc": "Only display the selected UV faces in the UV editor by default",
|
||||
@ -797,7 +797,7 @@
|
||||
"action.slider_size": "Size %0",
|
||||
"action.slider_size.desc": "Resize cubes on the %0 axis",
|
||||
"action.slider_inflate": "Inflate",
|
||||
"action.slider_inflate.desc": "Inflate cubes in all directions without changing the UV.",
|
||||
"action.slider_inflate.desc": "Inflate cubes in all directions without changing the UV",
|
||||
"action.slider_rotation": "Rotate %0",
|
||||
"action.slider_rotation.desc": "Rotate cubes on the %0 axis",
|
||||
"action.slider_origin": "Pivot %0",
|
||||
@ -851,6 +851,8 @@
|
||||
"action.pivot_tool.desc": "Tool to change the pivot point of cubes and bones",
|
||||
"action.seam_tool": "Seam Tool",
|
||||
"action.seam_tool.desc": "Tool to define UV seams on mesh edges",
|
||||
"action.pan_tool": "Pan Tool",
|
||||
"action.pan_tool.desc": "Tool to navigate in the viewport and the texture editor",
|
||||
"action.brush_tool": "Paint Brush",
|
||||
"action.brush_tool.desc": "Tool to paint on bitmap textures on surfaces or the UV editor",
|
||||
"action.fill_tool": "Paint Bucket",
|
||||
|
File diff suppressed because one or more lines are too long
Loading…
Reference in New Issue
Block a user