mirror of
				https://github.com/simon987/sist2.git
				synced 2025-10-31 16:06:53 +00:00 
			
		
		
		
	Shift click & select all/none in index picker
This commit is contained in:
		
							parent
							
								
									030643cee0
								
							
						
					
					
						commit
						e3f78fb693
					
				| @ -7,11 +7,28 @@ | ||||
|         value-field="id"></b-form-select> | ||||
|   </div> | ||||
|   <div v-else> | ||||
|     <b-list-group id="index-picker-desktop"> | ||||
| 
 | ||||
| 
 | ||||
|     <div class="d-flex justify-content-between align-content-center"> | ||||
|       <span> | ||||
|         {{ selectedIndices.length }} | ||||
|         {{ selectedIndices.length === 1 ? $t("indexPicker.selectedIndex") : $t("indexPicker.selectedIndices") }} | ||||
|       </span> | ||||
| 
 | ||||
|       <div> | ||||
|         <b-button variant="link" @click="selectAll()"> {{ $t("indexPicker.selectAll") }}</b-button> | ||||
|         <b-button variant="link" @click="selectNone()"> {{ $t("indexPicker.selectNone") }}</b-button> | ||||
|       </div> | ||||
|     </div> | ||||
| 
 | ||||
|     <b-list-group id="index-picker-desktop" class="unselectable"> | ||||
|       <b-list-group-item | ||||
|           v-for="idx in indices" | ||||
|           @click="toggleIndex(idx)" | ||||
|           class="d-flex justify-content-between align-items-center list-group-item-action pointer"> | ||||
|           @click="toggleIndex(idx, $event)" | ||||
|           @click.shift="shiftClick(idx, $event)" | ||||
|           class="d-flex justify-content-between align-items-center list-group-item-action pointer" | ||||
|           :class="{active: lastClickIndex === idx}" | ||||
|       > | ||||
|         <div class="d-flex"> | ||||
|           <b-checkbox @change="toggleIndex(idx)" :checked="isSelected(idx)"></b-checkbox> | ||||
|           {{ idx.name }} | ||||
| @ -36,6 +53,7 @@ export default Vue.extend({ | ||||
|   data() { | ||||
|     return { | ||||
|       loading: true, | ||||
|       lastClickIndex: null | ||||
|     } | ||||
|   }, | ||||
|   computed: { | ||||
| @ -53,13 +71,50 @@ export default Vue.extend({ | ||||
|     ...mapActions({ | ||||
|       setSelectedIndices: "setSelectedIndices" | ||||
|     }), | ||||
|     shiftClick(index, e) { | ||||
|       if (this.lastClickIndex === null) { | ||||
|         return; | ||||
|       } | ||||
| 
 | ||||
|       const select = this.isSelected(this.lastClickIndex); | ||||
| 
 | ||||
|       let leftBoundary = this.indices.indexOf(this.lastClickIndex); | ||||
|       let rightBoundary = this.indices.indexOf(index); | ||||
| 
 | ||||
|       if (rightBoundary < leftBoundary) { | ||||
|         let tmp = leftBoundary; | ||||
|         leftBoundary = rightBoundary; | ||||
|         rightBoundary = tmp; | ||||
|       } | ||||
| 
 | ||||
|       for (let i = leftBoundary; i <= rightBoundary; i++) { | ||||
|         if (select) { | ||||
|           if (!this.isSelected(this.indices[i])) { | ||||
|             this.setSelectedIndices([this.indices[i], ...this.selectedIndices]); | ||||
|           } | ||||
|         } else { | ||||
|           this.setSelectedIndices(this.selectedIndices.filter(idx => idx !== this.indices[i])); | ||||
|         } | ||||
|       } | ||||
|     }, | ||||
|     selectAll() { | ||||
|       this.setSelectedIndices(this.indices); | ||||
|     }, | ||||
|     selectNone() { | ||||
|       this.setSelectedIndices([]); | ||||
|     }, | ||||
|     onSelect(value) { | ||||
|       this.setSelectedIndices(this.indices.filter(idx => value.includes(idx.id))); | ||||
|     }, | ||||
|     formatIdxDate(timestamp: number): string { | ||||
|       return format(new Date(timestamp * 1000), "yyyy-MM-dd"); | ||||
|     }, | ||||
|     toggleIndex(index) { | ||||
|     toggleIndex(index, e) { | ||||
|       if (e.shiftKey) { | ||||
|         return; | ||||
|       } | ||||
| 
 | ||||
|       this.lastClickIndex = index; | ||||
|       if (this.isSelected(index)) { | ||||
|         this.setSelectedIndices(this.selectedIndices.filter(idx => idx.id != index.id)); | ||||
|       } else { | ||||
| @ -92,4 +147,21 @@ export default Vue.extend({ | ||||
|   overflow-y: auto; | ||||
|   max-height: 132px; | ||||
| } | ||||
| 
 | ||||
| .btn-link:focus { | ||||
|   box-shadow: none; | ||||
| } | ||||
| 
 | ||||
| .unselectable { | ||||
|   user-select: none; | ||||
|   -ms-user-select: none; | ||||
|   -moz-user-select: none; | ||||
|   -webkit-user-select: none; | ||||
| } | ||||
| 
 | ||||
| .list-group-item.active { | ||||
|   z-index: 2; | ||||
|   background-color: inherit; | ||||
|   color: inherit; | ||||
| } | ||||
| </style> | ||||
| @ -23,7 +23,7 @@ | ||||
| <script lang="ts"> | ||||
| import {EsResult} from "@/Sist2Api"; | ||||
| import Vue from "vue"; | ||||
| import {humanFileSize, humanTime} from "@/util"; | ||||
| import {humanFileSize} from "@/util"; | ||||
| import DisplayModeToggle from "@/components/DisplayModeToggle.vue"; | ||||
| import SortSelect from "@/components/SortSelect.vue"; | ||||
| 
 | ||||
|  | ||||
| @ -131,7 +131,6 @@ export default { | ||||
|         saveTagModalTitle: "Add tag", | ||||
|         saveTagPlaceholder: "Tag name", | ||||
|         confirm: "Confirm", | ||||
|         indexPickerPlaceholder: "Select indices", | ||||
|         sort: { | ||||
|             relevance: "Relevance", | ||||
|             dateAsc: "Date (Older first)", | ||||
| @ -145,7 +144,13 @@ export default { | ||||
|             mimeSize: "Size distribution by media type", | ||||
|             dateHistogram: "File modification time distribution", | ||||
|             sizeHistogram: "File size distribution", | ||||
|         } | ||||
|         }, | ||||
|         indexPicker: { | ||||
|             selectNone: "Select None", | ||||
|             selectAll: "Select All", | ||||
|             selectedIndex: "selected index", | ||||
|             selectedIndices: "selected indices", | ||||
|         }, | ||||
|     }, | ||||
|     fr: { | ||||
|         searchBar: { | ||||
|  | ||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user