diff --git a/.github/workflows/close_blank_issues.yaml b/.github/workflows/close_blank_issues.yaml new file mode 100644 index 00000000..c7108827 --- /dev/null +++ b/.github/workflows/close_blank_issues.yaml @@ -0,0 +1,42 @@ +name: Close Issues not using a template + +on: + issues: + types: + - opened + +permissions: + issues: write + +jobs: + close_issue: + runs-on: ubuntu-latest + + steps: + - name: Check issue headings + uses: actions/github-script@v6 + with: + script: | + const issueBody = context.payload.issue.body || ""; + + // Match Markdown headings (e.g., # Heading, ## Heading) + const headingRegex = /^(#{1,6})\s.+/gm; + const headings = [...issueBody.matchAll(headingRegex)]; + + if (headings.length < 3) { + // Post a comment + await github.rest.issues.createComment({ + owner: context.repo.owner, + repo: context.repo.repo, + issue_number: context.payload.issue.number, + body: "Thank you for opening an issue! To help us review your request efficiently, please use one of the provided issue templates. If you're seeking information or have a general question, consider opening a Discussion or joining the conversation on our Discord. Thanks!" + }); + + // Close the issue + await github.rest.issues.update({ + owner: context.repo.owner, + repo: context.repo.repo, + issue_number: context.payload.issue.number, + state: "closed" + }); + } \ No newline at end of file diff --git a/client/assets/app.css b/client/assets/app.css index 0cd4ac49..36b3b4ba 100644 --- a/client/assets/app.css +++ b/client/assets/app.css @@ -92,11 +92,10 @@ } /* Firefox */ -input[type=number] { +input[type='number'] { -moz-appearance: textfield; } - .tracksTable { border-collapse: collapse; width: 100%; @@ -177,6 +176,10 @@ input[type=number] { box-shadow: 4px 1px 8px #11111166, -4px 1px 8px #11111166, 1px -4px 8px #11111166; } +.box-shadow-progressbar { + box-shadow: 0px -1px 4px rgb(62, 50, 2, 0.5); +} + .shadow-height { height: calc(100% - 4px); } @@ -204,7 +207,6 @@ Bookshelf Label color: #fce3a6; } - .cover-bg { width: calc(100% + 40px); height: calc(100% + 40px); diff --git a/client/assets/defaultStyles.css b/client/assets/defaultStyles.css index 027ccdf2..e0ca79e2 100644 --- a/client/assets/defaultStyles.css +++ b/client/assets/defaultStyles.css @@ -52,4 +52,17 @@ text-indent: 0px !important; text-align: start !important; text-align-last: start !important; -} \ No newline at end of file +} + +.default-style.less-spacing p { + margin-block-start: 0; +} + +.default-style.less-spacing ul { + margin-block-start: 0; +} + +.default-style.less-spacing ol { + margin-block-start: 0; +} + diff --git a/client/assets/trix.css b/client/assets/trix.css index 8f88c61f..7432b25f 100644 --- a/client/assets/trix.css +++ b/client/assets/trix.css @@ -446,7 +446,7 @@ trix-editor .attachment__metadata .attachment__size { } .trix-content { - line-height: 1.5; + line-height: inherit; } .trix-content * { @@ -455,6 +455,13 @@ trix-editor .attachment__metadata .attachment__size { padding: 0; } +.trix-content p { + box-sizing: border-box; + margin-top: 0; + margin-bottom: 0.5em; + padding: 0; +} + .trix-content h1 { font-size: 1.2em; line-height: 1.2; @@ -560,4 +567,4 @@ trix-editor .attachment__metadata .attachment__size { .trix-content .attachment-gallery.attachment-gallery--4 .attachment { flex-basis: 50%; max-width: 50%; -} \ No newline at end of file +} diff --git a/client/components/app/LazyBookshelf.vue b/client/components/app/LazyBookshelf.vue index 29b06df3..22ab731d 100644 --- a/client/components/app/LazyBookshelf.vue +++ b/client/components/app/LazyBookshelf.vue @@ -19,6 +19,14 @@

{{ emptyMessage }}

+
+ {{ emptyMessageHelp }} + + + help_outline + + +
{{ $strings.ButtonClearFilter }} @@ -109,6 +117,11 @@ export default { } return this.$strings.MessageNoResults }, + emptyMessageHelp() { + if (this.page === 'collections') return this.$strings.MessageBookshelfNoCollectionsHelp + if (this.page === 'playlists') return this.$strings.MessageNoUserPlaylistsHelp + return '' + }, entityName() { if (!this.page) return 'items' return this.page diff --git a/client/components/app/MediaPlayerContainer.vue b/client/components/app/MediaPlayerContainer.vue index 61b10ba8..cf22d322 100644 --- a/client/components/app/MediaPlayerContainer.vue +++ b/client/components/app/MediaPlayerContainer.vue @@ -394,7 +394,8 @@ export default { { src: this.$store.getters['globals/getLibraryItemCoverSrc'](this.streamLibraryItem, '/Logo.png', true) } - ] + ], + chapterInfo }) console.log('Set media session metadata', navigator.mediaSession.metadata) diff --git a/client/components/cards/BookMatchCard.vue b/client/components/cards/BookMatchCard.vue index d5355e91..4fa24c1f 100644 --- a/client/components/cards/BookMatchCard.vue +++ b/client/components/cards/BookMatchCard.vue @@ -24,7 +24,7 @@
-

{{ book.description }}

+

{{ book.descriptionPlain }}

diff --git a/client/components/cards/LazyBookCard.vue b/client/components/cards/LazyBookCard.vue index 884e54b6..544b7fec 100644 --- a/client/components/cards/LazyBookCard.vue +++ b/client/components/cards/LazyBookCard.vue @@ -39,7 +39,7 @@
-
+
diff --git a/client/components/cards/LazySeriesCard.vue b/client/components/cards/LazySeriesCard.vue index 6b1633c4..f8ae8fd2 100644 --- a/client/components/cards/LazySeriesCard.vue +++ b/client/components/cards/LazySeriesCard.vue @@ -10,7 +10,7 @@

{{ books.length }}

-
+
-
-

{{ $strings.MessageNoCollections }}

+
+
+

{{ $strings.MessageNoCollections }}

+
+

{{ $strings.MessageBookshelfNoCollectionsHelp }}

+ + + help_outline + + +
+
+
diff --git a/client/components/modals/item/tabs/Match.vue b/client/components/modals/item/tabs/Match.vue index c7247d51..623ef2a1 100644 --- a/client/components/modals/item/tabs/Match.vue +++ b/client/components/modals/item/tabs/Match.vue @@ -94,9 +94,9 @@ diff --git a/client/components/modals/playlists/AddCreateModal.vue b/client/components/modals/playlists/AddCreateModal.vue index d1f910b8..4a7daad9 100644 --- a/client/components/modals/playlists/AddCreateModal.vue +++ b/client/components/modals/playlists/AddCreateModal.vue @@ -19,8 +19,18 @@
-
-

{{ $strings.MessageNoUserPlaylists }}

+
+
+

{{ $strings.MessageNoUserPlaylists }}

+
+

{{ $strings.MessageNoUserPlaylistsHelp }}

+ + + help_outline + + +
+
diff --git a/client/components/modals/podcast/ViewEpisode.vue b/client/components/modals/podcast/ViewEpisode.vue index af67242a..6c1a678c 100644 --- a/client/components/modals/podcast/ViewEpisode.vue +++ b/client/components/modals/podcast/ViewEpisode.vue @@ -16,7 +16,7 @@

{{ title }}

-
+

{{ $strings.MessageNoDescription }}

diff --git a/client/components/modals/rssfeed/OpenCloseModal.vue b/client/components/modals/rssfeed/OpenCloseModal.vue index 86dfeccf..1d7811ed 100644 --- a/client/components/modals/rssfeed/OpenCloseModal.vue +++ b/client/components/modals/rssfeed/OpenCloseModal.vue @@ -10,9 +10,7 @@

{{ $strings.HeaderRSSFeedIsOpen }}

- - - {{ copiedToClipboard ? 'check' : 'content_copy' }} +
@@ -68,8 +66,7 @@ export default { preventIndexing: true, ownerName: '', ownerEmail: '' - }, - copiedToClipboard: false + } } }, watch: { @@ -161,12 +158,6 @@ export default { this.processing = false }) }, - async copyToClipboard(str) { - this.copiedToClipboard = await this.$copyToClipboard(str) - setTimeout(() => { - this.copiedToClipboard = false - }, 2000) - }, closeFeed() { this.processing = true this.$axios diff --git a/client/components/modals/rssfeed/ViewFeedModal.vue b/client/components/modals/rssfeed/ViewFeedModal.vue index ac594ed7..8fc13ff9 100644 --- a/client/components/modals/rssfeed/ViewFeedModal.vue +++ b/client/components/modals/rssfeed/ViewFeedModal.vue @@ -5,8 +5,7 @@

{{ $strings.HeaderRSSFeedGeneral }}

- - {{ copiedToClipboard ? 'check' : 'content_copy' }} +
@@ -56,8 +55,7 @@ export default { }, data() { return { - processing: false, - copiedToClipboard: false + processing: false } }, computed: { @@ -75,16 +73,7 @@ export default { feedUrl() { return this.feed ? `${window.origin}${this.$config.routerBasePath}${this.feed.feedUrl}` : '' } - }, - methods: { - async copyToClipboard(str) { - this.copiedToClipboard = await this.$copyToClipboard(str) - setTimeout(() => { - this.copiedToClipboard = false - }, 2000) - } - }, - mounted() {} + } } diff --git a/client/components/player/PlayerUi.vue b/client/components/player/PlayerUi.vue index 31267c7a..f4ad59d1 100644 --- a/client/components/player/PlayerUi.vue +++ b/client/components/player/PlayerUi.vue @@ -2,7 +2,7 @@
- +
@@ -23,7 +23,8 @@ export default { }, readonly: Boolean, disabled: Boolean, - inputClass: String + inputClass: String, + showCopy: Boolean }, data() { return {} diff --git a/client/components/ui/VueTrix.vue b/client/components/ui/VueTrix.vue index 5d351c72..8bbb42df 100644 --- a/client/components/ui/VueTrix.vue +++ b/client/components/ui/VueTrix.vue @@ -1,6 +1,37 @@ @@ -14,6 +45,30 @@ import Trix from 'trix' import '@/assets/trix.css' +function enableBreakParagraphOnReturn() { + // Trix works with divs by default, we want paragraphs instead + Trix.config.blockAttributes.default.tagName = 'p' + // Enable break paragraph on Enter (Shift + Enter will still create a line break) + Trix.config.blockAttributes.default.breakOnReturn = true + + // Hack to fix buggy paragraph breaks + // Copied from https://github.com/basecamp/trix/issues/680#issuecomment-735742942 + Trix.Block.prototype.breaksOnReturn = function () { + const attr = this.getLastAttribute() + const config = Trix.getBlockConfig(attr ? attr : 'default') + return config ? config.breakOnReturn : false + } + Trix.LineBreakInsertion.prototype.shouldInsertBlockBreak = function () { + if (this.block.hasAttributes() && this.block.isListItem() && !this.block.isEmpty()) { + return this.startLocation.offset > 0 + } else { + return !this.shouldBreakFormattedBlock() ? this.breaksOnReturn : false + } + } +} + +enableBreakParagraphOnReturn() + export default { name: 'vue-trix', model: { @@ -134,6 +189,9 @@ export default { * Compute a random id of hidden input * when it haven't been specified. */ + toolbarId() { + return `trix-toolbar-${this.generateId}` + }, generateId() { return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, (c) => { var r = (Math.random() * 16) | 0 @@ -223,13 +281,17 @@ export default { decorateDisabledEditor(editorState) { /** Disable toolbar and editor by pointer events styling */ if (editorState) { - this.$refs.trix.toolbarElement.style['pointer-events'] = 'none' + this.$refs.trix.disabled = true this.$refs.trix.contentEditable = false - this.$refs.trix.style['background'] = '#e9ecef' + this.$refs.trix.style['pointer-events'] = 'none' + this.$refs.trix.style['background-color'] = '#444' + this.$refs.trix.style['color'] = '#bbb' } else { - this.$refs.trix.toolbarElement.style['pointer-events'] = 'unset' + this.$refs.trix.disabled = false + this.$refs.trix.contentEditable = true this.$refs.trix.style['pointer-events'] = 'unset' - this.$refs.trix.style['background'] = 'transparent' + this.$refs.trix.style['background-color'] = '' + this.$refs.trix.style['color'] = '' } }, overrideConfig(config) { @@ -250,32 +312,15 @@ export default { } return target }, - enableBreakParagraphOnReturn() { - // Trix works with divs by default, we want paragraphs instead - Trix.config.blockAttributes.default.tagName = 'p' - // Enable break paragraph on Enter (Shift + Enter will still create a line break) - Trix.config.blockAttributes.default.breakOnReturn = true - - // Hack to fix buggy paragraph breaks - // Copied from https://github.com/basecamp/trix/issues/680#issuecomment-735742942 - Trix.Block.prototype.breaksOnReturn = function () { - const attr = this.getLastAttribute() - const config = Trix.getBlockConfig(attr ? attr : 'default') - return config ? config.breakOnReturn : false - } - Trix.LineBreakInsertion.prototype.shouldInsertBlockBreak = function () { - if (this.block.hasAttributes() && this.block.isListItem() && !this.block.isEmpty()) { - return this.startLocation.offset > 0 - } else { - return !this.shouldBreakFormattedBlock() ? this.breaksOnReturn : false - } + blur() { + if (this.$refs.trix && this.$refs.trix.blur) { + this.$refs.trix.blur() } } }, mounted() { /** Override editor configuration */ this.overrideConfig(this.config) - this.enableBreakParagraphOnReturn() /** Check if editor read-only mode is required */ this.decorateDisabledEditor(this.disabledEditor) this.$nextTick(() => { @@ -305,4 +350,12 @@ export default { .trix_container .trix-content { background-color: white; } +trix-editor { + max-height: calc(4 * 1lh); + overflow-y: auto; +} + +trix-editor * { + pointer-events: inherit; +} diff --git a/client/components/widgets/BookDetailsEdit.vue b/client/components/widgets/BookDetailsEdit.vue index 5fbcaa20..fa26bcf5 100644 --- a/client/components/widgets/BookDetailsEdit.vue +++ b/client/components/widgets/BookDetailsEdit.vue @@ -26,7 +26,7 @@
- +
diff --git a/client/pages/batch/index.vue b/client/pages/batch/index.vue index 5cc83176..263dee58 100644 --- a/client/pages/batch/index.vue +++ b/client/pages/batch/index.vue @@ -86,7 +86,12 @@
-
+
+ {{ $strings.ButtonReset }} + + {{ $strings.ButtonBatchEditPopulateFromExisting }} + +
{{ $strings.ButtonApply }}
@@ -97,6 +102,11 @@