I have a simple test application:
Model:
public class Counter
{
public int Count { get; set; }
public Counter()
{
Count = 4;
Html.TextBox() uses internally ViewData.Eval() method which first attempts to retrieve a value from the dictionary ViewData.ModelState and next to retrieve the value from a property of the ViewData.Model. This is done to allow restoring entered values after invalid form submit.
Removing Count value from ViewData.ModelState dictionary helps:
public ActionResult Increment(Counter counter)
{
counter.Count++;
ViewData.ModelState.Remove("Count");
return View(counter);
}
Another solution is to make two different controller methods for GET and POST operations:
public ActionResult Increment(int? count)
{
Counter counter = new Counter();
if (count != null)
counter.Count = count.Value;
return View("Increment", counter);
}
[AcceptVerbs(HttpVerbs.Post)]
public ActionResult Increment(Counter counter)
{
counter.Count++;
return RedirectToAction("Increment", counter);
}
Counter object could also be passed via TempData dictionary.
You may also be interested in the article Repopulate Form Fields with ViewData.Eval() by Stephen Walther.