在silverlight中经常会添加一些其他的dll或者第三方的类库,我们知道silverlight作为客户端的插件,每次访问都需要去下载xap包中的资源或者是文件,当然这个访问的速度快慢和这个xap包的大小有直接关系,所以要尽可能的使xap包小点,ok,今天来说下,怎么实现动态加载dll以及实现缓存.
一.实现加载Dll
其实加载的dll的原理很简单,没错,就是使用我们强大的WebClient进行下载,然后使用AssemblyPart进行Load就可以了,就是这么简单,为了减小Xap的大小,我们把要加载的dll的所属程序的编译路径设置为ClientBin(如果当前的dll为第三方,则直接赋值到Clientbin下)不说废话,开始....
1.修改要添加的类库的编译路径为Clientbin,右键类库,选择最后一个属性
void InitAssembly()
{
//得到当前的Xap的所属的位置,格式为 http://localhost:8080/ClientBin
string url = Application.Current.Host.Source.AbsoluteUri;
int index = url.IndexOf("/ClientBin");
//找到dll的文件
url = url.Substring(0, index) + "/ClientBin/SilverlightClassLibrary.dll";
//使用WebClient进行下载
WebClient client = new WebClient();
//绑定回调方法
client.OpenReadCompleted += new OpenReadCompletedEventHandler(client_OpenReadCompleted);
//使用OpenReaadAsync异步下载
client.OpenReadAsync(new Uri(url));
}
看看回调方法,回调方法中有一句关键代码
AssemblyPart.Load(e.result);没错就是这个AssemblyPart(MSDn解释:程序集部件是将要包括在基于 Silverlight 的应用程序的程序包 (.xap) 中的程序集。),说白了,就是可以使用它来注册Silverlight程序要加载的dll或者其他类库.到此我们的动态记载已经完了,可以看到imgDll的地址就是一个dll中的地址,所以,在加载完之后就可以使用这个类库中的资源了.
void client_OpenReadCompleted(object sender, OpenReadCompletedEventArgs e)
{
if ((e.Error == null) && (e.Cancelled == false))
{
AssemblyPart assemblyPart = new AssemblyPart();
assemblyPart.Load(e.Result);
imgDll.Source = new BitmapImage() { UriSource = new Uri("/SilverlightClassLibrary;component/1.jpg", UriKind.RelativeOrAbsolute) };
}
}
<?xml version="1.0" encoding="utf-8" ?>
<manifest xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<assembly>
<!--最好和程序集一致-->
<name>SilverlightClassLibrary</name>
<version>1.0.0.0</version>
<!--就是上一步生成的Key-->
<publickeytoken>0fd6d4d48098ffeb</publickeytoken>
<!--当前程序编译的dll文件-->
<relpath>SilverlightClassLibrary.dll</relpath>
<!--缓存后压缩包的名字-->
<extension downloadUri="SilverlightClassLibrary.zip" />
</assembly>
</manifest>
有一点很重要,设置xml的Build Action为None,并且设置为总是复制
ok,到此整个步骤已经结束,如果给我们的silverlight程序启用了缓存,那么我们在动态加载dll的时候dll就会被缓存,就不用每次都去加载了.