概述 Silverlight 的Data Bindings :Silverlight 與 ASP.NET Ajax 文/黃忠成 不可否認,對於網頁美工人員或是動畫設計師而言,Silverlight提供了Flash以外的一個畫布,令她們可盡情揮灑創意!但對於設計師而言,Silverlight如何結合資料庫來呈現資料則是更具吸引力的課題,很明顯的!Silverlight 1.0 RC與Silv
Silverlight 的Data Bindings :Silverlight 與 ASP.NET AJAX 文/黃忠成 不可否認,對於網頁美工人員或是動畫設計師而言,Silverlight提供了Flash以外的一個畫布,令她們可盡情揮灑創意!但對於設計師而言,Silverlight如何結合資料庫來呈現資料則是更具吸引力的課題,很明顯的!Silverlight 1.0 RC與Silverlight 1.1並不支援Data Binding機制,而且目前對於中文顯示仍存在著問題(下載字型不算是個解法,因為有法律問題),不過如果這個問題獲得解決,Silverlight結合資料庫後所呈現的效果,相信會給客戶完全不同的網頁 *** 作感受,當然!前提得要Silverlight支援Data Bindings,否則一切都是紙上談兵罷了。要令Silverlight支援Data Bindings說來也不難,只要處理幾個關鍵問題即可。一、資料提供者為何?ASP.NET AJAX的PageMethods/Web Service可以勝任此工作,如下列程式片段所示。
private static Datatable BuildDataCache() { if (httpRuntime.Cache["DataCache_Employees"] != null) return httpRuntime.Cache["DataCache_Employees"] as Datatable; else { using (sqlConnection conn = new sqlConnection(ConfigurationManager.ConnectionStrings[ "northwindConnectionString" ].ConnectionString)) { sqlDataAdapter adapter = new sqlDataAdapter( "SELECT * FROM Employees ORDER BY EmployeeID" ,conn); Datatable table = new Datatable("Employees"); adapter.Fill(table); httpRuntime.Cache["DataCache_Employees"] = table; return table; } } } [WebMethod] public static Employee GetData(int index) { Datatable table = BuildDataCache(); return new Employee(table.defaultview[index]); } [WebMethod] public static int GetCount() { Datatable table = BuildDataCache(); return table.defaultview.Count; } protected voID button1_Click(object sender,EventArgs e) { } } [Serializable] public class Employee { [NonSerialized] private DaTarowVIEw _rv = null; public string EmployeeID { get { return (_rv.Row.IsNull("EmployeeID") ? string.Empty : _rv["EmployeeID"].ToString()); } } public string Lastname { get { return (_rv.Row.IsNull("Lastname") ? string.Empty : (string)_rv["Lastname"]); } } public string Firstname { get { return (_rv.Row.IsNull("Firstname") ? string.Empty : (string)_rv["Firstname"]); } } public string Title { get { return (_rv.Row.IsNull("Title") ? string.Empty : (string)_rv["Title"]); } } public string HireDate { get { return (_rv.Row.IsNull("HireDate") ? string .Empty : ((DateTime)_rv["HireDate"]).ToShortDateString()); } } public Employee(DaTarowVIEw rv) { _rv = rv; } } |
運用ASP.NET AJAX及JsON,我們可以輕易的用JavaScript來取得資料庫的資料,接著只要將資料設定給指定Silverlight控制項即可,這個工作可以簡單化也可以複雜化,簡單的作法是直接在JavaScript以findname來取得控制項,然後一一設定其屬性值。
handleLoad: function(plugIn,userContext,rootElement) { this.plugIn = plugIn; this.dataContext = rootElement.children.getItem(0); PageMethods.GetCount(this.OnSucceeded,this.OnFailed,this); this.receiveData(this.currentDataIndex); }, OnSucceeded: function(result,methodname) { if (methodname == "GetData") { userContext.displayData(result); } else if(methodname == "GetCount") userContext.recordCount = result; }, OnFailed:function(error,methodname) { if(error !== null) { alert(error.get_message()); } }, displayData: function(data) { var IDCtrl = this.dataContext.findname('txtEmployeeID'); var firstnameCtrl = this.dataContext.findname('txtLastname'); var lastnameCtrl = this.dataContext.findname('txtFirstname'); var TitleCtrl = this.dataContext.findname('txtTitle'); var hireDateCtrl = this.dataContext.findname('txtHireDate'); var imgCtrl = this.dataContext.findname("imgPhoto"); IDCtrl.text = data.EmployeeID; firstnameCtrl.text = data.Firstname; lastnameCtrl.text = data.Lastname; TitleCtrl.text = data.Title; hireDateCtrl.text = data.HireDate; imgCtrl.source = "Default.aspx?ID="+IDCtrl.text; this.dataContext.findname("imgAnimation").begin(); } |
這種做法的缺點是設計師得用 JavaScript 寫下許多程式碼。另一種做法是利用 Silverlight 控制項的 Tag 屬性,指定 Binding Expression ,然後於 JavaScript 中巡覽她們來一一指定值,如下列片段所示。 < Canvas xmlns = "http://schemas.microsoft.com/clIEnt/2007" xmlns:x = "http://schemas.microsoft.com/winfx/2006/xaml"> < Canvas name = "DataDemo"Height="600"WIDth="800"Tag="BindingContext:GetData,GetCount"> < Canvas.Background > < linearGradIEntBrush > < GradIEntStop color = "Yellow"Offset="0.0" /> < GradIEntStop color = "Orange"Offset="0.5" /> < GradIEntStop color = "Red"Offset="1.0" /> </ linearGradIEntBrush > </ Canvas.Background > < TextBlock Tag = "BindingFIEld:EmployeeID;BindingProperty:Text" name = "txtEmployeeID"WIDth="144"Height="24"Canvas.left="166"Canvas.top="23"Text="A00001"textwrapPing="Wrap"/> < TextBlock Tag = "BindingFIEld:Lastname;BindingProperty:Text"name="txtLastname"WIDth="320"Height="24"Canvas.left="500"Canvas.top="23"Text="Alean Company"textwrapPing="Wrap"/> < TextBlock Tag = "BindingFIEld:Firstname;BindingProperty:Text"name="txtFirstname"WIDth="320"Height="24"Canvas.left="166"Canvas.top="72"Text="Jeffray"textwrapPing="Wrap"/> < TextBlock Tag = "BindingFIEld:Title;BindingProperty:Text"name="txtTitle"WIDth="576"Height="24"Canvas.left="166"Canvas.top="122"Text="Taipen 101"textwrapPing="Wrap"/> < TextBlock Tag = "BindingFIEld:HireDate;BindingProperty:Text"name="txtHireDate"WIDth="576"Height="24"Canvas.left="166"Canvas.top="171"Text="2005/3/4"textwrapPing="Wrap"/> < Image name = "imgPhoto" Tag="BindingFIEld:EmployeeID;BindingProperty:Source;Format:Default.aspx?ID={0}"WIDth="357"Height="206"Canvas.left="400"Canvas.top="301"> < Image.Triggers > < EventTrigger RoutedEvent = "Image.Loaded"> < BeginStoryboard > < Storyboard name = "imgAnimation"> < DoubleAnimation Storyboard.Targetname = "imgPhoto" Storyboard.TargetProperty = "Opacity" From = "0.0"To="1.0"Duration="0:0:6"/> </ Storyboard > </ BeginStoryboard > </ EventTrigger > </ Image.Triggers > </ Image > < TextBlock name = "txtLabel1"WIDth="114"Height="24"Canvas.left="18"Canvas.top="23"Text="Employee ID:"textwrapPing="Wrap"/> < TextBlock name = "txtLabel1_copy"WIDth="120"Height="24"Canvas.left="349"Canvas.top="23"Text="Last name:"textwrapPing="Wrap"/> < TextBlock name = "txtLabel1_copy1"WIDth="130"Height="24"Canvas.left="18"Canvas.top="72"Text="First name:"textwrapPing="Wrap"/> < TextBlock name = "txtLabel1_copy2"WIDth="104"Height="24"Canvas.left="18"Canvas.top="122"Text="Title :"textwrapPing="Wrap"/> < TextBlock name = "txtLabel1_copy3"WIDth="93"Height="24"Canvas.left="18"Canvas.top="171"Text="Hire Date:"textwrapPing="Wrap"/> </ Canvas > </ Canvas > |
那如何解析 Tag 的 Binding Expression 並指定值呢?答案是利用 Silverlight 的 JavaScript 支援,一一巡覽所有控制項,一一解析 Tag ,然後再指定值。 ///////////////////////////////////////////////////////////////////////// // Silverlight Data Binding Helper 0.1 ///////////////////////////////////////////////////////////////////////// if (!window.SilverlightBinding) window.SilverlightBinding = {}; SilverlightBinding.BindingData = function(ctrl,bindingExpression) { var bindings = bindingExpression.split(';'); this.bindingComplete = false; this.ctrl = ctrl; for(var i = 0; i < bindings.length; i++) { var temp = bindings[i].split(':'); if(temp.length != 2) { this.bindingComplete = false; return; } if(temp[0] == 'BindingFIEld') this.bindingFIEld = temp[1]; else if(temp[0] == 'BindingProperty') this.bindingProperty = temp[1]; else if(temp[0] == 'Format') this.format = temp[1]; } this.bindingComplete = true; } SilverlightBinding.BindingData.prototype = { updateValue : function(dataItem) { if(this.bindingComplete) { if(this.format) eval('this.ctrl.'+this.bindingProperty+ " = this.format.replace('{0}',dataItem." +this.bindingFIEld+');'); else eval('this.ctrl.'+this.bindingProperty+' = dataItem.'+this.bindingFIEld+';'); } } } SilverlightBinding.BindingContext = function(bindingContainer) { var parseBinding = bindingContainer.tag.split(':'); this.bindingComplete = false; this.bindingContainer = bindingContainer; this.bindingControls = new Array(); this.currentDataIndex = 0; this.recordCount = 0; if(parseBinding.length == 2 && parseBinding[0] == "BindingContext") { var bindingMethods = parseBinding[1].split(','); if(bindingMethods.length == 2) { this.bindingMethod = bindingMethods[0]; this.bindingCountMethod = bindingMethods[1]; this.bindingComplete = true; } } if(!this.bindingComplete) alert('ERROR,Binding Failed.'); } SilverlightBinding.BindingContext.prototype = { _chilDWorker : function(parent,parseParent) { if(parent.tag && parent.tag != '') { if(parseParent) { var bindingData = new SilverlightBinding.BindingData(parent,parent.tag); if(bindingData.bindingComplete) { this.bindingControls.length++; this.bindingControls[this.bindingControls.length-1] = bindingData; } else delete bindingData; } try { var temp = parent.children; } catch(err) { return; } for(var i = 0; i < parent.children.count; i++) this._chilDWorker(parent.children.getItem(i),true); } }, initialize:function() { this._chilDWorker(this.bindingContainer,false); this._receiveCount(); this._receiveData(0); }, OnSucceeded: function(result,methodname) { if (methodname == userContext.bindingMethod) { for(var i = 0; i < userContext.bindingControls.length; i++) userContext.bindingControls[i].updateValue(result); } else if(methodname == userContext.bindingCountMethod) userContext.recordCount = result; }, OnFailed:function(error,methodname) { if(error !== null) { alert(error.get_message()); } }, _receiveData: function(index) { eval('PageMethods.'+this.bindingMethod+ '(index,this.OnSucceeded,this);' ); }, _receiveCount: function() { eval('PageMethods.'+this.bindingCountMethod+ '(this.OnSucceeded, next:function() { if(this.currentDataIndex+1 >= this.recordCount) return; this._receiveData(++this.currentDataIndex); }, prev:function() { if(this.currentDataIndex -1 < 0) return; this._receiveData(--this.currentDataIndex); } } |
使用此 JavaScript 物件的方法很簡單,只要於 handleLoad 中建立此物件,然後將 Silverlight 的根控制項傳入即可。 handleLoad: function(plugIn,rootElement) { this.plugIn = plugIn; this.dataContext = rootElement.children.getItem(0); this.bindingContext = new SilverlightBinding.BindingContext(rootElement.children.getItem(0)); this.bindingContext.initialize(); } |
切換上下筆時也很簡單。 function Next() { window.Silverlight.current_DataContext.bindingContext.next(); window.Silverlight.current_DataContext.dataContext.findname("imgAnimation").begin(); } function Prev() { window.Silverlight.current_DataContext.bindingContext.prev(); window.Silverlight.current_DataContext.dataContext.findname("imgAnimation").begin(); } |
下圖為執行畫面。 看不到炫麗效果啊?哈 ~~~ 我承認,我的美工細胞粉差! 本例下載位址: http://www.dreams.IDv.tw/~code6421/files/SLDataDemo1.zip 总结
以上是内存溢出为你收集整理的Silverlight 的 DataBindings全部内容,希望文章能够帮你解决Silverlight 的 DataBindings所遇到的程序开发问题。
如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。
评论列表(0条)