javascript sveltekit在旧页面上添加新页面

ibps3vxo  于 2023-03-28  发布在  Java
关注(0)|答案(3)|浏览(155)

我刚刚在我的sveltekit应用程序中遇到了一个意想不到的错误,我在网上找不到任何关于它的信息
我有一个普通的sveltekit应用程序,但是当导航到一个新页面时,它并没有添加新代码,而是将新代码添加到旧代码之上,当我刷新页面时,它会删除旧代码(从上一页)
编辑:经过一点探索,我意识到它只发生在一个页面上,我的代码的哪一部分可以实现这一点?

qf9go6mv

qf9go6mv1#

我在SvelteKit上有一个页面加载指示器用于内部导航时遇到了同样的问题。任何页面DOM修改,在页面导航期间显示加载指示器,都会导致页面出现两次错误。解决方法是在导航期间不修改页面,只使用CSS来显示,动画和隐藏加载指示器。
Here is my loading indicator codeHere is my documentation regarding the issue。我不确定这是否是SvelteKit的内部错误,所以我没有提交任何错误报告,因为我没有一个干净的可重复的例子。

<script>
    /**
     * Svelte does not give a load indication if you hit a link that leads to a page with slow load() function.
     * Svelte uses internal router, not server-side loading.
     * Thus, we need to manually give some indication in the user interface if the loading takes more than a blink of an eye.
     *
     * The component is originally made for https://tradingstrategy.ai
     *
     * Based on the original implementation https://github.com/shajidhasan/sveltekit-page-progress-demo by Shajid Hasan.
     *
     * As this component is absolutely position, you can put it at any part of your __layout.svelte.
     */
    import { onDestroy, onMount } from 'svelte';
    import { writable } from 'svelte/store';
    import { tweened } from 'svelte/motion';
    import { cubicOut } from 'svelte/easing';

    const navigationState = writable();

    const progress = tweened(0, {
        duration: 3500,
        easing: cubicOut
    });

    const unsubscribe = navigationState.subscribe((state) => {

        // You will always get state=undefined
        // event on the server-side rendering, so
        // safely ignore it
        //console.log("The loading state is", state);

        if (state === 'loading-with-progress-bar') {
            progress.set(0, { duration: 0 });
            progress.set(0.8, { duration: 5000 });
        } else if (state === 'loaded') {
            progress.set(1, { duration: 1000 });
        }
    });

    onMount(() => {
        // progress.set(0.7);
    });
    onDestroy(() => {
        unsubscribe();
    });
</script>

<!-- See the (little) documentation of special SvelteKit events here https://kit.svelte.dev/docs#events -->
<svelte:window
    on:sveltekit:navigation-start={() => {

        // If the page loads fast enough in the preloading state,
        // never display the progress bar
        $navigationState = 'preloading';

        // Delay the progress bar to become visible an eyeblink... only show if the page load takes too long
        setTimeout(function() {
            // After 250ms switch preloading to loading-with-progress-bar
            if($navigationState === 'preloading') {
                $navigationState = 'loading-with-progress-bar';
            }
        }, 500);
    }}
    on:sveltekit:navigation-end={() => {
        $navigationState = 'loaded';
    }}
/>

<!--
    Make sure the container component is always in the DOM structure.

    If we make changes to the page structure during the navigation, we get a page double render error:
    https://stackoverflow.com/questions/70051025/sveltekit-adds-new-page-on-top-of-old-one

    Not sure if this is a bug or a feature.
    Thus, make sure any progress animation is done using CSS only.
-->
<div class="page-progress-bar" class:loaded={$navigationState === 'loaded'} class:preloading={$navigationState === 'preloading'} class:loading={$navigationState === 'loading-with-progress-bar'}>
    <div class="progress-sliver" style={`--width: ${$progress * 100}%`} />
</div>

<style>
     /* Always stay fixed at the top, but stay transparent if no activity is going on */
    .page-progress-bar {
        position: fixed;
        top: 0;
        left: 0;
        right: 0;
        height: 0.5rem;
        background: transparent;
        z-index: 100;
        opacity: 0;
        transition: opacity 0.5s;
    }

     /* After transitioning from preloading to loading state, make the progress bar visible with CSS transition on opacity */
    .page-progress-bar.loading {
        opacity: 1;
        transition: opacity 0.5s;
    }

    .progress-sliver {
        width: var(--width);
        background-color: var(--price-up-green);
        height: 100%;
    }
</style>
c3frrgcw

c3frrgcw2#

我也看到了这个问题与过渡指令。新的页面加载时,退出动画正在播放。我使用本地过渡来解决这个问题。
https://svelte.dev/tutorial/local-transitions

hrirmatl

hrirmatl3#

我在尝试实现一个auth组件时也遇到了同样的问题。我想出了一个解决方案,那就是在组件中添加out:fade={{duration:0}}。我发现这种情况主要发生在具有许多{#if}块的页面上,但情况并非总是如此。下面是我如何实现修复的示例。请注意,我使用的是Fireabse,因此您可能必须适应此情况。
Auth.svelte

<script lang="ts">
        import { onAuthStateChanged, getAuth } from "firebase/auth";
        import { fade } from "svelte/transition";
        import { getApp } from "$lib/firebase";
        import { onMount } from "svelte";
        import { goto } from "svelte/navigation";

        const auth = getAuth(getApp());
        let isLoggedIn = false;
        let isLoading = true;
    
        onMount(()=>{
            isLoading = false;
            return onAuthStateChanged(auth, (user)=>{
                isLoggedIn = !!user;
                // or whatever your login page is
                if (!isLoggedIn) goto("/login")
            });
        });
    </script>
    {#if isLoggedIn && !isLoading}
       <div out:fade={{duration:0}}>
            <slot></slot>
        </div>
    {:else if isLoading && !isLoggedIn}
        <div></div>
    {/if}

相关问题