# Model ## 物件製作 ### 類別 ``` public class Student { public string id { get; set; } public string name { get; set; } public int score { get; set; } public Student()//宣告一個建構子裏面有id,name,score三項,如果沒有填入的話則會給預設值 { id = string.Empty; name = string.Empty; score = 0; } public Student(string _id, string _name, int _score)//和上面相同,不過這個是可以直接在後面加入參數來宣告建構子 { id = _id; name = _name; score = _score; } public override string ToString()//覆蓋Tostring這個方法 { return $"學號:{id}, 姓名:{name}, 分數:{score}."; } } ``` ### 結構 ``` 除了類別以外,另一種描述複雜資料的方式就是結構,有幾個特點: 不能被繼承 2.無須使用new來建立物件 3.屬於實值型別 結構和類別很像,都可以宣告欄位、方法、屬性等成員,結構適用在表示 "少量"資料"的強況,例如: 『System.Date.Time』結構就無需使用new關鍵字,便可以直接使用. ``` ## json 序列、反序列化 序列化,它又稱串行化,.NET運行時環境用來支持用戶定義類型的流化的機制。 序列化就是把一個對象保存到一個文件或數據庫字段中去,反序列化就是在適當的時候把這個文件再轉化成原來的對象使用。 假設物件: Student stu = new Student() { ID = 1, Name = "孔子", Age = 2000, Sex = "男" }; ``` using System.Web.Script.Serialization; //序列化 JavaScriptSerializer js = new JavaScriptSerializer(); string jsonData = js.Serialize(stu);//序列化 Console.WriteLine(jsonData); //反序列化 string desJson = jsonData; Student model = js.Deserialize<Student>(desJson);// //反序列化 string message = string.Format("ID={0},Name={1},Age={2},Sex={3}", model.ID, model.Name, model.Age, model.Sex); ``` # View ## 傳遞物件 ViewBag 物件:它和 ViewData 一樣,使用 Key / Value 存取,並能放入任何的資料,但不同的是,它能產生「動態屬性」。 TempData 物件:TempData 由字面上的意思看來,即告訴我們是「暫存」的資料,而暫存又是暫存多久?其實就是一次的請求,假定我們今天輸入網址 /Home/Index 而透過 Redirect 的方法轉向至 /Home/About ,若是用 ViewData 或 ViewBag 資料及會消失,但若透過 TempData 它能將資料傳遞至 /Home/About 供其使用,而最後返回頁面後 TempData 內的資料隨即消失,代表它的生命週期只有一次性,當使用一次我們就丟掉它。 ## Razor Razor又稱Razor Syntax,是用來將Server Side的C#程式嵌入到HTML中的標記語法 Razor中只有HTML及C#兩種元素,結合再一起就形成了Razor語法。 C#程式區塊是以@{…}包覆,裡面是一般C#程式。 Razor inline表達式是指C#變數穿插在HTML中,而Razor中預設是Html語言,若遇到@符號,表示後面接的是C#指令。 Razor會依不同的規則或符號在HTML和c#間切換。 ``` @{ var greetingMessage="" //程式碼 } <p>The greeting is: @greetingMessage</p>//inline表達式 ``` ## 跨網頁傳值 [https://coolmandiary.blogspot.com/2020/12/aspnet-mvcgetpostviewcontoller.html](https://coolmandiary.blogspot.com/2020/12/aspnet-mvcgetpostviewcontoller.html) ## Controller向View傳值 controller ``` viewbag.test1="test1 hello world"; viewdata["test2"]="test2 hello world"; tempdata["test3"]="test3 hello world";//可以跨action Session["currentTime"] = DateTime.Now//可以跨action ``` view ``` @ViewBag.Test123 @ViewData["Test123"] @TempData["tmpData"] Session : @Session["currentTime"] ``` ## View向controller傳值 使用Html.BeginForm(...)方法提交表單 ``` @using(Html.BeginForm("actionName","controllerName")) { <div>表單內容</div> <div>...</div> <input type="submit" value="提交表單" /> } ``` 傳統Form表單的Action屬性提交 ``` <form id="postForm" action="@Url.Action("Save")" method="post"> <div>表單內容</div> <div>...</div> <input type="submit" value="提交表單" /> </form> ``` 使用Ajax方式提交表單, Ajax.BeginForm(...) ``` @Ajax.BeginForm("actionName", new AjaxOptions { Url="",OnSuccess="",HttpMethod="get" }) { <div>表單內容</div> <div>...</div> <input type="submit" value="提交表單" /> } ``` ## 跳轉 Return view() 返回View ``` Return View();//返回與Action名稱一樣的view Return View("view名稱")//本view所在文件夾和share文件夾中找 Return View("~/Views/Home/Index.cshtml")//完整路徑 ``` Redirect() 重新導向到指定URL ``` return Redirect("index?page=2"); return Redirect("delete"); return Redirect("/User/Index"); ``` RedirectToAction() 重新導向到特定Action ``` return RedirectToAction(nameof(action),nameof(controller)); //例如 RedirectToAction(nameof(HomeController.Login),nameof(HomeController)); ``` ## HTML Helper ASP.NET MVC中可以使用HTML Helper輔助產生需要的HTML語法,進而增加專案開發的效率 ### 輸出超連結 1. 一般使用 ``` @Html.ActionLink("linkText","actionName") 第一個參數為想顯示的文字,第二個參數為此View預設Controller中的Action ex: @Html.ActionLink("首頁","Index") ``` 2. 第三個參數可以指定Controller名稱 ``` @Html.ActionLink("linkText","actionName","ControllerName") 第三個參數可以指定Controller名稱 ex: @Html.ActionLink("首頁","Index","Home") ``` 3. 第三個參數為路由的參數 ``` @Html.ActionLink("linkText","actionName",RouteValues) 第三個參數為路由的參數 ex: @Html.ActionLink("關於","Aboot",new { id = 0 }) ``` 4. 第四個參數可以設定HTML屬性,需在關鍵字前加上@才能正確編譯,若HTML屬性含有「-」 符號必須用底線「_」代替,如data-value需改為data_value ``` @Html.ActionLink("linkText","actionName",RouteValues,htmlAttributes) 第四個參數可以設定HTML屬性,需在關鍵字前加上@才能正確編譯,若HTML屬性含有「-」 符號必須用底線「_」代替,如data-value需改為data_value ex: @Html.ActionLink("關於","Aboot",new { id = 0 },new {@class='btn') ``` # Controller ## Action資料傳遞 TempData.Keep("key") 資料會標記刪除,所以生命周期會減少。也就是跳轉回去后,刷新頁面或是切換頁面,資料都會消失 TempData.Peek("key") 資料不會標記刪除,所以生命周期不會減少。也就是跳轉后,刷新頁面或是切換頁面,資料都不會消失 ``` public class HomeController : Controller { public IActionResult Index() { ViewData["Label"] = "TOYOTA"; ViewData["Type"] = "Vios"; ViewData["cc"] = "1.5"; TempData["FN"] = TempData["file"];//取得B的TempData["file"]的值 return View(); } public IActionResult B(){ TempData["file"] = "123"; TempData.Keep("file");//資料使用一次后就會清空 //TempData.Peek("file");//資料使用后不會清空 return View(); } public IActionResult C() { return View(); } [ResponseCache(Duration = 0, Location = ResponseCacheLocation.None, NoStore = true)] public IActionResult Error() { return View(new ErrorViewModel { RequestId = Activity.Current?.Id ?? HttpContext.TraceIdentifier }); } } ``` ## Actionreslt類型 <table width="624"> <thead> <tr> <th width="155">型別</th> <th width="272">簡介</th> <th width="195">Controller Helper Methods</th></tr></thead> <tbody> <tr> <td width="155">EmptyResult</td> <td width="272">甚麼事都不做…</td> <td width="195">無</td></tr> <tr> <td width="155">ContentResult</td> <td width="272">回傳文字至瀏覽器,可以自行設定content-type。</td> <td width="195">Content</td></tr> <tr> <td width="155">FileResult</td> <td width="272">回傳二位元資料,例如Server上的mp3等檔案。</td> <td width="195">File</td></tr> <tr> <td width="155">ViewResult</td> <td width="272">呈現指定或是預設的View。</td> <td width="195">View</td></tr> <tr> <td width="155">PartialViewResult</td> <td width="272">呈現指定或是預設的View樣板</td> <td width="195">PartialView</td></tr> <tr> <td width="155">RedirectToRouteResult</td> <td width="272">如果產生HTTP 301、302則會重新導向到另外一個Action或是其他指定的URL、或是設定好的Router。</td> <td width="195"> <p>RedirectToAction RedirectToActionPermanent RedirectToRoute RedirectToRoutePermanent</p> </td></tr> <tr> <td width="155">RedirectResult</td> <td width="272">如果產生HTTP 301、302則會導向至另外一個URL。</td> <td width="195">Redirect RedirectPermanent</td></tr> <tr> <td width="155">JsonResult</td> <td width="272">將.net 物件序列化成Json格式並回傳。</td> <td width="195">Json</td></tr> <tr> <td width="155">JavaScriptResult</td> <td width="272">回傳一個JavaScript的程式碼片段,通常用於Ajax裡面。</td> <td width="195">JavaScript</td></tr> <tr> <td width="155">HttpUnauthorizedResult</td> <td width="272">回傳HTTP 401 ( 未授權 )。</td> <td width="195">None</td></tr> <tr> <td width="155">HttpNotFoundResult</td> <td width="272">回傳HTTP 404。</td> <td width="195">HttpNotFound</td></tr> <tr> <td width="155">HttpStatusCodeResult</td> <td width="272">返回指定的HTTP代碼。</td> <td width="195">無</td></tr></tbody></table> ## 連接SQL 範例 ``` using MVCTest.Models; using MySql.Data.MySqlClient;// using System.Data.SqlClient; //mssql連綫需要 using System; using System.Collections.Generic; using System.Data; using System.Linq; using System.Web; using System.Web.Mvc; namespace MVCTest.Controllers { public class HomeController : Controller { //mysql "server=主機位置;port=3306;user id=用戶名;password=密碼;database=資料庫名稱;charset=編碼方式;" //mssql "data source=主機位置; initial catalog = 資料庫名稱; user id = 帳號; password = 密碼"; string connString = "server=127.0.0.1;port=3306;user id=root;password=Acuteboy1215;database=mvctest;charset=utf8;"; MySqlConnection conn = new MySqlConnection(); public ActionResult Index() { conn.ConnectionString = connString; if (conn.State != ConnectionState.Open)//檢查連綫狀態是否開啓,如果重複開啓會出錯 conn.Open(); //sql指令 string sql = @"INSERT INTO `City` (`Id`, `City`) VALUES ('0', '基隆市'), ('1', '臺北市'), ('2', '新北市')"; //設定Insert的cmd指令 MySqlCommand cmd = new MySqlCommand(sql, conn); int index = cmd.ExecuteNonQuery();//執行 bool success = false; if (index > 0) success = true; else success = false; ViewBag.Success = success; conn.Close(); return View(); } } } ```