I am trying to pass input values to an array within my viewmodel. Then loop through the values and save the new changes in each however, every time I submit, the model values come in as null except for one value(duration). I've tried changing the names and id's but to avail.
View
@{
var SMs = ((List<Stage_Media>)ViewBag.Stage_Media);
}
<div class="col-lg-12">
<div class="card card-alt3">
<div class="card-header">
<h3><strong>Show Order</strong></h3>
</div>
<div class="card-body">
<table class="dd table" id="show_list">
<thead>
<tr>
<th></th>
<th>Order</th>
<th>Name</th>
<th>Path</th>
<th>Upload Date</th>
<th>Duration (Min:Sec)</th>
<th></th>
</tr>
</thead>
@if (SMs.Count() > 0)
{
<tbody class="dd-list">
@foreach (var sm in SMs.OrderBy(sm => sm.order))
{
<tr class="dd-item dd3-item" data-id="@sm.media.id" data-duration="@sm.duration">
<td class="dd-handle dd3-handle"></td>
<td class="dd3-content">@sm.order</td>
<td class="dd3-content">@sm.media.name</td>
<td class="dd3-content">@sm.media.ext</td>
<td class="dd3-content">@sm.media.uploaded</td>
<td class="dd3-content">
@if (sm.media.ext == "jpg" || sm.media.ext == "png")
{
<input name="sm_duration" id="sm.duration" placeholder = "mm:ss"
value = @(sm.duration != null ? TimeSpan.FromTicks((long)@sm.duration).ToString(@"m\:ss", null) : "00:10") />
}
<input name="sm_start_date" id="sm.start_date" type="date" />
<input name="sm_end_date" id="sm.end_date" type="date" />
<select name="sm_occurrence">
<option default value=Everyday>Every day</option>
<option value="Bi-Weekly">Bi-Weekly</option>
</select>
</td>
<td style="width: 15%">
<div class="row align-items-center align-middle" style="margin: 0; height: 6em; max-height: 6em">
@if (sm.media.ext == "mp4" || sm.media.ext == "mov" || sm.media.ext == "mkv")
{
<video id="video" src="/api/[email protected]" style="object-fit: cover; width: 100%; max-width: 100%; max-height: 100%;" autoplay muted playsinline loop></video>
}
else
{
<img id="image" src="/api/[email protected]" style="width: 100%; height:100%; object-fit: contain;">
}
</div>
</td>
</tr>
}
</tbody>
}
else
{
<tbody class="dd-empty">
<tr class="dd-placeholder">
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
</tbody>
}
</table>
</div>
</div>
</div>
<div class="form-group row">
<div class="col-3">
<button type="button" name="Save" onclick="return saveStage(@ViewBag.Branch_id,
@ViewBag.Stage.id);" class="btn btn-alt1">Save Stage</button>
<button type="button" name="Delete" onclick="return deleteStage(@ViewBag.Stage.id);"
class="btn btn-alt1">Delete Stage</button>
<a name="View" href="/home/[email protected]" class="btn btn-alt1">View</a>
</div>
ViewModel
public class SaveStage_ViewModel
{
public int stage_id { get; set; }
public string name { get; set; }
public File[] ids { get; set; }
public class File
{
public int id { get; set; }
[DataType(DataType.Time)]
[DisplayFormat(DataFormatString = "{mm\\:ss}")]
[Display(Name = "Duration")]
public string duration { get; set; }
[Display(Name = "Start Date")]
public DateTime? start_date { get; set; }
[Display(Name = "End Date")]
public DateTime? end_date { get; set; }
[Display(Name = "Occurence")]
public string occurrence { get; set; }
}
}
Model
public class Stage_Media
{
[Key]
public int id { get; set; }
public int stage_id { get; set; }
[ForeignKey("stage_id")]
public Stage stage { get; set; }
public int media_id { get; set; }
public long? duration { get; set; }
[ForeignKey("media_id")]
public Media media { get; set; }
public int order { get; set; }
public DateTime? start_date { get; set; }
public DateTime? end_date { get; set; }
public string occurrence { get; set; }
}
Controller
[HttpPost]
public string SaveStage(SaveStage_ViewModel model)
{
using (var c = new Context())
{
var stage = c.Stage.Find(model.stage_id);
stage.name = model.name;
stage.modified = DateTime.Now;
stage.modified_by = User.Identity.Name;
var sml = new List<Stage_Media>();
for (var i = 0; i < model.ids.Count(); i++)
{
var sm = new Stage_Media();
sm.stage_id = model.stage_id;
sm.media_id = model.ids[i].id;
sm.start_date = model.ids[i].start_date;
sm.end_date = model.ids[i].start_date;
sm.occurrence = model.ids[i].occurrence;
sm.order = i + 1;
sm.duration = !string.IsNullOrWhiteSpace(model.ids[i].duration) ? (long?)TimeSpan.ParseExact(model.ids[i].duration, @"m\:ss", null).Ticks : null;
sml.Add(sm);
}
c.Stage.Update(stage);
c.Stage_Media.RemoveRange(c.Stage_Media.Where(smr => smr.stage_id == model.stage_id));
c.Stage_Media.AddRange(sml);
c.SaveChanges();
}
return $"Stage Save Successful";
}
Actually, it would be more convenient if you would have shared your page initialization code snippet where you have set your
@ViewBag.Branch_idvalue and this is one of the reason of your null value on submit.I have tried to similate your issue and worked as expected. Here is the sample for your reference how I have tested the scenario.
Demo Model:
Controller:
Note: I have assigned demo value on ViewBag.Stage_Media while loading index view.
View:
Note: You either can pass value using
saveStage(@SMs.Branch_id, @SMs.stage_id);orsaveStage(@ViewBag.Stage_Media.Branch_id, @@ViewBag.Stage_Media.stage_id);Both will work accordingly. I have used single model but you can use List and pass the index value you want.Output:
Take Ways: Check your
@Viewbagdata first if that has assigned correctly. On top of this, double check yoursaveStagefunction if the value has been passed as expected. You can use browser network trace and console. You may refer to this official link for debugging assistance. Furthermore, you can have a look at this official sample.