fix(client): タッチ機能付きディスプレイを使っていてマウス操作をしている場合に一部機能が動作しない問題を修正
This commit is contained in:
		
							parent
							
								
									b1bd7307bb
								
							
						
					
					
						commit
						fbe4869d1e
					
				
					 9 changed files with 40 additions and 26 deletions
				
			
		|  | @ -7,6 +7,13 @@ | ||||||
| 
 | 
 | ||||||
| --> | --> | ||||||
| 
 | 
 | ||||||
|  | ## 12.x.x (unreleased) | ||||||
|  | 
 | ||||||
|  | ### Improvements | ||||||
|  | 
 | ||||||
|  | ### Bugfixes | ||||||
|  | - クライアント: タッチ機能付きディスプレイを使っていてマウス操作をしている場合に一部機能が動作しない問題を修正 | ||||||
|  | 
 | ||||||
| ## 12.98.0 (2021/12/03) | ## 12.98.0 (2021/12/03) | ||||||
| 
 | 
 | ||||||
| ### Improvements | ### Improvements | ||||||
|  |  | ||||||
|  | @ -79,7 +79,7 @@ import { emojilist } from '@/scripts/emojilist'; | ||||||
| import { getStaticImageUrl } from '@/scripts/get-static-image-url'; | import { getStaticImageUrl } from '@/scripts/get-static-image-url'; | ||||||
| import Particle from '@/components/particle.vue'; | import Particle from '@/components/particle.vue'; | ||||||
| import * as os from '@/os'; | import * as os from '@/os'; | ||||||
| import { isDeviceTouch } from '@/scripts/is-device-touch'; | import { isTouchUsing } from '@/scripts/touch'; | ||||||
| import { isMobile } from '@/scripts/is-mobile'; | import { isMobile } from '@/scripts/is-mobile'; | ||||||
| import { emojiCategories } from '@/instance'; | import { emojiCategories } from '@/instance'; | ||||||
| import XSection from './emoji-picker.section.vue'; | import XSection from './emoji-picker.section.vue'; | ||||||
|  | @ -108,7 +108,7 @@ export default defineComponent({ | ||||||
| 			pinned: this.$store.reactiveState.reactions, | 			pinned: this.$store.reactiveState.reactions, | ||||||
| 			width: this.asReactionPicker ? this.$store.state.reactionPickerWidth : 3, | 			width: this.asReactionPicker ? this.$store.state.reactionPickerWidth : 3, | ||||||
| 			height: this.asReactionPicker ? this.$store.state.reactionPickerHeight : 2, | 			height: this.asReactionPicker ? this.$store.state.reactionPickerHeight : 2, | ||||||
| 			big: this.asReactionPicker ? isDeviceTouch : false, | 			big: this.asReactionPicker ? isTouchUsing : false, | ||||||
| 			customEmojiCategories: emojiCategories, | 			customEmojiCategories: emojiCategories, | ||||||
| 			customEmojis: this.$instance.emojis, | 			customEmojis: this.$instance.emojis, | ||||||
| 			q: null, | 			q: null, | ||||||
|  | @ -268,7 +268,7 @@ export default defineComponent({ | ||||||
| 
 | 
 | ||||||
| 	methods: { | 	methods: { | ||||||
| 		focus() { | 		focus() { | ||||||
| 			if (!isMobile && !isDeviceTouch) { | 			if (!isMobile && !isTouchUsing) { | ||||||
| 				this.$refs.search.focus({ | 				this.$refs.search.focus({ | ||||||
| 					preventScroll: true | 					preventScroll: true | ||||||
| 				}); | 				}); | ||||||
|  |  | ||||||
|  | @ -23,7 +23,7 @@ | ||||||
| import { defineComponent } from 'vue'; | import { defineComponent } from 'vue'; | ||||||
| import { toUnicode as decodePunycode } from 'punycode/'; | import { toUnicode as decodePunycode } from 'punycode/'; | ||||||
| import { url as local } from '@/config'; | import { url as local } from '@/config'; | ||||||
| import { isDeviceTouch } from '@/scripts/is-device-touch'; | import { isTouchUsing } from '@/scripts/touch'; | ||||||
| import * as os from '@/os'; | import * as os from '@/os'; | ||||||
| 
 | 
 | ||||||
| export default defineComponent({ | export default defineComponent({ | ||||||
|  | @ -91,13 +91,13 @@ export default defineComponent({ | ||||||
| 			} | 			} | ||||||
| 		}, | 		}, | ||||||
| 		onMouseover() { | 		onMouseover() { | ||||||
| 			if (isDeviceTouch) return; | 			if (isTouchUsing) return; | ||||||
| 			clearTimeout(this.showTimer); | 			clearTimeout(this.showTimer); | ||||||
| 			clearTimeout(this.hideTimer); | 			clearTimeout(this.hideTimer); | ||||||
| 			this.showTimer = setTimeout(this.showPreview, 500); | 			this.showTimer = setTimeout(this.showPreview, 500); | ||||||
| 		}, | 		}, | ||||||
| 		onMouseleave() { | 		onMouseleave() { | ||||||
| 			if (isDeviceTouch) return; | 			if (isTouchUsing) return; | ||||||
| 			clearTimeout(this.showTimer); | 			clearTimeout(this.showTimer); | ||||||
| 			clearTimeout(this.hideTimer); | 			clearTimeout(this.hideTimer); | ||||||
| 			this.hideTimer = setTimeout(this.closePreview, 500); | 			this.hideTimer = setTimeout(this.closePreview, 500); | ||||||
|  |  | ||||||
|  | @ -12,7 +12,7 @@ | ||||||
| <script lang="ts"> | <script lang="ts"> | ||||||
| import { defineComponent } from 'vue'; | import { defineComponent } from 'vue'; | ||||||
| import { url as local } from '@/config'; | import { url as local } from '@/config'; | ||||||
| import { isDeviceTouch } from '@/scripts/is-device-touch'; | import { isTouchUsing } from '@/scripts/touch'; | ||||||
| import * as os from '@/os'; | import * as os from '@/os'; | ||||||
| 
 | 
 | ||||||
| export default defineComponent({ | export default defineComponent({ | ||||||
|  | @ -65,13 +65,13 @@ export default defineComponent({ | ||||||
| 			} | 			} | ||||||
| 		}, | 		}, | ||||||
| 		onMouseover() { | 		onMouseover() { | ||||||
| 			if (isDeviceTouch) return; | 			if (isTouchUsing) return; | ||||||
| 			clearTimeout(this.showTimer); | 			clearTimeout(this.showTimer); | ||||||
| 			clearTimeout(this.hideTimer); | 			clearTimeout(this.hideTimer); | ||||||
| 			this.showTimer = setTimeout(this.showPreview, 500); | 			this.showTimer = setTimeout(this.showPreview, 500); | ||||||
| 		}, | 		}, | ||||||
| 		onMouseleave() { | 		onMouseleave() { | ||||||
| 			if (isDeviceTouch) return; | 			if (isTouchUsing) return; | ||||||
| 			clearTimeout(this.showTimer); | 			clearTimeout(this.showTimer); | ||||||
| 			clearTimeout(this.hideTimer); | 			clearTimeout(this.hideTimer); | ||||||
| 			this.hideTimer = setTimeout(this.closePreview, 500); | 			this.hideTimer = setTimeout(this.closePreview, 500); | ||||||
|  |  | ||||||
|  | @ -2,11 +2,11 @@ | ||||||
| // ただディレクティブ内でonUnmountedなどのcomposition api使えるのか不明
 | // ただディレクティブ内でonUnmountedなどのcomposition api使えるのか不明
 | ||||||
| 
 | 
 | ||||||
| import { Directive, ref } from 'vue'; | import { Directive, ref } from 'vue'; | ||||||
| import { isDeviceTouch } from '@/scripts/is-device-touch'; | import { isTouchUsing } from '@/scripts/touch'; | ||||||
| import { popup, alert } from '@/os'; | import { popup, alert } from '@/os'; | ||||||
| 
 | 
 | ||||||
| const start = isDeviceTouch ? 'touchstart' : 'mouseover'; | const start = isTouchUsing ? 'touchstart' : 'mouseover'; | ||||||
| const end = isDeviceTouch ? 'touchend' : 'mouseleave'; | const end = isTouchUsing ? 'touchend' : 'mouseleave'; | ||||||
| const delay = 100; | const delay = 100; | ||||||
| 
 | 
 | ||||||
| export default { | export default { | ||||||
|  |  | ||||||
|  | @ -12,16 +12,6 @@ import { resolve } from '@/router'; | ||||||
| import { $i } from '@/account'; | import { $i } from '@/account'; | ||||||
| import { defaultStore } from '@/store'; | import { defaultStore } from '@/store'; | ||||||
| 
 | 
 | ||||||
| export let isScreenTouching = false; |  | ||||||
| 
 |  | ||||||
| window.addEventListener('touchstart', () => { |  | ||||||
| 	isScreenTouching = true; |  | ||||||
| }, { passive: true }); |  | ||||||
| 
 |  | ||||||
| window.addEventListener('touchend', () => { |  | ||||||
| 	isScreenTouching = false; |  | ||||||
| }, { passive: true }); |  | ||||||
| 
 |  | ||||||
| export const stream = markRaw(new Misskey.Stream(url, $i)); | export const stream = markRaw(new Misskey.Stream(url, $i)); | ||||||
| 
 | 
 | ||||||
| export const pendingApiRequestsCount = ref(0); | export const pendingApiRequestsCount = ref(0); | ||||||
|  |  | ||||||
|  | @ -1 +0,0 @@ | ||||||
| export const isDeviceTouch = 'maxTouchPoints' in navigator && navigator.maxTouchPoints > 0; |  | ||||||
							
								
								
									
										19
									
								
								packages/client/src/scripts/touch.ts
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										19
									
								
								packages/client/src/scripts/touch.ts
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,19 @@ | ||||||
|  | const isTouchSupported = 'maxTouchPoints' in navigator && navigator.maxTouchPoints > 0; | ||||||
|  | 
 | ||||||
|  | export let isTouchUsing = false; | ||||||
|  | 
 | ||||||
|  | export let isScreenTouching = false; | ||||||
|  | 
 | ||||||
|  | if (isTouchSupported) { | ||||||
|  | 	window.addEventListener('touchstart', () => { | ||||||
|  | 		// maxTouchPointsなどでの判定だけだと、「タッチ機能付きディスプレイを使っているがマウスでしか操作しない」場合にも
 | ||||||
|  | 		// タッチで使っていると判定されてしまうため、実際に一度でもタッチされたらtrueにする
 | ||||||
|  | 		isTouchUsing = true; | ||||||
|  | 
 | ||||||
|  | 		isScreenTouching = true; | ||||||
|  | 	}, { passive: true }); | ||||||
|  | 	 | ||||||
|  | 	window.addEventListener('touchend', () => { | ||||||
|  | 		isScreenTouching = false; | ||||||
|  | 	}, { passive: true }); | ||||||
|  | } | ||||||
|  | @ -1,6 +1,5 @@ | ||||||
| import { isScreenTouching } from '@/os'; |  | ||||||
| import { Ref, ref } from 'vue'; | import { Ref, ref } from 'vue'; | ||||||
| import { isDeviceTouch } from './is-device-touch'; | import { isScreenTouching, isTouchUsing } from './touch'; | ||||||
| 
 | 
 | ||||||
| export function useTooltip(onShow: (showing: Ref<boolean>) => void) { | export function useTooltip(onShow: (showing: Ref<boolean>) => void) { | ||||||
| 	let isHovering = false; | 	let isHovering = false; | ||||||
|  | @ -14,7 +13,7 @@ export function useTooltip(onShow: (showing: Ref<boolean>) => void) { | ||||||
| 
 | 
 | ||||||
| 		// iOS(Androidも?)では、要素をタップした直後に(おせっかいで)mouseoverイベントを発火させたりするため、その対策
 | 		// iOS(Androidも?)では、要素をタップした直後に(おせっかいで)mouseoverイベントを発火させたりするため、その対策
 | ||||||
| 		// これが無いと、画面に触れてないのにツールチップが出たりしてしまう
 | 		// これが無いと、画面に触れてないのにツールチップが出たりしてしまう
 | ||||||
| 		if (isDeviceTouch && !isScreenTouching) return; | 		if (isTouchUsing && !isScreenTouching) return; | ||||||
| 
 | 
 | ||||||
| 		const showing = ref(true); | 		const showing = ref(true); | ||||||
| 		onShow(showing); | 		onShow(showing); | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue