FWIW、既存の Web フォーム コードから部分ビューを動的にレンダリングし、それを特定のコントロールの上部に挿入できるようにする必要がありました。キースの回答により、部分ビューが<html />
タグの外側にレンダリングされる可能性があることがわかりました。
HttpContext.Current.Response.Output に直接レンダリングするのではなく、Keith と Hilarius からの回答をインスピレーションとして使用して、html 文字列をレンダリングし、関連するコントロールに LiteralControl として追加しました。
静的ヘルパー クラス:
public static string RenderPartial(string partialName, object model)
{
//get a wrapper for the legacy WebForm context
var httpCtx = new HttpContextWrapper(HttpContext.Current);
//create a mock route that points to the empty controller
var rt = new RouteData();
rt.Values.Add("controller", "WebFormController");
//create a controller context for the route and http context
var ctx = new ControllerContext(new RequestContext(httpCtx, rt), new WebFormController());
//find the partial view using the viewengine
var view = ViewEngines.Engines.FindPartialView(ctx, partialName).View;
//create a view context and assign the model
var vctx = new ViewContext(ctx, view, new ViewDataDictionary { Model = model }, new TempDataDictionary(), new StringWriter());
// This will render the partial view direct to the output, but be careful as it may end up outside of the <html /> tag
//view.Render(vctx, HttpContext.Current.Response.Output);
// Better to render like this and create a literal control to add to the parent
var html = new StringWriter();
view.Render(vctx, html);
return html.GetStringBuilder().ToString();
}
呼び出しクラスで:
internal void AddPartialViewToControl(HtmlGenericControl ctrl, int? insertAt = null, object model)
{
var lit = new LiteralControl { Text = MvcHelper.RenderPartial("~/Views/Shared/_MySharedView.cshtml", model};
if (insertAt == null)
{
ctrl.Controls.Add(lit);
return;
}
ctrl.Controls.AddAt(insertAt.Value, lit);
}