Custom paging logic in MVC 4 view with Stored procedures - asp.net-mvc-4

I am returning records from a stored procedure and I want to use custom paging in view. This is what I have so far:
Controller:
public ActionResult Index(int currentPage=1, int PageNo = 1, int PageSize = 10, string SortColumn = "Name", string SortOrder = "Asc", string SearchString = "", int totalRecords=0)
{
DataContextDataContext obj = new DataContextDataContext();
System.Nullable<int> Total = null;
//PageCount = (int)Math.Ceiling((double)Total / PageSize);
var model = obj.TempItemSubClassList(PageNo, PageSize, SortColumn, SortOrder, SearchString, ref Total).ToList();
int PageCount = (int)(Total + PageSize - 1) / PageSize;
StringBuilder sb1 = new StringBuilder();
int seed = currentPage % PageSize == 0 ? currentPage : currentPage - (currentPage % PageSize);
if (currentPage > 0)
sb1.AppendLine(String.Format("Previous", SearchString, currentPage));
if (currentPage - PageSize >= 0)
sb1.AppendLine(String.Format("...", SearchString, (currentPage - PageSize) + 1));
for (int i = seed; i < Math.Round((totalRecords / 10) + 0.5) && i < seed + PageSize; i++)
{
sb1.AppendLine(String.Format("{1}", SearchString, i + 1));
}
if (currentPage + PageSize <= (Math.Round((totalRecords / 10) + 0.5) - 1))
sb1.AppendLine(String.Format("...", SearchString, (currentPage + PageSize) + 1));
if (currentPage < (Math.Round((totalRecords / 10) + 0.5) - 1))
sb1.AppendLine(String.Format("Next", SearchString, currentPage + 2));
//Response.Write(sb1);////can/should I append this to the model?
return View(model);
}
View:
#model IEnumerable<ArtGuildMVC2.Models.TempItemSubClassListResult>
#{
ViewBag.Title = "Index";
}
<h2>Index</h2>
<p>
#Html.ActionLink("Create New", "Create")
</p>
<table>
<tr>
<th>
#Html.DisplayNameFor(model => model.ItemClassId)
</th>
<th>
#Html.DisplayNameFor(model => model.Description)
</th>
<th></th>
</tr>
#foreach (var item in Model) {
<tr>
<td>
#Html.DisplayFor(modelItem => item.ItemClassId)
</td>
<td>
#Html.DisplayFor(modelItem => item.Description)
</td>
<td>
#Html.ActionLink("Edit", "Edit", new { id=item.Id }) |
#Html.ActionLink("Details", "Details", new { id=item.Id }) |
#Html.ActionLink("Delete", "Delete", new { id=item.Id })
</td>
</tr>
}
</table>
/////What do I do hereafter????
#{
if (ViewBag.currentPage > 1) {
First
Prev
}
if (ViewBag.currentPage < ViewBag.Total)
{
Next
Last
}}
How do I implement the paging logic in view?
Thanks in advance.
P.S.: You may not find the code very logical since I have picked it up from 2-3 places and am trying to make it work on trial & error basis.

I would say that you are going to break MVC pattern by the code that you have written in your Action method.
By the way, Paging is a solved problem by some libraries like MvcPaging so, I strongly recommend you using one of them.

Related

Some Items of ViewModel get lost between View and controller

the problem is, that my ViewModel has e.g. 12 items. In the Chrome-Browser i can see (Network--> klick on the postback request --> Headers--> Form Data), that all 12 items have modified values, that i want to save in the controller. But in the controller there are just 9 items that have content arriving. Where are the other three? The Capacity of the Model is 16 but the other items from 9 to 15 are set to null.
How can i find out what happens between the view and controller during the postback?
Update
Ok, now i found out that the ModelState doesnt contains all Items, but the Information will be transfered to the controller in the Request --> Form container. Let see, how the missing items will also be transfered to the ModelState...
ViewModel
public class ViewModel
{
public List<tool.Models.Issue> OpenIssue { get; set; }
public List<tool.Models.Issue> AllIssuesExceptOriginal { get; set; }
public List<tool.Models.Issue> ClosedIssue { get; set; }
public tool.Models.Site Site { get; set; }
public int ID { get; set; }
}
Controller
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Edit( ViewModels.ViewModel ViewModel)
{
//Do something with the content of the ViewModel
}
View (a lot more complex)
#for (int i = 0; i < Model.OpenIssue.Count(); i++)
{
#Html.HiddenFor(modelItem => modelItem.OpenIssue[i].Id);
//a lot more HiddenFor fields
Model.AllIssuesExceptOriginal.Capacity = Model.AllIssuesExceptOriginal.Count;
var History = Model.OpenIssue[i].Histories.Where(p => p.IssueId == Model.OpenIssue[i].Id).OrderByDescending(a => a.LastUpdate).First();
<tr class="Content_table">
<td class="Content_Column">
<div class="Content_all">
<div class="History">#Html.DisplayFor(modelItem => History.Description)</div>
#if( Model.AllIssuesExceptOriginal.Where(p => p.InternalNotes.Replace("Updated:", "") == Model.OpenIssue[i].Id.ToString()).Count() != null)
{
for (int a = 0; a < Model.AllIssuesExceptOriginal.Where(p => p.InternalNotes.Replace("Updated:", "") == Model.OpenIssue[i].Id.ToString()).Except(Model.AllIssuesExceptOriginal.Where(l=>l.LastUpdate == DateTime.MinValue)).Count(); a++)
{
var OtherIssues = Model.AllIssuesExceptOriginal.Where(p => p.InternalNotes.Replace("Updated:", "") == Model.OpenIssue[i].Id.ToString()).Except(Model.AllIssuesExceptOriginal.Where(l=>l.LastUpdate == DateTime.MinValue)).OrderBy(p => p.LastUpdate).ToList();
if(OtherIssues[a].Description != "noUpdate")
{
<div class="updated" style="position:relative" id="#i:#a:Description">
<b>#Html.DisplayFor(modelitem=> OtherIssues[a].User.FirstName) #Html.DisplayFor(modelitem=> OtherIssues[a].User.LastName)</b> <span style="color:grey;">-#Html.ValueFor(modelitem=> OtherIssues[a].LastUpdate, "{0:dd.MM.yy HH:mm}") </span> <br />
#Html.DisplayFor(modelItem => OtherIssues[a].Description, new { #class = "meeting" })
<span style="float:right; "><img src="~/Images/ic_cancel_black_18dp.png" id="Description:#i:#a:#Model.AllIssuesExceptOriginal.FindIndex(p=>p.Id == OtherIssues[a].Id)" onclick="markActiveLinkDelete(this);">
#Html.HiddenFor(modelItem => modelItem.AllIssuesExceptOriginal[Model.AllIssuesExceptOriginal.FindIndex(p=>p.Id == OtherIssues[a].Id)].Description)
</span>
</div>
}
}
}
<div class="updated" >#Html.TextAreaFor(modelItem => modelItem.AllIssuesExceptOriginal[Model.AllIssuesExceptOriginal.FindLastIndex(p=>p.InternalNotes.Replace("Updated:","") == Model.OpenIssue[i].Id.ToString())].Description, new { #class = "meeting" })</div>
#Html.HiddenFor(modelItem=>modelItem.AllIssuesExceptOriginal[Model.AllIssuesExceptOriginal.FindLastIndex(p=>p.InternalNotes.Replace("Updated:","") == Model.OpenIssue[i].Id.ToString())].InternalNotes)
</div>
</td>
}
</table>
</div>
<p>
<input type="submit" value="Save" name = "Save"/>
<input type="submit" value="Cancel" name = "Cancel"/>
</p>
</fieldset>
}
Thanks for your help in advance.
To solve this, i added a Hidden field with the indexer for each item of the Model.
View Updated
#if( Model.AllIssuesExceptOriginal.Where(p => p.InternalNotes.Replace("Updated:", "") == Model.OpenIssue[i].Id.ToString()).Count() != null)
{
for (int a = 0; a < Model.AllIssuesExceptOriginal.Where(p => p.InternalNotes.Replace("Updated:", "") == Model.OpenIssue[i].Id.ToString()).Except(Model.AllIssuesExceptOriginal.Where(l=>l.LastUpdate == DateTime.MinValue)).Count(); a++)
{
var OtherIssues = Model.AllIssuesExceptOriginal.Where(p => p.InternalNotes.Replace("Updated:", "") == Model.OpenIssue[i].Id.ToString()).Except(Model.AllIssuesExceptOriginal.Where(l=>l.LastUpdate == DateTime.MinValue)).OrderBy(p => p.LastUpdate).ToList();
if(OtherIssues[a].Description != "noUpdate")
{
//content
}
//This is new
#Html.HiddenFor(modelItem => modelItem.AllIssuesExceptOriginal[Model.AllIssuesExceptOriginal.FindIndex(p=>p.Id == OtherIssues[a].Id)].Id)
}
}

How display the last n of records in MVC

i am taking last 4 four comments and want to display in the tooltip,
I am doing the below code but its showing the contents like "System.Collection.Generic.List"
var list = db.PO_Prd_Comments.Where(t => t.PO_TrgCal_ID == item.ID && t.Reply == false).OrderByDescending(t => t.PO_TrgCal_ID).Take(4).ToList();
List<string> comments = new List<string>();
if (list.Count != 0)
{
foreach (var ts in list)
{
comments.Add(ts.PrdComment);
if (list.Count == 1)
{
notify = list.SingleOrDefault().notify;
}
else
{
notify = true;
}
}
}
<td>
<a href="#" onclick="popup4(#CountID)" title="#comments"
<img src="~/Images/comment.GIF"/></a>
</td>
How i display these four comments in the tooltip.
comments is a list of string. You need to convert that to a single string and use that as the title property value.
<a href="#" onclick="popup4(#CountID)" title="#String.Join(Environment.NewLine,comments)">
<img src="~/Images/comment.GIF"/>
</a>

Retrieve selected checkboxes in an array into the controller

How can i retrieve the selected checkbox in the controller.
This is the main view where the user can choose a request access.
#using (Html.BeginForm("addBatch_CARF", "CARF", FormMethod.Post, new { #name = "register" }))
{
#Html.ValidationSummary(true)
<div id="formAlert" class="alert alert-danger">
<a class="close">×</a>
<strong>Warning!</strong> Make sure all fields are filled and try again.
</div>
var catName = "";
var displayCan = "";
var candidates = "";
for (int i = 0; i < Model.Count; i++)
{
if (catName != Model[i].request_category)
{
<li class="list-group-item list-group-item-success">
#Html.DisplayFor(modelItem => Model[i].request_category)
<span class="pull-right" style="margin-right:60px;">Special Instructions</span>
</li>
catName = Model[i].request_category;
displayCan = catName;
}
if (displayCan == Model[i].request_category)
{
candidates = Model[i].request_name;
<div class="checkbox_request">
#Html.CheckBoxFor(model => model[i].isSelected, new { #class = "is_selected" })
#Html.DisplayFor(model => model[i].request_name)
#if(Model[i].request_name == "Folder Access")
{
<span class="label label-danger">Pls specify all the drive path. Note: For accessing of drives outside PETC please proceed to Online CARF</span>
}
<span class="pull-right">
#Html.EditorFor(model => model[i].special_instruction)
</span>
#Html.HiddenFor(model => model[i].request_type_id)
#Html.HiddenFor(model => model[i].system_roles_id)
</div>
}
}
<li class="list-group-item list-group-item-success">
Access to:
</li>
<div id="employeeAdd">
#{Html.RenderAction("AddRequestor"); }
</div>
<p class="request_btn">
<button type="submit" class="btn btn-primary" id="addbtn">Save</button>
</p>
}
I have only rendered this view AddRequestor in selecting or adding an employee.
<table class="table table-hover">
#for (int i = 0; i < Model.Count; i++){
<tr>
<th>
#Html.CheckBox("checkbox", new { #class = "is_selected" })
#Html.DisplayFor(model => model[i].FullName)
#Html.HiddenFor(model => model[i].Emp_Badge_No)
</th>
</tr>
}
</table>
The main goal of this is all the chosen employees must have also all the chosen request access.
[HttpPost]
public ActionResult addBatch_CARF(List<Request_Type> list, List<Employees_All_vw> emp, string[] checkboxes)
{
foreach (var x in emp)
{
int num = 1;
bool z = Convert.ToBoolean(num);
if (x.checkbox == z)
{
//add data into CARF table
CARF carf = new CARF();
carf.requestor = x.Emp_Badge_No;
carf.carf_type = "BATCH CARF";
carf.created_by = #User.Identity.Name.Remove(0, 9).ToLower();
carf.created_date = System.DateTime.Now;
carf.active_flag = true;
db.CARves.Add(carf);
db.SaveChanges();
int id = carf.carf_id;
//add data into Request Access Table
foreach (var i in list)
{
int val = 1;
bool y = Convert.ToBoolean(val);
if (i.isSelected == y)
{
Request_Access ra = new Request_Access();
ra.request_access_id = 1;
ra.carf_id = id;
ra.request_type_id = i.request_type_id;
ra.special_instruction = i.special_instruction;
ra.ra_assignee = i.system_roles_id;
ra.dept_approval = null;
ra.dept_approval_date = null;
ra.dept_remarks = null;
ra.final_approval = null;
ra.final_approval_date = null;
ra.final_remarks = null;
ra.acknowledge_by = null;
ra.acknowledge_date = null;
ra.journal = null;
ra.closed_by = null;
ra.closed_date = null;
ra.verified_by = null;
ra.verified_date = null;
db.Request_Access.Add(ra);
}
}
db.SaveChanges();
}
TempData["MessageAlert"] = "Successfully created!";
return RedirectToAction("Batch_CARF");
}
}
I've got an error on this line if (x.checkbox == z)
Operator '==' cannot be applied to operands of type 'string[]' and 'bool'
Your parameter string[] checkboxes contains values that are typeof string (either "True" or "False") so you would need to use the Convert.ToBoolean() method before comparing if (x.checkbox == z). However this will not work since #Html.CheckBox("checkbox", ..) generates 2 inputs type="checkbox" with value="True" and a type="hidden" with value="False" so if its checked, both true and false post back and if its unchecked, then only false is posted. There is no way you can possibly match up which values belong to which employee.
Instead create a view model to represent the selection of employees
public class EmployeeVM
{
public string BadgeNumber { get; set; }
public string Name { get; set; }
public bool IsSelected { get; set; }
}
And then in your AddRequestor() method (assumes you have an Employees table)
public ActionResult AddRequestor()
{
List<EmployeeVM> model = db.Employees.Where(e => e.active_flag).Select(e => new EmployeeVM
{
BadgeNumber = e.Emp_Badge_No,
Name = e.FullName
}.ToList();
return PartialView(model);
}
and in the view
#model List<EmployeeVM>
#for (int i = 0; i < Model.Count; i++)
{
#Html.HiddenFor(m => m[i].BadgeNumber)
<label>
#Html.CheckboxFor(m => m[i].IsSelected)
<span>#Html.DisplayFor(m => m[i].Name)</span>
</label>
}
And finally, in the POST method
[HttpPost]
public ActionResult addBatch_CARF(List<Request_Type> list, List<EmployeesVM> employees)
{
// To get the selected employees
IEnumerable<string> selectedEmployees = employees.Where(e => e.IsSelected);
foreach(EmployeesVM employee in selectedEmployees)
{
....
carf.requestor = employee.BadgeNumber;
....

need help for inserting multiple row data into database using asp.net mvc4

I have done a simple applicaion using ASP.NET MVC4.
I am trying to insert multiple row data into the database.What i have done that is working fine for single row.
Single row is inserted but in multiple row i am getting a problem... the data are not pass from client side to server side (catch by a form collection object )in controller and also loop is not properly working.
my view is:
<table style="width:100%" id="tbldata">
<tr>
<th>Document </th>
<th>Sem/Year(ifapplicable)</th>
<th>File</th>
</tr>
#for (int i = 0; i < 7; i++ )
{
<tr class="document">
<td style="width:40%">#Html.DropDownListFor(m => m.selectdocId, ViewBag.selectdocId as IEnumerable<SelectListItem>,"--Select--", new { #id="docid" +i , #class="Doctype"})</td>
<td style="width:10%">#Html.TextBoxFor(m => m.sem, new { #id="sem" +i, #class="semid"})</td>
<td style="width:40%"><input type="file" multiple="" name="file" value="Browse" /></td>
</tr>
}
</table>
My controller is:
public ActionResult display(FormCollection collection, IEnumerable<HttpPostedFileBase>file )
{
for(int i=0; i<7; i++)
{
int semid = Convert.ToInt32(collection["sem" + i]);
int docid = Convert.ToInt32(collection["docid" + i]);
tbldocumentdetail doc = new tbldocumentdetail();
doc.sem = Convert.ToInt32(semid);
doc.selectdocId = Convert.ToInt32(docid);
db.tbldocumentdetails.Add(doc);
db.SaveChanges();
}
foreach (var item in file)
{
if (item == null && item.ContentLength < 0)
{
ModelState.AddModelError("file", "please uploded your file");
}
else
{
var filename = Path.GetFileName(item.FileName);
var path = Path.Combine(Server.MapPath("~/Content/savedoc"), filename);
item.SaveAs(path);
tbldocumentdetail doc = new tbldocumentdetail();
doc.fileName = filename;
string a = "~/Content/savedoc" + filename;
doc.path = a;
db.tbldocumentdetails.Add(doc);
db.SaveChanges();
}
For this , Instead of using form collection you can use IEnumerable as the POST action parameter. You can refer below link
MVC Form not able to post List of objects

how to upload a image in jsp and store database as blob

<%#page import="java.sql.*" %>
<html>
<form method="get" action="blobexcode.jsp" onsubmit="txtvalidate()">
<head>
<style type="text/css">
body{
background-color:#d0e4fe;
}
</style>
</head>
<body>
<table>
<tr>
<td>
Customer Name <input type="text" name="Customername" id="customername">
</td>
</tr>
<tr>
<td>
Customer Mob: <input type="text" onkeypress="return
isNumberKey(event)" name="Customerphone" id="customerphone" >
</td>
</tr>
<tr>
<td>
Upload File: <input type="file" id="f" name="f" >
</td>
</tr>
<tr>
<td>
<input type="submit" value="SUBMIT" id="submit">
</td>
</tr>
<script type="text/javascript">
function isNumberKey(evt)
{
var charCode = (evt.which) ? evt.which : event.keyCode
if (charCode > 31 && (charCode < 48 || charCode > 57))
return false;
else
return true;
}
</script>
<script type="text/javascript">
function txtvalidate()
{
if(document.getElementById("customername").value=="" ||
document.getElementById("customerphone").value=="")
{
alert("Fill all fields");
return false;
document.Customername.focus();
}
else
return true;
}
</script>
</table>
</body>
</form>
</html>
Read the following article for storing image in db. This example does not use JSP
http://java-x.blogspot.com/2007/01/handling-oracle-large-objects-with-jdbc.html
Once you have understanding of the article stated above you can use commons-file upload to upload the file and retrieve the inputstream of uploaded file and insert it in db.
Refer to following articles for help on file upload
http://commons.apache.org/fileupload/using.html
http://www.theserverside.com/news/1365153/HttpClient-and-FileUpload
Working Example
String saveFile = "";
String contentType = request.getContentType();
if ((contentType != null)
&& (contentType.indexOf("multipart/form-data") >= 0)) {
DataInputStream in = new DataInputStream(
request.getInputStream());
int formDataLength = request.getContentLength();
byte dataBytes[] = new byte[formDataLength];
int byteRead = 0;
int totalBytesRead = 0;
while (totalBytesRead < formDataLength) {
byteRead = in.read(dataBytes, totalBytesRead,
formDataLength);
totalBytesRead += byteRead;
}
String file = new String(dataBytes);
saveFile = file.substring(file.indexOf("filename=\"") + 10);
saveFile = saveFile.substring(0, saveFile.indexOf("\n"));
saveFile = saveFile.substring(saveFile.lastIndexOf("\\") + 1,
saveFile.indexOf("\""));
int lastIndex = contentType.lastIndexOf("=");
String boundary = contentType.substring(lastIndex + 1,
contentType.length());
int pos;
pos = file.indexOf("filename=\"");
pos = file.indexOf("\n", pos) + 1;
pos = file.indexOf("\n", pos) + 1;
pos = file.indexOf("\n", pos) + 1;
int boundaryLocation = file.indexOf(boundary, pos) - 4;
int startPos = ((file.substring(0, pos)).getBytes()).length;
int endPos = ((file.substring(0, boundaryLocation)).getBytes()).length;
File ff = new File(saveFile);
FileOutputStream fileOut = new FileOutputStream(ff);
fileOut.write(dataBytes, startPos, (endPos - startPos));
fileOut.flush();
fileOut.close();
ResultSet rs = null;
PreparedStatement psmnt = null;
FileInputStream fis;
try {
Connection connection = DbConnection.getConnection();
File f = new File(saveFile);
String idd = request.getAttribute("userid").toString();
String insert = "UPDATE `employee` SET `Picture`=? WHERE `id`='"
+ idd + "'";
psmnt = connection.prepareStatement(insert);
fis = new FileInputStream(f);
psmnt.setBinaryStream(1, (InputStream) fis,
(int) (f.length()));
int s = psmnt.executeUpdate();
if (s > 0) {
System.out.println("Uploaded successfully !");
} else {
System.out.println("Error!");
}
} catch (Exception e) {
e.printStackTrace();
}
}