ASP.NET - Read Component Parameter In Razor View - c#

I have an existing ASP.NET app that uses one Razor component throughout. Unfortunately, this component does not have a model associated with it. I'm in a scenario where I need to add one parameter. At this time, I have the following in the component host view:
#await Component.InvokeAsync("MyTextField", new { Align = "Left" })
The component Razor code currently looks like this:
MyTextField.cshtml
<div class="text-right">
<form asp-action="ReadItem" asp-controller="Inventory" method="get" id="inventory-form">
<input id="inputField" class="input-text" type="text" />
<button class="submit-button" type="submit">Submit</button>
</form>
</div>
Currently, the component renders. However, I want to get the value of the Align parameter, if it exists, in the MyTextField.cshtml view. Is there a way for me to get a parameter value there? If so, how?
Thanks

You can do that in this way:
#await Component.InvokeAsync("MyTextField", new User{ Align = "Left" })
and in View (cshtml file):
#using UserNamespace
#model User
<div class="text-right">
<form asp-action="ReadItem" asp-controller="Inventory" method="get" id="inventory-form">
<input id="inputField" class="input-text" type="text" value="#Model.Align" />
<button class="submit-button" type="submit">Submit</button>
</form>
</div>

Related

Razor Pages POST Multiple Forms w/ Model Binding

I have multiple forms on a single razor page that I want to be POSTed after one button is clicked. I tried using a javascript function that would .submit() both forms (put in the onclick= of the button), but only one form's values were actually passed to the OnPost() method serverside. Here's the relevant code from the .cshtml and the .cs files:
StudentMain.cshtml
<!--first form-->
<form class="login100-form" method="post">
<span class="login100-form-title" style="padding-bottom: 38px">
Student Information
</span>
<div class="wrap-input100">
<input class="input100 has-val" type="text" name="name" value='#ViewData["name"]' readonly/>
<span class="focus-input100" data-placeholder="Student Name"></span>
</div>
...more divs/inputs as above
</form>
<!--second form-->
<form class="login100-form" method="post">
<div class="wrap-input100">
<select class="input100 select" name="eduplan" selectedval='#ViewData["eduplan"]'>
<option disabled selected value style="display:none"/>
<option>High School Diploma</option>
<option>Technical Training</option>
<option>Associate Degree</option>
<option>Bachelor's Degree</option>
<option>Advanced Degree</option>
<option>Military</option>
<option>Other</option>
</select>
<span class="focus-input100" data-placeholder="Education Plan"></span>
</div>
...more divs/selects as above
<div class="container-login100-form-btn">
<div class="wrap-login100-form-btn">
<div class="login100-form-bgbtn"></div>
<button class="login100-form-btn" type="submit">
Save
</button>
</div>
</div>
</form>
StudentMain.cshtml.cs
public class StudentMain : PageModel
{
public void OnPost(string eduplan, string college, string major, string careerpath, string ethnicity, string gender, string ncaa, string firstgen, string onlineinterest)
{
Database.SaveStudentData(eduplan, college, major, careerpath, ethnicity, gender, ncaa, firstgen, onlineinterest);
}
}
So, what's the best way to go about doing this? How can I make sure that the values from both forms are passed to the OnPost() method simultaneously? Do I need to use AJAX in some capacity? Any help is appreciated.
You can use different methods for different form POSTs by specifying the method's name as the value for the asp-page-handler tag helper on each form. More information can be found on this Youtube Video
UPDATE
For example, you have two POST methods in your Model class, namely: OnPostAdd and OnPostSubtract, the different forms to post to the different methods would look like this:
<form method="post" asp-page-handler="Add">
<button type="submit">Add</button>
</form>
<form method="post" asp-page-handler="Subtract">
<button type="submit">Subtract</button>
</form>
PS: It doesn't matter whether your method is named OnPostAdd or OnPostAddAsync, ASP.NET Core still expects your handler name to be Add as it automatically resolves prefixes like OnPost, OnGet etc, and suffixes like Async

How to transfer data to the controller from view outside the form or dont create new input

I'm writing an application in asp.net core 2.0.
I have some data that I send to the controller from the view but I also have data that I want to pass to the same controller but they are not in the form.
It is possible to pass this data to the same controller and I do not have to create new inputs.
How to pass data to the controller from outside the form or in form but without creating new inputs.
I have two variables #Model.MinUppercase ,#Model.MinLowercase but I do not use them in the form, how can I pass them to the controller together with variables from the form?
#model Project2.Models.UserModel
<h1>Step2: Register</h1>
<div>
#if (#ViewData["Message"] != null)
{
<div class="alert alert-danger space text-center">
#ViewData["Message"]
</div>
}
#Model.MinUppercase
#Model.MinLowercase
<center>
<h2>Register form:</h2>
</center>
<div>
<form asp-action="Middle" asp-controller="Home" method="POST" class="form-wrapper">
<div class="input-group">
<label>Login:</label>
<input id="Login" asp-for="Login" type="text" class="input" size="35">
</div>
<div class="input-group">
<label>Password:</label>
<input id="Password" asp-for="Password" type="Password" class="input" size="35">
</div>
<div class="input-group">
<label>Your Regex Description:</label>
<input id="Description" asp-for="Description" type="text" class="input" size="35" value=#Model.Description>
</div>
<div class="input-group">
<label>Your Regex:</label>
<input id="Reg" asp-for="Reg" type="text" class="input" size="35" value=#Model.Reg>
</div>
<div class="input-group">
<a asp-controller="Home" asp-action="CreateRegex">
<button type="button" class="btn btn-danger">Back</button>
</a>
<button class="btn btn-success">Create</button>
</div>
</form>
</div>
Inside your form html content add hidden fields (using razor helper #Html.Hidden/For):
#Html.Hidden("MyName", "Carlos")
or
#Html.HiddenFor(i => i.PropertyOfYourModel) - if is some property of your model.
As carlosfcmendes already answered you can add data with hidden fields.
Or if you want to be more flexible you can intercept the form submit and add data.
There are plenty of answers here on how to do that:
Intercept form, add data, ajax, then submit.
How can I listen to the form submit event in javascript?

How to check in razor view if field is valid?

I use bootstrap with ASP.NET Core and to indicate form field validation errors i want to add has-errors class to form-group div when given field has an error. The view looks like that:
<div class="form-group">
<label asp-for="Fragment.Content" class="col-lg-2 control-label "></label>
<div class="col-lg-10">
<textarea asp-for="Fragment.Content" class="form-control content-editor"></textarea>
<span class="help-block">A longer block of help text that breaks onto a new line and may extend beyond one line.</span>
<span asp-validation-for="Fragment.Content"></span>
</div>
</div>
I would like to do something like:
<div class="form-group" asp-add-class-if-error="has-errors" for-field="Fragment.Content"/>
I know i can write my own tag helper, however i am curious if there is a built-in solution.
I found that you can use:
#using Microsoft.AspNetCore.Mvc.ModelBinding
#if(ViewData.ModelState.GetFieldValidationState("Fragment.Content") == Microsoft.AspNetCore.Mvc.ModelBinding.ModelValidationState.Invalid)
{
// something here
}

Form post to another page

I am fairly new to C# and asp.net and am having trouble showing something submitted in a form. The form element is a tag. The drop-down info is pulled from a data base and displays correctly. It's just getting it to post to another page after the form is submitted is where I am having the problem. Any help would be appreciated.
Contact.aspx:
<form action="Default.aspx" method="post" data-transition="pop">
<div data-role="fieldcontain">
<label for="topEmails">Business Entity ID:</label>
<select name="topEmails" id="topEmails" data-native-menu="false"
runat="server">
</select>
</div>
<input type="submit" data-iconpos="right" data-inline="true"
data-icon="plus" name="sendMessage" id="sendMessage" value="Send Info">
</form>
Contact.aspx.cs:
AdventureWorks2012DataContext db = new AdventureWorks2012DataContext();
var emails = (from b in db.EmailAddresses
select new { b.EmailAddressID, b.BusinessEntityID }).Take(20);
topEmails.DataTextField = "BusinessEntityID";
topEmails.DataValueField = "BusinessEntityID";
topEmails.DataSource = emails;
topEmails.DataBind();
Default.aspx.cs:
FormSuccessBID.InnerHtml = "Business Entity ID: " + Request.Form["topEmails"] + "";
Any ideas why this wouldn't be working?
Update:
Contact.aspx:
<asp:Content runat="server" ID="BodyContent" ContentPlaceHolderID="MainContent">
<h2 style="text-align: center;">Contact Kyle</h2>
<form action="Default.aspx" method="post" data-transition="pop">
<div data-role="fieldcontain">
<label for="userFName">First Name:</label>
<input type="text" name="firstName" id="uFName">
</div>
<div data-role="fieldcontain">
<label for="userLName">Last Name :</label>
<input type="text" name="lastName" id="uLName">
</div>
<div data-role="fieldcontain">
<label for="productsCategories">Products:</label>
<select name="productCategories" id="productCategories" data-native-menu="false" runat="server"></select>
</div>
<div data-role="fieldcontain">
<label for="topEmails">Business Entity ID:</label>
<select name="topEmails" id="topEmails" data-native-menu="false" runat="server"></select>
</div>
<input type="submit" data-iconpos="right" data-inline="true" data-icon="plus" name="sendMessage" id="sendMessage" value="Send Info">
</form>
</asp:Content>
You're missing "runat='server'" in your form definition.
In ASP.NET you're also allowed one form per page. Not sure from what you're posted if you're trying to put multiple forms on there, but if you are, it's not going to work.
I think all you need to do to accomplish what you want is have an ASP.NET button on the page, with the postbackURL set to the page you want to go to. (Of course, you need to do this in a server-side form)
I think you're mixing ASP.NET methods with other, different technologies. (From the look of it, you probably used classic ASP or PHP perhaps?)
If you can't use .NET for whatever reason, the ID/name of the field is not going to be what you're expecting. You need to inspect the form post and find its value - something along the lines of "clt00_somethingelse_topEmails". (Again, this is going to be a heck of a lot easier if you use the .NET way of doing things, but you may have a requirement not to)

Adding <form> tags around form disables Razor code from filling in input elements

I am creating an edit form for an Event data model in which the input elements are populated with the Event properties for editing. After I finished populating the fields and formatting the page, I realised I had forgotten the form tags. After adding them in, my Razor code completely stops working, leaving all of the input elements empty. I have tried disabling various parts of the code, including all javascript and css and nothing seems to re-populate the fields except removing the form tags.
Here is the code:
#model Objects.Models.Event.Event
#using EventSignup.Extensions
#{
ViewBag.Title = "Edit";
}
<script src="#Url.Content("~/Scripts/jquery-ui-1.8.22.min.js")" type="text/javascript"></script>
<link href="#Url.Content("~/Content/themes/base/jquery.ui.all.css")" rel="stylesheet" type="text/css" />
<script src="#Url.Content("~/Javascript/jquery-ui-timepicker-addon.js")" type="text/javascript"></script>
<script src="#Url.Content("~/Javascript/Edit.js")" type="text/javascript" ></script>
<h2>Edit</h2>
<div class="hero-unit">
<form action="" id="event_form" method="post">
<label for="name">Event Name:</label>
<input type="text" name="name" id="name" value="#Model.EventName" /><br />
<label for="tickets"># of Tickets:</label>
<input type="text" name="tickets" id="tickets" value="#Model.Tickets" /><br />
<label for="location">Location:</label>
<select name="location" id="location">
#foreach (var Element in ViewBag.Buildings as List<EventSignup.ViewModels.SelectElement>)
{
<option value="#Element.ID" #((Model.TicketsLocation.ID == #Element.ID) ? "selected='selected'" : "")>#Element.DisplayName</option>
}
</select><br />
<label for="dates">Dates/Times:</label>
#foreach (var EventInfo in Model.Dates)
{
<input type="text" class="date" name="dates" id="dates#(Model.Dates.IndexOf(EventInfo)+1)" value="#EventInfo.DateTime.ToDateTimePickerString()"/><br />
if (EventInfo != Model.Dates.Last())
{
<label></label>
}
}
<div id="date_inputs">
</div>
<label></label>
<span id="new_date" class="fauxlink" onclick="newDate()">New Date/Time</span><br /><br />
<input type="hidden" id="num_dates" value="#Model.Dates.Count" />
<input type="submit" id="submit" value="Submit" /><br />
</form>
</div>
Don't use form elements directly - use the BeginForm HTML helper:
#using (Html.BeginForm())
{
}
You should also be using the template editors for the different model properties:
#Html.EditorFor(model => model.EventName)
Update:
I normally find that Visual Studio/Razor will stop working (no intellisense for instance) if the markup is not valid (missing " at the end of an attribute, elements that are not properly closed etc...). Check your markup carefully to see where your have such an error.
You should consider using Asp.net mvc 3 helpers to build your forms instead of regular html tags, and build your form based on the Model. This also encodes your form input and allows you to verify AntiFrogery token:
#using (Html.BeginForm("actionhere", ..other arguments))
{
#Html.DropDownFor(x => x.ModelProperty, Model.List);
}

Categories

Resources