# client-side navigation
## preserving player state across navigation
the player lives in the root layout (`+layout.svelte`) and persists across all page navigations. to maintain uninterrupted playback, client-side navigation must work correctly.
## critical rule: never use `stopPropagation()` on links
**problem**: calling `e.stopPropagation()` on link click handlers breaks SvelteKit's client-side router, causing full page reloads that unmount and remount the player.
```svelte
e.stopPropagation()}>{tag}
```
```svelte
{tag}
```
## handling links inside clickable containers
when you have links nested inside a clickable button/div, check the event target instead of using `stopPropagation()`:
```svelte
```
this pattern:
1. lets the link trigger proper client-side navigation
2. only calls `doSomething()` when clicking non-link elements
3. preserves all global state including the player
## why this matters
SvelteKit's client-side router intercepts `` tag clicks to:
- avoid full page reload
- preserve global state (player, queue, auth)
- enable smooth transitions
when `stopPropagation()` is called, the click event never reaches SvelteKit's router, falling back to native browser navigation which:
- performs a full page reload
- unmounts and remounts all components
- resets audio playback
## examples from the codebase
### TrackItem.svelte
the track container is a button that plays the track on click. it contains multiple links (artist, album, tags) that should navigate without affecting playback:
```svelte
```
## debugging navigation issues
**symptom**: clicking a link stops music playback
**diagnosis**:
1. check if the link has `onclick={(e) => e.stopPropagation()}`
2. check parent elements for event handling that might interfere
3. verify the route uses SvelteKit conventions (`+page.svelte`, `+page.ts`)
**fix**: remove `stopPropagation()` and use event target checking in parent handlers instead