パート 3、ASP.NET Core MVC アプリへのビューの追加
Note
これは、この記事の最新バージョンではありません。 現在のリリースについては、この記事の .NET 9 バージョンを参照してください。
警告
このバージョンの ASP.NET Core はサポート対象から除外されました。 詳細については、「.NET および .NET Core サポート ポリシー」を参照してください。 現在のリリースについては、この記事の .NET 8 バージョンを参照してください。
重要
この情報はリリース前の製品に関する事項であり、正式版がリリースされるまでに大幅に変更される可能性があります。 Microsoft はここに示されている情報について、明示か黙示かを問わず、一切保証しません。
現在のリリースについては、この記事の .NET 9 バージョンを参照してください。
作成者: Rick Anderson
このセクションでは、Razor ビュー ファイルを使用するよう、HelloWorldController
クラスを変更します。 これにより、クライアントへの HTML 応答を生成するプロセスが完全にカプセル化されます。
ビュー テンプレートは Razor を使用して作成されます。 Razor ベースのビュー テンプレートは次のとおりです。
.cshtml
ファイル拡張子を含めます。- C# を使用して HTML 出力を作成する洗練された方法が提供されます。
現在、Index
メソッドは、コントローラー クラスにメッセージを含め文字列を返します。 HelloWorldController
クラスでは、Index
メソッドを次のコードで置き換えます。
public IActionResult Index()
{
return View();
}
上記のコードでは、次のことが行われます。
- コントローラーの View メソッドを呼び出します。
- ビュー テンプレートを使用し HTML 応答を生成します。
コントローラー メソッドは次のとおりです。
- "アクション メソッド" と呼ばれます。 たとえば、前のコードの
Index
アクション メソッドです。 - 通常、
string
のような型ではなく IActionResult または ActionResult から派生したクラスを返します。
ビューを追加する
Views フォルダーを右クリックし、[追加] > [新しいフォルダー] の順に選択して、フォルダーに HelloWorld という名前を付けます。
Views/HelloWorld フォルダーを右クリックし、[追加] > [新しい項目] の順に選択します。
[新しい項目の追加] ダイアログで、[すべてのテンプレートの表示] を選びます。
[新しい項目の追加 - MvcMovie] ダイアログで次を行います。
- 右上の検索ボックスに「view」と入力します。
- [Razor ビュー - 空] を選択します。
- [名前] ボックスの値、
Index.cshtml
を維持します。 - [追加] を選択します。
Views/HelloWorld/Index.cshtml
Razor ビュー ファイルの内容を次に置き換えます。
@{
ViewData["Title"] = "Index";
}
<h2>Index</h2>
<p>Hello from our View Template!</p>
次のように https://localhost:{PORT}/HelloWorld
に移動します。
HelloWorldController
のIndex
メソッドにより、ビュー テンプレート ファイルを使用して、ブラウザーに応答をレンダリングするようメソッドを指定する、ステートメントreturn View();
が実行されました。ビュー テンプレートのファイル名が指定されていないため、MVC で既定のビュー ファイルが使われました。 ビュー ファイル名を指定しない場合は、既定のビューが返されます。 この例では、既定のビューの名前は、アクション メソッド
Index
と同じ名前が付けられています。 ビュー テンプレート/Views/HelloWorld/Index.cshtml
が使用されています。次の画像は、ビューにハードコーディングされた "Hello from our View Template!" という文字列を示しています。
ビューとレイアウト ページを変更する
MvcMovie、 Home 、 Privacy の各メニューのリンクを選択します。 各ページには同じメニューのレイアウトが表示されます。 メニューのレイアウトは、Views/Shared/_Layout.cshtml
ファイルに実装されています。
Views/Shared/_Layout.cshtml
ファイルを開きます。
レイアウト テンプレートでは、次のことが可能です。
- 1 か所でサイトの HTML コンテナー レイアウトを指定できます。
- サイト内の複数のページに HTML コンテナー レイアウトを適用できます。
@RenderBody()
という行を見つけます。 RenderBody
は、作成したビュー固有のページがすべて表示されるプレースホルダーで、レイアウト ページにラップされます。 たとえば、Privacy リンクを選択すると、Views/Home/Privacy.cshtml
ビューが RenderBody
メソッド内でレンダリングされます。
レイアウト ファイルでのタイトル、フッター、およびメニュー リンクの変更
Views/Shared/_Layout.cshtml
ファイルの内容を次のマークアップに置き換えます。 変更が強調表示されています。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>@ViewData["Title"] - Movie App</title>
<link rel="stylesheet" href="~/lib/bootstrap/dist/css/bootstrap.css" />
<link rel="stylesheet" href="~/css/site.css" asp-append-version="true" />
<link rel="stylesheet" href="~/MvcMovie.styles.css" asp-append-version="true" />
</head>
<body>
<header>
<nav class="navbar navbar-expand-sm navbar-toggleable-sm navbar-light bg-white border-bottom box-shadow mb-3">
<div class="container-fluid">
<a class="navbar-brand" asp-area="" asp-controller="Movies" asp-action="Index">Movie App</a>
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target=".navbar-collapse" aria-controls="navbarSupportedContent"
aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="navbar-collapse collapse d-sm-inline-flex justify-content-between">
<ul class="navbar-nav flex-grow-1">
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Index">Home</a>
</li>
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</li>
</ul>
</div>
</div>
</nav>
</header>
<div class="container">
<main role="main" class="pb-3">
@RenderBody()
</main>
</div>
<footer class="border-top footer text-muted">
<div class="container">
© 2024 - Movie App - <a asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</div>
</footer>
<script src="~/lib/jquery/dist/jquery.js"></script>
<script src="~/lib/bootstrap/dist/js/bootstrap.js"></script>
<script src="~/js/site.js" asp-append-version="true"></script>
@await RenderSectionAsync("Scripts", required: false)
</body>
</html>
上記のマークアップでは、次の変更が加えられています。
MvcMovie
からMovie App
が 3 回発生します。- アンカー要素
<a class="navbar-brand" asp-area="" asp-controller="Home" asp-action="Index">MvcMovie</a>
が<a class="navbar-brand" asp-controller="Movies" asp-action="Index">Movie App</a>
になりました。
上記のマークアップでは、このアプリでは Area が使用されていないため、asp-area=""
アンカー タグ ヘルパー属性と属性値が省略されています。
注: まだ Movies
コントローラーは実装されていません。 この時点では、Movie App
リンクは機能していません。
変更を保存し、 Privacy リンクを選択します。 ブラウザー タブのタイトルの表示が、Privacy Policy - MvcMovie ではなく、Privacy Policy - Movie App になっていることに注目してください。
[Home](ログの一元化) リンクを選択します。
タイトルとアンカー テキストに Movie App と表示されていることに着目してください。 レイアウト テンプレートが一度変更され、この新しいリンク テキストと新しいタイトルがサイト上のすべてのページに反映されました。
Views/_ViewStart.cshtml
ファイルを調べます。
@{
Layout = "_Layout";
}
Views/_ViewStart.cshtml
ファイルは Views/Shared/_Layout.cshtml
ファイルに取り込まれ、各ビューに適用されます。 Layout
プロパティを使用すれば、別のレイアウト ビューを設定することも、null
に設定してレイアウト ファイルが使用されないようにすることもできます。
Views/HelloWorld/Index.cshtml
ビュー ファイルを開きます。
タイトルと <h2>
要素を、以下の強調表示どおりに変更します。
@{
ViewData["Title"] = "Movie List";
}
<h2>My Movie List</h2>
<p>Hello from our View Template!</p>
タイトルと <h2>
要素は若干違うので、コードのどの部分によって表示が変更されるのかを確認できます。
上のコードの ViewData["Title"] = "Movie List";
では、Title
ディクショナリの ViewData
プロパティを "Movie List" に設定します。 Title
プロパティは、次のように、レイアウト ページの <title>
HTML 要素で使用されます。
<title>@ViewData["Title"] - Movie App</title>
変更内容を保存して、https://localhost:{PORT}/HelloWorld
に移動します。
次が変更されたことを確認します。
- ブラウザー タイトル。
- 1 番目の見出し。
- 2 番目の見出し。
ブラウザーに変更がない場合は、キャッシュされたコンテンツが表示されている場合があります。 ブラウザーで Ctrl + F5 キーを押して、サーバーからの応答が強制的に読み込まれるようにします。 ブラウザーのタイトルは、Index.cshtml
ビュー テンプレートで設定した ViewData["Title"]
で作成されます。レイアウト ファイルには "- Movie App" が追加されます。
Index.cshtml
ビュー テンプレート内のコンテンツは、Views/Shared/_Layout.cshtml
ビュー テンプレートにマージされます。 1 つの HTML 応答がブラウザーに送信されます。 レイアウト テンプレートを使用すれば、アプリのすべてのページに適用される変更を簡単に行うことができます。 詳細については、「Layout」(レイアウト) を参照してください。
ここでは、"データ" の一部 ("Hello from our View Template!" というメッセージ) がハードコーディングされています。 MVC アプリケーションには "V" (ビュー) があり、"C" (コントローラー) もありますが、"M" (モデル) はまだありません。
コントローラーからビューへのデータの受け渡し
コントローラー アクションは、受信 URL 要求への応答として呼び出されます。 コントローラー クラスでは、受信ブラウザー要求を処理するコードが記述されます。 コントローラーはデータ ソースからデータを取得し、ブラウザーに返す応答の種類を決定します。 ビュー テンプレートを使用すれば、コントローラーからブラウザーへの HTML 応答を生成して書式を設定できます。
コントローラーは、ビュー テンプレートで応答をレンダリングするために必要なデータを提供します。
ビュー テンプレートでは、次を行いません。
- ビジネス ロジックの実行
- データベースとの直接のやりとり
ビュー テンプレートは、コントローラーから提供されるデータのみを処理する必要があります。 この "関心の分離" を維持すれば、コードを次のように保つことができます。
- クリーン。
- テスト可能。
- 保守しやすい。
現時点では、HelloWorldController
クラスの Welcome
メソッドは name
と ID
パラメーターを受け取ってから、ブラウザーに直接値を出力します。
コントローラーにこの応答を文字列としてレンダリングさせるのではなく、代わりにビュー テンプレートを使用するようにコントローラーを変更します。 このビュー テンプレートは、応答を動的に生成します。つまり、応答の生成には、コントローラーからビューに適切なデータが渡される必要があります。 そのためには、ビュー テンプレートが必要とする動的データ (パラメーター) を、コントローラーに ViewData
ディレクトリに配置させます。 これにより、ビュー テンプレートが動的データにアクセスできるようになります。
HelloWorldController.cs
内で、Welcome
メソッドを変更して Message
および NumTimes
値を ViewData
ディクショナリに追加します。
ViewData
ディクショナリは、すべての型を使用できる動的なオブジェクトです。 ViewData
オブジェクトには、何かが追加されるまで、プロパティは定義されていません。 MVC のモデル バインド システムは、name
と numTimes
の名前付きパラメーターをクエリ文字列からメソッドのパラメーターに自動的にマップします。 完全な HelloWorldController
は次のとおりです。
using Microsoft.AspNetCore.Mvc;
using System.Text.Encodings.Web;
namespace MvcMovie.Controllers;
public class HelloWorldController : Controller
{
public IActionResult Index()
{
return View();
}
public IActionResult Welcome(string name, int numTimes = 1)
{
ViewData["Message"] = "Hello " + name;
ViewData["NumTimes"] = numTimes;
return View();
}
}
ViewData
ディクショナリ オブジェクトには、ビューに渡されるデータが含まれています。
Views/HelloWorld/Welcome.cshtml
という名前の [ようこそ] ビュー テンプレートを作成します。
"Hello" NumTimes
を表示する Welcome.cshtml
ビュー テンプレートにループを作成します。 Views/HelloWorld/Welcome.cshtml
の内容を次に置き換えます。
@{
ViewData["Title"] = "Welcome";
}
<h2>Welcome</h2>
<ul>
@for (int i = 0; i < (int)ViewData["NumTimes"]!; i++)
{
<li>@ViewData["Message"]</li>
}
</ul>
変更内容を保存し、次の URL を参照します。
https://localhost:{PORT}/HelloWorld/Welcome?name=Rick&numtimes=4
データは URL から取得され、MVC モデル バインダーを使用してコントローラーに渡されます。 コントローラーはデータを ViewData
ディクショナリにパッケージ化し、そのオブジェクトをビューに渡します。 その後、ビューでブラウザーに HTML としてデータがレンダリングされます。
上のサンプルでは、ViewData
ディクショナリを使用して、コントローラーからビューにデータを渡しました。 チュートリアルの後半では、ビュー モデルを使用して、コントローラーからビューにデータを渡します。 データを渡すには、ViewData
ディクショナリを使用する方法より、ビュー モデルを使用する方法が推奨されます。
次のチュートリアルでは、ムービーのデータベースを作成します。
このセクションでは、Razor ビュー ファイルを使用するよう、HelloWorldController
クラスを変更します。 これにより、クライアントへの HTML 応答を生成するプロセスが完全にカプセル化されます。
ビュー テンプレートは Razor を使用して作成されます。 Razor ベースのビュー テンプレートは次のとおりです。
.cshtml
ファイル拡張子を含めます。- C# を使用して HTML 出力を作成する洗練された方法が提供されます。
現在、Index
メソッドは、コントローラー クラスにメッセージを含め文字列を返します。 HelloWorldController
クラスでは、Index
メソッドを次のコードで置き換えます。
public IActionResult Index()
{
return View();
}
上記のコードでは、次のことが行われます。
- コントローラーの View メソッドを呼び出します。
- ビュー テンプレートを使用し HTML 応答を生成します。
コントローラー メソッドは次のとおりです。
- "アクション メソッド" と呼ばれます。 たとえば、前のコードの
Index
アクション メソッドです。 - 通常、
string
のような型ではなく IActionResult または ActionResult から派生したクラスを返します。
ビューを追加する
Views フォルダーを右クリックし、[追加] > [新しいフォルダー] の順に選択して、フォルダーに HelloWorld という名前を付けます。
Views/HelloWorld フォルダーを右クリックし、[追加] > [新しい項目] の順に選択します。
[新しい項目の追加] ダイアログで、[すべてのテンプレートの表示] を選びます。
[新しい項目の追加 - MvcMovie] ダイアログで次を行います。
- 右上の検索ボックスに「view」と入力します。
- [Razor ビュー - 空] を選択します。
- [名前] ボックスの値、
Index.cshtml
を維持します。 - [追加] を選択します。
Views/HelloWorld/Index.cshtml
Razor ビュー ファイルの内容を次に置き換えます。
@{
ViewData["Title"] = "Index";
}
<h2>Index</h2>
<p>Hello from our View Template!</p>
次のように https://localhost:{PORT}/HelloWorld
に移動します。
HelloWorldController
のIndex
メソッドにより、ビュー テンプレート ファイルを使用して、ブラウザーに応答をレンダリングするようメソッドを指定する、ステートメントreturn View();
が実行されました。ビュー テンプレートのファイル名が指定されていないため、MVC で既定のビュー ファイルが使われました。 ビュー ファイル名を指定しない場合は、既定のビューが返されます。 この例では、既定のビューの名前は、アクション メソッド
Index
と同じ名前が付けられています。 ビュー テンプレート/Views/HelloWorld/Index.cshtml
が使用されています。次の画像は、ビューにハードコーディングされた "Hello from our View Template!" という文字列を示しています。
ビューとレイアウト ページを変更する
MvcMovie、 Home 、 Privacy の各メニューのリンクを選択します。 各ページには同じメニューのレイアウトが表示されます。 メニューのレイアウトは、Views/Shared/_Layout.cshtml
ファイルに実装されています。
Views/Shared/_Layout.cshtml
ファイルを開きます。
レイアウト テンプレートでは、次のことが可能です。
- 1 か所でサイトの HTML コンテナー レイアウトを指定できます。
- サイト内の複数のページに HTML コンテナー レイアウトを適用できます。
@RenderBody()
という行を見つけます。 RenderBody
は、作成したビュー固有のページがすべて表示されるプレースホルダーで、レイアウト ページにラップされます。 たとえば、Privacy リンクを選択すると、Views/Home/Privacy.cshtml
ビューが RenderBody
メソッド内でレンダリングされます。
レイアウト ファイルでのタイトル、フッター、およびメニュー リンクの変更
Views/Shared/_Layout.cshtml
ファイルの内容を次のマークアップに置き換えます。 変更が強調表示されています。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>@ViewData["Title"] - Movie App</title>
<link rel="stylesheet" href="~/lib/bootstrap/dist/css/bootstrap.css" />
<link rel="stylesheet" href="~/css/site.css" asp-append-version="true" />
</head>
<body>
<header>
<nav class="navbar navbar-expand-sm navbar-toggleable-sm navbar-light bg-white border-bottom box-shadow mb-3">
<div class="container-fluid">
<a class="navbar-brand" asp-area="" asp-controller="Movies" asp-action="Index">Movie App</a>
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target=".navbar-collapse" aria-controls="navbarSupportedContent"
aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="navbar-collapse collapse d-sm-inline-flex justify-content-between">
<ul class="navbar-nav flex-grow-1">
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Index">Home</a>
</li>
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</li>
</ul>
</div>
</div>
</nav>
</header>
<div class="container">
<main role="main" class="pb-3">
@RenderBody()
</main>
</div>
<footer class="border-top footer text-muted">
<div class="container">
© 2023 - Movie App - <a asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</div>
</footer>
<script src="~/lib/jquery/dist/jquery.js"></script>
<script src="~/lib/bootstrap/dist/js/bootstrap.js"></script>
<script src="~/js/site.js" asp-append-version="true"></script>
@await RenderSectionAsync("Scripts", required: false)
</body>
</html>
上記のマークアップでは、次の変更が加えられています。
MvcMovie
からMovie App
が 3 回発生します。- アンカー要素
<a class="navbar-brand" asp-area="" asp-controller="Home" asp-action="Index">MvcMovie</a>
が<a class="navbar-brand" asp-controller="Movies" asp-action="Index">Movie App</a>
になりました。
上記のマークアップでは、このアプリでは Area が使用されていないため、asp-area=""
アンカー タグ ヘルパー属性と属性値が省略されています。
注: まだ Movies
コントローラーは実装されていません。 この時点では、Movie App
リンクは機能していません。
変更を保存し、 Privacy リンクを選択します。 ブラウザー タブのタイトルの表示が、Privacy Policy - MvcMovie ではなく、Privacy Policy - Movie App になっていることに注目してください。
[Home](ログの一元化) リンクを選択します。
タイトルとアンカー テキストに Movie App と表示されていることに着目してください。 レイアウト テンプレートが一度変更され、この新しいリンク テキストと新しいタイトルがサイト上のすべてのページに反映されました。
Views/_ViewStart.cshtml
ファイルを調べます。
@{
Layout = "_Layout";
}
Views/_ViewStart.cshtml
ファイルは Views/Shared/_Layout.cshtml
ファイルに取り込まれ、各ビューに適用されます。 Layout
プロパティを使用すれば、別のレイアウト ビューを設定することも、null
に設定してレイアウト ファイルが使用されないようにすることもできます。
Views/HelloWorld/Index.cshtml
ビュー ファイルを開きます。
タイトルと <h2>
要素を、以下の強調表示どおりに変更します。
@{
ViewData["Title"] = "Movie List";
}
<h2>My Movie List</h2>
<p>Hello from our View Template!</p>
タイトルと <h2>
要素は若干違うので、コードのどの部分によって表示が変更されるのかを確認できます。
上のコードの ViewData["Title"] = "Movie List";
では、Title
ディクショナリの ViewData
プロパティを "Movie List" に設定します。 Title
プロパティは、次のように、レイアウト ページの <title>
HTML 要素で使用されます。
<title>@ViewData["Title"] - Movie App</title>
変更内容を保存して、https://localhost:{PORT}/HelloWorld
に移動します。
次が変更されたことを確認します。
- ブラウザー タイトル。
- 1 番目の見出し。
- 2 番目の見出し。
ブラウザーに変更がない場合は、キャッシュされたコンテンツが表示されている場合があります。 ブラウザーで Ctrl + F5 キーを押して、サーバーからの応答が強制的に読み込まれるようにします。 ブラウザーのタイトルは、Index.cshtml
ビュー テンプレートで設定した ViewData["Title"]
で作成されます。レイアウト ファイルには "- Movie App" が追加されます。
Index.cshtml
ビュー テンプレート内のコンテンツは、Views/Shared/_Layout.cshtml
ビュー テンプレートにマージされます。 1 つの HTML 応答がブラウザーに送信されます。 レイアウト テンプレートを使用すれば、アプリのすべてのページに適用される変更を簡単に行うことができます。 詳細については、「Layout」(レイアウト) を参照してください。
ここでは、"データ" の一部 ("Hello from our View Template!" というメッセージ) がハードコーディングされています。 MVC アプリケーションには "V" (ビュー) があり、"C" (コントローラー) もありますが、"M" (モデル) はまだありません。
コントローラーからビューへのデータの受け渡し
コントローラー アクションは、受信 URL 要求への応答として呼び出されます。 コントローラー クラスでは、受信ブラウザー要求を処理するコードが記述されます。 コントローラーはデータ ソースからデータを取得し、ブラウザーに返す応答の種類を決定します。 ビュー テンプレートを使用すれば、コントローラーからブラウザーへの HTML 応答を生成して書式を設定できます。
コントローラーは、ビュー テンプレートで応答をレンダリングするために必要なデータを提供します。
ビュー テンプレートでは、次を行いません。
- ビジネス ロジックの実行
- データベースとの直接のやりとり
ビュー テンプレートは、コントローラーから提供されるデータのみを処理する必要があります。 この "関心の分離" を維持すれば、コードを次のように保つことができます。
- クリーン。
- テスト可能。
- 保守しやすい。
現時点では、HelloWorldController
クラスの Welcome
メソッドは name
と ID
パラメーターを受け取ってから、ブラウザーに直接値を出力します。
コントローラーにこの応答を文字列としてレンダリングさせるのではなく、代わりにビュー テンプレートを使用するようにコントローラーを変更します。 このビュー テンプレートは、応答を動的に生成します。つまり、応答の生成には、コントローラーからビューに適切なデータが渡される必要があります。 そのためには、ビュー テンプレートが必要とする動的データ (パラメーター) を、コントローラーに ViewData
ディレクトリに配置させます。 これにより、ビュー テンプレートが動的データにアクセスできるようになります。
HelloWorldController.cs
内で、Welcome
メソッドを変更して Message
および NumTimes
値を ViewData
ディクショナリに追加します。
ViewData
ディクショナリは、すべての型を使用できる動的なオブジェクトです。 ViewData
オブジェクトには、何かが追加されるまで、プロパティは定義されていません。 MVC のモデル バインド システムは、name
と numTimes
の名前付きパラメーターをクエリ文字列からメソッドのパラメーターに自動的にマップします。 完全な HelloWorldController
は次のとおりです。
using Microsoft.AspNetCore.Mvc;
using System.Text.Encodings.Web;
namespace MvcMovie.Controllers;
public class HelloWorldController : Controller
{
public IActionResult Index()
{
return View();
}
public IActionResult Welcome(string name, int numTimes = 1)
{
ViewData["Message"] = "Hello " + name;
ViewData["NumTimes"] = numTimes;
return View();
}
}
ViewData
ディクショナリ オブジェクトには、ビューに渡されるデータが含まれています。
Views/HelloWorld/Welcome.cshtml
という名前の [ようこそ] ビュー テンプレートを作成します。
"Hello" NumTimes
を表示する Welcome.cshtml
ビュー テンプレートにループを作成します。 Views/HelloWorld/Welcome.cshtml
の内容を次に置き換えます。
@{
ViewData["Title"] = "Welcome";
}
<h2>Welcome</h2>
<ul>
@for (int i = 0; i < (int)ViewData["NumTimes"]!; i++)
{
<li>@ViewData["Message"]</li>
}
</ul>
変更内容を保存し、次の URL を参照します。
https://localhost:{PORT}/HelloWorld/Welcome?name=Rick&numtimes=4
データは URL から取得され、MVC モデル バインダーを使用してコントローラーに渡されます。 コントローラーはデータを ViewData
ディクショナリにパッケージ化し、そのオブジェクトをビューに渡します。 その後、ビューでブラウザーに HTML としてデータがレンダリングされます。
上のサンプルでは、ViewData
ディクショナリを使用して、コントローラーからビューにデータを渡しました。 チュートリアルの後半では、ビュー モデルを使用して、コントローラーからビューにデータを渡します。 データを渡すには、ViewData
ディクショナリを使用する方法より、ビュー モデルを使用する方法が推奨されます。
次のチュートリアルでは、ムービーのデータベースを作成します。
このセクションでは、Razor ビュー ファイルを使用するよう、HelloWorldController
クラスを変更します。 これにより、クライアントへの HTML 応答を生成するプロセスが完全にカプセル化されます。
ビュー テンプレートは Razor を使用して作成されます。 Razor ベースのビュー テンプレートは次のとおりです。
.cshtml
ファイル拡張子を含めます。- C# を使用して HTML 出力を作成する洗練された方法が提供されます。
現在、Index
メソッドは、コントローラー クラスにメッセージを含め文字列を返します。 HelloWorldController
クラスでは、Index
メソッドを次のコードで置き換えます。
public IActionResult Index()
{
return View();
}
上記のコードでは、次のことが行われます。
- コントローラーの View メソッドを呼び出します。
- ビュー テンプレートを使用し HTML 応答を生成します。
コントローラー メソッドは次のとおりです。
- "アクション メソッド" と呼ばれます。 たとえば、前のコードの
Index
アクション メソッドです。 - 通常、
string
のような型ではなく IActionResult または ActionResult から派生したクラスを返します。
ビューを追加する
Views フォルダーを右クリックし、[追加] > [新しいフォルダー] の順に選択して、フォルダーに HelloWorld という名前を付けます。
Views/HelloWorld フォルダーを右クリックし、[追加] > [新しい項目] の順に選択します。
[新しい項目の追加 - MvcMovie] ダイアログで次を行います。
- 右上の検索ボックスに「view」と入力します。
- [Razor ビュー - 空] を選択します。
- [名前] ボックスの値、
Index.cshtml
を維持します。 - [追加] を選択します。
Views/HelloWorld/Index.cshtml
Razor ビュー ファイルの内容を次に置き換えます。
@{
ViewData["Title"] = "Index";
}
<h2>Index</h2>
<p>Hello from our View Template!</p>
次のように https://localhost:{PORT}/HelloWorld
に移動します。
HelloWorldController
のIndex
メソッドにより、ビュー テンプレート ファイルを使用して、ブラウザーに応答をレンダリングするようメソッドを指定する、ステートメントreturn View();
が実行されました。ビュー テンプレートのファイル名が指定されていないため、MVC で既定のビュー ファイルが使われました。 ビュー ファイル名を指定しない場合は、既定のビューが返されます。 この例では、既定のビューの名前は、アクション メソッド
Index
と同じ名前が付けられています。 ビュー テンプレート/Views/HelloWorld/Index.cshtml
が使用されています。次の画像は、ビューにハードコーディングされた "Hello from our View Template!" という文字列を示しています。
ビューとレイアウト ページを変更する
MvcMovie、 Home 、 Privacy の各メニューのリンクを選択します。 各ページには同じメニューのレイアウトが表示されます。 メニューのレイアウトは、Views/Shared/_Layout.cshtml
ファイルに実装されています。
Views/Shared/_Layout.cshtml
ファイルを開きます。
レイアウト テンプレートでは、次のことが可能です。
- 1 か所でサイトの HTML コンテナー レイアウトを指定できます。
- サイト内の複数のページに HTML コンテナー レイアウトを適用できます。
@RenderBody()
という行を見つけます。 RenderBody
は、作成したビュー固有のページがすべて表示されるプレースホルダーで、レイアウト ページにラップされます。 たとえば、Privacy リンクを選択すると、Views/Home/Privacy.cshtml
ビューが RenderBody
メソッド内でレンダリングされます。
レイアウト ファイルでのタイトル、フッター、およびメニュー リンクの変更
Views/Shared/_Layout.cshtml
ファイルの内容を次のマークアップに置き換えます。 変更が強調表示されています。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>@ViewData["Title"] - Movie App</title>
<link rel="stylesheet" href="~/lib/bootstrap/dist/css/bootstrap.css" />
<link rel="stylesheet" href="~/css/site.css" asp-append-version="true" />
</head>
<body>
<header>
<nav class="navbar navbar-expand-sm navbar-toggleable-sm navbar-light bg-white border-bottom box-shadow mb-3">
<div class="container-fluid">
<a class="navbar-brand" asp-area="" asp-controller="Movies" asp-action="Index">Movie App</a>
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target=".navbar-collapse" aria-controls="navbarSupportedContent"
aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="navbar-collapse collapse d-sm-inline-flex justify-content-between">
<ul class="navbar-nav flex-grow-1">
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Index">Home</a>
</li>
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</li>
</ul>
</div>
</div>
</nav>
</header>
<div class="container">
<main role="main" class="pb-3">
@RenderBody()
</main>
</div>
<footer class="border-top footer text-muted">
<div class="container">
© 2022 - Movie App - <a asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</div>
</footer>
<script src="~/lib/jquery/dist/jquery.js"></script>
<script src="~/lib/bootstrap/dist/js/bootstrap.js"></script>
<script src="~/js/site.js" asp-append-version="true"></script>
@await RenderSectionAsync("Scripts", required: false)
</body>
</html>
上記のマークアップでは、次の変更が加えられています。
MvcMovie
からMovie App
が 3 回発生します。- アンカー要素
<a class="navbar-brand" asp-area="" asp-controller="Home" asp-action="Index">MvcMovie</a>
が<a class="navbar-brand" asp-controller="Movies" asp-action="Index">Movie App</a>
になりました。
上記のマークアップでは、このアプリでは Area が使用されていないため、asp-area=""
アンカー タグ ヘルパー属性と属性値が省略されています。
注: まだ Movies
コントローラーは実装されていません。 この時点では、Movie App
リンクは機能していません。
変更を保存し、 Privacy リンクを選択します。 ブラウザー タブのタイトルの表示が、Privacy Policy - MvcMovie ではなく、Privacy Policy - Movie App になっていることに注目してください。
[Home](ログの一元化) リンクを選択します。
タイトルとアンカー テキストに Movie App と表示されていることに着目してください。 レイアウト テンプレートが一度変更され、この新しいリンク テキストと新しいタイトルがサイト上のすべてのページに反映されました。
Views/_ViewStart.cshtml
ファイルを調べます。
@{
Layout = "_Layout";
}
Views/_ViewStart.cshtml
ファイルは Views/Shared/_Layout.cshtml
ファイルに取り込まれ、各ビューに適用されます。 Layout
プロパティを使用すれば、別のレイアウト ビューを設定することも、null
に設定してレイアウト ファイルが使用されないようにすることもできます。
Views/HelloWorld/Index.cshtml
ビュー ファイルを開きます。
タイトルと <h2>
要素を、以下の強調表示どおりに変更します。
@{
ViewData["Title"] = "Movie List";
}
<h2>My Movie List</h2>
<p>Hello from our View Template!</p>
タイトルと <h2>
要素は若干違うので、コードのどの部分によって表示が変更されるのかを確認できます。
上のコードの ViewData["Title"] = "Movie List";
では、Title
ディクショナリの ViewData
プロパティを "Movie List" に設定します。 Title
プロパティは、次のように、レイアウト ページの <title>
HTML 要素で使用されます。
<title>@ViewData["Title"] - Movie App</title>
変更内容を保存して、https://localhost:{PORT}/HelloWorld
に移動します。
次が変更されたことを確認します。
- ブラウザー タイトル。
- 1 番目の見出し。
- 2 番目の見出し。
ブラウザーに変更がない場合は、キャッシュされたコンテンツが表示されている場合があります。 ブラウザーで Ctrl + F5 キーを押して、サーバーからの応答が強制的に読み込まれるようにします。 ブラウザーのタイトルは、Index.cshtml
ビュー テンプレートで設定した ViewData["Title"]
で作成されます。レイアウト ファイルには "- Movie App" が追加されます。
Index.cshtml
ビュー テンプレート内のコンテンツは、Views/Shared/_Layout.cshtml
ビュー テンプレートにマージされます。 1 つの HTML 応答がブラウザーに送信されます。 レイアウト テンプレートを使用すれば、アプリのすべてのページに適用される変更を簡単に行うことができます。 詳細については、「Layout」(レイアウト) を参照してください。
ここでは、"データ" の一部 ("Hello from our View Template!" というメッセージ) がハードコーディングされています。 MVC アプリケーションには "V" (ビュー) があり、"C" (コントローラー) もありますが、"M" (モデル) はまだありません。
コントローラーからビューへのデータの受け渡し
コントローラー アクションは、受信 URL 要求への応答として呼び出されます。 コントローラー クラスでは、受信ブラウザー要求を処理するコードが記述されます。 コントローラーはデータ ソースからデータを取得し、ブラウザーに返す応答の種類を決定します。 ビュー テンプレートを使用すれば、コントローラーからブラウザーへの HTML 応答を生成して書式を設定できます。
コントローラーは、ビュー テンプレートで応答をレンダリングするために必要なデータを提供します。
ビュー テンプレートでは、次を行いません。
- ビジネス ロジックの実行
- データベースとの直接のやりとり
ビュー テンプレートは、コントローラーから提供されるデータのみを処理する必要があります。 この "関心の分離" を維持すれば、コードを次のように保つことができます。
- クリーン。
- テスト可能。
- 保守しやすい。
現時点では、HelloWorldController
クラスの Welcome
メソッドは name
と ID
パラメーターを受け取ってから、ブラウザーに直接値を出力します。
コントローラーにこの応答を文字列としてレンダリングさせるのではなく、代わりにビュー テンプレートを使用するようにコントローラーを変更します。 このビュー テンプレートは、応答を動的に生成します。つまり、応答の生成には、コントローラーからビューに適切なデータが渡される必要があります。 そのためには、ビュー テンプレートが必要とする動的データ (パラメーター) を、コントローラーに ViewData
ディレクトリに配置させます。 これにより、ビュー テンプレートが動的データにアクセスできるようになります。
HelloWorldController.cs
内で、Welcome
メソッドを変更して Message
および NumTimes
値を ViewData
ディクショナリに追加します。
ViewData
ディクショナリは、すべての型を使用できる動的なオブジェクトです。 ViewData
オブジェクトには、何かが追加されるまで、プロパティは定義されていません。 MVC のモデル バインド システムは、name
と numTimes
の名前付きパラメーターをクエリ文字列からメソッドのパラメーターに自動的にマップします。 完全な HelloWorldController
は次のとおりです。
using Microsoft.AspNetCore.Mvc;
using System.Text.Encodings.Web;
namespace MvcMovie.Controllers;
public class HelloWorldController : Controller
{
public IActionResult Index()
{
return View();
}
public IActionResult Welcome(string name, int numTimes = 1)
{
ViewData["Message"] = "Hello " + name;
ViewData["NumTimes"] = numTimes;
return View();
}
}
ViewData
ディクショナリ オブジェクトには、ビューに渡されるデータが含まれています。
Views/HelloWorld/Welcome.cshtml
という名前の [ようこそ] ビュー テンプレートを作成します。
"Hello" NumTimes
を表示する Welcome.cshtml
ビュー テンプレートにループを作成します。 Views/HelloWorld/Welcome.cshtml
の内容を次に置き換えます。
@{
ViewData["Title"] = "Welcome";
}
<h2>Welcome</h2>
<ul>
@for (int i = 0; i < (int)ViewData["NumTimes"]!; i++)
{
<li>@ViewData["Message"]</li>
}
</ul>
変更内容を保存し、次の URL を参照します。
https://localhost:{PORT}/HelloWorld/Welcome?name=Rick&numtimes=4
データは URL から取得され、MVC モデル バインダーを使用してコントローラーに渡されます。 コントローラーはデータを ViewData
ディクショナリにパッケージ化し、そのオブジェクトをビューに渡します。 その後、ビューでブラウザーに HTML としてデータがレンダリングされます。
上のサンプルでは、ViewData
ディクショナリを使用して、コントローラーからビューにデータを渡しました。 チュートリアルの後半では、ビュー モデルを使用して、コントローラーからビューにデータを渡します。 データを渡すには、ViewData
ディクショナリを使用する方法より、ビュー モデルを使用する方法が推奨されます。
次のチュートリアルでは、ムービーのデータベースを作成します。
このセクションでは、Razor ビュー ファイルを使用するよう、HelloWorldController
クラスを変更します。 これにより、クライアントへの HTML 応答を生成するプロセスが完全にカプセル化されます。
ビュー テンプレートは Razor を使用して作成されます。 Razor ベースのビュー テンプレートは次のとおりです。
.cshtml
ファイル拡張子を含めます。- C# を使用して HTML 出力を作成する洗練された方法が提供されます。
現在、Index
メソッドは、コントローラー クラスにメッセージを含め文字列を返します。 HelloWorldController
クラスでは、Index
メソッドを次のコードで置き換えます。
public IActionResult Index()
{
return View();
}
上記のコードでは、次のことが行われます。
- コントローラーの View メソッドを呼び出します。
- ビュー テンプレートを使用し HTML 応答を生成します。
コントローラー メソッドは次のとおりです。
- "アクション メソッド" と呼ばれます。 たとえば、前のコードの
Index
アクション メソッドです。 - 通常、
string
のような型ではなく IActionResult または ActionResult から派生したクラスを返します。
ビューを追加する
Views フォルダーを右クリックし、[追加] > [新しいフォルダー] の順に選択して、フォルダーに HelloWorld という名前を付けます。
Views/HelloWorld フォルダーを右クリックし、[追加] > [新しい項目] の順に選択します。
[新しい項目の追加 - MvcMovie] ダイアログで次を行います。
- 右上の検索ボックスに「view」と入力します。
- [Razor ビュー - 空] を選択します。
- [名前] ボックスの値、
Index.cshtml
を維持します。 - [追加] を選択します。
Views/HelloWorld/Index.cshtml
Razor ビュー ファイルの内容を次に置き換えます。
@{
ViewData["Title"] = "Index";
}
<h2>Index</h2>
<p>Hello from our View Template!</p>
次のように https://localhost:{PORT}/HelloWorld
に移動します。
HelloWorldController
のIndex
メソッドにより、ビュー テンプレート ファイルを使用して、ブラウザーに応答をレンダリングするようメソッドを指定する、ステートメントreturn View();
が実行されました。ビュー テンプレートのファイル名が指定されていないため、MVC で既定のビュー ファイルが使われました。 ビュー ファイル名を指定しない場合は、既定のビューが返されます。 この例では、既定のビューの名前は、アクション メソッド
Index
と同じ名前が付けられています。 ビュー テンプレート/Views/HelloWorld/Index.cshtml
が使用されています。次の画像は、ビューにハードコーディングされた "Hello from our View Template!" という文字列を示しています。
ビューとレイアウト ページを変更する
MvcMovie、 Home 、 Privacy の各メニューのリンクを選択します。 各ページには同じメニューのレイアウトが表示されます。 メニューのレイアウトは、Views/Shared/_Layout.cshtml
ファイルに実装されています。
Views/Shared/_Layout.cshtml
ファイルを開きます。
レイアウト テンプレートでは、次のことが可能です。
- 1 か所でサイトの HTML コンテナー レイアウトを指定できます。
- サイト内の複数のページに HTML コンテナー レイアウトを適用できます。
@RenderBody()
という行を見つけます。 RenderBody
は、作成したビュー固有のページがすべて表示されるプレースホルダーで、レイアウト ページにラップされます。 たとえば、Privacy リンクを選択すると、Views/Home/Privacy.cshtml
ビューが RenderBody
メソッド内でレンダリングされます。
レイアウト ファイルでのタイトル、フッター、およびメニュー リンクの変更
Views/Shared/_Layout.cshtml
ファイルの内容を次のマークアップに置き換えます。 変更が強調表示されています。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>@ViewData["Title"] - Movie App</title>
<link rel="stylesheet" href="~/lib/bootstrap/dist/css/bootstrap.css" />
<link rel="stylesheet" href="~/css/site.css" asp-append-version="true" />
</head>
<body>
<header>
<nav class="navbar navbar-expand-sm navbar-toggleable-sm navbar-light bg-white border-bottom box-shadow mb-3">
<div class="container-fluid">
<a class="navbar-brand" asp-area="" asp-controller="Movies" asp-action="Index">Movie App</a>
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target=".navbar-collapse" aria-controls="navbarSupportedContent"
aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="navbar-collapse collapse d-sm-inline-flex justify-content-between">
<ul class="navbar-nav flex-grow-1">
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Index">Home</a>
</li>
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</li>
</ul>
</div>
</div>
</nav>
</header>
<div class="container">
<main role="main" class="pb-3">
@RenderBody()
</main>
</div>
<footer class="border-top footer text-muted">
<div class="container">
© 2021 - Movie App - <a asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</div>
</footer>
<script src="~/lib/jquery/dist/jquery.js"></script>
<script src="~/lib/bootstrap/dist/js/bootstrap.js"></script>
<script src="~/js/site.js" asp-append-version="true"></script>
@await RenderSectionAsync("Scripts", required: false)
</body>
</html>
上記のマークアップでは、次の変更が加えられています。
MvcMovie
からMovie App
が 3 回発生します。- アンカー要素
<a class="navbar-brand" asp-area="" asp-controller="Home" asp-action="Index">MvcMovie</a>
が<a class="navbar-brand" asp-controller="Movies" asp-action="Index">Movie App</a>
になりました。
上記のマークアップでは、このアプリでは Area が使用されていないため、asp-area=""
アンカー タグ ヘルパー属性と属性値が省略されています。
注: まだ Movies
コントローラーは実装されていません。 この時点では、Movie App
リンクは機能していません。
変更を保存し、 Privacy リンクを選択します。 ブラウザー タブのタイトルの表示が、Privacy Policy - MvcMovie ではなく、Privacy Policy - Movie App になっていることに注目してください。
[Home](ログの一元化) リンクを選択します。
タイトルとアンカー テキストに Movie App と表示されていることに着目してください。 レイアウト テンプレートが一度変更され、この新しいリンク テキストと新しいタイトルがサイト上のすべてのページに反映されました。
Views/_ViewStart.cshtml
ファイルを調べます。
@{
Layout = "_Layout";
}
Views/_ViewStart.cshtml
ファイルは Views/Shared/_Layout.cshtml
ファイルに取り込まれ、各ビューに適用されます。 Layout
プロパティを使用すれば、別のレイアウト ビューを設定することも、null
に設定してレイアウト ファイルが使用されないようにすることもできます。
Views/HelloWorld/Index.cshtml
ビュー ファイルを開きます。
タイトルと <h2>
要素を、以下の強調表示どおりに変更します。
@{
ViewData["Title"] = "Movie List";
}
<h2>My Movie List</h2>
<p>Hello from our View Template!</p>
タイトルと <h2>
要素は若干違うので、コードのどの部分によって表示が変更されるのかを確認できます。
上のコードの ViewData["Title"] = "Movie List";
では、Title
ディクショナリの ViewData
プロパティを "Movie List" に設定します。 Title
プロパティは、次のように、レイアウト ページの <title>
HTML 要素で使用されます。
<title>@ViewData["Title"] - Movie App</title>
変更内容を保存して、https://localhost:{PORT}/HelloWorld
に移動します。
次が変更されたことを確認します。
- ブラウザー タイトル。
- 1 番目の見出し。
- 2 番目の見出し。
ブラウザーに変更がない場合は、キャッシュされたコンテンツが表示されている場合があります。 ブラウザーで Ctrl + F5 キーを押して、サーバーからの応答が強制的に読み込まれるようにします。 ブラウザーのタイトルは、Index.cshtml
ビュー テンプレートで設定した ViewData["Title"]
で作成されます。レイアウト ファイルには "- Movie App" が追加されます。
Index.cshtml
ビュー テンプレート内のコンテンツは、Views/Shared/_Layout.cshtml
ビュー テンプレートにマージされます。 1 つの HTML 応答がブラウザーに送信されます。 レイアウト テンプレートを使用すれば、アプリのすべてのページに適用される変更を簡単に行うことができます。 詳細については、「Layout」(レイアウト) を参照してください。
ここでは、"データ" の一部 ("Hello from our View Template!" というメッセージ) がハードコーディングされています。 MVC アプリケーションには "V" (ビュー) があり、"C" (コントローラー) もありますが、"M" (モデル) はまだありません。
コントローラーからビューへのデータの受け渡し
コントローラー アクションは、受信 URL 要求への応答として呼び出されます。 コントローラー クラスでは、受信ブラウザー要求を処理するコードが記述されます。 コントローラーはデータ ソースからデータを取得し、ブラウザーに返す応答の種類を決定します。 ビュー テンプレートを使用すれば、コントローラーからブラウザーへの HTML 応答を生成して書式を設定できます。
コントローラーは、ビュー テンプレートで応答をレンダリングするために必要なデータを提供します。
ビュー テンプレートでは、次を行いません。
- ビジネス ロジックの実行
- データベースとの直接のやりとり
ビュー テンプレートは、コントローラーから提供されるデータのみを処理する必要があります。 この "関心の分離" を維持すれば、コードを次のように保つことができます。
- クリーン。
- テスト可能。
- 保守しやすい。
現時点では、HelloWorldController
クラスの Welcome
メソッドは name
と ID
パラメーターを受け取ってから、ブラウザーに直接値を出力します。
コントローラーにこの応答を文字列としてレンダリングさせるのではなく、代わりにビュー テンプレートを使用するようにコントローラーを変更します。 このビュー テンプレートは、応答を動的に生成します。つまり、応答の生成には、コントローラーからビューに適切なデータが渡される必要があります。 そのためには、ビュー テンプレートが必要とする動的データ (パラメーター) を、コントローラーに ViewData
ディレクトリに配置させます。 これにより、ビュー テンプレートが動的データにアクセスできるようになります。
HelloWorldController.cs
内で、Welcome
メソッドを変更して Message
および NumTimes
値を ViewData
ディクショナリに追加します。
ViewData
ディクショナリは、すべての型を使用できる動的なオブジェクトです。 ViewData
オブジェクトには、何かが追加されるまで、プロパティは定義されていません。 MVC のモデル バインド システムは、name
と numTimes
の名前付きパラメーターをクエリ文字列からメソッドのパラメーターに自動的にマップします。 完全な HelloWorldController
は次のとおりです。
using Microsoft.AspNetCore.Mvc;
using System.Text.Encodings.Web;
namespace MvcMovie.Controllers
{
public class HelloWorldController : Controller
{
public IActionResult Index()
{
return View();
}
public IActionResult Welcome(string name, int numTimes = 1)
{
ViewData["Message"] = "Hello " + name;
ViewData["NumTimes"] = numTimes;
return View();
}
}
}
ViewData
ディクショナリ オブジェクトには、ビューに渡されるデータが含まれています。
Views/HelloWorld/Welcome.cshtml
という名前の [ようこそ] ビュー テンプレートを作成します。
"Hello" NumTimes
を表示する Welcome.cshtml
ビュー テンプレートにループを作成します。 Views/HelloWorld/Welcome.cshtml
の内容を次に置き換えます。
@{
ViewData["Title"] = "Welcome";
}
<h2>Welcome</h2>
<ul>
@for (int i = 0; i < (int)ViewData["NumTimes"]!; i++)
{
<li>@ViewData["Message"]</li>
}
</ul>
変更内容を保存し、次の URL を参照します。
https://localhost:{PORT}/HelloWorld/Welcome?name=Rick&numtimes=4
データは URL から取得され、MVC モデル バインダーを使用してコントローラーに渡されます。 コントローラーはデータを ViewData
ディクショナリにパッケージ化し、そのオブジェクトをビューに渡します。 その後、ビューでブラウザーに HTML としてデータがレンダリングされます。
上のサンプルでは、ViewData
ディクショナリを使用して、コントローラーからビューにデータを渡しました。 チュートリアルの後半では、ビュー モデルを使用して、コントローラーからビューにデータを渡します。 データを渡すには、ViewData
ディクショナリを使用する方法より、ビュー モデルを使用する方法が推奨されます。
次のチュートリアルでは、ムービーのデータベースを作成します。
このセクションでは、Razor ビュー ファイルを使用するよう、HelloWorldController
クラスを変更します。 これにより、クライアントへの HTML 応答を生成するプロセスが完全にカプセル化されます。
ビュー テンプレートは Razor を使用して作成されます。 Razor ベースのビュー テンプレートは次のとおりです。
.cshtml
ファイル拡張子を含めます。- C# を使用して HTML 出力を作成する洗練された方法が提供されます。
現在、Index
メソッドは、コントローラー クラスにメッセージを含め文字列を返します。 HelloWorldController
クラスでは、Index
メソッドを次のコードで置き換えます。
public IActionResult Index()
{
return View();
}
上記のコードでは、次のことが行われます。
- コントローラーの View メソッドを呼び出します。
- ビュー テンプレートを使用し HTML 応答を生成します。
コントローラー メソッドは次のとおりです。
- "アクション メソッド" と呼ばれます。 たとえば、前のコードの
Index
アクション メソッドです。 - 通常、
string
のような型ではなく IActionResult または ActionResult から派生したクラスを返します。
ビューを追加する
Views フォルダーを右クリックし、[追加] > [新しいフォルダー] の順に選択して、フォルダーに HelloWorld という名前を付けます。
Views/HelloWorld フォルダーを右クリックし、[追加] > [新しい項目] の順に選択します。
[新しい項目の追加 - MvcMovie] ダイアログで次を行います。
- 右上の検索ボックスに「view」と入力します。
- [Razor ビュー - 空] を選択します。
- [名前] ボックスの値、
Index.cshtml
を維持します。 - [追加] を選択します。
Views/HelloWorld/Index.cshtml
Razor ビュー ファイルの内容を次に置き換えます。
@{
ViewData["Title"] = "Index";
}
<h2>Index</h2>
<p>Hello from our View Template!</p>
次のように https://localhost:{PORT}/HelloWorld
に移動します。
HelloWorldController
のIndex
メソッドにより、ビュー テンプレート ファイルを使用して、ブラウザーに応答をレンダリングするようメソッドを指定する、ステートメントreturn View();
が実行されました。ビュー テンプレートのファイル名が指定されていないため、MVC で既定のビュー ファイルが使われました。 ビュー ファイル名を指定しない場合は、既定のビューが返されます。 この例では、既定のビューの名前は、アクション メソッド
Index
と同じ名前が付けられています。 ビュー テンプレート/Views/HelloWorld/Index.cshtml
が使用されています。次の画像は、ビューにハードコーディングされた "Hello from our View Template!" という文字列を示しています。
ビューとレイアウト ページを変更する
MvcMovie、 Home 、 Privacy の各メニューのリンクを選択します。 各ページには同じメニューのレイアウトが表示されます。 メニューのレイアウトは、Views/Shared/_Layout.cshtml
ファイルに実装されています。
Views/Shared/_Layout.cshtml
ファイルを開きます。
レイアウト テンプレートでは、次のことが可能です。
- 1 か所でサイトの HTML コンテナー レイアウトを指定できます。
- サイト内の複数のページに HTML コンテナー レイアウトを適用できます。
@RenderBody()
という行を見つけます。 RenderBody
は、作成したビュー固有のページがすべて表示されるプレースホルダーで、レイアウト ページにラップされます。 たとえば、Privacy リンクを選択すると、Views/Home/Privacy.cshtml
ビューが RenderBody
メソッド内でレンダリングされます。
レイアウト ファイルでのタイトル、フッター、およびメニュー リンクの変更
Views/Shared/_Layout.cshtml
ファイルの内容を次のマークアップに置き換えます。 変更が強調表示されています。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>@ViewData["Title"] - Movie App</title>
<link rel="stylesheet" href="~/lib/bootstrap/dist/css/bootstrap.css" />
<link rel="stylesheet" href="~/css/site.css" />
</head>
<body>
<header>
<nav class="navbar navbar-expand-sm navbar-toggleable-sm navbar-light bg-white border-bottom box-shadow mb-3">
<div class="container">
<a class="navbar-brand" asp-controller="Movies" asp-action="Index">Movie App</a>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target=".navbar-collapse" aria-controls="navbarSupportedContent"
aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="navbar-collapse collapse d-sm-inline-flex justify-content-between">
<ul class="navbar-nav flex-grow-1">
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Index">Home</a>
</li>
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</li>
</ul>
</div>
</div>
</nav>
</header>
<div class="container">
<main role="main" class="pb-3">
@RenderBody()
</main>
</div>
<footer class="border-top footer text-muted">
<div class="container">
© 2020 - Movie App - <a asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</div>
</footer>
<script src="~/lib/jquery/dist/jquery.js"></script>
<script src="~/lib/bootstrap/dist/js/bootstrap.bundle.js"></script>
<script src="~/js/site.js" asp-append-version="true"></script>
@await RenderSectionAsync("Scripts", required: false)
</body>
</html>
上記のマークアップでは、次の変更が加えられています。
MvcMovie
からMovie App
が 3 回発生します。- アンカー要素
<a class="navbar-brand" asp-area="" asp-controller="Home" asp-action="Index">MvcMovie</a>
が<a class="navbar-brand" asp-controller="Movies" asp-action="Index">Movie App</a>
になりました。
上記のマークアップでは、このアプリでは Area が使用されていないため、asp-area=""
アンカー タグ ヘルパー属性と属性値が省略されています。
注: まだ Movies
コントローラーは実装されていません。 この時点では、Movie App
リンクは機能していません。
変更を保存し、 Privacy リンクを選択します。 ブラウザー タブのタイトルの表示が、Privacy Policy - MvcMovie ではなく、Privacy Policy - Movie App になっていることに注目してください。
[Home](ログの一元化) リンクを選択します。
タイトルとアンカー テキストに Movie App と表示されていることに着目してください。 レイアウト テンプレートが一度変更され、この新しいリンク テキストと新しいタイトルがサイト上のすべてのページに反映されました。
Views/_ViewStart.cshtml
ファイルを調べます。
@{
Layout = "_Layout";
}
Views/_ViewStart.cshtml
ファイルは Views/Shared/_Layout.cshtml
ファイルに取り込まれ、各ビューに適用されます。 Layout
プロパティを使用すれば、別のレイアウト ビューを設定することも、null
に設定してレイアウト ファイルが使用されないようにすることもできます。
Views/HelloWorld/Index.cshtml
ビュー ファイルを開きます。
タイトルと <h2>
要素を、以下の強調表示どおりに変更します。
@{
ViewData["Title"] = "Movie List";
}
<h2>My Movie List</h2>
<p>Hello from our View Template!</p>
タイトルと <h2>
要素は若干違うので、コードのどの部分によって表示が変更されるのかを確認できます。
上のコードの ViewData["Title"] = "Movie List";
では、Title
ディクショナリの ViewData
プロパティを "Movie List" に設定します。 Title
プロパティは、次のように、レイアウト ページの <title>
HTML 要素で使用されます。
<title>@ViewData["Title"] - Movie App</title>
変更内容を保存して、https://localhost:{PORT}/HelloWorld
に移動します。
次が変更されたことを確認します。
- ブラウザー タイトル。
- 1 番目の見出し。
- 2 番目の見出し。
ブラウザーに変更がない場合は、キャッシュされたコンテンツが表示されている場合があります。 ブラウザーで Ctrl + F5 キーを押して、サーバーからの応答が強制的に読み込まれるようにします。 ブラウザーのタイトルは、Index.cshtml
ビュー テンプレートで設定した ViewData["Title"]
で作成されます。レイアウト ファイルには "- Movie App" が追加されます。
Index.cshtml
ビュー テンプレート内のコンテンツは、Views/Shared/_Layout.cshtml
ビュー テンプレートにマージされます。 1 つの HTML 応答がブラウザーに送信されます。 レイアウト テンプレートを使用すれば、アプリのすべてのページに適用される変更を簡単に行うことができます。 詳細については、「Layout」(レイアウト) を参照してください。
ここでは、"データ" の一部 ("Hello from our View Template!" というメッセージ) がハードコーディングされています。 MVC アプリケーションには "V" (ビュー) があり、"C" (コントローラー) もありますが、"M" (モデル) はまだありません。
コントローラーからビューへのデータの受け渡し
コントローラー アクションは、受信 URL 要求への応答として呼び出されます。 コントローラー クラスでは、受信ブラウザー要求を処理するコードが記述されます。 コントローラーはデータ ソースからデータを取得し、ブラウザーに返す応答の種類を決定します。 ビュー テンプレートを使用すれば、コントローラーからブラウザーへの HTML 応答を生成して書式を設定できます。
コントローラーは、ビュー テンプレートで応答をレンダリングするために必要なデータを提供します。
ビュー テンプレートでは、次を行いません。
- ビジネス ロジックの実行
- データベースとの直接のやりとり
ビュー テンプレートは、コントローラーから提供されるデータのみを処理する必要があります。 この "関心の分離" を維持すれば、コードを次のように保つことができます。
- クリーン。
- テスト可能。
- 保守しやすい。
現時点では、HelloWorldController
クラスの Welcome
メソッドは name
と ID
パラメーターを受け取ってから、ブラウザーに直接値を出力します。
コントローラーにこの応答を文字列としてレンダリングさせるのではなく、代わりにビュー テンプレートを使用するようにコントローラーを変更します。 このビュー テンプレートは、応答を動的に生成します。つまり、応答の生成には、コントローラーからビューに適切なデータが渡される必要があります。 そのためには、ビュー テンプレートが必要とする動的データ (パラメーター) を、コントローラーに ViewData
ディレクトリに配置させます。 これにより、ビュー テンプレートが動的データにアクセスできるようになります。
HelloWorldController.cs
内で、Welcome
メソッドを変更して Message
および NumTimes
値を ViewData
ディクショナリに追加します。
ViewData
ディクショナリは、すべての型を使用できる動的なオブジェクトです。 ViewData
オブジェクトには、何かが追加されるまで、プロパティは定義されていません。 MVC のモデル バインド システムは、name
と numTimes
の名前付きパラメーターをクエリ文字列からメソッドのパラメーターに自動的にマップします。 完全な HelloWorldController
は次のとおりです。
using Microsoft.AspNetCore.Mvc;
using System.Text.Encodings.Web;
namespace MvcMovie.Controllers
{
public class HelloWorldController : Controller
{
public IActionResult Index()
{
return View();
}
public IActionResult Welcome(string name, int numTimes = 1)
{
ViewData["Message"] = "Hello " + name;
ViewData["NumTimes"] = numTimes;
return View();
}
}
}
ViewData
ディクショナリ オブジェクトには、ビューに渡されるデータが含まれています。
Views/HelloWorld/Welcome.cshtml
という名前の [ようこそ] ビュー テンプレートを作成します。
"Hello" NumTimes
を表示する Welcome.cshtml
ビュー テンプレートにループを作成します。 Views/HelloWorld/Welcome.cshtml
の内容を次に置き換えます。
@{
ViewData["Title"] = "Welcome";
}
<h2>Welcome</h2>
<ul>
@for (int i = 0; i < (int)ViewData["NumTimes"]; i++)
{
<li>@ViewData["Message"]</li>
}
</ul>
変更内容を保存し、次の URL を参照します。
https://localhost:{PORT}/HelloWorld/Welcome?name=Rick&numtimes=4
データは URL から取得され、MVC モデル バインダーを使用してコントローラーに渡されます。 コントローラーはデータを ViewData
ディクショナリにパッケージ化し、そのオブジェクトをビューに渡します。 その後、ビューでブラウザーに HTML としてデータがレンダリングされます。
上のサンプルでは、ViewData
ディクショナリを使用して、コントローラーからビューにデータを渡しました。 チュートリアルの後半では、ビュー モデルを使用して、コントローラーからビューにデータを渡します。 データを渡すには、ViewData
ディクショナリを使用する方法より、ビュー モデルを使用する方法が推奨されます。
次のチュートリアルでは、ムービーのデータベースを作成します。
このセクションでは、Razor ビュー ファイルを使用するよう、HelloWorldController
クラスを変更します。 これにより、クライアントへの HTML 応答を生成するプロセスが完全にカプセル化されます。
ビュー テンプレートは Razor を使用して作成されます。 Razor ベースのビュー テンプレートは次のとおりです。
.cshtml
ファイル拡張子を含めます。- C# を使用して HTML 出力を作成する洗練された方法が提供されます。
現在、Index
メソッドは、コントローラー クラスにメッセージを含め文字列を返します。 HelloWorldController
クラスでは、Index
メソッドを次のコードで置き換えます。
public IActionResult Index()
{
return View();
}
上記のコードでは、次のことが行われます。
- コントローラーの View メソッドを呼び出します。
- ビュー テンプレートを使用し HTML 応答を生成します。
コントローラー メソッドは次のとおりです。
- "アクション メソッド" と呼ばれます。 たとえば、前のコードの
Index
アクション メソッドです。 - 通常、
string
のような型ではなく IActionResult または ActionResult から派生したクラスを返します。
ビューを追加する
Views フォルダーを右クリックし、[追加] > [新しいフォルダー] の順に選択して、フォルダーに HelloWorld という名前を付けます。
Views/HelloWorld フォルダーを右クリックし、[追加] > [新しい項目] の順に選択します。
[新しい項目の追加 - MvcMovie] ダイアログで次を行います。
- 右上の検索ボックスに「view」と入力します。
- [Razor ビュー - 空] を選択します。
- [名前] ボックスの値、
Index.cshtml
を維持します。 - [追加] を選択します。
Views/HelloWorld/Index.cshtml
Razor ビュー ファイルの内容を次に置き換えます。
@{
ViewData["Title"] = "Index";
}
<h2>Index</h2>
<p>Hello from our View Template!</p>
次のように https://localhost:{PORT}/HelloWorld
に移動します。
HelloWorldController
のIndex
メソッドにより、ビュー テンプレート ファイルを使用して、ブラウザーに応答をレンダリングするようメソッドを指定する、ステートメントreturn View();
が実行されました。ビュー テンプレートのファイル名が指定されていないため、MVC で既定のビュー ファイルが使われました。 ビュー ファイル名を指定しない場合は、既定のビューが返されます。 この例では、既定のビューの名前は、アクション メソッド
Index
と同じ名前が付けられています。 ビュー テンプレート/Views/HelloWorld/Index.cshtml
が使用されています。次の画像は、ビューにハードコーディングされた "Hello from our View Template!" という文字列を示しています。
ビューとレイアウト ページを変更する
MvcMovie、 Home 、 Privacy の各メニューのリンクを選択します。 各ページには同じメニューのレイアウトが表示されます。 メニューのレイアウトは、Views/Shared/_Layout.cshtml
ファイルに実装されています。
Views/Shared/_Layout.cshtml
ファイルを開きます。
レイアウト テンプレートでは、次のことが可能です。
- 1 か所でサイトの HTML コンテナー レイアウトを指定できます。
- サイト内の複数のページに HTML コンテナー レイアウトを適用できます。
@RenderBody()
という行を見つけます。 RenderBody
は、作成したビュー固有のページがすべて表示されるプレースホルダーで、レイアウト ページにラップされます。 たとえば、Privacy リンクを選択すると、Views/Home/Privacy.cshtml
ビューが RenderBody
メソッド内でレンダリングされます。
レイアウト ファイルでのタイトル、フッター、およびメニュー リンクの変更
Views/Shared/_Layout.cshtml
ファイルの内容を次のマークアップに置き換えます。 変更が強調表示されています。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>@ViewData["Title"] - Movie App</title>
<link rel="stylesheet" href="~/lib/bootstrap/dist/css/bootstrap.css" />
<link rel="stylesheet" href="~/css/site.css" />
</head>
<body>
<header>
<nav class="navbar navbar-expand-sm navbar-toggleable-sm navbar-light bg-white border-bottom box-shadow mb-3">
<div class="container">
<a class="navbar-brand" asp-controller="Movies" asp-action="Index">Movie App</a>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target=".navbar-collapse" aria-controls="navbarSupportedContent"
aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="navbar-collapse collapse d-sm-inline-flex flex-sm-row-reverse">
<ul class="navbar-nav flex-grow-1">
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Index">Home</a>
</li>
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</li>
</ul>
</div>
</div>
</nav>
</header>
<div class="container">
<main role="main" class="pb-3">
@RenderBody()
</main>
</div>
<footer class="border-top footer text-muted">
<div class="container">
© 2020 - Movie App - <a asp-area="" asp-controller="Home" asp-action="Privacy">Privacy</a>
</div>
</footer>
<script src="~/lib/jquery/dist/jquery.js"></script>
<script src="~/lib/bootstrap/dist/js/bootstrap.bundle.js"></script>
<script src="~/js/site.js" asp-append-version="true"></script>
@RenderSection("Scripts", required: false)
</body>
</html>
上記のマークアップでは、次の変更が加えられています。
MvcMovie
からMovie App
が 3 回発生します。- アンカー要素
<a class="navbar-brand" asp-area="" asp-controller="Home" asp-action="Index">MvcMovie</a>
が<a class="navbar-brand" asp-controller="Movies" asp-action="Index">Movie App</a>
になりました。
上記のマークアップでは、このアプリでは Area が使用されていないため、asp-area=""
アンカー タグ ヘルパー属性と属性値が省略されています。
注: まだ Movies
コントローラーは実装されていません。 この時点では、Movie App
リンクは機能していません。
変更を保存し、 Privacy リンクを選択します。 ブラウザー タブのタイトルの表示が、Privacy Policy - MvcMovie ではなく、Privacy Policy - Movie App になっていることに注目してください。
[Home](ログの一元化) リンクを選択します。
タイトルとアンカー テキストに Movie App と表示されていることに着目してください。 レイアウト テンプレートが一度変更され、この新しいリンク テキストと新しいタイトルがサイト上のすべてのページに反映されました。
Views/_ViewStart.cshtml
ファイルを調べます。
@{
Layout = "_Layout";
}
Views/_ViewStart.cshtml
ファイルは Views/Shared/_Layout.cshtml
ファイルに取り込まれ、各ビューに適用されます。 Layout
プロパティを使用すれば、別のレイアウト ビューを設定することも、null
に設定してレイアウト ファイルが使用されないようにすることもできます。
Views/HelloWorld/Index.cshtml
ビュー ファイルを開きます。
タイトルと <h2>
要素を、以下の強調表示どおりに変更します。
@{
ViewData["Title"] = "Movie List";
}
<h2>My Movie List</h2>
<p>Hello from our View Template!</p>
タイトルと <h2>
要素は若干違うので、コードのどの部分によって表示が変更されるのかを確認できます。
上のコードの ViewData["Title"] = "Movie List";
では、Title
ディクショナリの ViewData
プロパティを "Movie List" に設定します。 Title
プロパティは、次のように、レイアウト ページの <title>
HTML 要素で使用されます。
<title>@ViewData["Title"] - Movie App</title>
変更内容を保存して、https://localhost:{PORT}/HelloWorld
に移動します。
次が変更されたことを確認します。
- ブラウザー タイトル。
- 1 番目の見出し。
- 2 番目の見出し。
ブラウザーに変更がない場合は、キャッシュされたコンテンツが表示されている場合があります。 ブラウザーで Ctrl + F5 キーを押して、サーバーからの応答が強制的に読み込まれるようにします。 ブラウザーのタイトルは、Index.cshtml
ビュー テンプレートで設定した ViewData["Title"]
で作成されます。レイアウト ファイルには "- Movie App" が追加されます。
Index.cshtml
ビュー テンプレート内のコンテンツは、Views/Shared/_Layout.cshtml
ビュー テンプレートにマージされます。 1 つの HTML 応答がブラウザーに送信されます。 レイアウト テンプレートを使用すれば、アプリのすべてのページに適用される変更を簡単に行うことができます。 詳細については、「Layout」(レイアウト) を参照してください。
ここでは、"データ" の一部 ("Hello from our View Template!" というメッセージ) がハードコーディングされています。 MVC アプリケーションには "V" (ビュー) があり、"C" (コントローラー) もありますが、"M" (モデル) はまだありません。
コントローラーからビューへのデータの受け渡し
コントローラー アクションは、受信 URL 要求への応答として呼び出されます。 コントローラー クラスでは、受信ブラウザー要求を処理するコードが記述されます。 コントローラーはデータ ソースからデータを取得し、ブラウザーに返す応答の種類を決定します。 ビュー テンプレートを使用すれば、コントローラーからブラウザーへの HTML 応答を生成して書式を設定できます。
コントローラーは、ビュー テンプレートで応答をレンダリングするために必要なデータを提供します。
ビュー テンプレートでは、次を行いません。
- ビジネス ロジックの実行
- データベースとの直接のやりとり
ビュー テンプレートは、コントローラーから提供されるデータのみを処理する必要があります。 この "関心の分離" を維持すれば、コードを次のように保つことができます。
- クリーン。
- テスト可能。
- 保守しやすい。
現時点では、HelloWorldController
クラスの Welcome
メソッドは name
と ID
パラメーターを受け取ってから、ブラウザーに直接値を出力します。
コントローラーにこの応答を文字列としてレンダリングさせるのではなく、代わりにビュー テンプレートを使用するようにコントローラーを変更します。 このビュー テンプレートは、応答を動的に生成します。つまり、応答の生成には、コントローラーからビューに適切なデータが渡される必要があります。 そのためには、ビュー テンプレートが必要とする動的データ (パラメーター) を、コントローラーに ViewData
ディレクトリに配置させます。 これにより、ビュー テンプレートが動的データにアクセスできるようになります。
HelloWorldController.cs
内で、Welcome
メソッドを変更して Message
および NumTimes
値を ViewData
ディクショナリに追加します。
ViewData
ディクショナリは、すべての型を使用できる動的なオブジェクトです。 ViewData
オブジェクトには、何かが追加されるまで、プロパティは定義されていません。 MVC のモデル バインド システムは、name
と numTimes
の名前付きパラメーターをクエリ文字列からメソッドのパラメーターに自動的にマップします。 完全な HelloWorldController
は次のとおりです。
using Microsoft.AspNetCore.Mvc;
using System.Text.Encodings.Web;
namespace MvcMovie.Controllers
{
public class HelloWorldController : Controller
{
public IActionResult Index()
{
return View();
}
public IActionResult Welcome(string name, int numTimes = 1)
{
ViewData["Message"] = "Hello " + name;
ViewData["NumTimes"] = numTimes;
return View();
}
}
}
ViewData
ディクショナリ オブジェクトには、ビューに渡されるデータが含まれています。
Views/HelloWorld/Welcome.cshtml
という名前の [ようこそ] ビュー テンプレートを作成します。
"Hello" NumTimes
を表示する Welcome.cshtml
ビュー テンプレートにループを作成します。 Views/HelloWorld/Welcome.cshtml
の内容を次に置き換えます。
@{
ViewData["Title"] = "Welcome";
}
<h2>Welcome</h2>
<ul>
@for (int i = 0; i < (int)ViewData["NumTimes"]; i++)
{
<li>@ViewData["Message"]</li>
}
</ul>
変更内容を保存し、次の URL を参照します。
https://localhost:{PORT}/HelloWorld/Welcome?name=Rick&numtimes=4
データは URL から取得され、MVC モデル バインダーを使用してコントローラーに渡されます。 コントローラーはデータを ViewData
ディクショナリにパッケージ化し、そのオブジェクトをビューに渡します。 その後、ビューでブラウザーに HTML としてデータがレンダリングされます。
上のサンプルでは、ViewData
ディクショナリを使用して、コントローラーからビューにデータを渡しました。 チュートリアルの後半では、ビュー モデルを使用して、コントローラーからビューにデータを渡します。 データを渡すには、ViewData
ディクショナリを使用する方法より、ビュー モデルを使用する方法が推奨されます。
次のチュートリアルでは、ムービーのデータベースを作成します。
ASP.NET Core