我是WP7编码新手。 我正在寻找示例代码或指导以下任务:
我在远程服务器上有3个html页面,我想下载每个页面的内容并将其发布到3个不同的全景页面(显示为文本块)。
我写了3套webclient来加载html页面;它可以显示为它所假设的位置。我面临的问题是,在下载时/期间,UI线程是“freez”且没有响应。
任何人都可以指导我/向我展示示例代码,我可以将线程放到后台,一旦完成,并在UI中显示?
这是我用来下载HTML页面的代码。
private async void GetNewsIndex(string theN)
{
string newsURI = newsURL + theN;
string fileName = theN + "-temp.html";
string folderName = "news";
prgBar01.Visibility = System.Windows.Visibility.Visible;
try
{
Task<string> contentDataDownloaded = new WebClient().DownloadStringTaskAsync(new Uri(newsURI));
string response = await contentDataDownloaded;
WriteTempFile(theN, response.ToString());
string contentData = ProcessDataToXMLNews(fileName, folderName);
WritenewsIndexXMLFile(newsIndexURI, folderName, contentData);
DisplayNewsIndex();
}
catch
{
//
}
}
我根据 Sinh Pham 的建议修改了上述代码,并且它按预期完美运行。但是,因为我需要运行它的3个瞬间来同时从不同的源下载页面;代码中断。有什么想法吗?
答案 0 :(得分:2)
您可以查看使用HttpWebRequest。这在后台线程上异步工作,与WebClient
内部使用的相同。 WebClient简单地抽象了较低级别的工作,但正如您所看到的,它具有在UI线程上返回的缺点。有一个如何使用HttpWebRequest here的例子。
答案 1 :(得分:2)
您确定在下载时用户界面冻结,而不是在处理数据时冻结吗?从您的代码看来,您似乎只是在做
WriteTempFile(theN, response.ToString());
string contentData = ProcessDataToXMLNews(fileName, folderName);
WritenewsIndexXMLFile(newsIndexURI, folderName, contentData);
DisplayNewsIndex();
UI线程上的。尝试将它们包装在BackgroundWorker中。
编辑:类似这样的事情:
Edit2:由于你的DisplayNewsIndex()函数导致UI发生变化,因此必须在UI线程上执行。
var bw = new BackgroundWorker();
bw.DoWork += delegate {
WriteTempFile(theN, response.ToString());
string contentData = ProcessDataToXMLNews(fileName, folderName);
WritenewsIndexXMLFile(newsIndexURI, folderName, contentData);
Deployment.Current.Dispatcher.BeginInvoke(() => {
DisplayNewsIndex();
});
};
bw.RunWorkerAsync();
答案 2 :(得分:1)
下载完全异步。但是你的问题是在UI线程上处理数据。您应该考虑在不同的线程上执行此操作。
答案 3 :(得分:1)
无论你在哪里启动.webClient(),或者它是否异步(我怀疑你在windows phone webClient中有其他选项而不是异步)“它完全在UI线上运行”。
这就是你的用户界面冻结的原因。这实际上是一个错误,所以其他人也建议您考虑使用HttpWebRequest
。我要添加的内容是我的博客文章下面的链接,其中包含一个名为WebDownloader
的帮助程序类,它可以减少所有麻烦并使您的生活更轻松:
http://www.manorey.net/mohblog/?p=17#content
你唯一需要做的就是:
var downloader = new WebDownloader{ Url = "something" };
downloader.OnCompleted += (a, b) => { /*downloader.Result is ready!*/ };
downloader.OnFailed += (a, b) => { /*download failed!*/ };
downloader.Download();
您还可以通过以下方式调用取消下载任务:
downloader.Cancel();
答案 4 :(得分:0)
这是因为你可能正在主线程(UI线程)上下载内容。当你这样做时,它将占用该线程的所有资源,没有处理器时间来更新屏幕。将下载移动到后台,它将(如果这是问题)解决!