做一個WEB程序能夠在盡量修改極少程序代碼的情況下輕松制定皮膚以及切換皮膚應該都是需要的誰也不想在網站界面想要改版的時候要改一大片邏輯代碼
一個合格的皮膚機制體系的實現應該要做到以下幾點
>頁面模板上要極少擁有邏輯代碼(如果模板上擁有大量邏輯代碼那估計這個也不叫作模板了)
>能夠輕松改變頁面布局同時不影響程序代碼(cs)
>新模板的定制基本上能由皮膚制作者參照舊模板自行完成不需要開發人員太多介入
>保持性能
然後來看看都有哪些方法大家用來實現所謂的皮膚機制同時進行各個方法的一些個人說明
改變頁面調用的CSS文件來換膚
這一個嚴格上來講不應該算作皮膚機制雖然CSS非常強大也能夠通過它來任意改變頁面元素布局但它的HTML始終是不變的所以局限性是非常大的
優點完全不影響性能甚至可以完全不由服務端代碼來管理它的變換可以使用JS來切換皮膚(由此在我們有一套完美皮膚機制的情況下這種方法可以完全不與此機制沖突讓用戶在客戶端作更多的個性化)
缺點如果作為核心皮膚機制的話非常有局限性
示例如QQCOM LACOM上面的一些可點擊的小色塊就是改變調用的CSS文件來實現換膚
讀取模板文件替換標識符為要顯示的內容與數據輸出
這一個方法的靈活性比較高每套皮膚可以有自己的布局有自己的個性
實現比如模板中有一個標識$Subject程序代碼會把它替換成文章標題然後有一個標識塊<!—Loop[ArticleList]><h>$Subject</h><div>$Content</div><!/Loop>程序代碼會把它替換成一個文章列表最後輸出處理完所有標識符的內容
通常我們會緩存讀取到的模板內容但字符串的替換始終不可避免或者也會把替換過的內容也緩存起來但這樣子就等於要緩存模板內容以及替換過的內容占用了兩份似乎挺重復內容的內存(為什麼?不然總不該每次數據有改變的時候就去作IO操作讀取操作讀模板文件吧這似乎比字符串替換性能更差)
優點模板靈活程度很高可以隨便改動頁面布局
缺點影響性能開發人員維護難必須有特定的標識符來表示頁面變量後期維護可能會帶來非常多的問題
使用ASPNET的App_Themes
這一個方法應該是極差的一個方法根本只是ASPNET的一個小纂頭雞肋基本上不實用
實現比如定制一個BUTTON的樣式是這樣子的<asp:buttonrunat=server BackColor=lightblueForeColor=black />類似這樣的代碼存在於skin文件中然後它的換膚機制如下<%@ Page Language=C# Theme=default %>在App_Themes目錄下是各套皮膚的獨立文件夾各個文件夾包含皮膚的樣式以及圖片文件等等也可以包含skin文件
優點只有ASPNET才有
缺點包含了第一種方法的缺點skin的樣式定制方式還要嚴重依賴使用ASPNET服務端控件同時也影響性能靈活性也極低
動態載入ASCX文件(ASPNET用戶控件)|| 使用master(母版)
這個方法應該也是很多使用ASPNET的人使用的方法有時候它還會與第三種方法結合使用如果對性能需求不是很嚴格的話中小型項目可以使用
實現使用LoadControl()動態載入ASCX文件或(與)指定頁面的MasterPageFile(目標皮膚文件夾的)實現(通常ascx與master還會結合使用)
優點靈活性極高每個皮膚有獨立的布局直接使用了CS文件的變量與方法ETC…甚至每套皮膚還有自己獨立的代碼文件
缺點影響性能有興趣可以自己去反編譯LoadControl方法同時在頁面要使用<%%>這種代碼塊有時候感覺也有點不雅
Xml + xslt
傳說xml取代html是趨勢??不清楚不了解應該不可能此種方法我沒有深入了解過不過大概實現應該是要這樣子?每一個XML(輸出數據)會有一個對應的XSL文件(控制樣式)如下
xml文件
<?xml version=encoding=ISO ?><breakfast_menu><food><name>Belgian Waffles</name><price>$</price><description>two of our famous Belgian Waffles with plenty of real maplesyrup</description><calories></calories></food><food><name>Cakes</name><price>$</price><description>sweet cakes</description><calories></calories></food></breakfast_menu>
xsl文件
<?xmlversion= encoding=ISO ?><html xsl:version= xmlns:xsl=
xmlns=
><body ><xsl:for
each select=
breakfast_menu/food
> <div > <span ><xsl:value
of select=
name
/></span><xsl:value
of select=
price
/></div> <div><xsl:value
of select=
description
/> <span ><xsl:value
of select=
calories
/></span></div></xsl:for
each></body></html>
這樣子做有什麼好處麼我沒有體驗到
讀取模板文件生成aspx文件到每套皮膚的獨立文件夾下通過地址重寫指定到這些文件夾
這個方法的最終效果對於用戶來說和第二種方法應該是差不多的優點就是性能比較高而且還能直接使用CS代碼裡面的變量方法ETC…另外也可以不會有<%%>代碼塊的存在可以存在自己的模板語言如同第二種方法的$Subject <!—Loop>標識符一般
優點幾乎不影響性能只有第一次讀取生成ASPX文件需要損失性能靈活性極高模板代碼可讀性也可以實現到很高
缺點啟動時需要讀取分析時間(不過這應該算是小問題)另外有一套皮膚它就要生成與之對應的一套ASPX文件(當然這個可以解決)
利用ASPNET開始才擁有的VirtualPathProvider來實現
虛擬文件機制這個應該算是第六種方法的加強版最終的效果和第六種差不多只是不會生成那些ASPX文件而已取而代之的便是長駐在內存中
實現實現兩個類一個繼承至VirtualPathProvider一個繼承至SkinFileVirtualPathProvider裡有個FileExists方法重寫成判斷請求的路徑是否是皮膚文件路徑如果是GetFile就實例一個SkinFile(這一個SkinFile我們會對模板進行處理可以擁有自己的模板語言)另外有一個GetCacheDependency方法可以來將模板文件作為虛擬文件機制的緩存依賴文件一旦模板文件被修改了它就會再重新解析模板文件這裡先不作贅述具體的查看MSDN的相關文檔具可了解
優點與相同
缺點第一次啟動需要損失性能(但這也不可避免)
還有更多的實現方法還沒用過個人先不發表觀點比如使用BuildProvider但這一個需要有比較強的詞法分析與語法分析能力
From:http://tw.wingwit.com/Article/program/net/201311/13030.html