diff --git a/locales/de-DE.yml b/locales/de-DE.yml index cf9296981f..469b1c9493 100644 --- a/locales/de-DE.yml +++ b/locales/de-DE.yml @@ -704,6 +704,11 @@ editCode: "Code bearbeiten" apply: "Anwenden" receiveAnnouncementFromInstance: "E-Mail-Benachrichtigungen von dieser Instanz empfangen" emailNotification: "E-Mail-Benachrichtigungen" +inChannelSearch: "In Kanal suchen" +useReactionPickerForContextMenu: "Reaktionsauswahl durch Rechtsklick öffnen" +jumpToSpecifiedDate: "Zu bestimmtem Datum springen" +showingPastTimeline: "Momentan wird eine alte Chronik angezeigt" +clear: "Zurückkehren" _email: _follow: title: "Du hast einen neuen Follower" diff --git a/locales/en-US.yml b/locales/en-US.yml index 467fbdfd13..d3b6804744 100644 --- a/locales/en-US.yml +++ b/locales/en-US.yml @@ -704,6 +704,11 @@ editCode: "Edit code" apply: "Apply" receiveAnnouncementFromInstance: "Receive Email notifications from this instance" emailNotification: "Email notifications" +inChannelSearch: "Search in channel" +useReactionPickerForContextMenu: "Open reaction picker on right-click" +jumpToSpecifiedDate: "Jump to specific date" +showingPastTimeline: "Currently displaying an old timeline" +clear: "Return" _email: _follow: title: "You've got a new follower" diff --git a/locales/ja-JP.yml b/locales/ja-JP.yml index 51a82a32b9..e5700fe059 100644 --- a/locales/ja-JP.yml +++ b/locales/ja-JP.yml @@ -705,6 +705,11 @@ apply: "適用" receiveAnnouncementFromInstance: "インスタンスからのお知らせを受け取る" emailNotification: "メール通知" inChannelSearch: "チャンネル内検索" +useReactionPickerForContextMenu: "右クリックでリアクションピッカーを開く" +typingUsers: "{users}が入力中" +jumpToSpecifiedDate: "特定の日付にジャンプ" +showingPastTimeline: "過去のタイムラインを表示しています" +clear: "クリア" _email: _follow: diff --git a/locales/ru-RU.yml b/locales/ru-RU.yml index 07cd456796..4f8cc6d85c 100644 --- a/locales/ru-RU.yml +++ b/locales/ru-RU.yml @@ -704,6 +704,7 @@ editCode: "Редактировать исходный текст" apply: "Применить" receiveAnnouncementFromInstance: "Получать оповещения с инстанса" emailNotification: "Уведомления по электронной почте" +inChannelSearch: "Поиск по каналу" _email: _follow: title: "Новый подписчик" diff --git a/locales/zh-CN.yml b/locales/zh-CN.yml index f19562b1e4..c13cf12220 100644 --- a/locales/zh-CN.yml +++ b/locales/zh-CN.yml @@ -309,7 +309,7 @@ monthX: "{month}月" yearX: "{year}年" pages: "页面" integration: "关联" -connectSerice: "已连接" +connectSerice: "连接" disconnectSerice: "断开连接" enableLocalTimeline: "启用本地时间线功能" enableGlobalTimeline: "启用全局时间线" @@ -321,7 +321,7 @@ proxyRemoteFiles: "代理远程文件" proxyRemoteFilesDescription: "启用此设置后,由于超出存储容量而导致未保存被删除的远程文件将被本地代理,并且会生成缩略图。不会影响服务器的存储。" driveCapacityPerLocalAccount: "每个用户的网盘空间" driveCapacityPerRemoteAccount: "每个远程用户的网盘容量" -inMb: "以兆字节(Mbps)为单位" +inMb: "以兆字节(MegaByte)为单位" iconUrl: "图标URL" bannerUrl: "Banner URL" basicInfo: "基本信息" @@ -579,7 +579,7 @@ smtpPort: "端口" smtpUser: "用户名" smtpPass: "密码" emptyToDisableSmtpAuth: "用户名和密码留空可以禁用SMTP验证" -smtpSecure: "在 SMTP 连接中使用隐式 SSL / TLS" +smtpSecure: "在 SMTP 连接中默认使用 SSL / TLS" smtpSecureInfo: "使用STARTTLS时关闭。" testEmail: "邮件发送测试" wordMute: "文字屏蔽" @@ -638,8 +638,8 @@ repliedCount: "回复数" renotedCount: "转发数" followingCount: "正在关注数量" followersCount: "关注者数量" -sentReactionsCount: "发送反应数" -receivedReactionsCount: "收到反应数" +sentReactionsCount: "发送回应数" +receivedReactionsCount: "收到回应数" pollVotesCount: "问卷调查的投票数" pollVotedCount: "问卷调查的被投票数" yes: "是" @@ -704,6 +704,12 @@ editCode: "编辑代码" apply: "应用" receiveAnnouncementFromInstance: "从实例接收通知" emailNotification: "邮件通知" +inChannelSearch: "频道内搜索" +useReactionPickerForContextMenu: "单击右键打开回应工具栏" +typingUsers: "{users}正在输入" +jumpToSpecifiedDate: "跳转到特定日期" +showingPastTimeline: "显示过去的时间线" +clear: "清除" _email: _follow: title: "你有新的关注者" diff --git a/package.json b/package.json index 42f986cda3..cbc9f06aae 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "misskey", "author": "syuilo ", - "version": "12.70.0", + "version": "12.71.0", "codename": "indigo", "repository": { "type": "git", @@ -62,9 +62,9 @@ "@types/is-url": "1.2.28", "@types/js-yaml": "4.0.0", "@types/jsdom": "16.2.6", - "@types/jsonld": "1.5.2", + "@types/jsonld": "1.5.3", "@types/katex": "0.11.0", - "@types/koa": "2.11.7", + "@types/koa": "2.13.0", "@types/koa-bodyparser": "4.3.0", "@types/koa-cors": "0.0.0", "@types/koa-favicon": "2.0.19", @@ -77,8 +77,8 @@ "@types/koa__router": "8.0.4", "@types/markdown-it": "12.0.1", "@types/matter-js": "0.14.10", - "@types/mocha": "8.2.0", - "@types/node": "14.14.25", + "@types/mocha": "8.2.1", + "@types/node": "14.14.31", "@types/node-fetch": "2.5.8", "@types/nodemailer": "6.4.0", "@types/nprogress": "0.2.0", @@ -110,23 +110,23 @@ "@typescript-eslint/parser": "4.14.2", "@vue/compiler-sfc": "3.0.5", "abort-controller": "3.0.0", - "apexcharts": "3.24.0", + "apexcharts": "3.25.0", "autobind-decorator": "2.4.0", "autosize": "4.0.2", "autwh": "0.1.0", - "aws-sdk": "2.840.0", + "aws-sdk": "2.848.0", "bcryptjs": "2.4.3", "blurhash": "1.1.3", "broadcast-channel": "3.4.1", "bull": "3.20.1", "cafy": "15.2.1", - "cbor": "6.0.1", + "cbor": "7.0.1", "chalk": "4.1.0", "chart.js": "2.9.4", "cli-highlight": "2.1.10", "commander": "4.1.1", "content-disposition": "0.5.3", - "core-js": "3.8.3", + "core-js": "3.9.0", "crc-32": "1.2.0", "css-loader": "5.0.2", "cssnano": "4.1.10", @@ -134,8 +134,8 @@ "diskusage": "1.1.3", "double-ended-queue": "2.1.0-0", "escape-regexp": "0.0.1", - "eslint": "7.19.0", - "eslint-plugin-vue": "7.5.0", + "eslint": "7.20.0", + "eslint-plugin-vue": "7.6.0", "eventemitter3": "4.0.7", "feed": "4.2.2", "fibers": "5.0.0", @@ -163,7 +163,7 @@ "jsdom": "16.4.0", "json5": "2.2.0", "json5-loader": "4.0.1", - "jsonld": "3.3.0", + "jsonld": "4.0.1", "jsrsasign": "8.0.20", "katex": "0.12.0", "koa": "2.13.1", @@ -194,7 +194,7 @@ "parsimmon": "1.16.0", "pg": "8.5.1", "portscanner": "2.2.0", - "postcss": "8.2.5", + "postcss": "8.2.6", "postcss-loader": "5.0.0", "prismjs": "1.23.0", "probe-image-size": "6.0.0", @@ -218,7 +218,7 @@ "rimraf": "3.0.2", "rndstr": "1.0.0", "s-age": "1.1.2", - "sass": "1.32.6", + "sass": "1.32.8", "sass-loader": "11.0.1", "seedrandom": "3.0.5", "sharp": "0.27.1", @@ -234,11 +234,11 @@ "throttle-debounce": "3.0.1", "tinycolor2": "1.4.2", "tmp": "0.2.1", - "ts-loader": "8.0.16", + "ts-loader": "8.0.17", "ts-node": "9.1.1", "tslint": "6.1.3", "tslint-sonarts": "1.9.0", - "typeorm": "0.2.30", + "typeorm": "0.2.31", "typescript": "4.1.5", "ulid": "2.3.0", "url-loader": "4.1.1", @@ -254,7 +254,7 @@ "vue-style-loader": "4.1.2", "vuedraggable": "4.0.1", "web-push": "3.4.4", - "webpack": "5.21.2", + "webpack": "5.23.0", "webpack-cli": "4.5.0", "websocket": "1.0.33", "ws": "7.4.3", diff --git a/src/client/components/note-detailed.vue b/src/client/components/note-detailed.vue index 1108bd2c27..434dd56ba3 100644 --- a/src/client/components/note-detailed.vue +++ b/src/client/components/note-detailed.vue @@ -756,7 +756,13 @@ export default defineComponent({ }; if (isLink(e.target)) return; if (window.getSelection().toString() !== '') return; - os.contextMenu(this.getMenu(), e).then(this.focus); + + if (this.$store.state.useReactionPickerForContextMenu) { + e.preventDefault(); + this.react(); + } else { + os.contextMenu(this.getMenu(), e).then(this.focus); + } }, menu(viaKeyboard = false) { diff --git a/src/client/components/note.vue b/src/client/components/note.vue index d532289857..24c374869d 100644 --- a/src/client/components/note.vue +++ b/src/client/components/note.vue @@ -731,7 +731,13 @@ export default defineComponent({ }; if (isLink(e.target)) return; if (window.getSelection().toString() !== '') return; - os.contextMenu(this.getMenu(), e).then(this.focus); + + if (this.$store.state.useReactionPickerForContextMenu) { + e.preventDefault(); + this.react(); + } else { + os.contextMenu(this.getMenu(), e).then(this.focus); + } }, menu(viaKeyboard = false) { diff --git a/src/client/components/notes.vue b/src/client/components/notes.vue index bd6d5bb4f5..332f00e5db 100644 --- a/src/client/components/notes.vue +++ b/src/client/components/notes.vue @@ -8,10 +8,10 @@
- +
@@ -19,10 +19,10 @@
- +
@@ -32,10 +32,11 @@ import { defineComponent } from 'vue'; import paging from '@/scripts/paging'; import XNote from './note.vue'; import XList from './date-separated-list.vue'; +import MkButton from '@/components/ui/button.vue'; export default defineComponent({ components: { - XNote, XList, + XNote, XList, MkButton, }, mixins: [ diff --git a/src/client/components/post-form.vue b/src/client/components/post-form.vue index fa9aeff8af..7849095ba8 100644 --- a/src/client/components/post-form.vue +++ b/src/client/components/post-form.vue @@ -70,6 +70,7 @@ import * as os from '@/os'; import { selectFile } from '@/scripts/select-file'; import { notePostInterruptors, postFormActions } from '@/store'; import { isMobile } from '@/scripts/is-mobile'; +import { throttle } from 'throttle-debounce'; export default defineComponent({ components: { @@ -144,6 +145,11 @@ export default defineComponent({ quoteId: null, recentHashtags: JSON.parse(localStorage.getItem('hashtags') || '[]'), imeText: '', + typing: throttle(3000, () => { + if (this.channel) { + os.stream.send('typingOnChannel', { channel: this.channel.id }); + } + }), postFormActions, faReply, faQuoteRight, faPaperPlane, faTimes, faUpload, faPollH, faGlobe, faHome, faUnlock, faEnvelope, faEyeSlash, faLaughSquint, faPlus, faPhotoVideo, faAt, faBiohazard, faPlug }; @@ -434,10 +440,12 @@ export default defineComponent({ onKeydown(e: KeyboardEvent) { if ((e.which === 10 || e.which === 13) && (e.ctrlKey || e.metaKey) && this.canPost) this.post(); if (e.which === 27) this.$emit('esc'); + this.typing(); }, onCompositionUpdate(e: CompositionEvent) { this.imeText = e.data; + this.typing(); }, onCompositionEnd(e: CompositionEvent) { diff --git a/src/client/components/ui/modal.vue b/src/client/components/ui/modal.vue index 69a83e002c..405fa4aaa5 100644 --- a/src/client/components/ui/modal.vue +++ b/src/client/components/ui/modal.vue @@ -70,6 +70,7 @@ export default defineComponent({ // TODO: ResizeObserver無くしたい new ResizeObserver((entries, observer) => { const rect = this.src.getBoundingClientRect(); + const width = popover.offsetWidth; const height = popover.offsetHeight; diff --git a/src/client/init.ts b/src/client/init.ts index c60b25359b..ce12849770 100644 --- a/src/client/init.ts +++ b/src/client/init.ts @@ -63,6 +63,9 @@ import { reloadChannel } from '@/scripts/unison-reload'; console.info(`Misskey v${version}`); +// boot.jsのやつを解除 +window.onerror = null; + if (_DEV_) { console.warn('Development mode!!!'); diff --git a/src/client/pages/messaging/messaging-room.form.vue b/src/client/pages/messaging/messaging-room.form.vue index e561cb3db5..258300dc52 100644 --- a/src/client/pages/messaging/messaging-room.form.vue +++ b/src/client/pages/messaging/messaging-room.form.vue @@ -7,6 +7,7 @@ v-model="text" ref="text" @keypress="onKeypress" + @compositionupdate="onCompositionUpdate" @paste="onPaste" :placeholder="$ts.inputMessageHere" > @@ -29,6 +30,7 @@ import { formatTimeString } from '../../../misc/format-time-string'; import { selectFile } from '@/scripts/select-file'; import * as os from '@/os'; import { Autocomplete } from '@/scripts/autocomplete'; +import { throttle } from 'throttle-debounce'; export default defineComponent({ props: { @@ -46,6 +48,9 @@ export default defineComponent({ text: null, file: null, sending: false, + typing: throttle(3000, () => { + os.stream.send('typingOnMessaging', this.user ? { partner: this.user.id } : { group: this.group.id }); + }), faPaperPlane, faPhotoVideo, faLaughSquint }; }, @@ -147,11 +152,16 @@ export default defineComponent({ }, onKeypress(e) { + this.typing(); if ((e.which == 10 || e.which == 13) && (e.ctrlKey || e.metaKey) && this.canSend) { this.send(); } }, + onCompositionUpdate() { + this.typing(); + }, + chooseFile(e) { selectFile(e.currentTarget || e.target, this.$ts.selectFile, false).then(file => { this.file = file; diff --git a/src/client/pages/messaging/messaging-room.vue b/src/client/pages/messaging/messaging-room.vue index 7fdd0a201b..3921a081d1 100644 --- a/src/client/pages/messaging/messaging-room.vue +++ b/src/client/pages/messaging/messaging-room.vue @@ -16,6 +16,14 @@