Javascript 我应该在哪里包含视图组件的脚本?

Javascript 我应该在哪里包含视图组件的脚本?,javascript,asp.net-core,razor,asp.net-core-viewcomponent,Javascript,Asp.net Core,Razor,Asp.net Core Viewcomponent,我尝试在视图组件的视图中添加一个节脚本 @section scripts { <script src="~/somepath" asp-append-version="true"></script> } 在局部视图和项目中的其他位置使用时,脚本可以很好地加载。但是,在视图组件中,脚本不会加载 我想我可以在调用组件的每个视图的section标记中包含脚本。我觉得这不符合视图组件的自包含特性 还有别的办法吗 据我所见,ViewComponent中的“@section

我尝试在视图组件的视图中添加一个节脚本

@section scripts {
    <script src="~/somepath" asp-append-version="true"></script>
}
在局部视图和项目中的其他位置使用时,脚本可以很好地加载。但是,在视图组件中,脚本不会加载

我想我可以在调用组件的每个视图的section标记中包含脚本。我觉得这不符合视图组件的自包含特性


还有别的办法吗

据我所见,ViewComponent中的
“@section Scripts{}”
被忽略,并且不会在
ViewComponents\u*layout.cshtml的相关
@RenderSection()
中呈现


为什么我不知道

我在viewcomponents中的sections标记也有问题。事实证明,据我所知,viewcomponents中不支持它。看

Jake Shakesworth实现了一个标记助手,如所示:

另一方面,您可以将其作为一个组件包含在viewcomponent中

<script defer src"...">
  </script>

我的要求是从viewcomponent显示google地图。问题是在调用jquery、jquery.ui之前调用了脚本。
通过使用defer,您告诉解析器在文档加载之前不要执行它,从而避免了必须将其放入布局中才能正确执行的问题。 延迟由chrome、safari和ie(10+、ff(3.6+)、o(15+)支持

希望这有帮助

这是我的代码示例:

@using MobileVet.WebApp.Services;
@inject ISettingsService SettingsService
@{
     var Options = SettingsService.Value();

    <!--Service Area-->
    <div class="container-fluid">
         <div class="row p-3">
            <!--First column-->
            <div class="col-md-3">
                <h5 class="title">Site Navigation</h5>
                <ul>
                    <li><a href="#!">Home</a></li>
                    <li><a href="#!">Services</a></li>
                    <li><a href="#!">Link 3</a></li>
                    <li><a href="#!">Link 4</a></li>
                </ul> 

            </div>
            <!--/.First column-->
            <hr class="w-100 clearfix d-md-none">

            <!--Second column-->
            <div class="col-md-9">

                <div id="map-canvas" style="min-height: 300px; min-width: 200px;"> 
                </div>
            </div>
            <!--/.Second column-->

        </div>
    </div>
    <!--Service Area-->


<script src="http://maps.google.com/maps/api/js?key=XXXXXXXXXXXXXXXXXXXXXXX&sensor=false"></script>
<script type="text/javascript" src="~/js/components/servicearea.js" defer ></script>

}
@使用MobileVet.WebApp.Services;
@注入ISettingsService设置服务
@{
var Options=设置服务值();
站点导航

}

请注意,如果视图组件在一个页面上出现多次,您可能需要编写一些逻辑来防止脚本被多次包含,这不是我的情况

这是我如何使用Asp.net core 2.0将脚本插入视图组件的方法

首先,我创建了一个局部视图,并将其放置在view components view文件夹中

路径:Views/Shared/Components/CalendarWidget/_calendarscriptsparial.cshtml

\u CalendarScriptSpatial.cshtml

<environment include="Development">
    <script src="~/lib/jquery/dist/jquery.js"></script>
    <script src="~/lib/moment/moment.js"></script>
    <script src="~/lib/fullcalendar/dist/fullcalendar.js"></script>
    <script src="~/js/calendarWidget.js"></script>
</environment>
<environment exclude="Development">
    <script src="~/lib/jquery/dist/jquery.min.js"></script>
    <script src="~/lib/moment/min/moment.min.js"></script>
    <script src="~/lib/fullcalendar/dist/fullcalendar.min.js"></script>
    <script src="~/js/calendarWidget.js"></script>
</environment>
<section id="calendar"></section>
@await Html.PartialAsync( "Components/CalendarWidget/_CalendarScriptsPartial" )

然后,我通过视图组件视图中的Html部分异步助手方法引入了脚本

路径:Views/Shared/Components/CalendarWidget/Default.cshtml

Default.cshtml

<environment include="Development">
    <script src="~/lib/jquery/dist/jquery.js"></script>
    <script src="~/lib/moment/moment.js"></script>
    <script src="~/lib/fullcalendar/dist/fullcalendar.js"></script>
    <script src="~/js/calendarWidget.js"></script>
</environment>
<environment exclude="Development">
    <script src="~/lib/jquery/dist/jquery.min.js"></script>
    <script src="~/lib/moment/min/moment.min.js"></script>
    <script src="~/lib/fullcalendar/dist/fullcalendar.min.js"></script>
    <script src="~/js/calendarWidget.js"></script>
</environment>
<section id="calendar"></section>
@await Html.PartialAsync( "Components/CalendarWidget/_CalendarScriptsPartial" )

@等待Html.PartialAsync(“组件/CalendarWidget/_CalendarScriptSpatial”)
为了完整起见,这里是我的视图组件类

路径:ViewComponents/CalendarWidgetViewComponent.cs

CalendarWidgetViewComponent.cs

using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;

namespace LodgersChoice.ViewComponents
{
    public class CalendarWidgetViewComponent : ViewComponent
    {
        public async Task<IViewComponentResult> InvokeAsync( )
        {
            return View( );
        }
    }
}
使用System.Threading.Tasks;
使用Microsoft.AspNetCore.Mvc;
命名空间LodgersChoice.ViewComponents
{
公共类CalendarWidgetViewComponent:ViewComponent
{
公共异步任务InvokeAsync()
{
返回视图();
}
}
}
注意:在我的示例中,目前不需要异步,但我打算将一个存储库注入到将使用Async/await的类的ctor中


注2:开发完成后,我计划将所有内容捆绑并缩小到一个脚本中。

ASP.NET核心中的视图组件就像带有独立控制器的独立视图,因此您可以在视图组件上方插入下面的标记

@{
Layout = null;
}
在此之后,插入下面的标记以使用相关脚本,例如:

<environment include="Development">

<script src="~/js/chart.js"></script>

</environment>
 <environment exclude="Development">

<script src="~/js/chart.min.js"></script>

</environment>

@Asp.Net渲染引擎将忽略viewcomponents中的节脚本{},并且不会渲染该脚本。因此,只需在视图组件的末尾使用。此外,如果在布局的末尾指定了jquery脚本,那么jquery将无法在viewcomponents中使用。当然,将jquery脚本移动到layout中的head部分可以解决问题,但建议在最后加载js文件

因此,如果您希望在布局的末尾保留jquery脚本,并且仍然在viewcomponents中使用jquery,那么可以使用javascript domcontentloaded,并且任何jquery都可以在domcontentloaded中编写。这不是一个永久的好方法,但对我来说很有效

<script>
    document.addEventListener('DOMContentLoaded', function (event) {
        console.log($ === jQuery)
    });
</script>

document.addEventListener('DOMContentLoaded',函数(事件){
console.log($==jQuery)
});
或者,正如@Alberto L.Bonfiglio所提到的,您也可以尝试将脚本移动到另一个JS文件中,并延迟将其加载到您的viewcomponent中:

<script src="viewComponentScript.js" defer></script>


我的用例要求我在一个页面中拥有多个视图组件。以您的回答为例,这是否需要确保为
地图
服务区
脚本中的每一个脚本添加一个?您可以在一个视图中拥有所需的任意多个viewcomponent或同一viewcomponent的实例。如果您的视图组件有脚本,那么您应该编写一些逻辑,检查脚本是否已经包含在页面中,如果已经包含,则跳过添加脚本。我没有这个需要,所以我没有经常使用它,但一个快速修复可能是有一个空的viewcomponent,其中只包含脚本,并且在实际viewcomponent的所有需要的实例都完成后添加。实际上,我只是尝试过删除脚本并将它们放置在单独的viewcomponent中。需要注意的是,现在您的脚本必须足够智能,以正确识别它们应该与之交互的对象,并且您的viewcomponent应该为dom对象提供唯一的ID(例如map-canvas-001、map-canvas-002)。初始化功能可以