44-->
55<template >
66 <div class =" cell-stars" :style =" { opacity: !canEditCell() ? 0.6 : 1 }" >
7- <div v-if =" !isEditing" @click =" startEditing" >
8- <div class =" stars-display" >
9- {{ getValue }}
10- </div >
11- </div >
12- <div v-else
13- ref =" editingContainer"
14- class =" inline-editing-container"
15- tabindex =" 0"
16- @keydown.enter =" saveChanges"
17- @keydown.escape =" cancelEdit" >
18- <div class =" align-center" :class =" { 'is-loading': localLoading }" >
19- <div class =" clickable-stars" >
20- <span v-for =" star in 5"
21- :key =" star"
22- class =" star"
23- :class =" { 'filled': star <= editValue, 'clickable': !localLoading && canEditCell() }"
24- :aria-label =" t('tables', 'Set {star} stars', { star })"
25- @click =" setStar(star)" >
26- {{ star <= editValue ? '★' : '☆' }}
27- </span >
28- </div >
29- <div v-if =" localLoading" class =" icon-loading-small icon-loading-inline" />
7+ <div class =" inline-editing-container" >
8+ <div class =" interactive-stars"
9+ @mouseleave =" hoverValue = null" >
10+ <span v-for =" star in 5"
11+ :key =" star"
12+ class =" star"
13+ :class =" {
14+ 'filled': star <= displayValue,
15+ 'clickable': isClickable,
16+ 'hovering': hoverValue !== null
17+ }"
18+ :aria-label =" t('tables', 'Set {star} stars', { star })"
19+ @mouseenter =" hoverValue = star"
20+ @click =" setStar(star)" >
21+ {{ star <= displayValue ? '★' : '☆' }}
22+ </span >
3023 </div >
24+ <div v-if =" localLoading" class =" icon-loading-small icon-loading-inline" />
3125 </div >
3226 </div >
3327</template >
3428
3529<script >
36- import cellEditMixin from ' ../mixins/cellEditMixin.js'
3730import { translate as t } from ' @nextcloud/l10n'
31+ import cellEditMixin from ' ../mixins/cellEditMixin.js'
3832
3933export default {
4034 name: ' TableCellStars' ,
4135
4236 mixins: [cellEditMixin],
4337
4438 props: {
45- column: {
46- type: Object ,
47- default : () => {},
48- },
49- rowId: {
50- type: Number ,
51- default: null ,
52- },
5339 value: {
5440 type: Number ,
5541 default: 0 ,
5642 },
5743 },
5844
45+ data () {
46+ return {
47+ hoverValue: null ,
48+ editValue: this .value ,
49+ }
50+ },
51+
5952 computed: {
60- getValue () {
61- const starEmpty = ' ☆'
62- const starFull = ' ★'
63- const v = this .value
64- return starFull .repeat (v) + starEmpty .repeat (5 - v)
53+ displayValue () {
54+ return this .hoverValue !== null ? this .hoverValue : this .editValue
55+ },
56+
57+ isClickable () {
58+ return ! this .localLoading && this .canEditCell ()
6559 },
6660 },
6761
6862 watch: {
69- isEditing (newValue ) {
70- if (newValue) {
71- this .$nextTick (() => {
72- document .addEventListener (' click' , this .handleClickOutside )
73- })
74- } else {
75- document .removeEventListener (' click' , this .handleClickOutside )
76- }
63+ value (newValue ) {
64+ this .editValue = newValue
7765 },
7866 },
7967
8068 methods: {
8169 t,
8270
8371 setStar (starNumber ) {
84- if (! this .localLoading && this . canEditCell () ) {
72+ if (this .isClickable ) {
8573 // If clicking on a star that represents the current rating, clear to 0
86- if (starNumber === this .editValue ) {
74+ if (starNumber === this .value ) {
8775 this .editValue = 0
8876 } else {
8977 this .editValue = starNumber
9078 }
79+
80+ this .hoverValue = null
81+ this .saveChanges ()
9182 }
9283 },
9384
@@ -97,25 +88,16 @@ export default {
9788 }
9889
9990 if (this .editValue === this .value ) {
100- this .isEditing = false
10191 return
10292 }
10393
10494 const success = await this .updateCellValue (this .editValue )
10595
10696 if (! success) {
107- this .cancelEdit ()
97+ this .editValue = this . value
10898 }
10999
110100 this .localLoading = false
111- this .isEditing = false
112- },
113-
114- handleClickOutside (event ) {
115- // Check if the click is outside the editing container
116- if (this .$refs .editingContainer && ! this .$refs .editingContainer .contains (event .target )) {
117- this .saveChanges ()
118- }
119101 },
120102 },
121103}
@@ -126,45 +108,35 @@ export default {
126108 width : 100% ;
127109}
128110
129- .cell-stars > div :first-child {
130- cursor : pointer ;
131- }
132-
133- .stars-display {
134- font-size : 20px ;
135- cursor : pointer ;
136- }
137-
138- .align-center {
139- align-items : center ;
111+ .inline-editing-container {
140112 display : flex ;
141-
142- & .is-loading {
143- opacity : 0.7 ;
144- }
113+ align-items : center ;
145114}
146115
147- .clickable -stars {
116+ .interactive -stars {
148117 display : flex ;
149118 align-items : center ;
150- gap : 2 px ;
119+ gap : 0 ;
151120}
152121
153122.star {
154- font-size : 1.4em ;
155- padding : 4px ;
156- transition : transform 0.1s ease ;
123+ font-size : 20px ;
124+ color : var (--color-main-text );
125+ padding : 0 ;
126+ transition : color 0.1s ease ;
157127
158128 & .clickable {
159129 cursor : pointer ;
160-
161- & :hover {
162- transform : scale (1.1 );
163- }
164130 }
165131
166132 & .filled {
167- color : var (--color-warning );
133+ color : var (--color-main-text );
134+ }
135+
136+ & .hovering {
137+ & .filled {
138+ color : var (--color-text-maxcontrast );
139+ }
168140 }
169141}
170142
0 commit comments