Skip to content

Commit

Permalink
feat: drag and drop image support
Browse files Browse the repository at this point in the history
  • Loading branch information
selimdoyranli committed May 23, 2023
1 parent dbad5b0 commit 4a38711
Show file tree
Hide file tree
Showing 9 changed files with 115 additions and 9 deletions.
2 changes: 2 additions & 0 deletions assets/style/css/variables/color.css
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
--color-border-01: #090909;
--color-border-02: #171717;
--color-border-03: #202020;
--color-border-04: #eee;

/* Typographic */
--color-text-01: #999;
Expand All @@ -35,4 +36,5 @@

/* Overlays */
--color-overlay-01: rgba(0, 0, 0, 0.1);
--color-overlay-02: rgba(0, 0, 0, 0.8);
}
22 changes: 19 additions & 3 deletions components/Card/UploadImageCard/UploadImageCard.component.vue
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
</template>

<script>
import { defineComponent, useContext, useStore, ref, computed } from '@nuxtjs/composition-api'
import { defineComponent, useContext, useStore, ref, computed, watch } from '@nuxtjs/composition-api'
import useEditor from '@/hooks/useEditor'
import { AppIcon } from '@/components/Icon'
Expand All @@ -26,6 +26,7 @@ export default defineComponent({
setup(_, { emit }) {
const context = useContext()
const store = useStore()
const { sleep, acceptedFileExtensions, getFileExtension } = useEditor()
const rootRef = ref(null)
Expand All @@ -44,16 +45,31 @@ export default defineComponent({
imageFileRef.value.click()
}
const droppedFiles = computed(() => store.getters['editor/droppedFiles'])
watch(
() => droppedFiles.value,
value => {
const file = value[0]
setFile(file)
}
)
const handleChangeFile = () => {
const file = imageFileRef.value.files[0]
setFile(file)
}
const setFile = file => {
store.commit('editor/SET_IS_BUSY', true)
const fileExtension = getFileExtension(imageFileRef.value.files[0].name).toLowerCase()
const fileExtension = getFileExtension(file.name).toLowerCase()
if (acceptedFileExtensions.value.includes(fileExtension)) {
sleep(1000).then(() => {
store.commit('editor/SET_IS_READY', true)
store.commit('editor/SET_IS_BUSY', false)
store.commit('editor/SET_ORIGINAL', { file: imageFileRef.value.files[0] })
store.commit('editor/SET_ORIGINAL', { file: file })
})
} else {
store.commit('editor/SET_IS_BUSY', false)
Expand Down
29 changes: 29 additions & 0 deletions layouts/Default/Default.layout.scss
Original file line number Diff line number Diff line change
@@ -1,3 +1,32 @@
.default-layout {
$drop-target: '.drop-target';

position: relative;

&--dragOver {
#{$drop-target} {
visibility: visible !important;
}
}

.drop-target {
position: fixed;
top: var(--header-height);
left: 0;
z-index: var(--z-index-overlay);
display: flex;
align-items: center;
justify-content: center;
width: 100%;
height: calc(100vh - var(--header-height));
background-color: var(--color-overlay-02);
border: 2px dashed var(--color-border-04);
visibility: hidden;

&__title {
color: var(--color-text-03);
font-size: var(--font-size-text-14);
pointer-events: none;
}
}
}
56 changes: 52 additions & 4 deletions layouts/Default/Default.layout.vue
Original file line number Diff line number Diff line change
@@ -1,20 +1,31 @@
<template lang="pug">
.layout.default-layout
.layout.default-layout(@drag.stop.prevent @dragstart.stop.prevent @dragend.stop.prevent @dragover.stop.prevent @drop.prevent)
AppPreloader
AppHeader(@on-click-credits-dialog="isOpenCreditsDialog = true")

// Main
.layout__inner
.layout__inner(
:class="[dragEnterActiveClass]"
@drag.stop.prevent
@dragstart.stop.prevent
@dragend.stop.prevent
@dragover.stop.prevent="onDragOver"
@drop.prevent="onFileDrop"
)
.col.col-12
.router-view
nuxt

// Drop target
.drop-target(v-if="!preloader.isLoading && !isReady" @dragleave.stop.prevent="onDragLeave")
span.drop-target__title {{ $t('uploader.drop') }}

// App Credits Dialog
AppCreditsDialog(:is-open="isOpenCreditsDialog" @on-close="isOpenCreditsDialog = false")
</template>

<script>
import { defineComponent, ref } from '@nuxtjs/composition-api'
import { defineComponent, useStore, ref, computed } from '@nuxtjs/composition-api'
import { AppPreloader } from '@/components/Preloader'
import { AppHeader } from '@/components/Header'
import { AppCreditsDialog } from '@/components/Dialog'
Expand All @@ -26,10 +37,47 @@ export default defineComponent({
AppCreditsDialog
},
setup() {
const baseClassName = 'default-layout'
const store = useStore()
const isActiveDragOver = ref(false)
const isOpenCreditsDialog = ref(false)
const preloader = computed(() => store.getters['preloader/preloader'])
const isReady = computed(() => store.getters['editor/isReady'])
const onDragOver = () => {
isActiveDragOver.value = true
}
const onDragLeave = () => {
isActiveDragOver.value = false
}
const onFileDrop = event => {
if (!isReady.value) {
store.commit('editor/SET_DROPPED_FILES', event.dataTransfer.files)
isActiveDragOver.value = false
}
}
const dragEnterActiveClass = computed(() => {
if (isActiveDragOver.value) {
return `${baseClassName}--dragOver`
}
})
return {
isOpenCreditsDialog
preloader,
isReady,
isOpenCreditsDialog,
onDragOver,
onDragLeave,
onFileDrop,
dragEnterActiveClass
}
}
})
Expand Down
3 changes: 2 additions & 1 deletion locales/en.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,8 @@ export default {
uploader: {
title: 'START CROPPING',
description: `Quickly crop a photo for multiple ratios on the same screen. <br> Supported ratios are; 16:9, 9:16, 1:1 and free-ratio.`,
choosePhoto: 'Choose a photo'
choosePhoto: 'Choose a photo',
drop: 'Drop here'
},
editor: {
chooseCustomAspectRatio: 'Choose custom ratio',
Expand Down
3 changes: 2 additions & 1 deletion locales/tr.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,8 @@ export default {
uploader: {
title: 'KIRPMAYA BAŞLA',
description: `Birden fazla en boy oranı için tek ekranda hızlıca fotoğraf kırp. <br> 16:9, 9:16, 1:1 ve serbest oran desteklenir.`,
choosePhoto: 'Fotoğraf Seç'
choosePhoto: 'Fotoğraf Seç',
drop: 'Görseli buraya bırak'
},
editor: {
chooseCustomAspectRatio: 'Özel oran seç',
Expand Down
4 changes: 4 additions & 0 deletions store/editor/getters.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,8 @@
export default {
droppedFiles(state) {
return state.droppedFiles
},

isReady(state) {
return state.isReady
},
Expand Down
4 changes: 4 additions & 0 deletions store/editor/mutations.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,10 @@
import { cropTypeEnum } from '@/enums'

export default {
SET_DROPPED_FILES(state, files) {
state.droppedFiles = files
},

SET_IS_READY(state, isReady) {
state.isReady = isReady
},
Expand Down
1 change: 1 addition & 0 deletions store/editor/state.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { cropTypeEnum } from '@/enums'

export default () => ({
droppedFiles: [],
isReady: false,
isBusy: false,
original: {
Expand Down

0 comments on commit 4a38711

Please sign in to comment.