chore(client): tweak ui
This commit is contained in:
		
							parent
							
								
									ec41aefeea
								
							
						
					
					
						commit
						9c6a220810
					
				
					 4 changed files with 46 additions and 28 deletions
				
			
		|  | @ -6,7 +6,7 @@ | |||
| 			<div class="track"> | ||||
| 				<div class="highlight" :style="{ width: (steppedRawValue * 100) + '%' }"></div> | ||||
| 			</div> | ||||
| 			<div v-if="steps" class="ticks"> | ||||
| 			<div v-if="steps && showTicks" class="ticks"> | ||||
| 				<div v-for="i in (steps + 1)" class="tick" :style="{ left: (((i - 1) / steps) * 100) + '%' }"></div> | ||||
| 			</div> | ||||
| 			<div ref="thumbEl" v-tooltip="textConverter(finalValue)" class="thumb" :style="{ left: thumbPosition + 'px' }" @mousedown="onMousedown" @touchstart="onMousedown"></div> | ||||
|  | @ -27,6 +27,7 @@ const props = withDefaults(defineProps<{ | |||
| 	max: number; | ||||
| 	step?: number; | ||||
| 	textConverter?: (value: number) => string, | ||||
| 	showTicks?: boolean; | ||||
| }>(), { | ||||
| 	step: 1, | ||||
| 	textConverter: (v) => v.toString(), | ||||
|  |  | |||
|  | @ -1,5 +1,5 @@ | |||
| <script lang="ts"> | ||||
| import { h, onMounted, onUnmounted, ref } from 'vue'; | ||||
| import { h, onMounted, onUnmounted, ref, watch } from 'vue'; | ||||
| 
 | ||||
| export default { | ||||
| 	name: 'MarqueeText', | ||||
|  | @ -32,6 +32,8 @@ export default { | |||
| 			contentEl.value.style.animationDuration = `${duration}s`; | ||||
| 		} | ||||
| 
 | ||||
| 		watch(() => props.duration, calc); | ||||
| 
 | ||||
| 		onMounted(() => { | ||||
| 			calc(); | ||||
| 		}); | ||||
|  |  | |||
|  | @ -4,6 +4,8 @@ export function useInterval(fn: () => void, interval: number, options: { | |||
| 	immediate: boolean; | ||||
| 	afterMounted: boolean; | ||||
| }): void { | ||||
| 	if (Number.isNaN(interval)) return; | ||||
| 
 | ||||
| 	let intervalId: number | null = null; | ||||
| 
 | ||||
| 	if (options.afterMounted) { | ||||
|  |  | |||
|  | @ -6,11 +6,13 @@ | |||
| 	<div class="ekmkgxbk"> | ||||
| 		<MkLoading v-if="fetching"/> | ||||
| 		<div v-else class="feed"> | ||||
| 			<MarqueeText :key="key" :duration="widgetProps.speed" :reverse="widgetProps.reverse"> | ||||
| 				<span v-for="item in items" class="item"> | ||||
| 					<a class="link" :href="item.link" rel="nofollow noopener" target="_blank" :title="item.title">{{ item.title }}</a><span class="divider"></span> | ||||
| 				</span> | ||||
| 			</MarqueeText> | ||||
| 			<transition name="change" mode="default"> | ||||
| 				<MarqueeText :key="key" :duration="widgetProps.duration" :reverse="widgetProps.reverse"> | ||||
| 					<span v-for="item in items" class="item"> | ||||
| 						<a class="link" :href="item.link" rel="nofollow noopener" target="_blank" :title="item.title">{{ item.title }}</a><span class="divider"></span> | ||||
| 					</span> | ||||
| 				</MarqueeText> | ||||
| 			</transition> | ||||
| 		</div> | ||||
| 	</div> | ||||
| </MkContainer> | ||||
|  | @ -32,6 +34,21 @@ const widgetPropsDef = { | |||
| 		type: 'string' as const, | ||||
| 		default: 'http://feeds.afpbb.com/rss/afpbb/afpbbnews', | ||||
| 	}, | ||||
| 	refreshIntervalSec: { | ||||
| 		type: 'number' as const, | ||||
| 		default: 60, | ||||
| 	}, | ||||
| 	duration: { | ||||
| 		type: 'range' as const, | ||||
| 		default: 70, | ||||
| 		step: 1, | ||||
| 		min: 5, | ||||
| 		max: 200, | ||||
| 	}, | ||||
| 	reverse: { | ||||
| 		type: 'boolean' as const, | ||||
| 		default: false, | ||||
| 	}, | ||||
| 	showHeader: { | ||||
| 		type: 'boolean' as const, | ||||
| 		default: false, | ||||
|  | @ -40,25 +57,6 @@ const widgetPropsDef = { | |||
| 		type: 'boolean' as const, | ||||
| 		default: false, | ||||
| 	}, | ||||
| 	speed: { | ||||
| 		type: 'radio' as const, | ||||
| 		default: 70, | ||||
| 		options: [{ | ||||
| 			value: 170, label: 'very slow', | ||||
| 		}, { | ||||
| 			value: 100, label: 'slow', | ||||
| 		}, { | ||||
| 			value: 70, label: 'medium', | ||||
| 		}, { | ||||
| 			value: 40, label: 'fast', | ||||
| 		}, { | ||||
| 			value: 20, label: 'very fast', | ||||
| 		}], | ||||
| 	}, | ||||
| 	reverse: { | ||||
| 		type: 'boolean' as const, | ||||
| 		default: false, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| type WidgetProps = GetFormResultType<typeof widgetPropsDef>; | ||||
|  | @ -91,7 +89,7 @@ const tick = () => { | |||
| 
 | ||||
| watch(() => widgetProps.url, tick); | ||||
| 
 | ||||
| useInterval(tick, 60000, { | ||||
| useInterval(tick, Math.max(10000, widgetProps.refreshIntervalSec * 1000), { | ||||
| 	immediate: true, | ||||
| 	afterMounted: true, | ||||
| }); | ||||
|  | @ -104,17 +102,32 @@ defineExpose<WidgetComponentExpose>({ | |||
| </script> | ||||
| 
 | ||||
| <style lang="scss" scoped> | ||||
| .change-enter-active, .change-leave-active { | ||||
| 	position: absolute; | ||||
| 	top: 0; | ||||
|   transition: all 1s ease; | ||||
| } | ||||
| .change-enter-from { | ||||
|   opacity: 0; | ||||
| 	transform: translateY(-100%); | ||||
| } | ||||
| .change-leave-to { | ||||
|   opacity: 0; | ||||
| 	transform: translateY(100%); | ||||
| } | ||||
| 
 | ||||
| .ekmkgxbk { | ||||
| 	> .feed { | ||||
| 		padding: 0; | ||||
| 		font-size: 0.9em; | ||||
| 		line-height: 42px; | ||||
| 		height: 42px; | ||||
| 
 | ||||
| 		::v-deep(.item) { | ||||
| 			display: inline-flex; | ||||
| 			align-items: center; | ||||
| 			vertical-align: bottom; | ||||
| 			color: var(--fg); | ||||
| 			margin: 12px 0; | ||||
| 
 | ||||
| 			> .divider { | ||||
| 				display: inline-block; | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue