Add form to layout - asp.net-mvc

I need to add a login popup to the header of every page, so naturally I want to add it to the layout as a partial view.
The problem is, the layout doesnt have a pagemodel.
We do use a BasePageModel that every page inherits from, where I can add 2 strings for username/password. But how would the layout see those fields?

You can specify a model for the Layout page just as you would a standard content page:
#model BasePageModel
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
...
Then your properties are accessible via the Model property of the Layout page. The BasePageModel will also be passed to any partials that you add to the layout (unless you specify a different model for the partial), so you can also access the properties in those.

I need to add a login popup to the header of every page, so naturally
I want to add it to the layout as a partial view.
According to your description, I do a demo for that situation. But I don’t use a BasePageModel that every page inherits from.
The demo as below, hoping it can help you.
1.Add a Login page with page model, and post method
Login.cshtml.cs:
public class LoginModel : PageModel
{
[BindProperty]
public string Username { get; set; }
[BindProperty]
public string Password { get; set; }
public string Msg { get; set; }
public void OnGet()
{
}
public IActionResult OnPost(string Username, string Password)
{
//do your other things...
return Page();
}
}
Login.cshtml:
#page
#model Login.Pages.LoginModel
#{
}
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width" />
<title>Login</title>
</head>
<body>
<h3>Login Form</h3>
#Model.Msg
<form method="post" asp-page="Login">
<table>
<tr>
<td>Username</td>
<td><input type="text" asp-for="#Model.Username" /></td>
</tr>
<tr>
<td>Password</td>
<td><input type="password" asp-for="#Model.Password" /></td>
</tr>
<tr>
<td> </td>
<td><input type="submit" value="Login" /></td>
</tr>
</table>
</form>
</body>
</html>
Add the login form in the layout. Using name attribute: change input type="text" asp-for="#Model.Username" into input type="text" name="Username"
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<link rel="stylesheet" href="~/lib/bootstrap/dist/css/bootstrap.min.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">
<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-page="/Index">Home</a>
</li>
<li class="nav-item">
<a class="nav-link text-dark" asp-area="" asp-page="/Privacy">Privacy</a>
</li>
</ul>
</div>
<div>
<fieldset>
<div class="container">
<div class="row">
<div class="col-xs-12">
<button id="btnShowModal" type="button"
class="btn btn-sm btn-default pull-left col-lg-11 button button4">
login
</button>
<div class="modal fade" tabindex="-1" id="loginModal"
data-keyboard="false" data-backdrop="static">
<div class="modal-dialog modal-lg">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal">
×
</button>
</div>
<div class="modal-body">
<form method="post" asp-page="Login">
<table border="0" cellpadding="2" cellspacing="2">
<tr>
<td>Username</td>
<td><input type="text" name="Username"></td>
</tr>
<tr>
<td>Password</td>
<td><input type="password" name="Password"></td>
</tr>
<tr>
<td> </td>
<td><input type="submit" value="Login"></td>
</tr>
</table>
</form>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</fieldset>
</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 - Login - <a asp-area="" asp-page="/Privacy">Privacy</a>
</div>
</footer>
<script src="~/lib/jquery/dist/jquery.min.js"></script>
<script src="~/lib/bootstrap/dist/js/bootstrap.bundle.min.js"></script>
<script src="~/js/site.js" asp-append-version="true"></script>
#await RenderSectionAsync("Scripts", required: false)
<script type="text/javascript">
$(document).ready(function () {
$("#btnShowModal").click(function () {
$("#loginModal").modal('show');
});
$("#btnHideModal").click(function () {
$("#loginModal").modal('hide');
});
});
</script>
</body>
</html>
Results:

Related

(MVC) I have a search bar in my shared _Layout. It works from other Views but not in the _Layout

Basically what the title says. I have a view named books in which the search bar works perfectly and gives results. This is not happening in the _Layout shared view. I've tried several scripts and stuff but to no avail. Any advice?
This is the _Layout
<!DOCTYPE html>
#model IEnumerable<GoodReads.Models.Libro>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<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("Nombre de aplicación", "Index", "Home", new { area = "" }, new { #class = "navbar-brand" })
</div>
<div class="navbar-collapse collapse">
<ul class="nav navbar-nav">
<li>#Html.ActionLink("Inicio", "Index", "Home")</li>
<li>#Html.ActionLink("Registrar Turno", "AltaTurno", "Turno")</li>
<li>#Html.ActionLink("Buscar Libros", "Books", "Libro")</li>
<li>
#using (Html.BeginForm(FormMethod.Get))
{
<div>
#Html.TextBox("parametro")
<input type="submit" id="btnSearch" value="Some text"/>
</div>
}
</li>
</ul>
</div>
</div>
</div>
<div id="Books">
</div>
<div class="container body-content">
#RenderBody()
<hr />
<footer></footer>
</div>
#Scripts.Render("~/bundles/jquery")
#Scripts.Render("~/bundles/bootstrap")
#RenderSection("scripts", required: false)
</body>
</html>
This is the Books view
#model IEnumerable<GoodReads.Models.Libro>
#{
/**/
ViewBag.Title = "Books";
}
<head>
<link href="#Url.Content("~/Content/Style.css")" rel="stylesheet" type="text/css" />
</head>
<body>
#foreach (var item in Model)
{
<div style="margin-left: 350px; margin-top: 50px;">
<h1 class="title-font">
#item.Title
<small class="year-font">(#item.Year)</small>
</h1>
</div>
<div style="margin-left: 350px; margin-top: 10px;">
<p style="font-size: 22px;">by #item.Author</p>
</div>
<div style="margin-left: 350px; margin-top: 10px;">
<p style="font-size: 22px;">#item.ISBN</p>
</div>
}
</body>
The Controller for Books (The conection to the database is made through instead of doing it directly in the controller)
// GET: Libro
public ActionResult Index()
{
return View();
}
public ActionResult Books(string parametro)
{
List<Libro> listalibros = ADLibros.BuscarLibro(parametro);
return View(listalibros);
}
The problem is your form. You don't set its action. If you don't tell it it will use the default which is the controller that renders the page. So when your Books controller renders the page this works because the default controller will be the books controller. You need to specify the action of your get form explicitly. To see the problem use your browser developer tools to inspect the form for the books page and the other pages.
To fix (assuming your controller for books is called BooksController) change the form code in your _Layout page to this
#using (Html.BeginForm("books", "books", FormMethod.Get))
{
<div>
#Html.TextBox("parametro")
<input type="submit" id="btnSearch" value="Some text" />
</div>
}
We are using an overload of Html.BeginForm with 3 arguments. The first is the actionName, the second is the controllerName and the 3rd is the FormMethod.

mvc) I wanna get list of player in my listplayer view

namespace Seoyoung_K_301000618.Model
{
public class Repository
{
private static List<Player> addplayers = new List<Player>();
public static IEnumerable<Player> Players
{
get
{
return addplayers;
}
}
public static void AddPlayer(Player player)
{
addplayers.Add(player);
}
}
}
I have an error >> InvalidOperationException: The model item passed into the ViewDataDictionary is of type 'Seoyoung_K_301000618.Model.Player', but this ViewDataDictionary instance requires a model item of type 'System.Collections.Generic.IEnumerable`1[Seoyoung_K_301000618.Model.Player]'.
I want to add player name and ID in listplayer view but I can't.
I want to fix my code like if player choose "Yes, I will", the player name and ID will be added to listplayer.
Here is my "manage" code (join page)
#model Seoyoung_K_301000618.Model.Player
#{
Layout = null;
}
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width" />
<title>Join us</title>
<link rel="stylesheet" href="~/lib/bootstrap/css/bootstrap.min.css" />
<link href="~/css/style.css" rel="stylesheet" />
</head>
<body>
<header>
<nav class="navbar navbar-expand-md navbar-cheerful fixed-top bg-dark">
<a class="navbar-brand disabled" href="/Home/Index">
<img src="~/images/logo.png" width="50" height="50" />
</a>
<button class="navbar-toggler" type="button"
data-toggle="collapse" data-target="#navbarCollapse" id="btnNavigation"
aria-expanded="false">
<i class="fa fa-caret-down" style="color:#feb0cc"></i>
</button>
<div class="collapse navbar-collapse" id="navbarCollapse">
<ul class="navbar-nav mr-auto" style="text-align:center">
<li class="nav-item active">
<a class="nav-link" href="/Home/Index">Home</a>
</li>
<li class="nav-item">
<a class="nav-link" href="/Home/club">More Information</a>
</li>
<li class="nav-item">
<a class="nav-link" href="/Home/Manage">Join</a>
</li>
</ul>
</div>
</nav>
</header>
<main role="main">
<div class="album py-5">
<div class="container">
<div class="col-md-12">
<div class="col-md-4"> </div>
<div class="col-md-4"> </div>
<h1>Join us!</h1>
<hr />
<form class="p-a-l" asp-action="RsvpForm" method="Post">
<div asp-validation-summary="All"></div>
<div class="form-group">
<label asp-for="Name">Your name:</label>
<input class="form-control" asp-for="Name" />
</div>
<div class="form-group">
<label asp-for="Email">Your ID</label>
<input class="form-control" asp-for="Email" />
</div>
<div class="form-group">
<label asp-for="Phone">Your Password</label>
<input class="form-control" asp-for="Phone" />
</div>
<div class="form-group">
<label asp-for="WillJoin">Will you join?</label>
<select class="form-control" asp-for="WillAttend">
<option value="">Choose an option</option>
<option value="true">Yes, I want</option>
<option value="false">No, I don't want</option>
</select>
</div>
<div class="text-center">
<button class="btn btn-primary" type="submit">Register</button>
</div>
</form>
</div>
</div>
</div>
</main>
<footer class="container">
<p>© 2020 Seoyoung - Centennial College - COMP229.</p>
</footer>
<script src="~/js/jquery.min.js"></script>
<script>window.jQuery || document.write('<script src="~/js/jquery.min.js"><\/script>')</script>
<script src="~/lib/bootstrap/js/bootstrap.bundle.min.js"></script>
</body>
</html>
Here is my Homecontroller code
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Seoyoung_K_301000618.Model;
namespace Seoyoung_K_301000618.Controllers
{
public class HomeController : Controller
{
[HttpPost]
public ViewResult Manage(Player player)
{
if (ModelState.IsValid)
{
Repository.AddPlayer(player);
return View("ListPlayer", player);
}
else
{
return View();
}
}
[HttpGet]
public ViewResult Manage()
{
return View();
}
public ViewResult ListPlayer()
{
return View(Repository.Players.Where(r => r.WillJoin == true));
}
public ViewResult Index()
{
return View();
}
public ViewResult Club()
{
return View();
}
}
}
And, Here is my listplayer code (the player information will be added here)
#model IEnumerable<Seoyoung_K_301000618.Model.Player>
#{
Layout = null;
}
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width" />
<title>List of Player</title>
<link rel="stylesheet" href="~/lib/bootstrap/css/bootstrap.min.css" />
<link href="~/css/style.css" rel="stylesheet" />
</head>
<body>
<header>
<nav class="navbar navbar-expand-md navbar-cheerful fixed-top bg-dark">
<a class="navbar-brand disabled" href="/Home/Index">
<img src="~/images/logo.png" width="50" height="50" />
</a>
<button class="navbar-toggler" type="button"
data-toggle="collapse" data-target="#navbarCollapse" id="btnNavigation"
aria-expanded="false">
<i class="fa fa-caret-down" style="color:#feb0cc"></i>
</button>
<div class="collapse navbar-collapse" id="navbarCollapse">
<ul class="navbar-nav mr-auto" style="text-align:center">
<li class="nav-item active">
<a class="nav-link" href="/Home/Index">Home</a>
</li>
<li class="nav-item">
<a class="nav-link" href="/Home/club">More Information</a>
</li>
<li class="nav-item">
<a class="nav-link" href="/Home/Manage">Join</a>
</li>
</ul>
</div>
</nav>
</header>
<main role="main">
<div class="album py-5">
<div class="container">
<div class="col-md-12">
<div class="col-md-4"> </div>
<div class="col-md-4"> </div>
<h1>Here is the list of player</h1>
<hr />
</div>
</div>
<table class="table table-sm table-striped table-bordered">
<thead>
<tr>
<tr>
<th>Name</th>
<th>ID</th>
</tr>
</thead>
<tbody>
#foreach (Seoyoung_K_301000618.Model.Player addplayers in Model)
{
<tr>
<td>#addplayers.Name</td>
<td>#addplayers.Id</td>
</tr>
}
</tbody>
</table>
</div>
</main>
<footer class="container">
<p>© 2020 Seoyoung - Centennial College - COMP229.</p>
</footer>
<script src="~/js/jquery.min.js"></script>
<script>window.jQuery || document.write('<script src="~/js/jquery.min.js"><\/script>')</script>
<script src="~/lib/bootstrap/js/bootstrap.bundle.min.js"></script>
</body>
</html>
The listplayer view looks like that
namespace Seoyoung_K_301000618.Model
{
public class Repository
{
private static List<Player> addplayers = new List<Player>();
public static IEnumerable<Player> Players
{
get
{
return addplayers;
}
}
public static void AddPlayer(Player player)
{
addplayers.Add(player);
}
}
}
You made a mistake here
if (ModelState.IsValid)
{
Repository.AddPlayer(player);
//you have return single player object
return View("ListPlayer", player);
}
Right Code
if (ModelState.IsValid)
{
Repository.AddPlayer(player);
Repository.SaveChanges();
return RedirectToAction("ListPlayer");
}

How to dynamically change a section of a view using the onChange event of a g:select tag?

I'm having a hard time figuring out how to essentially reload a section of my view with new data after a selection from a DropDownMenu(in grails 3.3.9)
I've tried using the same convention of a button in grails, which is pretty straight forward:
<g:select class="btn bg-primary" action="filterByCommittee" controller="management"
from="${Committee.list()}" optionKey="id" optionValue="${name}"
name="committees" value="${committees}" noSelection="${['null':'Select..']}"/>
the code above means(AFAIK) i want to trigger an action(filterByCommittee) which resides in a controller(Management), using params.committees(the name of the field). the mentioned action would filter the purchases(a list shown to the user) by the selected committee.
any help would be greatly appreciated!
some relevant code:
class ManagementController {
PurchaseService purchaseService
CommitteeService committeeService
def index(Integer max) {
params.max = Math.min(max ?: 10, 100)
List<Purchase> purchaseList = Purchase.findAllByAccountantApprovalInList(Approval.findAllByApproved(true))
}
respond purchaseList, model:[purchaseCount: purchaseService.count()]
}
def filterByCommittee() {
Committee selectedCommittee = Committee.findByName(params.committees)
List<User> userList = User.findAllByCommittee(selectedCommittee)
List<Purchase> purchaseList = Purchase.findAllByUserInList(userList)
respond purchaseList, model:[purchaseCount: purchaseService.count()]
}
}
class Committee {
String name
static hasMany = [users:User, summaries:Summary]
static constraints = {
users(nullable: true)
summaries(nullable: true)
}
#Override
public String toString() {
return name
}
}
<!DOCTYPE html>
<!--<%# page import="attainrvtwo.Committee" contentType="text/html;charset=UTF-8" %>-->
<html xmlns:g="http://www.w3.org/1999/html">
<body>
<g:message code="default.link.skip.label" default="Skip to content…"/>
<div class="nav" role="navigation">
<ul>
<li><g:select class="btn bg-primary" action="filterByCommittee" controller="management" from="${Committee.list()}" optionKey="id" optionValue="${name}" name="committees" value="${committees}" noSelection="${['null':'Select..']}"/></li>
</ul>
</div>
<div id="list-purchase" class="content scaffold-list" role="main">
<h1><g:message code="default.list.label" args="[entityName]" /></h1>
<g:if test="${flash.message}">
<div class="message" role="status">${flash.message}</div>
</g:if>
<f:table collection="${purchaseList}" />
<div class="pagination">
<g:paginate total="${purchaseCount ?: 0}" />
</div>
</div>
</body>
</html>
In gsp file, on select (fill "" with the corresponding values):
<g:select id="" name="" value="" from='${}' optionKey="id"
onchange="optionChanged(this.value);" >
</g:select>
<div id="tabla" style="display:block;"></div>
In same gsp file:
<script>
function optionChanged(committeeId) {
<g:remoteFunction controller="management" action="filterByCommittee"
update="tabla" params="'commId='+committeeId"/>
}
</script>
In another gsp file name="filterByCommittee.gsp":
Code to display
In the controller add the id param to the function:
def filterByCommittee(commId)
the solution i pieced together looks something like this:
in the ManagementController
package attainrvtwo
class ManagementController {
CommitteeService committeeService
List<Purchase> purchaseList
def filterByCommittee() {
session.filterPurchases = true
Committee selectedCommittee = committeeService.get(params.id)
List<User> userList = User.findAllByCommittee(selectedCommittee)
purchaseList = Purchase.findAllByUserInList(userList)
respond purchaseList, model:[purchaseCount: purchaseService.count()]
}
}
in the index.gsp file of management view
<!DOCTYPE html>
<!--<%# page import="attainrvtwo.Committee" contentType="text/html;charset=UTF-8" %>-->
<html xmlns:g="http://www.w3.org/1999/html">
<head>
<meta name="layout" content="main" />
<g:set var="entityName" value="${message(code: 'purchase.label', default: 'Purchase')}" />
<title></title>
</head>
<body>
<g:message code="default.link.skip.label" default="Skip to content…"/>
<div class="nav" role="navigation">
<ul>
<!-- <li><a class="home" href="${createLink(uri: '/volunteer/index')}"><g:message code="default.home.label"/></a></li>-->
<li><g:select class="btn bg-primary" id="commDDLid" name="committeeDDL" action="filterByCommittee" controller="management" from="${Committee.list()}" optionKey="id" optionValue="${name}" value="${committees}" noSelection="${['null':'Select..']}" onchange="goToPage(this.value)"/></li>
</ul>
</div>
<div id="list-purchase" class="content scaffold-list" role="main">
<h1><g:message code="default.list.label" args="[entityName]" /></h1>
<g:if test="${flash.message}">
<div class="message" role="status">${flash.message}</div>
</g:if>
<f:table collection="${purchaseList}" />
<div class="pagination">
<g:paginate total="${purchaseCount ?: 0}" />
</div>
</div>
<script type="text/javascript">
function goToPage(requestParams) {
window.location.href="${'/management/filterByCommittee'}" + "/" + requestParams;
}
</script>
</body>
</html>
then i've also added the filterByCommitty.gsp view which is basically a copy of my index.gsp
(notice the import line at the beginning and the script tag at the end)
<!DOCTYPE html>
<!--<%# page import="attainrvtwo.Committee" contentType="text/html;charset=UTF-8" %>-->
<html xmlns:g="http://www.w3.org/1999/html">
<head>
<meta name="layout" content="main" />
<g:set var="entityName" value="${message(code: 'purchase.label', default: 'Purchase')}" />
<title></title>
</head>
<body>
<g:message code="default.link.skip.label" default="Skip to content…"/>
<div class="nav" role="navigation">
<ul>
<li><g:select class="btn bg-primary" id="commDDLid" name="committeeDDL" action="filterByCommittee" controller="management" from="${Committee.list()}" optionKey="id" optionValue="${name}" value="${committees}" noSelection="${['null':'Select..']}" onchange="goToPage(this.value)"/></li>
</ul>
</div>
<div id="list-purchase" class="content scaffold-list" role="main">
<h1><g:message code="default.list.label" args="[entityName]" /></h1>
<g:if test="${flash.message}">
<div class="message" role="status">${flash.message}</div>
</g:if>
<f:table collection="${purchaseList}" />
<div class="pagination">
<g:paginate total="${purchaseCount ?: 0}" />
</div>
</div>
<script type="text/javascript">
function goToPage(requestParams) {
window.location.href="${'/management/filterByCommittee'}" + "/" + requestParams;
}
</script>
</body>
</html>
i hope this helps someone.
if there are any improvement suggestions i'd be glad to correct them.
cheers ;)

Knockout: foreach not working with asp.net mvc

I know this might be easy but somehow I'm unable to implement foreach for a knockout binding. The code is as below:
#{
Layout = "~/Views/Shared/_Layout.cshtml";
}
#section scripts
{
<script type="text/javascript">
ko.applyBindings({
people: [
{ firstName: 'Bert', lastName: 'Bertington' },
{ firstName: 'Charles', lastName: 'Charlesforth' },
{ firstName: 'Denise', lastName: 'Dentiste' }
]
});
</script>
}
<div>
<table>
<thead>
<tr><th>First name</th><th>Last name</th></tr>
</thead>
<tbody data-bind="foreach: people">
<tr>
<td data-bind="text: firstName"></td>
<td data-bind="text: lastName"></td>
</tr>
</tbody>
</table>
</div>
And the rendered HTML is as follows:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title> - My ASP.NET Application</title>
<link href="/Content/bootstrap.css" rel="stylesheet"/>
<link href="/Content/site.css" rel="stylesheet"/>
<script src="/Scripts/modernizr-2.6.2.js"></script>
</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>
<a class="navbar-brand" href="/">Application name</a>
</div>
<div class="navbar-collapse collapse">
<ul class="nav navbar-nav">
<li>Home</li>
<li>About</li>
<li>Contact</li>
</ul>
</div>
</div>
</div>
<div class="container body-content">
<div>
<table>
<thead>
<tr><th>First name</th><th>Last name</th></tr>
</thead>
<tbody data-bind="foreach: people">
<tr>
<td data-bind="text: firstName"></td>
<td data-bind="text: lastName"></td>
</tr>
</tbody>
</table>
</div>
<hr />
<footer>
<p>© 2014 - My ASP.NET Application</p>
</footer>
</div>
<script src="/Scripts/jquery-1.10.2.js"></script>
<script src="/Scripts/bootstrap.js"></script>
<script src="/Scripts/respond.js"></script>
<script src="/Scripts/knockout.debug.js"></script>
<script src="/Scripts/knockout.mapping-latest.debug.js"></script>
<script src="/Scripts/knockout.js"></script>
<script src="/Scripts/knockout.mapping-latest.js"></script>
<script type="text/javascript">
ko.applyBindings({
people: [
{ firstName: 'Bert', lastName: 'Bertington' },
{ firstName: 'Charles', lastName: 'Charlesforth' },
{ firstName: 'Denise', lastName: 'Dentiste' }
]
});
</script>
</body>
</html>
The problem is that the foreach doesn't work as implemented in the code. The error I get is (debugged using Knockout context):
ExtensionError: TypeError message: "Object.getOwnPropertyNames called
on non-object" stack: (...) get stack: function () { [native code] }
set stack: function () { [native code] }
proto: Error info: "Please select a dom node with ko data."
Uncaught TypeError: undefined is not a function
I have trying this for a while now but with no success.
Thanks.
So I solved it!
The problem was that knockout 2.0 has a line of code:
var elems = jQuery['clean']([html]);
But the jQuery 1.10 that I was using deprecated the clean method.
So I upgraded my knockout to 3.0 and it worked!
Thanks to #Boaz for answering this question on stackoverflow

Why does my partial view not working?

I created a partial view and I use this partial to another view that it inherit from a _layout m code is true and doesn't have a bug, but when I click on submit it shows this message : (The resource cannot be found). I can't trace this error . please help me . thanks
This is my news.Cshtml:
#model MPortal.Models.WebSite_OpinionDB
#{
Layout = "~/Views/Shared/_Layout.cshtml";
}
#section Body{
#Html.Partial("CreateOpinion")
#Html.Action("CreateOpinion", "User")
}
And this is my _Layout.cshtml :
<html>
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width" />
<title>#ViewBag.Title</title>
<link href="~/Theme/css/bootstrap.css" rel="stylesheet">
<link href="~/Content/CssFramework.css" rel="stylesheet" />
#RenderSection("CSS", required: false)
</head>
<body>
#RenderSection("Body", required: false)
<script src="~/Scripts/jquery-1.7.1.min.js"></script>
<script src="~/Scripts/modernizr-2.5.3.js"></script>
<script src="~/Theme/js/bootstrap.js"></script>
#RenderSection("scripts", required: false)
</body>
</html>
And this is my Partialview :(CreateOpinion.cshtml)
#model MPortal.Models.WebSite_OpinionDB
#section Body{
<div class="" style="float: right; width: 75%">
#Html.Raw(Session["Right"])
#using (Html.BeginForm())
{
<div class="rateit" style="float: right; width: 25%">
<input type="text" maxlength="100" value="name" class="form-control" name="Values" id="NameFamily" />
<br />
<input type="text" maxlength="100" value="email" class="form-control" name="Values" id="Email" />
<br />
#Html.TextAreaFor(x => x.OpinionText, new { #class = "form-control", #placeholder = "opinion" })
<br />
<button class="btn btn-primary" type="submit">submit</button>
</div>
}
<div class="" style="width: 20%; height: 625px; border: 1px solid black; float: left">
#Html.Raw(Session["Left"])
</div>
</div>
<div class="" style="float: right; width: 75%">
#if (ViewData["Success"] != null)
{
<div class="alert alert-success alert-dismissable">
<button aria-hidden="true" data-dismiss="alert" class="close" type="button">×</button>
#(ViewData["Success"] != null ? ViewData["Success"].ToString() : "")
</div>
}
#if (ViewData["UnSuccess"] != null)
{
<div class="alert alert-danger bs-alert-old-docs">
<button aria-hidden="true" data-dismiss="alert" class="close" type="button">×</button>
#(ViewData["UnSuccess"] != null ? ViewData["UnSuccess"].ToString() : "")
</div>
}
</div>
}
and this is my action of partial view :
[ChildActionOnly]
public ActionResult CreateOpinion(MPortal.Models.WebSite_OpinionDB saveop, FormCollection frm)
{
if (!string.IsNullOrEmpty(frm["Values"]))
{
int mtID = (int)MPortal_CL.Globals.GetParam("MetaDataID", 0);
MPortal.Models.WebSite_OpinionDB op = new MPortal.Models.WebSite_OpinionDB();
String[] texts = frm["Values"].Split(',');
.....
.......
}
Remove attribute [ChildActionOnly] and if this does not work please use the overloaded version
#using (Html.BeginForm("CreateOpinion","ControllerName"))

Resources