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

formが書き途中でページ遷移を行おうとしたときに確認メッセージを出す #903

Merged
merged 7 commits into from
Oct 27, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
107 changes: 107 additions & 0 deletions src/components/event/EventFormBase.vue
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,10 @@ import EventFormSummary, {
} from '@/components/event/EventFormSummary.vue'
import FormNextButton from '@/components/shared/FormNextButton.vue'
import FormBackButton from '@/components/shared/FormBackButton.vue'
import { useDraftConfirmer } from '@/workers/draftConfirmer'
import { removeDraftConfirmer } from '@/workers/draftConfirmer'
import router from '@/router'
import { Route } from 'vue-router'

export type EventInput = EventInputContent &
(
Expand Down Expand Up @@ -115,6 +119,10 @@ export default class EventFormBase extends Vue {

instant: boolean = null!

originalSummary: EventSummary = null!

beforeEachControl: (() => void) | null = null

created() {
this.content = {
name: this.event?.name ?? '',
Expand Down Expand Up @@ -197,8 +205,107 @@ export default class EventFormBase extends Vue {
}
}

isChanged(): boolean {
if (this.summary && this.originalSummary) {
return (
JSON.stringify(this.summary) !== JSON.stringify(this.originalSummary)
)
}
return false
}

cleanupContent(): void {
this.summary.name = ''
this.summary.description = ''
this.summary.tags = []
this.summary.groupName = ''
this.summary.place = ''
this.summary.timeStart = ''
this.summary.timeEnd = ''
this.summary.open = false
this.summary.sharedRoom = true
}

isEventNewOrEdit(): boolean {
const currentRoute: Route = this.$route
return currentRoute.name === 'EventNew'
}

beforLeaveGuardinEventEdit = (to, from, next) => {
if (from.name !== 'EventEdit') {
return next()
}

if (!this.isChanged()) {
return next()
}

if (
confirm(
'入力されたデータは送信されないまま破棄されますが,よろしいですか。'
)
) {
removeDraftConfirmer()
this.cleanupContent()
return next()
}

return next(false)
}

beforLeaveGuardinEventNew = (to, from, next) => {
if (from.name !== 'EventNew' || !this.isChanged()) {
return next()
}

if (
confirm(
'入力されたデータは送信されないまま破棄されますが,よろしいですか。'
)
) {
removeDraftConfirmer()
this.cleanupContent()
return next()
}

return next(false)
}

mounted() {
this.$watch(
'summary',
() => {
if (this.isChanged()) {
useDraftConfirmer()
} else {
removeDraftConfirmer()
}
},
{ deep: true }
)
if (this.isEventNewOrEdit()) {
this.beforeEachControl = router.beforeEach(this.beforLeaveGuardinEventNew)
} else {
this.beforeEachControl = router.beforeEach(
this.beforLeaveGuardinEventEdit
)
}
this.originalSummary = JSON.parse(JSON.stringify(this.summary))
}

beforeDestroy() {
if (this.beforeEachControl) {
this.beforeEachControl()
}
}

@Emit()
submit(): EventOutput {
removeDraftConfirmer()
this.cleanupContent()
if (this.beforeEachControl) {
this.beforeEachControl()
}
return {
...this.content,
group: this.content.group!,
Expand Down
31 changes: 27 additions & 4 deletions src/components/main/SidebarFooter.vue
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,8 @@

<script lang="ts">
import { isValidVerifiedroomData } from '@/workers/isValidVerifiedroomData'
import { useDraftConfirmer } from '@/workers/draftConfirmer'
import { removeDraftConfirmer } from '@/workers/draftConfirmer'
import { baseURL } from '@/workers/api'

export default {
Expand All @@ -75,21 +77,42 @@ export default {
return this.$store.direct.state.me?.privileged ?? false
},
},
mounted: function () {
this.$watch('inputData', newVal => {
if (newVal !== '') {
useDraftConfirmer()
} else {
removeDraftConfirmer()
}
})
},
methods: {
showModal() {
this.isVisible = true
},
hideModal() {
this.isVisible = false
this.showError = false
this.inputData = ''
if (this.inputData) {
if (
confirm(
'入力されたデータは送信されないまま破棄されますが,よろしいですか。'
)
) {
this.isVisible = false
this.showError = false
this.inputData = ''
}
return
} else {
this.isVisible = false
this.showError = false
this.inputData = ''
}
},
async saveData() {
if (isValidVerifiedroomData(this.inputData)) {
this.showError = false
try {
await fetch(`${baseURL}/rooms/all`, {
//開発環境url
method: 'POST',
credentials: 'include',
headers: {
Expand Down
66 changes: 63 additions & 3 deletions src/pages/GroupEdit.vue
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,9 @@ import FormBackButton from '@/components/shared/FormBackButton.vue'
import ProgressCircular from '@/components/shared/ProgressCircular.vue'
import LoadFailedText from '@/components/shared/LoadFailedText.vue'
import api, { RequestGroup } from '@/api'
import router from '@/router'
import { useDraftConfirmer } from '@/workers/draftConfirmer'
import { removeDraftConfirmer } from '@/workers/draftConfirmer'

@Component({
components: {
Expand All @@ -74,6 +77,8 @@ export default class GroupEdit extends Vue {
step = 1

group: RequestGroup | null = null
originalGroup: RequestGroup | null = null
beforeEachControl: (() => void) | null = null

get groupId() {
return this.$route.params.id
Expand All @@ -84,6 +89,7 @@ export default class GroupEdit extends Vue {
try {
const group = await api.groups.getGroup({ groupID: this.groupId })
this.group = group
this.originalGroup = JSON.parse(JSON.stringify(group))
this.canEdit =
!group.isTraQGroup && !!this.me && group.admins.includes(this.me)
this.status = 'loaded'
Expand All @@ -92,13 +98,44 @@ export default class GroupEdit extends Vue {
}
}

isChanged(): boolean {
if (this.group && this.originalGroup) {
return JSON.stringify(this.group) !== JSON.stringify(this.originalGroup)
}
return false
}

cleanupContent(): void {
this.group = this.originalGroup
}

beforeLeaveGuard = (to, from, next) => {
if (from.path !== `/groups/edit/${this.groupId}` || !this.isChanged()) {
return next()
}

if (
confirm(
'入力されたデータは送信されないまま破棄されますが,よろしいですか。'
)
) {
removeDraftConfirmer()
this.cleanupContent()
return next()
}

return next(false)
}

async submitGroup() {
if (!this.group) return
try {
await api.groups.updateGroup({
groupID: this.groupId,
requestGroup: this.group,
})
removeDraftConfirmer()
this.cleanupContent()
this.$router.push(`/groups/${this.groupId}`)
} catch (__) {
alert('Failed to submit...')
Expand All @@ -125,9 +162,32 @@ export default class GroupEdit extends Vue {
if (!confirmed) return
try {
await api.groups.deleteGroup({ groupID: this.groupId })
this.$router.push('/')
} catch (__) {
alert('Failed to submit...')
removeDraftConfirmer()
this.cleanupContent()
this.$router.push('/groups')
} catch (error) {
alert('Failed to delete...')
}
}

mounted() {
this.$watch(
'group',
() => {
if (this.isChanged()) {
useDraftConfirmer()
} else {
removeDraftConfirmer()
}
},
{ deep: true }
)
this.beforeEachControl = router.beforeEach(this.beforeLeaveGuard)
}

beforeDestroy() {
if (this.beforeEachControl) {
this.beforeEachControl()
}
}

Expand Down
58 changes: 58 additions & 0 deletions src/pages/GroupNew.vue
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,9 @@ import GroupFormSummary from '@/components/group/GroupFormSummary.vue'
import FormNextButton from '@/components/shared/FormNextButton.vue'
import FormBackButton from '@/components/shared/FormBackButton.vue'
import api, { RequestGroup } from '@/api'
import { useDraftConfirmer } from '@/workers/draftConfirmer'
import { removeDraftConfirmer } from '@/workers/draftConfirmer'
import router from '@/router'

@Component({
components: {
Expand All @@ -48,6 +51,8 @@ export default class GroupNew extends Vue {
valid = false
step = 1

beforeEachControl: (() => void) | null = null

group: RequestGroup = {
name: '',
description: '',
Expand All @@ -60,13 +65,66 @@ export default class GroupNew extends Vue {
: [],
}

hasContent(): boolean {
return (
this.group.name !== '' || this.group.description !== '' || this.group.open
)
}

cleanupContent(): void {
this.group.name = ''
this.group.description = ''
this.group.open = false
}

beforeLeaveGuard = (to, from, next) => {
if (from.name !== 'GroupNew' || this.hasContent()) {
return next()
}

if (
confirm(
'入力されたデータは送信されないまま破棄されますが,よろしいですか。'
)
) {
removeDraftConfirmer()
this.cleanupContent()
return next()
}

return next(false)
}

mounted() {
this.$watch(
'group',
() => {
if (this.hasContent()) {
useDraftConfirmer()
} else {
removeDraftConfirmer()
}
},
{ deep: true }
)
this.beforeEachControl = router.beforeEach(this.beforeLeaveGuard)
}

beforeDestroy() {
if (this.beforeEachControl) {
this.beforeEachControl()
}
}

async submitGroup() {
try {
await api.groups.createGroup({ requestGroup: this.group })
} catch (__) {
alert('Failed to submit...')
return
}
removeDraftConfirmer()
this.cleanupContent()
this.$router.push('/events/new')
}
}
Expand Down
13 changes: 13 additions & 0 deletions src/workers/draftConfirmer.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
const beforeUnloadListener = (event: BeforeUnloadEvent) => {
event.preventDefault()
event.returnValue =
'入力されたデータは送信されないまま破棄されますが,よろしいですか。'
}

export function useDraftConfirmer(): void {
window.addEventListener('beforeunload', beforeUnloadListener)
}

export function removeDraftConfirmer(): void {
window.removeEventListener('beforeunload', beforeUnloadListener)
}
Loading