user2185592
user2185592

Reputation: 388

MVC and angular JS in Single page application

I'm writing my first ever Angular application and it will be a single page application. I will be using it along with MVC though. I'm trying to write one sample application with two links but facing problems as described below. I have selected normal MVC project template and following is the code :

_Layout.cshtml

<!DOCTYPE html>
<html data-ng-app="Sample">
<head>
    <meta charset="utf-8" />
    <meta name="viewport" content="width=device-width" />
    <title>@ViewBag.Title</title>
    @Styles.Render("~/Content/css")
    @Scripts.Render("~/bundles/modernizr")
</head>
<body>
    <div class="navbar navbar-inverse navbar-fixed-top">
        <div class="container">
            <div class="navbar-header">
                <button type="button" class="navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse">
                    <span class="icon-bar"></span>
                    <span class="icon-bar"></span>
                    <span class="icon-bar"></span>
                </button>
                @Html.ActionLink("Application name", "Index", "Home", new { area = "" }, new { @class = "navbar-brand" })
            </div>
            <div class="navbar-collapse collapse">
                <ul class="nav navbar-nav">
                    <li>@Html.ActionLink("Home", "Index", "Home", new { area = "" }, null)</li>
                    <li>@Html.ActionLink("API", "Index", "Help", new { area = "" }, null)</li>
                    <li><a href="Link1">Link 1</a></li>
                    <li><a href="Link2">Link 2</a></li>
                </ul>
            </div>
        </div>
    </div>
    <div class="container body-content"  data-ng-view>
        @RenderBody()
        <hr />
        <footer>
            <p>&copy; @DateTime.Now.Year - My ASP.NET Application</p>
        </footer>
    </div>

    @Scripts.Render("~/bundles/jquery")
    @Scripts.Render("~/bundles/bootstrap")
    @RenderSection("scripts", required: false)

    <script src="~/Scripts/angular.min.js"></script>
    <script src="~/Scripts/angular-route.min.js"></script>
    <script src="~/MyScripts/Module.js"></script>
    <script src="~/MyScripts/LinkController.js"></script>
</body>
</html>

HomeController

    public ActionResult Index()
    {
        ViewBag.Title = "Home Page";

        return View();
    }

    public ActionResult Link1()
    {
        return PartialView("_Link1");
    }

    public ActionResult Link2()
    {
        return PartialView("_Link2");
    }

_Link1.cshtml (_Link2.cshtml similar only)

@{
    Layout = null;
}
<p>This is link 1 page</p>

Module.js (for angular)

var app = angular.module("Sample");

//The Factory used to define the value to
//Communicate and pass data across controllers

app.factory("ShareData", function () {
    return { value: 0 }
});

//Defining Routing
app.config(['$routeProvider','$locationProvider', function ($routeProvider,$locationProvider) {
    $routeProvider.when('/Link1',
                        {
                            templateUrl: 'Home/Link1',
                        });
    $routeProvider.when('/Link2',
                        {
                            templateUrl: 'Home/Link2',
                        });
    $routeProvider.otherwise(
                        {
                            redirectTo: '/'
                        });
   // $locationProvider.html5Mode(true);
    $locationProvider.html5Mode(true).hashPrefix('!')
}]);

So with above code in place, I'm facing following issues :

  1. When I press on "Link1" anchor item on my page, it is not routing to "Link1" route and hit break point inside "Link1" method of my mvc controller. However, if I write "Home/Link1" in browser then it hits the controller method. So how I could fix this i.e. Pressing on "Link1" directly open up the Link1 view?

  2. When I press, "AppURL/Home/Link1" in browser it does open up the "Link1" view, however it totally replaces the previous view (i.e. with menu bar and footer). What I want is I want to retain the layout (i.e. menu bar and footer) and load the partial view inside "RenderBody" area.

Can anyone correct above code and get me started with my first app?

Upvotes: 2

Views: 2538

Answers (1)

Chris Story
Chris Story

Reputation: 1197

As a person who was where you are when I first started learning Angular, I can help you with this request; but also, save you some heartache and give you some advice. The advice is to not mix Microsoft MVC routing with AngularJS routing for page routing. If anything, use MVC for your first landing page; however, from there, use AngularJS for your client side templates and leave MVC (or preferably WebAPI) to give the data to your client. Use the server side component to marshall data and AngularJS to let the use navigate through the application.

Here is a good sample for what I would suggest doing at a Microsoft shop using AngularJS - http://www.asp.net/web-api/overview/getting-started-with-aspnet-web-api/build-a-single-page-application-(spa)-with-aspnet-web-api-and-angularjs

Upvotes: 1

Related Questions