fix(client): タッチ機能付きディスプレイを使っていてマウス操作をしている場合に一部機能が動作しない問題を修正

This commit is contained in:
syuilo 2021-12-05 13:10:19 +09:00
parent b1bd7307bb
commit fbe4869d1e
9 changed files with 40 additions and 26 deletions

View file

@ -7,6 +7,13 @@
-->
## 12.x.x (unreleased)
### Improvements
### Bugfixes
- クライアント: タッチ機能付きディスプレイを使っていてマウス操作をしている場合に一部機能が動作しない問題を修正
## 12.98.0 (2021/12/03)
### Improvements

View file

@ -79,7 +79,7 @@ import { emojilist } from '@/scripts/emojilist';
import { getStaticImageUrl } from '@/scripts/get-static-image-url';
import Particle from '@/components/particle.vue';
import * as os from '@/os';
import { isDeviceTouch } from '@/scripts/is-device-touch';
import { isTouchUsing } from '@/scripts/touch';
import { isMobile } from '@/scripts/is-mobile';
import { emojiCategories } from '@/instance';
import XSection from './emoji-picker.section.vue';
@ -108,7 +108,7 @@ export default defineComponent({
pinned: this.$store.reactiveState.reactions,
width: this.asReactionPicker ? this.$store.state.reactionPickerWidth : 3,
height: this.asReactionPicker ? this.$store.state.reactionPickerHeight : 2,
big: this.asReactionPicker ? isDeviceTouch : false,
big: this.asReactionPicker ? isTouchUsing : false,
customEmojiCategories: emojiCategories,
customEmojis: this.$instance.emojis,
q: null,
@ -268,7 +268,7 @@ export default defineComponent({
methods: {
focus() {
if (!isMobile && !isDeviceTouch) {
if (!isMobile && !isTouchUsing) {
this.$refs.search.focus({
preventScroll: true
});

View file

@ -23,7 +23,7 @@
import { defineComponent } from 'vue';
import { toUnicode as decodePunycode } from 'punycode/';
import { url as local } from '@/config';
import { isDeviceTouch } from '@/scripts/is-device-touch';
import { isTouchUsing } from '@/scripts/touch';
import * as os from '@/os';
export default defineComponent({
@ -91,13 +91,13 @@ export default defineComponent({
}
},
onMouseover() {
if (isDeviceTouch) return;
if (isTouchUsing) return;
clearTimeout(this.showTimer);
clearTimeout(this.hideTimer);
this.showTimer = setTimeout(this.showPreview, 500);
},
onMouseleave() {
if (isDeviceTouch) return;
if (isTouchUsing) return;
clearTimeout(this.showTimer);
clearTimeout(this.hideTimer);
this.hideTimer = setTimeout(this.closePreview, 500);

View file

@ -12,7 +12,7 @@
<script lang="ts">
import { defineComponent } from 'vue';
import { url as local } from '@/config';
import { isDeviceTouch } from '@/scripts/is-device-touch';
import { isTouchUsing } from '@/scripts/touch';
import * as os from '@/os';
export default defineComponent({
@ -65,13 +65,13 @@ export default defineComponent({
}
},
onMouseover() {
if (isDeviceTouch) return;
if (isTouchUsing) return;
clearTimeout(this.showTimer);
clearTimeout(this.hideTimer);
this.showTimer = setTimeout(this.showPreview, 500);
},
onMouseleave() {
if (isDeviceTouch) return;
if (isTouchUsing) return;
clearTimeout(this.showTimer);
clearTimeout(this.hideTimer);
this.hideTimer = setTimeout(this.closePreview, 500);

View file

@ -2,11 +2,11 @@
// ただディレクティブ内でonUnmountedなどのcomposition api使えるのか不明
import { Directive, ref } from 'vue';
import { isDeviceTouch } from '@/scripts/is-device-touch';
import { isTouchUsing } from '@/scripts/touch';
import { popup, alert } from '@/os';
const start = isDeviceTouch ? 'touchstart' : 'mouseover';
const end = isDeviceTouch ? 'touchend' : 'mouseleave';
const start = isTouchUsing ? 'touchstart' : 'mouseover';
const end = isTouchUsing ? 'touchend' : 'mouseleave';
const delay = 100;
export default {

View file

@ -12,16 +12,6 @@ import { resolve } from '@/router';
import { $i } from '@/account';
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 pendingApiRequestsCount = ref(0);

View file

@ -1 +0,0 @@
export const isDeviceTouch = 'maxTouchPoints' in navigator && navigator.maxTouchPoints > 0;

View 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 });
}

View file

@ -1,6 +1,5 @@
import { isScreenTouching } from '@/os';
import { Ref, ref } from 'vue';
import { isDeviceTouch } from './is-device-touch';
import { isScreenTouching, isTouchUsing } from './touch';
export function useTooltip(onShow: (showing: Ref<boolean>) => void) {
let isHovering = false;
@ -14,7 +13,7 @@ export function useTooltip(onShow: (showing: Ref<boolean>) => void) {
// iOS(Androidも)では、要素をタップした直後に(おせっかいで)mouseoverイベントを発火させたりするため、その対策
// これが無いと、画面に触れてないのにツールチップが出たりしてしまう
if (isDeviceTouch && !isScreenTouching) return;
if (isTouchUsing && !isScreenTouching) return;
const showing = ref(true);
onShow(showing);