Display columns headers on each page inside a PDF document using ItextSharp in MVC - asp.net-mvc

I've been using this guide to create PDF reporting:
http://www.codeproject.com/Articles/260470/PDF-reporting-using-ASP-NET-MVC3
Basically I have a form that once it's submitted, It creates and opens a PDF report
the report is actually a view, for example this one:
#using MvcReportGeneratorDemo.Models
#model CustomerList
<br />
<table cellpadding="3" cellspacing="3">
`<tr border="1" bgcolor="#777777" color="#ffffff">`
<td>Name</td>
<td>Address</td>
<td>Place</td>
</tr>
#foreach (Customer customer in Model)
{
<tr border="1">
<td>#customer.Name</td>
<td>#customer.Address</td>
<td>#customer.Place</td>
</tr>
}
</table>
I want that each page in the PDF will have columns headers, not just the first one.
tried google but found nothing relevant.

You can use the following code at server side to solve your problem.
using (StringReader sr = new StringReader(html))
{
foreach (IElement el in iTextSharp.text.html.simpleparser.HTMLWorker.ParseToList(sr, null))
{
if (el is PdfPTable)
{
((PdfPTable)el).HeaderRows = 1;
}
doc.Add(el);
}
}

Related

if condition in the razor syntax for HTML table- MVC

I have a HTML table with 2 rows and 4 columns. The data in each cell is coming from the stored proc. Currently, the last column displays number, I have an image to display, but it has to be displayed only if(rejected_question>0) else it should not display anything. How do I accomplish this in razor.
I have tried this so far, the below code doesn't work:
#foreach (var item in Model)
{
//logic for first three columns..
//fourth column here.
<td align="center">
if(#Html.DisplayFor(modelItem => item.RejectedQuestion) >0)
{
return Html.Raw(string.Format("<text><img height='3' width='3' src="\{0}\" alt="\Image\" /></text>", Url.Content("../../content/images/icon_red_questions_returnedbyreviewer.gif")));
}
</td>
}
This is what your looking for, probably:
#foreach (var item in Model)
{
//logic for first three columns..
//fourth column here.
<td align="center">
#if(item.RejectedQuestion > 0)
{
<img height="3" width="3" alt="Image"
src="#Url.Content("~/content/images/icon_red_questions_returnedbyreviewer.gif")" />
}
</td>
}
Make the line inside the if statement
#Html.Raw(string.Format("<text><img height='3' width='3' src="\{0}\" alt="\Image\" /></text>", Url.Content("../../content/images/icon_red_questions_returnedbyreviewer.gif")))
to display it. view.Execute() returns void, so you cannot include a return statement.
I tried this and it worked, just in case if someone needs it in future
:
#if(item.RejectedQuestion > 0)
{
<img height="20" width="20" alt="Image"
src="#Url.Content("~/content/images/icon_red_questions_returnedbyreviewer.gif")" />
}

MVC foreach statement

Im new with MVC.
I have a model called UAV.
│Callsign│NumDeliveries│Mileage│MaxVelocity│MinVelocity│
 Hawk61   37    96    20     10
 BURL14   2047     57     30     15
 OTTO93   82    72    25     10
in cshtml file, i made a table only using Callsign, NumDeliveries, Mileage.
<table class="UAV_table" id="UAV_table">
<tr>
<th>Callsign</th>
<th>NumDeliveries</th>
<th>Mileage</th>
</tr>
#foreach (UAV uav in Model.UAVs)
{
<tr onclick="click_row()">
<td onclick="click_row()">
#Html.DisplayFor(modelItem => uav.Callsign)
</td>
<td>
#Html.DisplayFor(modelItem => uav.NumDeliveries)
</td>
<td>
#Html.DisplayFor(modelItem => uav.Mileage)
</td>
</tr>
}
</table>
 so the table shows all datas for Callsign, NumDeliveries, Mileage.
what i want to do is, when i click the row of the table, i want to see only that correspond information.
#foreach (UAVs uavid in Model.uavs)
{
<p class="detail_title" id="detail_title">
UAV: # (#Html.DisplayFor(modelItem => uavid.MaxVelocity))
</p>
}
for example, using above line of code, if i click first row of that table(callsign = Hawk61), i want to see like UAV: # 20 (MaxVelocity for Hawk61). MaxVelocity is not in the table, so i need to get it from database.
But I have problem with showing data. If i use right above code, it has #foreach statement, it shows all the Hawk61, BURL14, OTTO93's MaxVelocity.
it shows me like
UAV:# 20
UAV:# 30
UAV:# 25
I need to see only what i selected. (just shows what i click, in this example, only need to show UAV:# 20 which is first row, Hawk61's MaxVelocity).
is there any way to get the data from database not using foreach statement?
Thank you.
Since the values of MaxVelocityand MinVelocity are populated, you can make use of data- attributes to store the values in the DOM and use jquery to display them. For example
#foreach (UAV uav in Model.UAVs)
{
<tr class="uavrow" data-maxvelocity="#uav.MaxVelocity" data-minvelocity="#MinVelocity">
<td>#Html.DisplayFor(modelItem => uav.Callsign)</td>
<td>#Html.DisplayFor(modelItem => uav.NumDeliveries)</td>
<td>#Html.DisplayFor(modelItem => uav.Mileage)</td>
</tr>
}
And include some elements to display the associated data when you click on the row
<div>
<div><span>Call Sign: </span><span id="callsign"></span>
<div><span>Max Velocity: </span><span id="maxvelocity"></span>
<div><span>Min Velocity: </span><span id="minvelocity"></span>
</div>
And the script
$('.uavrow').click(function) {
// Get the call sign for the td element
$('#callsign').text($(this).children('td').eq(0).text());
// Get the velocity from the data attributes
$('#maxvelocity').text($(this).data('maxvelocity'));
$('#minvelocity').text($(this).data('minvelocity'));
});
If however the value were not populated, or you have a large number of properties to display, then it may be better to make an ajax call to a method (passing the callsign) which returns a partial view containing the details
<div id="uavdetails"></div>
$('.uavrow').click(function) {
var callSign = $('#callsign').text($(this).children('td').eq(0).text());
var url = '#Url.Action("Details", "YourController")';
$('#uavdetails').load(url, { CallSign: callsign });
});
Controller
public ActionResult Details(string CallSign)
{
UAV uav = // Get the UAV base on the CallSign value
return PartialView(uav);
}
Actually you have all data that you need in there.
The only thing that you need is to show proper item by using JavaScript.
You need to add parameter to your function call here:
<tr onclick="click_row('#uav.Callsign')">
And also add css class here:
#foreach (UAVs uavid in Model.uavs)
{
<p class="detail_title #uavid.Callsign" id="detail_title" style="display=none;">
UAV: # (#Html.DisplayFor(modelItem => uavid.MaxVelocity))
</p>
}
And then add a bit of javascript:
<script>
function click_row(elClass){
var elements = document.getElementsByClassName("detail_title");
for (i = 0; i < x.length; i++) {
if(x[i].className.contains(elClass)){
x[i].style.display = 'block';
} else{
x[i].style.display = 'none';
}
}
};
<script/>

Kendo grid MVC number link column sorting

I have a Kendo grid on a MVC .cshtml view page:
#model IEnumerable<Models.GetItems>
<script>
$(document).ready(function () {
$("#grid").kendoGrid({
sortable: true
});
});
</script>
<table class="table" id="grid">
<thead>
<tr>
<th data-field="Quantity">
Qty
</th>
</tr>
</thead>
<tbody>
#foreach (var item in Model)
{
<tr>
<td>
#Html.ActionLink(item.Quantity.ToString(), "kendo", "Groups", new { ID = item.ID }, null)
</td>
</tr>
}
</tbody>
</table>
It displays the way I want; as a number with a link to a drill down page, but the sorting doesn't work at all.
How can I tell the grid I want the data type to be a number so it can sort it like a number?
(item.Quantity is Int16 from the model, but had to make it a string for the ActionLink to work)
(I'm open to binding the grid differently if I have to (bind to json output from controller and/or use rowTemplate and/or bind to empty div and define columns in JS possibly with template), but not sure at this point if that will matter, seems like a data type issue regardless of binding method???)

Showing a dynamic table in GSP where column & data comes at run time

getting two arrays from controller and code is --
Sql db = new Sql(dataSource_wldb1) // Create a new instance of groovy.sql.Sql with the DB of the Grails app
def ivrColumns = []
db.eachRow(ivrColumnsQuery) {
rsRow ->
ivrColumns.add(rsRow.name) }
def ivrResults = []
db.eachRow(mssqlQuery) {rows ->
//print rows
ivrResults.add(rows)
}
one has all column names & other has all row data.as below-
return render(view:'xref',model:[ivrcolumns:ivrColumns,ivrresults:ivrResults] )
getting data in below format-
Columns
[ClientKey, Abbr, ConfigKey, Federal, State, DMA, Internal, Wireless, CRssing, CurfewExemption, CampaignID]
Data
[groovy.sql.GroovyResultSetExtension#12f8d75, groovy.sql.GroovyResultSetE
oovy.sql.GroovyResultSetExtension#12f8d75, groovy.sql.GroovyResultSetExtension#1
roovyResultSetExtension#12f8d75, groovy.sql.GroovyResultSetExtension#12f8d75, gr
tSetExtension#12f8d75, groovy.sql.GroovyResultSetExtension#12f8d75, groovy.sql.G
ion#12f8d75, groovy.sql.GroovyResultSetExtension#12f8d75]
view code is---
<g:if test="${ivrcolumns != null }">
<center>Database Location - WLDB1 <br>DB Name - IVR_GUARDIAN </center><br><br>
<table class="table loadTable" >
<thead>
<tr bgcolor="#f0f0f0" >
<g:each in="${ivrcolumns}" status="ii" var="columnivr">
<td nowrap>${columnivr}</td>
</g:each>
</tr>
</thead>
<tbody>
<g:each in="${ivrresults}" status="jj" var="hed">
<tr>
<g:each in="${ivrcolumns}" status="kk" var="col">
<td nowrap>${hed.col}</td> ///please suggest how to do it.
</g:each>
</tr>
</g:each>
</tbody>
</table>
now want to show in GSP page .i am able to display the column but having hard time to display data.not getting how the dot will be used to get correct data to each column.
Will appreciate any help.
thanks
Assuming that's just a sql result, you can just call ${ hed[ col ] } or ${ hed."$col" }

Form not submitting and no error is being produced with MVC

I have a form in my MVC application that in theory should submit data back to my database using a Repository class.
However, when I submit the form (http://localhost:1028/Admin/NewUser/), the URL changes to where the form should be submitting to, which is fine (http://localhost:1028/Admin/NewUser/Submit), but once it has been submitted, it should send the user to a confirmation page.
From what I can tell, I'm moving through all my pages correctly until it comes to the submit, where it displays the form again but under /Admin/NewUser/Submit and the data is not inserted into the database.
This is the ActionResult I'm using:
Public Function Submit() As ActionResult
Try
Dim user = New hdUser() With { _
.userLogon = Request.Form("UserLogin"), _
.userPass = Request.Form("UserPassword"), _
.userEmail = Request.Form("UserEmail"), _
.RealName = Request.Form("UserFullName"), _
.isLive = 1, _
.avatar = "noavatar.gif" _
}
userRepository.Add(user)
userRepository.Save()
Return Redirect("/Admin/NewUser/Confirm")
Catch ex As Exception
ModelState.AddModelError("Error", ex)
End Try
Return View()
End Function
I'm fairly new to MVC so I'm not entirely sure if the above is correct or not.
And in my data repository class UserRepository.vb, the two functions I'm using are:
Public Sub Add(ByVal user As hdUser) Implements IUserRepository.Add
db.hdUsers.InsertOnSubmit(user)
End Sub
and
Public Sub Save() Implements IUserRepository.Save
db.SubmitChanges()
End Sub
And the form I have created is:
<form action="/Admin/NewUser/Submit" method="post">
<table border="0" cellpadding="0" cellspacing="2">
<tr>
<td><strong>User's Full Name</strong> <br />
<%=Html.TextBox("UserFullName")%>
</td>
</tr>
<tr>
<td><strong>User Login</strong> <br />
<%=Html.TextBox("UserLogin")%>
</td>
</tr>
<tr>
<td><strong>Password</strong> <br />
<%=Html.Password("UserPassword")%>
</td>
</tr>
<tr>
<td><strong>Email Address</strong> <br />
<%=Html.TextBox("UserEmail")%>
</td>
</tr>
<tr>
<td align="right"><input type="submit" value="Create" /></td>
</tr>
</table>
</form>
The code doesn't produce any errors but also doesn't seem to be submitting to the database. So I'm not entirely sure where I've gone wrong.
It could be obvious to someone more experienced, but I really haven't a clue on this one.
Is this my code that's causing the issue or some other fault?
Thanks in advance for any help.
EDIT: Based on Zhaph - Ben Duguid comment, I have made the following edits:
AdminController.vb
<AcceptVerbs(HttpVerbs.Post)> _
Public Function NewUser(ByVal formValues As FormCollection) As ActionResult
Try
Dim user = New hdUser()
user.userLogon = Request.Form("UserLogin")
user.userPass = Request.Form("UserPassword")
user.userEmail = Request.Form("UserEmail")
user.RealName = Request.Form("UserFullName")
user.isLive = 1
user.avatar = "noavatar.gif"
UpdateModel(user)
userRepository.Add(user)
userRepository.Save()
Catch ex As Exception
ModelState.AddModelError("Error", ex)
End Try
Return View()
End Function
NewUser.aspx
<%Html.BeginForm()%>
<%=Html.ValidationMessage("Error")%>
<table border="0" cellpadding="0" cellspacing="2">
<tr>
<td><strong>User's Full Name</strong> <br />
<%=Html.TextBox("UserFullName")%>
<%=Html.ValidationMessage("Name", "*")%></td>
</tr>
<tr>
<td><strong>User Login</strong> <br />
<%=Html.TextBox("UserLogin")%>
<%=Html.ValidationMessage("Username", "*")%></td>
</tr>
<tr>
<td><strong>Password</strong> <br />
<%=Html.Password("UserPassword")%>
<%=Html.ValidationMessage("Password", "*")%></td>
</tr>
<tr>
<td><strong>Email Address</strong> <br />
<%=Html.TextBox("UserEmail")%>
<%=Html.ValidationMessage("Email", "*")%></td>
</tr>
<tr>
<td align="right"><input type="submit" value="Create" /></td>
</tr>
</table>
<% Html.EndForm() %>
Which now produces an error of The value '' is invalid. for me.
Does this mean that form values aren't being passed correctly to the controller?
EDIT: I've made those edits in response Zhaph - Ben Duguid's edit and I've changed the Form elements to the DB field names (for testing at least). And now, when the page is submitted Name, Login and Email are all filled, password is blank (which I'm assuming is expected behaviour as per password boxes) but I still receive the "The value '' is invalid" error.
Response.Write in your controller isn't going to do anything to the view.
You should be returning your model back to the edit page, with any errors in
ModelState.AddModelError();
There's a very good example of how you can implement a Repository pattern, and take advantage of the ASP.NET MVC model binding features, etc in the NerdDinner Chapter from the Professional ASP.NET MVC book.
An example controller I have (in c# I'm afraid) based on the Nerd Dinner samples:
//
// POST: /AdminAlbums/Create
[AcceptVerbs(HttpVerbs.Post)]
public ActionResult Create(FormCollection collection)
{
var album = new Album();
// Method on System.Web.Mvc.Controller, that takes a form collection, and
// using reflection on the Model, assigns values to it from the form.
UpdateModel(album);
if (album.IsValid)
{
// These methods are the same as yours
m_PhotoRepository.Add(album);
m_PhotoRepository.Save();
// In this instance, I'm returning the user to a list view of Albums
// for editing, probably ought to send them to the page to start
// uploading photos.
return RedirectToAction("Index");
}
// Still here, so I'm going to set up some ViewData I need.
ViewData["Title"] = "Create a new album";
ViewData["Message"] = "Create Album";
// I'm picking up errors from the model here.
// RuleViolation is my own class, implemented in a partial on Album.
foreach (RuleViolation violation in album.GetRuleViolations())
{
ModelState.AddModelError(violation.PropertyName, violation.ErrorMessage);
}
return View(album);
}
So you can see I return the model back to the main view if there's an error, to populate the Validation summary.
The relevant part of the view is:
<%= Html.ValidationSummary("Edit was unsuccessful. Please correct the errors and try again.") %>
<% using (Html.BeginForm()) {%>
<fieldset>
<legend>Album details</legend>
<div class="form_row">
<label for="Caption" class="left_label">Album caption:</label>
<%= Html.TextBox("Caption", Model.Caption, new { #class = "textbox" })%>
<%= Html.ValidationMessage("Caption", "*") %>
<div class="cleaner"> </div>
</div>
<div class="form_row">
<label for="IsPublic" class="left_label">Is this album public:</label>
<%= Html.CheckBox("IsPublic", Model.IsPublic) %>
</div>
<div class="form_row">
<input type="submit" value="Save" />
</div>
</fieldset>
<% } %>
Edit in response to question edit
Sorry, I should have clarified:
A lot of this is based on using the Helper methods provided by the ASP.NET MVC framework - you'll notice that I'm using methods like Html.TextBox to generate my fields, with their name/id pulled from the model itself. This way, if I load the view with ModelErrors in the ModelState, the helper will add the relevant details to rendered HTML to include the following mark-up
<label for="Caption" class="left_label">Caption:</label>
<input class="input-validation-error textbox"
id="Caption" name="Caption" type="text" value="" />
<span class="field-validation-error">*</span>
The other option you could have would be to add a message to the ViewData collection, and if it has a value, display that on your view.
Edit in response to question edit
A couple of things to bear in mind:
1) The identifiers of the Form elements and the Validation controls should be the same:
<%= Html.TextBox("Caption", Model.Caption, new { #class = "textbox" })%>
<%= Html.ValidationMessage("Caption", "*") %>
(you have things like "UserEmail" and "Email")
2) You should be returning the hdUser to the view on error - so try something like this:
<AcceptVerbs(HttpVerbs.Post)> _
Public Function NewUser(ByVal formValues As FormCollection) As ActionResult
Dim user = New hdUser()
Try
UpdateModel(user)
user.isLive = 1
user.avatar = "noavatar.gif"
userRepository.Add(user)
userRepository.Save()
Catch ex As Exception
ModelState.AddModelError("Error", ex)
End Try
Return View(user)
End Function

Resources