New vid, fixes for mass remove causing img to be blurry
This commit is contained in:
parent
1ca54ce7f7
commit
29d9b77bf1
22
src/App.vue
22
src/App.vue
@ -183,8 +183,9 @@
|
|||||||
const updateSpritePosition = (id: string, x: number, y: number) => {
|
const updateSpritePosition = (id: string, x: number, y: number) => {
|
||||||
const spriteIndex = sprites.value.findIndex(sprite => sprite.id === id);
|
const spriteIndex = sprites.value.findIndex(sprite => sprite.id === id);
|
||||||
if (spriteIndex !== -1) {
|
if (spriteIndex !== -1) {
|
||||||
sprites.value[spriteIndex].x = x;
|
// Ensure integer positions for pixel-perfect rendering
|
||||||
sprites.value[spriteIndex].y = y;
|
sprites.value[spriteIndex].x = Math.floor(x);
|
||||||
|
sprites.value[spriteIndex].y = Math.floor(y);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -442,24 +443,31 @@
|
|||||||
x = 0;
|
x = 0;
|
||||||
break;
|
break;
|
||||||
case 'center':
|
case 'center':
|
||||||
x = (maxWidth - sprite.width) / 2;
|
x = Math.floor((maxWidth - sprite.width) / 2);
|
||||||
break;
|
break;
|
||||||
case 'right':
|
case 'right':
|
||||||
x = maxWidth - sprite.width;
|
x = Math.floor(maxWidth - sprite.width);
|
||||||
break;
|
break;
|
||||||
case 'top':
|
case 'top':
|
||||||
y = 0;
|
y = 0;
|
||||||
break;
|
break;
|
||||||
case 'middle':
|
case 'middle':
|
||||||
y = (maxHeight - sprite.height) / 2;
|
y = Math.floor((maxHeight - sprite.height) / 2);
|
||||||
break;
|
break;
|
||||||
case 'bottom':
|
case 'bottom':
|
||||||
y = maxHeight - sprite.height;
|
y = Math.floor(maxHeight - sprite.height);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
return { ...sprite, x, y };
|
// Ensure integer positions for pixel-perfect rendering
|
||||||
|
return { ...sprite, x: Math.floor(x), y: Math.floor(y) };
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Force redraw of the preview canvas
|
||||||
|
setTimeout(() => {
|
||||||
|
const event = new Event('forceRedraw');
|
||||||
|
window.dispatchEvent(event);
|
||||||
|
}, 0);
|
||||||
};
|
};
|
||||||
|
|
||||||
const updateSpriteCell = (id: string, newIndex: number) => {
|
const updateSpriteCell = (id: string, newIndex: number) => {
|
||||||
|
Binary file not shown.
@ -20,7 +20,7 @@
|
|||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { ref, onMounted, watch, computed } from 'vue';
|
import { ref, onMounted, watch, computed, onUnmounted } from 'vue';
|
||||||
import { useSettingsStore } from '@/stores/useSettingsStore';
|
import { useSettingsStore } from '@/stores/useSettingsStore';
|
||||||
|
|
||||||
interface Sprite {
|
interface Sprite {
|
||||||
@ -211,9 +211,9 @@
|
|||||||
const newX = mouseX - position.cellX - dragOffsetX.value;
|
const newX = mouseX - position.cellX - dragOffsetX.value;
|
||||||
const newY = mouseY - position.cellY - dragOffsetY.value;
|
const newY = mouseY - position.cellY - dragOffsetY.value;
|
||||||
|
|
||||||
// Constrain within cell boundaries
|
// Constrain within cell boundaries and ensure integer positions
|
||||||
const constrainedX = Math.max(0, Math.min(position.maxWidth - props.sprites[spriteIndex].width, newX));
|
const constrainedX = Math.floor(Math.max(0, Math.min(position.maxWidth - props.sprites[spriteIndex].width, newX)));
|
||||||
const constrainedY = Math.max(0, Math.min(position.maxHeight - props.sprites[spriteIndex].height, newY));
|
const constrainedY = Math.floor(Math.max(0, Math.min(position.maxHeight - props.sprites[spriteIndex].height, newY)));
|
||||||
|
|
||||||
emit('updateSprite', activeSpriteId.value, constrainedX, constrainedY);
|
emit('updateSprite', activeSpriteId.value, constrainedX, constrainedY);
|
||||||
drawCanvas();
|
drawCanvas();
|
||||||
@ -346,8 +346,30 @@
|
|||||||
ctx.value = canvasRef.value.getContext('2d');
|
ctx.value = canvasRef.value.getContext('2d');
|
||||||
drawCanvas();
|
drawCanvas();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Listen for forceRedraw event from App.vue
|
||||||
|
window.addEventListener('forceRedraw', handleForceRedraw);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
onUnmounted(() => {
|
||||||
|
window.removeEventListener('forceRedraw', handleForceRedraw);
|
||||||
|
});
|
||||||
|
|
||||||
|
// Handler for force redraw event
|
||||||
|
const handleForceRedraw = () => {
|
||||||
|
// Ensure we're using integer positions for pixel-perfect rendering
|
||||||
|
props.sprites.forEach(sprite => {
|
||||||
|
sprite.x = Math.floor(sprite.x);
|
||||||
|
sprite.y = Math.floor(sprite.y);
|
||||||
|
});
|
||||||
|
|
||||||
|
// Force a redraw with the correct image smoothing settings
|
||||||
|
if (ctx.value) {
|
||||||
|
ctx.value.imageSmoothingEnabled = !settingsStore.pixelPerfect;
|
||||||
|
drawCanvas();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
watch(() => props.sprites, drawCanvas, { deep: true });
|
watch(() => props.sprites, drawCanvas, { deep: true });
|
||||||
watch(() => props.columns, drawCanvas);
|
watch(() => props.columns, drawCanvas);
|
||||||
watch(() => settingsStore.pixelPerfect, drawCanvas);
|
watch(() => settingsStore.pixelPerfect, drawCanvas);
|
||||||
|
@ -229,14 +229,15 @@
|
|||||||
ctx.value.globalAlpha = 0.3;
|
ctx.value.globalAlpha = 0.3;
|
||||||
props.sprites.forEach((sprite, index) => {
|
props.sprites.forEach((sprite, index) => {
|
||||||
if (index !== currentFrameIndex.value && !hiddenFrames.value.includes(index)) {
|
if (index !== currentFrameIndex.value && !hiddenFrames.value.includes(index)) {
|
||||||
ctx.value?.drawImage(sprite.img, sprite.x, sprite.y);
|
// Use Math.floor for pixel-perfect positioning
|
||||||
|
ctx.value?.drawImage(sprite.img, Math.floor(sprite.x), Math.floor(sprite.y));
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
ctx.value.globalAlpha = 1.0;
|
ctx.value.globalAlpha = 1.0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Draw current sprite
|
// Draw current sprite with integer positions for pixel-perfect rendering
|
||||||
ctx.value.drawImage(currentSprite.img, currentSprite.x, currentSprite.y);
|
ctx.value.drawImage(currentSprite.img, Math.floor(currentSprite.x), Math.floor(currentSprite.y));
|
||||||
|
|
||||||
// Draw cell border
|
// Draw cell border
|
||||||
ctx.value.strokeStyle = '#e5e7eb';
|
ctx.value.strokeStyle = '#e5e7eb';
|
||||||
@ -391,12 +392,31 @@
|
|||||||
ctx.value = previewCanvasRef.value.getContext('2d');
|
ctx.value = previewCanvasRef.value.getContext('2d');
|
||||||
drawPreviewCanvas();
|
drawPreviewCanvas();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Listen for forceRedraw event from App.vue
|
||||||
|
window.addEventListener('forceRedraw', handleForceRedraw);
|
||||||
});
|
});
|
||||||
|
|
||||||
onUnmounted(() => {
|
onUnmounted(() => {
|
||||||
stopAnimation();
|
stopAnimation();
|
||||||
|
window.removeEventListener('forceRedraw', handleForceRedraw);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Handler for force redraw event
|
||||||
|
const handleForceRedraw = () => {
|
||||||
|
// Ensure we're using integer positions for pixel-perfect rendering
|
||||||
|
props.sprites.forEach(sprite => {
|
||||||
|
sprite.x = Math.floor(sprite.x);
|
||||||
|
sprite.y = Math.floor(sprite.y);
|
||||||
|
});
|
||||||
|
|
||||||
|
// Force a redraw with the correct image smoothing settings
|
||||||
|
if (ctx.value) {
|
||||||
|
ctx.value.imageSmoothingEnabled = !settingsStore.pixelPerfect;
|
||||||
|
drawPreviewCanvas();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
// Watchers
|
// Watchers
|
||||||
watch(() => props.sprites, drawPreviewCanvas, { deep: true });
|
watch(() => props.sprites, drawPreviewCanvas, { deep: true });
|
||||||
watch(currentFrameIndex, drawPreviewCanvas);
|
watch(currentFrameIndex, drawPreviewCanvas);
|
||||||
|
Loading…
x
Reference in New Issue
Block a user