ViewBag is null on the second page of PagedList in mvc application - asp.net-mvc

I m stuck on this for a while now and will appreciate any help.
The value of ViewBag.SearchTerm is null when I click on the 2 item in the paged list. My List page is present in a partial view (_CentraladdrcdoQuery) as below
#using SFRS.GazMatching.Web.DAL
#model IPagedList<CentraladdrcdoQuery>
#using PagedList;
#using PagedList.Mvc;
<div id="results" class="col-md-10">
<div class="row">
<div class="col-md-4">
<table class="table pull-left table-condensed">
<tr>
<td>
#Html.DisplayNameFor(model => model.First().RecordId)
</td>
</tr>
</table>
</div>
<div class="col-md-4">
<table class="table pull-left table-condensed">
#foreach (var item in Model)
{
<tr>
<td>
#Html.DisplayFor(modelItem => item.RecordId)
</td>
</tr>
}
</table>
</div>
<br />
</div>
<div class="row">
<div class="col-md-4 clearfix">
#Html.PagedListPager(Model, page => Url.Action("Search", new { page, ViewBag.SearchTerm }), new PagedListRenderOptions
{
LinkToFirstPageFormat = "<<",
LinkToPreviousPageFormat = "prev",
LinkToNextPageFormat = "next",
LinkToLastPageFormat = ">>",
})
</div>
</div>
The main search view is
#model IPagedList<CentraladdrcdoQuery>
#{
SearchFormViewModel searchFormViewModel = new SearchFormViewModel();
}
#Html.Partial("_SearchForm",searchFormViewModel)
<h2>Search Results</h2>
#Html.Partial("_CentraladdrcdoQuery", Model)
and the Search Controller action is
public ActionResult Search(string searchTerm, int? page)
{
var centraladdrcdoQuerylst= GetCentraladdrcdoQueryData(searchTerm,page);
ViewBag.SourceList = GetSourceList();
ViewBag.SearhTerm = searchTerm;
return View(centraladdrcdoQuerylst);
}

Related

How to populate data on nav-tab in partial View in MVC?

I have partial View where I have 2 nav-tab. On Each tab, I want to populate data based on Country.
Currently, I am getting following error:
Insufficient stack to continue executing the program safely. This can
happen from having too many functions on the call stack or function on
the stack using too much stack space.
Controller
public ActionResult Index()
{
ClsHome model = new ClsHome();
return View(model);
}
public PartialViewResult EmployeeBasedCountry(int CountryId)
{
ClsHome clshome=new ClsHome();
clshome.Country = CountryId;
clshome.countries = CountryFilter(CountryId);
return PartialView("~/Views/Home/_pEmp.cshtml", clshome);
}
Index View
#model EmpWebsite.Models.Home.ClsHome
<div class="col-md-5">
#Html.Partial("_pEmp")
</div>
Partial View
#model EmpWebsite.Models.Home.ClsHome
<ul class="nav nav-tabs nav-justified">
<li class="active"><a data-toggle="tab" href="#Tab1">India</a></li>
<li><a data-toggle="tab" href="#Tab2" style="width:auto">USA</a></li>
</ul>
<div class="tab-content">
<div id="Tab1" class="tab-pane fade">
#Html.Action("EmployeeBasedCountry", new { #CountryId = "1" })
<div class="panel">
<table class="table-striped">
<tr class="heading">
<th>
EmpId
</th>
<th>
EmpName
</th>
</tr>
#foreach (var item in Model)
{
<tr>
<td>
#item.EmpId
</td>
<td>
<a>#item.EmpName</a>
</td>
</tr>
}
</table>
</div>
</div>
<div id="Tab2" class="tab-pane fade">
#Html.Action("EmployeeBasedCountry", new { #CountryId = "2" })
<div class="panel">
<table class="table-striped">
<tr class="heading">
<th>
EmpId
</th>
<th>
EmpName
</th>
</tr>
#foreach (var item in Model)
{
<tr>
<td>
#item.EmpId
</td>
<td>
<a>#item.EmpName</a>
</td>
</tr>
}
</table>
</div>
</div>
</div>

ASP MVC 5 Post a form from a link

I need to make a custom data grid view with multi column filtering and pagination. so i made a view model winch will encapsulate three class
IEnumerable from the data.
Filter class with some properties
Pager to holder page size, current page, total pages etc ..
Filtering working fine but pagination not :(. as i loose the view model when pressing pagination link "It seems that i need to also submit the search form"
Any one can show how i can submit the form when pressing a link.
here is my view
#model TestFilteringAndPagination.ViewModels.CarViewModel
#{
ViewBag.Title = "Home Page";
}
#*Search form*#
#using (Html.BeginForm("Index", "Home", FormMethod.Post, new { id = "frm" }))
{
#Html.HiddenFor(m => Model.Pager.CurrentPage)
#Html.HiddenFor(m => Model.Pager.PageSize)
#Html.HiddenFor(m => Model.Pager.EndPage)
#Html.HiddenFor(m => m.Pager.StartPage)
<div class="form-inline">
<div class="form-group">
<label>Car No</label>
#Html.EditorFor(x => x.Filter.CarNumber, new { #class = "form-control" })
</div>
<div class="form-group">
<label>Line name</label>
#Html.EditorFor(x => x.Filter.LineName, new { #class = "form-control" })
</div>
<button type="submit" class="btn btn-default">Search</button>
</div>
<ul class="pagination">
#for (var page = Model.Pager.StartPage; page <= Model.Pager.EndPage; page++)
{
<li class="#(page == Model.Pager.CurrentPage ? "active" : "")">
#page
</li>
}
</ul>
}
#*Data grid*#
<table class="table">
<thead>
<tr>
<th>
Car number
</th>
<th>
Car Line
</th>
</tr>
</thead>
<tbody>
#foreach (var car in Model.Cars)
{
<tr>
<td>
#Html.DisplayFor(x => car.CarNumber)
</td>
<td>
#Html.DisplayFor(x => car.LineName)
</td>
</tr>
}
</tbody>
</table>
You can install the PagedList.MVC NuGet Package, see this post for more info about how to create exactly what you want.
Sorting, Filtering, and Paging with the Entity Framework in an ASP.NET MVC Application

HttpPostedFileBase is coming null

below is the code in my View
#using ClaimBuildMVC.Models
#model IEnumerable<Asset>
#{
ViewBag.Title = "AssetsPage";
Layout = "~/Views/Shared/_SuperAdminLayout.cshtml";
}
<script type="text/javascript">
</script>
#using (Html.BeginForm("AssetsPage", "SuperAdmin", FormMethod.Post,new{enctype = "multipart/form-data"}))
{
<div class="Content-inner-pages">
<div class="TopHeading TopHeading2">
<h2>Assets</h2>
<a class="CreateBtn AssetsBtn" href="Javascript:void(0);" onclick="javascript:$('#hdnIsNew').val('1')">Add Asset</a>
<div class="clearfix"></div>
</div>
<input type="hidden" id="hdnIsNew" value="1" />
<input type="hidden" id="hdnRecId" />
<!-- Slide Popup panel -->
<div class="cd-panel from-right AddAssetForm">
<header class="cd-panel-header">
<h3>Add Asset</h3>
Close
</header>
<div class="cd-panel-container">
<div class="cd-panel-content">
<div class="form-horizontal form-details popup-box">
<div class="form-group">
<label class="col-md-5 control-label">
Asset Title
</label>
<div class="col-md-7">
<input type="text" id="txtTitle" name="txtTitle" class="form-control">
</div>
</div>
<div class="form-group">
<label class="col-md-5 control-label">Description</label>
<div class="col-md-7">
<textarea id="txtDesc" class="form-control" cols="5" rows="5"></textarea>
</div>
</div>
<div class="form-group">
<label class="col-md-5 control-label">Attachment</label>
<div class="col-md-7">
<input type="file" id="file" class="custom-file-input">
</div>
</div>
<div class="form-group">
<div class="col-md-7 col-md-offset-5">
<input type="submit" value="Save" name="actionType" class="btn-class btn-success">
</div>
</div>
</div>
</div>
</div>
</div>
<div class="box">
<div class="box-content Custom-DataTable">
<table id="AdministationAssets" class="table table-hover dt-responsive CustomDatable AdministationAssetsTable" cellspacing="0" width="100%">
<thead>
<tr>
<th style="width:5%;">Assets</th>
<th style="width:15%;">
#Html.DisplayNameFor(model =>model.Title)
</th>
<th style="width:50%;">
#Html.DisplayNameFor(model =>model.Description)
</th>
<th style="width:8%;">Options</th>
</tr>
</thead>
<tbody>
#foreach (var item in Model)
{
<tr>
<td></td>
<td>
#Html.DisplayFor(modelItem => item.Title)
</td>
<td>
#Html.DisplayFor(modelItem =>item.Description)
</td>
<td>
#Html.ActionLink("Edit", "AddEditRecord", new{ id = item.ID }, new { #class = "ActionEdit AssetEdit", onclick ="javascript:GetEditDetails(" + item.ID + ");" })
#Html.ActionLink("Delete", "AssetDelete", new{ id = item.ID }, new { #class = "ActionDelete", onclick = "return confirm('Are You Sure delete this record?');", })
</td>
</tr>
}
</tbody>
</table>
</div>
</div>
and below is my controller that what i want to call when click on save button but 'img' is coming as null and after searching in google i found that to add #using(Html.BeginForm()) but still it is coming as null
[HttpPost]
public ActionResult AssetsPage(Asset ast, HttpPostedFileBase file)
{
using (GenericUnitOfWork gc = new GenericUnitOfWork())
{
if (HttpContext.Request.Files.Count > 0)
{
ast.ContainerName = "reports";
ast.BlobName = HttpContext.Request.Files[0].FileName;
ast.BlobUrl = BlobUtilities.CreateBlob(ast.ContainerName, ast.BlobName, null, GetStream(HttpContext.Request.Files[0].FileName));
ast.FileName = HttpContext.Request.Files[0].FileName;
}
gc.GetRepoInstance<Asset>().Add(ast);
gc.SaveChanges();
}
return RedirectToAction("AssetsPage");
}
Not able to find the solution. Please help or give some reference if possible.
Asp.Net MVC default model binding works with name attribute, So add name="file" attribute with input type="file" as shown :-
<input type="file" name="file" id="file" class="custom-file-input">

MVC4 Filtering with checkboxes

I have created create function in my controller which display all genres in checkoxes like this:
Controller:
public ActionResult Create()
{
var db = new MainDatabaseEntities();
var viewModel = new ANIME
{
GENRES = db.GENRES.Select(c => new { ID_GE = c.ID_GE, GENRE = c.GENRE, isSelected = false }).ToList().Select(g => new GENRES
{
ID_GE = g.ID_GE,
GENRE = g.GENRE,
isSelected = false
}).ToList()
};
return View(viewModel);
}
View:
#model AnimeWeb.Models.ANIME
#using (Html.BeginForm(null, null, FormMethod.Post, new { enctype = "multipart/form-data" }))
{
#Html.AntiForgeryToken()
#Html.ValidationSummary(true)
<table>
<tr>
<td class="lefttablecontent" id="top">
<div class="editor-label">
#Html.HiddenFor(model => model.ID_AN)
</div>
<div class="editor-label">
Original title
</div>
<div class="editor-field">
#Html.EditorFor(model => model.TITLE_OR)
#Html.ValidationMessageFor(model => model.TITLE_OR)
</div>
<div class="editor-label">
English title
</div>
<div class="editor-field">
#Html.EditorFor(model => model.TITLE_EN)
#Html.ValidationMessageFor(model => model.TITLE_EN)
</div>
<div class="editor-label">
Genres
</div>
<div class="editor-list">
#Html.EditorFor(model => model.GENRES)
#Html.ValidationMessageFor(model => model.GENRES)
</div>
</td>
<td class="righttablecontent" id="top">
<p>
<input type="submit" value="Create" />
</p>
</td>
</tr>
</table>
}
}
EditorTemplate for Genres:
#model AnimeWeb.Models.GENRES
#Html.HiddenFor(model => model.ID_GE)
#Html.HiddenFor(model => model.GENRE)
<table>
<tr>
<td class=" right">
#Html.EditorFor(model => model.isSelected)
</td>
<td>
#Html.LabelFor(model => model.isSelected, Model.GENRE)
</td>
</tr>
</table>
Now I would like to display the same template with all genres and use it for filtering in index, but I'm not sure how to do this.
Controller:
public ActionResult Index(string sortOrder, string currentFilter, int? page)
{
using (var db = new MainDatabaseEntities())
{
ViewBag.CurrentSort = sortOrder;
if (searchString != null)
{
page = 1;
}
else
{
searchString = currentFilter;
}
ViewBag.CurrentFilter = searchString;
var anime = from s in db.ANIME.Include("GENRES")
select s;
int pageSize = 10;
int pageNumber = (page ?? 1);
return View(anime.ToPagedList(pageNumber, pageSize));
}
}
View:
#model PagedList.IPagedList<AnimeWeb.Models.ANIME>
#using PagedList.Mvc;
<link href="~/Content/PagedList.css" rel="stylesheet" type="text/css" />
#{
ViewBag.Title = "Index";
}
<p>
#if (Roles.IsUserInRole("Administrator"))
{
#Html.ActionLink("Create New", "Create")
}
</p>
#foreach (var item in Model) //
{ //
#Html.EditorFor(modelItem => item.GENRES); // I'm not sure about this line
} //
<table>
<tr>
<th>
Anime
</th>
<th>
</tr>
#foreach (var item in Model) {
<tr>
<td>
#Html.ActionLink(item.TITLE_OR, "Details", new { id = item.ID_AN })
</td>
</tr>
}
</table>
<br />
Page #(Model.PageCount < Model.PageNumber ? 0 : Model.PageNumber) of #Model.PageCount
#Html.PagedListPager(Model, page => Url.Action("Index",
new { page, sortOrder = ViewBag.CurrentSort, currentFilter = ViewBag.CurrentFilter }))
When I try to display it with #Html.EditorFor(modelItem => item.GENRES) it displays only genres that are selected within each anime but I need all genres to filter with them. I'm not even sure is this a good way to make it. Any suggestions?

ASP.NET MVC 4 Model property value lost coming back from Edit view

I have a model with a DateCreated value that is not scaffolded. Coming to GET Edit controller action I see that the model has a correct value that is passed on to the Edit view. Coming back from the view, POST method, the value for DateCreated is DateTime default. It's lost.
Does anyone know why? Controller and View are scaffolded.
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Edit(Product product)
{
try
{
if (ModelState.IsValid)
{
product.DateEdited = DateTime.Now;
db.Entry(product).State = EntityState.Modified;
db.SaveChanges();
return RedirectToAction("Index");
}
}
catch (DataException dex)
{
Console.Write(dex.Message);
ModelState.AddModelError("", reg6.Resources.UnableToSaveChanges);
}
return View(product);
}
#model reg6.Models.Product
#{
ViewBag.Title = "Edit";
}
<h2>Edit</h2>
#using (Html.BeginForm()) {
#Html.AntiForgeryToken()
#Html.ValidationSummary(true)
<fieldset>
<legend>Product</legend>
<table>
<tr>
<td>
<div class="editor-label">
#Html.LabelFor(model => model.Name)
</div>
</td>
<td>
<div class="editor-field">
#Html.EditorFor(model => model.Name)
<div>
#Html.ValidationMessageFor(model => model.Name)
</div>
</div>
</td>
<tr>
<tr>
<td>
<div class="editor-label">
#Html.LabelFor(model => model.Description)
</div>
</td>
<td>
<div class="editor-field">
#Html.EditorFor(model => model.Description)
<div>
#Html.ValidationMessageFor(model => model.Description)
</div>
</div>
</td>
<tr>
<tr>
<td>
<div class="editor-label">
#Html.LabelFor(model => model.BasePrice)
</div>
</td>
<td>
<div class="editor-field">
#Html.EditorFor(model => model.BasePrice)
<div>
#Html.ValidationMessageFor(model => model.BasePrice)
</div>
</div>
</td>
<tr>
<tr>
<td>
<div>
#Html.ActionLink("Back to List", "Index")
</div>
</td>
<td align="right">
<input type="submit" value="Create" id='CreateButton' />
<td>
</tr>
</table>
</fieldset>
}
In your view place a hidden element for the DateCreated
#Html.HiddenFor(m=>m.DateCreated)
All the hidden elements will be posted to the server.

Resources