$lib/circle/Circle.svelte
<script lang="ts">
import { onMount, setContext } from 'svelte';
import { spring } from 'svelte/motion';
import Dot from './Dot.svelte';
let num = 10;
let angle = (2 * Math.PI) / num;
let multiplier = spring(100, {
stiffness: 0.1,
damping: 0.63
});
setContext('multiplier', multiplier);
let scroll = 0;
let parentDiv: HTMLDivElement;
onMount(() => {
window.addEventListener('wheel', (event) => {
const delta = Math.sign(event.deltaY);
// console.info(event.deltaY, delta);
scroll += event.deltaY;
// $multiplier = 1 + Math.abs(event.deltaY) / 200;
});
$multiplier = 1;
});
</script>
<div bind:this={parentDiv} class="relative w-[350px] h-[350px]">
{#each Array(num) as item, i}
<Dot parent={parentDiv} index={i} {num} angle={angle * i + scroll * 0.003} />
{/each}
</div>
<style>
</style>
$lib/circle/Dot.svelte
<script lang="ts">
import { getContext, onMount } from 'svelte';
import { spring } from 'svelte/motion';
import { fade } from 'svelte/transition';
// dot
export let parent: HTMLDivElement;
export let index = 0;
export let angle: any = 0;
export let num = 10;
let x = 0;
let y = 0;
let multiplier: any = getContext('multiplier');
$: boxSize = parent?.offsetWidth / 7;
$: scale = parent?.offsetWidth / 2 - boxSize / 2;
// $: console.log('parent', parent, parent?.offsetWidth);
$: x = Math.cos(angle) * scale;
$: y = Math.sin(angle) * scale;
$: top = $multiplier * y + parent?.offsetWidth / 2 - boxSize / 2;
$: left = $multiplier * x + parent?.offsetHeight / 2 - boxSize / 2;
let url = '';
onMount(() => {
url = 'https://picsum.photos/seed/' + index + '/200/300';
});
function simulateClick() {
$multiplier = 6;
setTimeout(() => {
$multiplier = 1;
}, 1500);
}
</script>
{#if parent}
<a
href="#"
on:click={simulateClick}
transition:fade|local
class="dot"
style="left: {left}px; top: {top}px; width:{boxSize}px; height:{boxSize}px;"
>
<img class="w-full h-full object-cover object-center" src={url} alt="" />
</a>
{/if}
<style lang="postcss">
:global(.dot) {
height: 20px;
width: 20px;
/* border-radius: 50%; */
@apply bg-neutral-400;
position: absolute;
text-align: center;
}
</style>