2

I want to create reusable mvc4 UI components/controls that can be reused across the application. There is a lot of info about this on internet(mostly mvc3) but it seems incomplete or too specific.

The general application arhitecture will be to return rendered html from normal or ajax requests(I wanted to clarify that the question doesn't refer to SinglePageApp model, so components are on the server and may have a client side model and the communication is not done using a json webapi)

The question is "how is best to create a component so that it behaves as described below?"

The reusable component should have the following characteristics:

  • it should be reused on different places/views of same application (it's app specific and not intended to be packaged in a separate library for future use)
  • it should have declarative markup so it's easy to read for a developer(no extension methods, TagBuilder, etc);
  • it should receive a list of options that specify how it should behave (showCloseBtn:true, SaveUrl:{...} ), some event handler to treat events and also a data model if necessary (for binding to html controls)
  • it is observable; it can generate events and notify anyone that is registered to those events (i mean on client-side); similar behavior is on telerik controls but in our case there is the limitation of declarative aproach (we don't want to build a class library).

Sample:

@(Html.Telerik().Upload()
    .Name("attachments")
    .ClientEvents(events => events
        .OnLoad(
        @<text>
            function(e) {
                // Perform required actions here.
            }
        </text>)
    )
)
  • some components will only be used once per page others can appear multiple times depending on the options params
  • each component needs to render html and also javascript
  • it would be nice to be able to request a component from the client-side

Example (this is just to clarify the question, it's not a specific case i need to solve):

Lets say we have an application that manages roles in some departments. We have a Person entity that has Name, Age, DepartmentId (assume it can only belong to one department). We create a PersonComponent form for Edit/Insert that has label/textboxes for Name,Age and a ddl for department. It also has a Save btn. When the save btn is clicked, depending on how the component was initialized, it gets all the data from fields then it makes an ajax call sending json data to a url (url is received as param) and dispatches a Save event to anyone who is registered. The save event handler has a parameter containing the json data. If no url has been sent as param to the component it just notifies all listeners if any.

Each department has a different view where the component can be reused. A page can display more than one department at one time.

Things to consider:

  • to create this components we could use declarative HtmlHelpers, PartialViews or RenderAction helper (or other methods?)
  • in the case a component is only used once per page but the page has multiple components, it might be better for each component to actually get it's own business data in order to avoid the need of the parent container to obtain the data for each component
  • if same component appears multiple times on same page it would be preferable not to duplicate the javascript code; (there is a related discussion here)
  • in the case of PartialViews the ViewModel would have to encapsulate component options, modeldata and event handlers.
  • rendering an HtmlHelper as a response to a client-request is a bit strange
  • it is very important to have the event mechanism in order for components to be reusable; it's not enough to just render some html as a component/control
  • the architecture/solution could include some client-side api's like require.js (for loading a component js), knockout.js or others; what is important is not to overcomplicate it with dependencies, but use them if they are helpfull

Note:

There are similar questions here and here but the context of the question is different.

Community
  • 1
  • 1
eugen
  • 464
  • 5
  • 16
  • Exactly the question I'm facing now. Did you get anywhere with this? I'm assuming you used Editor Templates – tony Dec 04 '14 at 13:12
  • this was a long time ago, but from what i can remember each component was a div with an id in html and a corresponding typescript class similar to a durandal.js module, you could attack events to it, and so on. So it can be done but it's difficult to implement and as you go on it starts to become a framework, so I think it's kind of beyond the scope of a stackoverflow answer. – eugen Dec 04 '14 at 15:26

0 Answers0