5

I'm using ASP.NET MVC 3 with the Razor template engine for my website. I currently allow files uploads like this:

<form action="/File/Upload" method="post" enctype="multipart/form-data">
    <label for="file">Upload a file:</label>
    <input type="file" name="file" id="file" /> 
    <input type="submit" name="submit" value="Submit" />
</form>

But would like to use a 3rd party control such as NeatUpload, which allows a progress bar, multi file selection, etc.

In the documentation, they show the control being used like this:

<%@ Register TagPrefix="Upload" Namespace="Brettle.Web.NeatUpload"
         Assembly="Brettle.Web.NeatUpload" %>
<Upload:InputFile id="inputFileId" runat="server" />

with some code-behind.

The Razor engine understandably doesn't like this syntax. Is there another way to use 3rd party controls with it, or am I out of luck?

bgmCoder
  • 6,205
  • 8
  • 58
  • 105
Hank
  • 8,289
  • 12
  • 47
  • 57

6 Answers6

4

Third party controls that work with Web Forms aren't really compatible with a pure MVC application. Having said that, you may be able to work with a hybrid type of solution, leveraging Web Forms in certain places and MVC in others. It's not something I would do personally, but you could.

See this post by Scott Hanselman which goes into some detail about doing just that.

Using a web forms control on a Razor page just won't work though.

Joel
  • 19,175
  • 2
  • 63
  • 83
Scott
  • 13,735
  • 20
  • 94
  • 152
  • 1
    That's not true. With the WebFormsViewEngine ASP.NET web controls will work as expected on an ASP.NET MVC page. – smartcaveman Mar 28 '11 at 16:44
  • You downvoted me for that? He specifically said he's using Razor. – Scott Mar 28 '11 at 16:58
  • 1
    Change "on an MVC page" to "on a Razor page" and I'll change it to an upvote. – smartcaveman Mar 28 '11 at 17:02
  • Doesn't really matter that much to me. Besides, who in their right mind doesn't use Razor? It's practically synonymous with MVC now. :) – Scott Mar 28 '11 at 17:33
  • 2
    @smartcaveman it is not true that ASP.NET controls will work with the WebFormsViewEngine. Some controls that use a subset of the WebForms technology might work in MVC aspx views, but certainly the majority of them won't. – marcind Mar 29 '11 at 01:34
  • 1
    though it is possible to make them work in WebForms view engine. Not recommended, but possible. Placing items that require server side forms in a form with runat="server" in MVC will work (assuming you have 1 form) and defeat the purpose of your choice of using MVC. – Patrick Lee Scott Apr 26 '11 at 20:00
  • 1
    Why even use asp controls they are a mess. Im so glad that they moved away from asp controls. use pure Html and javascript instead. – Tan Jul 17 '13 at 13:45
1

Specifically for NeatUpload (which is amazing!) there is now the ability to get the uploading of very large files using javascript on a static HTML page. Clearly this will work just as well with MCV whatever view engine you use :)

http://www.brettle.com/NeatUpload-1.3/dotnet/docs/Manual.html#3.11.Using%20NeatUpload%20from%20JavaScript%7Coutline

So more general solution "ask the developer of the user control to update to an MCV compatible version"

Edit: I won't change the above but note that NeatUpload is now hosted http://neatupload.codeplex.com/ but maybe dead (why not pick it up if you have the developer skills and time!)

Loofer
  • 6,841
  • 9
  • 61
  • 102
  • The above link does not work, but simply pointed to section 3.11 of the Manual. The relevant example is the file [StaticPage.htm](http://neatupload.codeplex.com/SourceControl/latest#dotnet/app/Brettle.Web.NeatUpload/tests/StaticPage.htm). I've decided that I will work on encapsulating the needed logic into an easier to use package. – crush Dec 10 '13 at 21:25
0

I just found that the MVCRecaptcha project that appears to be doing exactly this. I haven't had the time to dig through the internal details, but the essence is contained in two small files. For those of you too lazy to follow the above link, let me try to explain:

Basically, they create the control programmatically, then call RenderControl to dump the html on the wire:

var captchaControl = new RecaptchaControl { ... }
var htmlWriter = new HtmlTextWriter(new StringWriter());
captchaControl.RenderControl(htmlWriter);
return htmlWriter.InnerWriter.ToString();

On the response side, they then create an attribute that you can add to your MVC actions:

class CaptchaValidatorAttribute : ActionFilterAttribute {...}

This class that re-creates the control, and calls:

var recaptchaResponse = captchaValidtor.Validate();

// this will push the result value into a parameter in our Action
filterContext.ActionParameters["captchaValid"] = recaptchaResponse.IsValid;

Which means that your controller will have to look something like this:

[CaptchaValidator]
[AcceptVerbs( HttpVerbs.Post )]
public ActionResult CreateComment( Int32 id, bool captchaValid )
{
    if (!captchaValid)
    {
        ModelState.AddModelError("_FORM", "You did not type the verification word correctly. Please try again.");
    }
    // ...
}

Although the project is now obsolete, it shows how to use an ASP.Net control in an MVC application.

VeeTheSecond
  • 3,086
  • 3
  • 20
  • 16
0

You can do this, assuming you just want a render of the control content and don't care about registering scripts or postbacks, etc.

Create your own HtmlTextWriter, write the output to it, and then render that string in your Razor. This is basically the idea from @VeeTheSecond, reduced to practice:

@{
    System.Web.UI.WebControls.Label label = new System.Web.UI.WebControls.Label()
    {
        Text = "Hello World!"
    };

    HtmlString renderedControl;

    using (StringWriter w = new StringWriter())
    {
        using (HtmlTextWriter htmlW = new HtmlTextWriter(w))
        {
            label.RenderControl(htmlW);

            renderedControl = new HtmlString(w.ToString());
        }
    }
}
<div>
    @renderedControl
</div>
Chris Hynes
  • 9,999
  • 2
  • 44
  • 54
0

The Razor view engine does not support WebForms controls. You will need to find a library that is specifically designed to work with MVC.

marcind
  • 52,944
  • 13
  • 125
  • 111
-2

Try placing the control in a <form runat="server"> tag.

Keith
  • 2,618
  • 4
  • 29
  • 44