Views and Razor

Back

Loading concept...

🎨 Views and Razor in ASP.NET MVC

The Art Gallery of Your Web Application


The Big Picture: What Are Views?

Imagine you’re running an art gallery. You have amazing paintings (your data), but you need beautiful frames and walls to display them. That’s exactly what Views do in ASP.NET MVC!

  • Model = The paintings (your data)
  • Controller = The curator who decides what to show
  • View = The gallery walls and frames that display everything beautifully

Views are the face of your application. They turn boring data into beautiful web pages that users actually want to look at!


🪒 Razor Syntax: Your Magic Paintbrush

Razor is a special language that lets you mix C# code with HTML. Think of it as a magic paintbrush that can paint both pictures AND do math at the same time!

The @ Symbol: Your Magic Wand

The @ symbol tells Razor: “Hey! The next thing is C# code, not regular HTML!”

<h1>Hello, @Model.Name!</h1>
<p>Today is @DateTime.Now.ToShortDateString()</p>
<p>2 + 2 = @(2 + 2)</p>

Code Blocks: When You Need More Space

@{
    var greeting = "Welcome!";
    var count = 5;
}
<h1>@greeting</h1>
<p>You have @count messages.</p>

If-Else: Making Decisions

@if (Model.Age >= 18)
{
    <p>You can vote! 🗳️</p>
}
else
{
    <p>Too young to vote.</p>
}

Loops: Repeating Things

<ul>
@foreach (var fruit in Model.Fruits)
{
    <li>@fruit</li>
}
</ul>

🏠 Layouts: The Master Blueprint

Think of a Layout as the blueprint of a house. Every room (page) in the house shares the same walls, roof, and foundation. You only build the unique stuff inside!

Why Layouts Are Awesome

Without layouts, you’d copy-paste the same header, footer, and navigation on EVERY page. That’s like building a new house for every room!

Creating a Layout

File: Views/Shared/_Layout.cshtml

<!DOCTYPE html>
<html>
<head>
    <title>@ViewBag.Title - My App</title>
</head>
<body>
    <header>
        <nav>Home | About | Contact</nav>
    </header>

    <main>
        @RenderBody()
    </main>

    <footer>&copy; 2024 My App</footer>
</body>
</html>

Using a Layout

@{
    Layout = "_Layout";
    ViewBag.Title = "Home";
}

<h1>Welcome Home!</h1>
<p>This goes inside @RenderBody()</p>

Sections: Special Spots

<!-- In Layout -->
<head>
    @RenderSection("Styles", required: false)
</head>

<!-- In View -->
@section Styles {
    <link href="special.css" rel="stylesheet">
}

🧩 Partial Views: Reusable Puzzle Pieces

Imagine you have a LEGO block that you use in many different creations. That’s a Partial View!

Real Example: A Product Card

File: Views/Shared/_ProductCard.cshtml

@model Product

<div class="product-card">
    <img src="@Model.ImageUrl" alt="@Model.Name">
    <h3>@Model.Name</h3>
    <p>$@Model.Price</p>
    <button>Add to Cart</button>
</div>

Using Partial Views

<!-- Method 1: Html.Partial -->
@Html.Partial("_ProductCard", product)

<!-- Method 2: Tag Helper (Modern Way) -->
<partial name="_ProductCard" model="product" />

<!-- Method 3: Async (Best for Performance) -->
@await Html.PartialAsync("_ProductCard", product)

When to Use Partials

  • Navigation menus
  • Product cards
  • Comment sections
  • Sidebars
  • Any repeated UI element!

💪 Strongly Typed Views: No Guessing Allowed!

Imagine ordering pizza by just saying “food please” vs “large pepperoni with extra cheese.” The second one is strongly typed!

The Problem Without Strong Typing

<!-- Dangerous! No IntelliSense, no compile-time checking -->
<h1>@ViewBag.Name</h1>
<p>@ViewBag.Prise</p>  <!-- Typo! Won't catch it! -->

The Solution: @model Directive

@model Product

<!-- Safe! IntelliSense helps you, typos caught at compile -->
<h1>@Model.Name</h1>
<p>$@Model.Price</p>

Benefits

Feature ViewBag Strongly Typed
IntelliSense ❌ No ✅ Yes
Typo Protection ❌ No ✅ Yes
Refactoring ❌ Breaks ✅ Works
Performance Slower Faster

🔧 View Components: Smart Widgets

Think of View Components as smart LEGO blocks that can think for themselves! Unlike partials, they have their own brain (logic).

When to Use View Components

  • Shopping cart widget (needs to count items)
  • Login/logout button (needs to check auth)
  • Recent posts sidebar (needs database)

Creating a View Component

Step 1: The Brain (Logic)

public class CartSummaryViewComponent : ViewComponent
{
    private readonly ICartService _cart;

    public CartSummaryViewComponent(ICartService cart)
    {
        _cart = cart;
    }

    public IViewComponentResult Invoke()
    {
        var items = _cart.GetItems();
        return View(items);
    }
}

Step 2: The Face (View)

File: Views/Shared/Components/CartSummary/Default.cshtml

@model List<CartItem>

<div class="cart-widget">
    🛒 <span>@Model.Count items</span>
</div>

Step 3: Use It!

@await Component.InvokeAsync("CartSummary")

<!-- Or with Tag Helper -->
<vc:cart-summary></vc:cart-summary>

🏷️ Tag Helpers: HTML That Knows C#

Tag Helpers make your HTML smart! Instead of ugly code, you get beautiful, readable HTML that secretly does powerful things.

Before (Ugly)

@Html.ActionLink("Home", "Index", "Home",
    null, new { @class = "nav-link" })

After (Beautiful)

<a asp-controller="Home"
   asp-action="Index"
   class="nav-link">Home</a>

Essential Tag Helpers

Links:

<a asp-controller="Products"
   asp-action="Details"
   asp-route-id="5">View Product</a>

Forms:

<form asp-controller="Account"
      asp-action="Login"
      method="post">

    <label asp-for="Email"></label>
    <input asp-for="Email" />
    <span asp-validation-for="Email"></span>

    <button type="submit">Login</button>
</form>

Images & Links:

<img src="~/images/logo.png"
     asp-append-version="true" />

<link href="~/css/site.css"
      rel="stylesheet"
      asp-append-version="true" />

Common Tag Helpers

Tag Helper Purpose
asp-controller Target controller
asp-action Target action
asp-route-* Route parameters
asp-for Model binding
asp-validation-for Validation
asp-append-version Cache busting

🛠️ Custom Tag Helpers: Build Your Own!

Sometimes the built-in tag helpers aren’t enough. Time to build your own!

Example: Email Link Tag Helper

[HtmlTargetElement("email")]
public class EmailTagHelper : TagHelper
{
    public string Address { get; set; }

    public override void Process(
        TagHelperContext context,
        TagHelperOutput output)
    {
        output.TagName = "a";
        output.Attributes.SetAttribute(
            "href", quot;mailto:{Address}");
        output.Content.SetContent(Address);
    }
}

Usage:

<email address="hello@example.com"></email>

<!-- Renders as: -->
<a href="mailto:hello@example.com">
    hello@example.com
</a>

Example: Condition Tag Helper

[HtmlTargetElement(Attributes = "show-if")]
public class ShowIfTagHelper : TagHelper
{
    public bool ShowIf { get; set; }

    public override void Process(
        TagHelperContext context,
        TagHelperOutput output)
    {
        if (!ShowIf)
        {
            output.SuppressOutput();
        }
    }
}

Usage:

<div show-if="@User.IsAdmin">
    Admin Panel Here
</div>

📬 View Data Passing: Sending Messages

There are several ways to send data from Controller to View. Think of them as different ways to send a package!

1. ViewData (Dictionary)

// Controller
ViewData["Message"] = "Hello!";
ViewData["Count"] = 42;
<!-- View -->
<p>@ViewData["Message"]</p>
<p>Count: @ViewData["Count"]</p>

2. ViewBag (Dynamic)

// Controller
ViewBag.Title = "Welcome";
ViewBag.Items = new[] { "A", "B", "C" };
<!-- View -->
<h1>@ViewBag.Title</h1>
@foreach (var item in ViewBag.Items)
{
    <span>@item</span>
}

3. TempData (One-Time Messages)

// Controller (survives redirect!)
TempData["Success"] = "Item saved!";
return RedirectToAction("Index");
<!-- View -->
@if (TempData["Success"] != null)
{
    <div class="alert">@TempData["Success"]</div>
}

4. Model (Strongly Typed - BEST!)

// Controller
var product = new Product {
    Name = "Laptop",
    Price = 999
};
return View(product);
<!-- View -->
@model Product
<h1>@Model.Name</h1>
<p>$@Model.Price</p>

Comparison Chart

graph TD A["Data Passing Methods"] --> B["ViewData"] A --> C["ViewBag"] A --> D["TempData"] A --> E["Model"] B --> B1["Dictionary&lt;br&gt;No IntelliSense"] C --> C1["Dynamic&lt;br&gt;No IntelliSense"] D --> D1["Survives Redirects&lt;br&gt;One-time use"] E --> E1["Strongly Typed&lt;br&gt;RECOMMENDED ✅"]

When to Use What?

Method Use When
Model Main page data (always preferred)
ViewBag Quick extras like page title
ViewData When you need dictionary access
TempData Success/error after redirect

🎯 Quick Reference Flow

graph TD A["User Request"] --> B["Controller"] B --> C{Prepare Data} C --> D["Pass via Model"] C --> E["Pass via ViewBag"] D --> F["View + Razor"] E --> F F --> G{Uses} G --> H["Layout"] G --> I["Partial Views"] G --> J["View Components"] G --> K["Tag Helpers"] H --> L["Final HTML"] I --> L J --> L K --> L L --> M["User Sees Page"]

🚀 You Did It!

You now understand:

  • Razor Syntax - Mixing C# with HTML
  • Layouts - Master blueprints for pages
  • Partial Views - Reusable UI pieces
  • Strongly Typed Views - Safe, smart views
  • View Components - Smart widgets with logic
  • Tag Helpers - Beautiful, intelligent HTML
  • Custom Tag Helpers - Build your own!
  • Data Passing - ViewData, ViewBag, TempData, Model

You’re now ready to build beautiful, maintainable web pages in ASP.NET MVC! 🎉

Loading story...

Story - Premium Content

Please sign in to view this story and start learning.

Upgrade to Premium to unlock full access to all stories.

Stay Tuned!

Story is coming soon.

Story Preview

Story - Premium Content

Please sign in to view this concept and start learning.

Upgrade to Premium to unlock full access to all content.