Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/asp.net-core/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Asp.net core 在用户内容中定位Blazor组件_Asp.net Core_Blazor_Blazor Server Side_Asp.net Blazor - Fatal编程技术网

Asp.net core 在用户内容中定位Blazor组件

Asp.net core 在用户内容中定位Blazor组件,asp.net-core,blazor,blazor-server-side,asp.net-blazor,Asp.net Core,Blazor,Blazor Server Side,Asp.net Blazor,我需要在用户提供的内容中动态放置Blazor组件。本质上,该组件应该使用一些UI元素扩展用户提供的标记 假设用户提供了一些内容,其中可以包含一个“问候容器”元素,组件应该在该元素中插入一个问候按钮 我目前的解决方案是调用一个JavaScript函数,在AfterRenderAsync中移动中的DOM元素(下面是完整的代码)。它似乎工作得很好,但在Blazor中,操作DOM元素似乎是不受鼓励的,因为它会影响扩散算法。我有几个问题要问: 像这样移动DOM元素有多糟糕?它是否会导致性能问题、功能问题或

我需要在用户提供的内容中动态放置Blazor组件。本质上,该组件应该使用一些UI元素扩展用户提供的标记

假设用户提供了一些内容,其中可以包含一个“问候容器”元素,组件应该在该元素中插入一个问候按钮

我目前的解决方案是调用一个JavaScript函数,在AfterRenderAsync中移动
中的DOM元素(下面是完整的代码)。它似乎工作得很好,但在Blazor中,操作DOM元素似乎是不受鼓励的,因为它会影响扩散算法。我有几个问题要问:

  • 像这样移动DOM元素有多糟糕?它是否会导致性能问题、功能问题或某些未定义的行为
  • 有没有更好的方法可以在不使用JavaScript的情况下实现相同的结果?我曾考虑使用
    RenderTreeBuilder
    来实现这一点,但它似乎不是为此目的而设计的,因为建议使用硬编码序列号,这在处理编译时未知的动态内容时似乎是不可能的
  • 当前解决方案代码:

    迎宾剃刀

    @page”/greeter
    @注入IJSRuntime JSRuntime;
    @((MarkupString)UserContentMarkup)
    切换问候语
    @如果(是否可见问候语){
    你好,@Name

    } @代码{ [参数] 公共字符串UserContentMarkup{get;set;} [参数] 公共字符串名称{get;set;} 私人布尔正在欢迎可见; 私有void ToggleGreeting() { isGreetingVisible=!isGreetingVisible; } AfterRenderAsync(bool firstRender)上受保护的重写异步任务 { 等待JSRuntime.InvokeVoidAsync(“moveGreetingToContainer”); } }
    _Host.cshtml

    window.moveGreetingToContainer=()=>{
    var greeting=document.getElementById(“greeting”);
    var container=document.getElementById(“问候容器”);
    容器.儿童(问候语);
    }
    
    UserContentTest.razor

    @page”/userContentTest
    @注入IJSRuntime JSRuntime;
    测试用户内容
    @代码{
    私有字符串userContentMarkup=“一些HTML文本,后跟问候语和更多文本”;
    }
    
    预期结果(单击“切换问候语”后):

    
    一些HTML文本,后跟问候语
    切换问候语
    你好,约翰

    还有更多的文字
    好问题-是的,使用JS移动dom元素非常糟糕,因为Blazor看不到您对dom所做的更改

    您可以做的是切换到使用
    RenderFragment
    ,更具体地说是
    RenderFragment
    ,这是一种将提供更多标记作为参数的标记

    在第二行,我调用UserContentMarkup方法(这是一个
    RenderFragment
    )并将
    内容作为
    上下文
    参数传递

    注意:它被包装在一个
    元素中,这实际上是一种将HTML嵌入C#中的方式。它不会向页面呈现
    元素

    迎宾剃刀
    
    @用户内容标记(
    @
    切换问候语
    @如果(是否可见问候语){
    你好,@Name

    } )
    @code{
    [参数]
    公共RenderFragment UserContentMarkup{get;set;}
    [参数]
    公共字符串名称{get;set;}
    私人布尔正在欢迎可见;
    私有void ToggleGreeting()
    {
    isGreetingVisible=!isGreetingVisible;
    }
    }
    
    UserContentTest.razor 在这里,您可以看到两种使用问候者的方法—在页面中使用标记,或者使用
    code
    方法

    测试用户内容
    @*使用标记来提供用户内容-@上下文是按钮所在的位置*@
    一些HTML文本,后跟问候语
    @上下文和更多文本
    @*使用一种方法来提供用户内容-@上下文就是按钮所在的位置*@
    
    code
    方法可能会令人困惑-它是一个
    RenderFragment
    ,这意味着它必须是一个接受
    RenderFragment
    作为其唯一参数的方法,并返回一个
    RenderFragment
    ——在本例中返回的
    RenderFragment
    是用
    包装的标记,以明确它是标记

    @code
    {
    RenderFragment用户内容
    =>context=>@Some-stuff@context-more-stuff;
    }
    

    请在此处试用:

    谢谢!这看起来几乎正是我需要的。唯一的附加问题是,这个字符串“Some stuff@context more stuff”能否像从数据库加载一样动态提供?因为它是我们事先不知道的用户内容是的,但是您需要一个上下文占位符,并在运行时替换它。有这样做的例子吗?从文档中我可以发现,似乎所有的标记都必须在编译时提供,这样“Blazor编译器”就可以将其翻译成html。但是,如果有任何方法可以动态地获取它,那就真的很难了。我猜你的意思是在呈现组件后,为上下文设置一个占位符,并通过JavaScript替换它?没有JS就不行。但是,只为pre和post设置两个渲染片段可能更容易