0 Files:
<MudFileUpload T="IBrowserFile" FilesChanged="UploadFiles"> <ButtonTemplate> <MudButton HtmlTag="label" Variant="Variant.Filled" Color="Color.Primary" StartIcon="@Icons.Material.Filled.CloudUpload" for=""> Upload Files </MudButton> </ButtonTemplate> </MudFileUpload> <MudFileUpload T="IBrowserFile" FilesChanged="UploadFiles"> <ButtonTemplate> <MudFab HtmlTag="label" Color="Color.Secondary" Icon="@Icons.Material.Filled.Image" Label="Load picture" for="" /> </ButtonTemplate> </MudFileUpload> <MudFileUpload T="IBrowserFile" FilesChanged="UploadFiles"> <ButtonTemplate> <MudFab HtmlTag="label" Color="Color.Success" Icon="@Icons.Material.Filled.AttachFile" for="" /> </ButtonTemplate> </MudFileUpload> <MudFileUpload T="IBrowserFile" FilesChanged="UploadFiles"> <ButtonTemplate> <MudIconButton HtmlTag="label" Color="Color.Info" Icon="@Icons.Material.Filled.PhotoCamera" for=""> </MudIconButton> </ButtonTemplate> </MudFileUpload> <MudFileUpload T="IBrowserFile" FilesChanged="UploadFiles" Disabled> <ButtonTemplate> <MudButton HtmlTag="label" Variant="Variant.Filled" Color="Color.Primary" for=""> Disabled Button </MudButton> </ButtonTemplate> </MudFileUpload> @if (files != null) { <MudText Typo="@Typo.h6">@files.Count() File@(files.Count() == 1 ? "" : "s"):</MudText> <MudList> @foreach (var file in files) { <MudListItem Icon="@Icons.Material.Filled.AttachFile" @key=""> @file.Name <code>@file.Size bytes</code> </MudListItem> } </MudList> }
@code { IList<IBrowserFile> files = new List<IBrowserFile>(); private void UploadFiles(IBrowserFile file) { files.Add(file); //TODO upload the files to the server } }
Multiple and Accept
Allow multiple files with T="IReadOnlyList<IBrowserFile>"
or limit the valid file types with Accept
.
To upload more than 10 files, you must specify a MaximumFileCount
.
<MudFileUpload T="IReadOnlyList<IBrowserFile>" FilesChanged="UploadFiles"> <ButtonTemplate> <MudButton HtmlTag="label" Variant="Variant.Filled" Color="Color.Primary" StartIcon="@Icons.Material.Filled.CloudUpload" for=""> Multiple Files </MudButton> </ButtonTemplate> </MudFileUpload> <MudFileUpload T="IBrowserFile" Accept=".pdf" FilesChanged="UploadFiles2" MaximumFileCount="100"> <ButtonTemplate> <MudButton HtmlTag="label" Variant="Variant.Filled" Color="Color.Primary" StartIcon="@Icons.Material.Filled.CloudUpload" for=""> Only .pdf files </MudButton> </ButtonTemplate> </MudFileUpload> @if (files != null) { <MudList> @foreach (var file in files) { <MudListItem Icon="@Icons.Material.Filled.AttachFile"> @file.Name <code>@file.Size bytes</code> </MudListItem> } </MudList> }
@code { IList<IBrowserFile> files = new List<IBrowserFile>(); private void UploadFiles(IReadOnlyList<IBrowserFile> files) { foreach (var file in files) { this.files.Add(file); } //TODO upload the files to the server } private void UploadFiles2(IBrowserFile file) { files.Add(file); //TODO upload the files to the server } }
Form Validation
Use the For
property to validate your files within a form, and bind your files to your model class using @bind-Files
.
You can then handle the file upload logic within your MudForm
submit method.
@using FluentValidation @using Severity = MudBlazor.Severity; @inject ISnackbar Snackbar <MudCard> <MudForm Model="" @ref="" Validation="@(ValidationRules.ValidateValue)" ValidationDelay="0"> <MudCardContent> <MudTextField @bind-Value="model.Name" For="@(() => model.Name)" Immediate="true" Label="Name" /> <MudFileUpload T="IBrowserFile" For="@(() => model.File)" @bind-Files="model.File" OnFilesChanged="UploadFiles" SuppressOnChangeWhenInvalid="SuppressOnChangeWhenInvalid"> <ButtonTemplate> <MudButton HtmlTag="label" Variant="Variant.Filled" Color="Color.Primary" StartIcon="@Icons.Material.Filled.CloudUpload" for=""> Upload Files </MudButton> </ButtonTemplate> </MudFileUpload> </MudCardContent> <MudCardActions> <MudSwitch Color="Color.Primary" @bind-Checked="SuppressOnChangeWhenInvalid">Suppress OnChange When Invalid</MudSwitch> <MudButton Variant="Variant.Filled" Color="Color.Primary" Class="ml-auto" OnClick="@(async () => await Submit())">Submit</MudButton> </MudCardActions> </MudForm> </MudCard>
@code { private MudForm form; private FileModel model = new(); private FileModelFluentValidator ValidationRules = new(); private bool SuppressOnChangeWhenInvalid; private void UploadFiles(InputFileChangeEventArgs e) { //If SuppressOnChangeWhenInvalid is false, perform your validations here Snackbar.Configuration.PositionClass = Defaults.Classes.Position.TopCenter; Snackbar.Add($"This file has the extension {model.File.Name.Split(".").Last()}", Severity.Info); //TODO upload the files to the server } private async Task Submit() { await form.Validate(); if (form.IsValid) { Snackbar.Add("Submited!"); } } public class FileModel { public string Name { get; set; } public IBrowserFile File { get; set; } } /// <summary> /// A standard AbstractValidator which contains multiple rules and can be shared with the back end API /// </summary> /// <typeparam name="OrderModel"></typeparam> public class FileModelFluentValidator : AbstractValidator<FileModel> { public FileModelFluentValidator() { RuleFor(x => x.Name) .NotEmpty() .Length(1, 100); RuleFor(x => x.File) .NotEmpty(); When(x => x.File != null, () => { RuleFor(x => x.File.Size).LessThanOrEqualTo(10485760).WithMessage("The maximum file size is 10 MB"); }); } public Func<object, string, Task<IEnumerable<string>>> ValidateValue => async (model, propertyName) => { var result = await ValidateAsync(ValidationContext<FileModel>.CreateWithOptions((FileModel)model, x => x.IncludeProperties(propertyName))); if (result.IsValid) return Array.Empty<string>(); return result.Errors.Select(e => e.ErrorMessage); }; } }
Event Options
You can use either Files
and FilesChanged
or the OnFilesChanged
callback.
The former is better when used within a MudForm
, and the latter is better for custom scenarios.
When using OnFilesChanged
, it will fire regardless of validation by default, but can be configured to only fire when valid using SuppressOnChangeWhenInvalid
.
0 Files:
<MudFileUpload T="IBrowserFile" FilesChanged="UploadFiles"> <ButtonTemplate> <MudButton HtmlTag="label" Variant="Variant.Filled" Color="Color.Primary" StartIcon="@Icons.Material.Filled.CloudUpload" for=""> Upload using FileValueChanged </MudButton> </ButtonTemplate> </MudFileUpload> <MudFileUpload T="IBrowserFile" OnFilesChanged="UploadFiles"> <ButtonTemplate> <MudButton HtmlTag="label" Variant="Variant.Filled" Color="Color.Primary" StartIcon="@Icons.Material.Filled.CloudUpload" for=""> Upload using OnFilesChanged </MudButton> </ButtonTemplate> </MudFileUpload> @if (files != null) { <MudText Typo="@Typo.h6">@files.Count() File@(files.Count() == 1 ? "" : "s"):</MudText> <MudList> @foreach (var file in files) { <MudListItem Icon="@Icons.Material.Filled.AttachFile" @key=""> @file.Name <code>@file.Size bytes</code> </MudListItem> } </MudList> }
@code { IList<IBrowserFile> files = new List<IBrowserFile>(); private void UploadFiles(IBrowserFile file) { files.Add(file); //TODO upload the files to the server } private void UploadFiles(InputFileChangeEventArgs args) { files.Add(args.File); //TODO upload the files to the server } }
SelectedTemplate
You can use the SelectedTemplate
RenderFragment to display the current files.
Its @context
parameter matches T
.
No File
No Files
<MudFileUpload T="IBrowserFile"> <ButtonTemplate> <MudButton HtmlTag="label" Variant="Variant.Filled" Color="Color.Primary" for=""> Single File </MudButton> </ButtonTemplate> <SelectedTemplate> @if (context != null) { <MudText>@context.Name</MudText> } else { <MudText>No File</MudText> } </SelectedTemplate> </MudFileUpload> <MudFileUpload T="IReadOnlyList<IBrowserFile>" Multiple> <ButtonTemplate> <MudButton HtmlTag="label" Variant="Variant.Filled" Color="Color.Secondary" for=""> Multiple Files </MudButton> </ButtonTemplate> <SelectedTemplate> @if (context != null) { @foreach (var file in context) { <MudText>@file.Name</MudText> } } else { <MudText>No Files</MudText> } </SelectedTemplate> </MudFileUpload>
Drag and Drop Example
Using the example below, you can compose a drag-and-drop uploader.
Drag and drop files here or click
@inject ISnackbar Snackbar <MudStack Style="width: 100%"> <MudFileUpload T="IReadOnlyList<IBrowserFile>" OnFilesChanged="OnInputFileChanged" Hidden="false" Class="flex-1" InputClass="absolute mud-width-full mud-height-full overflow-hidden z-20" InputStyle="opacity:0" @ondragenter="" @ondragleave="" @ondragend=""> <ButtonTemplate> <MudPaper Height="300px" Outlined="true" Class=""> <MudText Typo="Typo.h6">Drag and drop files here or click</MudText> @foreach (var file in fileNames) { <MudChip Color="Color.Dark" Text="" /> } </MudPaper> </ButtonTemplate> </MudFileUpload> <MudToolBar DisableGutters="true" Class="gap-4"> <MudButton OnClick="Upload" Disabled="@(!fileNames.Any())" Color="Color.Primary" Variant="Variant.Filled">Upload</MudButton> <MudButton OnClick="Clear" Disabled="@(!fileNames.Any())" Color="Color.Error" Variant="Variant.Filled">Clear</MudButton> </MudToolBar> </MudStack>
@code { private static string DefaultDragClass = "relative rounded-lg border-2 border-dashed pa-4 mt-4 mud-width-full mud-height-full z-10"; private string DragClass = DefaultDragClass; private List<string> fileNames = new List<string>(); private void OnInputFileChanged(InputFileChangeEventArgs e) { ClearDragClass(); var files = e.GetMultipleFiles(); foreach (var file in files) { fileNames.Add(file.Name); } } private async Task Clear() { fileNames.Clear(); ClearDragClass(); await Task.Delay(100); } private void Upload() { //Upload the files here Snackbar.Configuration.PositionClass = Defaults.Classes.Position.TopCenter; Snackbar.Add("TODO: Upload your files!", Severity.Normal); } private void SetDragClass() { DragClass = $"{DefaultDragClass} mud-border-primary"; } private void ClearDragClass() { DragClass = DefaultDragClass; } }