I have an Action result that returns a list
public ActionResult GetData(Profiles profiles)
{
Vertical Vdata = new Vertical();
List<Ver> Vertical = new List<Ver>();
//Code to fill list
return View(Vertical);
}
And then a partial view to display the List
#model IEnumerable< List<VerticalContainer.Models.Vertical>>
#foreach(var item in Model)
{
<span>#item.name</span>
}
I'm not sure how to render the partial view from my main view
#Html.Action("GetData")??
What do I pass with the Html.Action? or Should I use Partial/RenderPartial?
1- the correct way to render actions is as per the following:
#Html.RenderAction("ACTION_NAME","CONTROLLER_NAME")
where you replace both action name and controller name with the correct values according to your solution.
2- For the passed model, if this action is being rendered inside a view that has a Model property of Profiles
, then you don't have to specify the model to be passed to the action, as it will implicitly read it from the parent view.
if this is not the case, then you will need to store your Profiles values inside a medium variable (for example inside a ViewBag property) and then you will pass it when calling the action, so it should work on this passed model istead of working on the parent view one.
example: #Html.RenderAction("ACTION_NAME","CONTROLLER_NAME", YOUR_MODEL_VALUE_HERE)
Suggestion: if this parital view will just render the list passed, you can skip creating the mentioned action, and just make a call which can render the partial view, passing to it the correct list so it can work with.
To make it more clear, using your question I can see that the action named GetData is just constructing the list called Vertical from the Profiles model passed, so you can construct this list in your original action (Index, Details, WHAT_EVER_THE_NAME_IS) and store it in a ViewBag, then you can call RenderParial instead of RenderAction and this should result in the same output as your mentioned scenario.
example: #{ Html.Partial("ViewName", YOUR_MODEL_HERE);}
#{Html.RenderAction("actionName","controllerName");}
From your main view, you may simply render your Partial view as:
#Html.Partial("_PartialViewName", VerticalList);
VerticalList in this case will be the list of type VerticalContainer.Models.Vertical, that you populated in controller action.
Related
I have 2 action methods(a and b) and 2 views(a and b).
These action methods are having different models. Now I want to show view-b in view-a along with view-a. I don't want to use viewModel.
please help me!!
Put this in View A:
#Html.Action("ActionBName", "ActionBControllerName", new { area = string.Empty })
And in Controller for ViewB:
[ChildActionOnly]
public ActionResult ActionBName()
{
// Generate ViewModel vm
return PartialView("_NameOfViewB", vm);
}
Html.Action will run the Action method from the page to generate the html and the [ChildActionOnly] attribute means it cannot be accessed directly, but only from a View. The View name given in the Action return PartialView("_NameOfViewB", vm); assumes it is located in the Controllers main View folder and has a ViewModel generated with a name vm.
I used an ajax call in document.ready in view A and binded that data in a div.
This solved my problem.
For my Website model, I have a boolean property called isLive. My Index method shows the result of this property (if true it will display "live", "offline" otherwise). In my controller, I added a method called EditStatus that allows the user to update only the website's status. My EditStatus view (which belongs to the Websites controller) displays a dropdown menu with 2 options: Live/Offline. This is how I pass it to the Index view:
#Html.Partial("EditStatus", item)
I want to know how to pass the item's (aka the model) unique ID to this partial view so that specific model will be updated.
You can use viewdatadictionary:
example:
#Html.Partial("EditStatus", new ViewDataDictionary { { "item", someInteger } });
Can I create 2 views for a model and controller?
My current application is MVC complaint , and it has a single view.
I need to create a second GUI, that fetches few information from the model (updated from the first GUI data) , update it and display back in the first GUI.
You can have a different view per action. Based on your description, this seems to be what you are looking for. You have different actions for the same model, it's ok.
You can add a new action for the new information that you want to update and click on the right button of the mouse and click "add view". It will add a new view for that action.
The most common way to do this is to create other actions, one for each View you want to display.
You can have as many Views as you like, as long as you can route between them.
As default, the line return View(); or return View(model) will look for a view in this path: /Views/{ControllerName}/{ActionName}.
You can also specify the view name, as Controller.View() also accepts a string as the view name.
Knowing this, you could display different views from a single action, according to parameters passed to your action.
Example:
public ActionResult Example(bool a)
{
if (a) return View("a");
else return View("b");
}
this will call the view /Views/{ControllerName}/a.cshtml if a is true and /Views/{ControllerName}/b.cshtml if a is false.
You can also call other partial views or actions from your first view, using html helpers: #Html.Partial({ViewName}), #{Html.RenderPartial({ViewName});} or #{Html.RenderAction({ActionName});}
EDIT:
View() also searchs for /Views/Shared/{ActionName}
I have a partial view called _News that when called by itself works as expected.
When I call it from another view using the following code:
<div>
#html.Partial("_News");
</div>
It throws this error:
Object reference not set to an instance of an object
At this line of code in the view:
#foreach (var item in Model) {
Where the view is referencing the model. I realise this means that the view is not being passed the model from the Controller but I am perplexed as to why.
The Controller is called NewsController and is located in Controllers. The View is called _News and is located in Shared Views. The view calling the partial view is the default home/index page.
If your partial needs to access data from the model, you need to pass the model into the Partial() method:
#Html.Partial("_News", Model)
MSDN: http://msdn.microsoft.com/en-us/library/system.web.mvc.html.partialextensions.partial%28v=vs.108%29.aspx
EDIT:
Per your comment below, I think you're actually after this: http://haacked.com/archive/2009/11/17/aspnetmvc2-render-action.aspx - this lets you call a controller action and render the result into the current view.
Could your partial model be a subset or a property of your main views' model? I say could because, to Tieson's point, you can deal with almost any discrepancy between the model the partial wants and the model the view wants... BUT if the model your partial wants is so far disparate from the model your view wants then I will often take that as a possible smell that my two models are not flushed out thoroughly/correctly (basically: "Am I trying to represent too many things or unrelated things on the same page?") .
Additionally, if you can make the model of your partial be a property of the main view's model such that you can pass the model into the partial like this:
#Html.Partial("_News", Model.SomePropertyThatFulfillsTheDataSourceOfThePartial)
then if and when you need to submit the form, this would make model binding much easier as well.
Let's assume I have 2 Controllers, TopicsController and PostsController.
For each controller, I have a couple of views (Index & Details).
The Topic (Index) view inherits System.Web.Mvc.ViewPage<IEnumerable<MessageBoard.Models.Topic>>
The Topic (Details) view inherits System.Web.Mvc.ViewPage<MessageBoard.Models.TopicFormViewModel>
I'm using a TopicFormViewModel because I'm sending additional data along with the Model.
The Post (Details) view just inherits System.Web.Mvc.ViewPage<MessageBoard.Models.Post>
Now, I've created a partial view (CreatePost.ascx) which is (obviously :p) used to create a new Post. I want to be able to re-use this control on all of the views you see above.
Update
I've tried rendering the partial view using <% Html.RenderPartial("New"); %> from my Topics/Index.aspx View, but that results in an exception
The model item passed into the dictionary is of type 'System.Data.Linq.Table`1[MessageBoard.Models.Topic]', but this dictionary requires a model item of type 'MessageBoard.Models.Post'.
Now the problem is that my partial view (CreatePost.ascx) accepts a System.Web.Mvc.ViewUserControl<MessageBoard.Models.Post> and I'm not sure how to pass that from all my views above.
I'm also unsure know how to submit the .ascx values to a certain URL (i.e. /Topics/1/CreatePost), how do I tell the submit button to post to that URL?
Thanks in advance,
Marko
Ciao Marko,
Now the problem is that my partial
view (CreatePost.ascx) accepts a
System.Web.Mvc.ViewUserControl
and I'm not sure how to pass that from
all my views above.
I am not sure I understand what do you mean by "how to pass that from all my views above" but I am sure that you dont have to pass an instance of Post from your views. What is going on is that from your views you will invoke a controller action that creates the Post model object and then bind it to the CreatePost.ascx partial.
I'm also unsure know how to submit the
.ascx values to a certain URL (i.e.
/Topics/1/CreatePost), how do I tell
the submit button to post to that URL?
You have two options:
Inside your CreatePost.ascx partial you are probably using a form.
<% using (Html.BeginForm("action", "controller", FormMethod.Post, new {} )) { %>
If you use in the way I am showing you can change the first and the second params respectively to the names of the Action and the Controller that would habndle your submit.
The second option is using jQuery. Simply set an ID for your form and then
$("#myForm").submit(function(event) {
//post an ajax request to the server
});
Hope this helps!
P.S. To be able to reuse your CreatePost.ascx partial place it inside the shared view folder (where your master page is).
In regards to reusing a partial view which is not in the same view folder, use the following and pass in the model required, alternatively you can define a custom route for it.
<% html.RenderPartial("~/Views/<ControllerName>/<PartialViewName>.ascx", <model>);
#Marko
Another way would be to have in the PostController an Action like the following:
[HttpGet]
public ActionResult CreatePost( int topicId ) {
PostModel pm = _manager.CreateDefaultPost();
pm.TopicID = id;
return PartialView( "CreatePost", pm );
}
Then wherever you want to create a Post you can simply call this action that returns the strong-typed view for your new post.
Even if you have a supplementary http call over the network IMO this solution has the advantage to keep the initialization code of a new Post centralized to a single place.
From the View "point-of-view" the call to the action can be done when the user press the "New Post" button and then inject the received markup inside a modal dialog or in a place of your pleasure in the current page.
Hope it helps!