Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Vue实现截图遮罩效果 #64

Open
varHarrie opened this issue Jan 15, 2025 · 0 comments
Open

Vue实现截图遮罩效果 #64

varHarrie opened this issue Jan 15, 2025 · 0 comments

Comments

@varHarrie
Copy link
Owner

<template>
  <button @click="onScreenshot">Screenshot</button>
  <div v-if="cropping" class="cropper"
    :style="style"
    @mousedown="onStart"
    @mousemove="onMove"
    @mouseup="onEnd"
  >
    <div class="mask" v-if="style"></div>
    <div class="area" v-if="style"></div>
  </div>
</template>

<script setup>
import { ref, computed } from 'vue'

const cropping = ref(false);
const startPoint = ref();
const endPoint = ref();

const rect = computed(() => {
  if (!startPoint.value || !endPoint.value) return null;

   return {
    x: Math.min(startPoint.value.x, endPoint.value.x),
    y: Math.min(startPoint.value.y, endPoint.value.y),
    width: Math.abs(endPoint.value.x - startPoint.value.x),
    height: Math.abs(endPoint.value.y - startPoint.value.y),
  };
})

const style = computed(() => {
  if (!rect.value) return null

  return {
    '--x': `${rect.value.x}px`,
    '--y': `${rect.value.y}px`,
    '--width': `${rect.value.width}px`,
    '--height': `${rect.value.height}px`,
  };
});

const onScreenshot = () => {
  cropping.value = true;
}

const onStart = (e) => {
  startPoint.value = { x: e.clientX, y: e.clientY };
};

const onMove = (e) => {
  if (!startPoint.value) return;
  endPoint.value = { x: e.clientX, y: e.clientY };
};

const onEnd = () => {
  console.log(rect.value);
  startPoint.value = undefined;
  endPoint.value = undefined;
  cropping.value = false;
};
</script>

<style>
.cropper {
  position: fixed;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  cursor: crosshair;
}

.mask {
  width: 100%;
  height: 100%;
  background: rgba(0,0,0,0.2);
  clip-path: polygon(
    0% 0%,
    0% 100%,
    var(--x) 100%,
    var(--x) var(--y),
    calc(var(--x) + var(--width)) var(--y),
    calc(var(--x) + var(--width)) calc(var(--y) + var(--height)),
    var(--x) calc(var(--y) + var(--height)),
    var(--x) 100%,
    100% 100%,
    100% 0%
  );
}

.area {
  position: absolute;
  top: var(--y);
  left: var(--x);
  width: var(--width);
  height: var(--height);
  border: 1px solid black;
}
</style>
@varHarrie varHarrie added this to the Snippets milestone Jan 15, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

1 participant