早上好,我一直在尝试为我的应用程序创建一个更新程序,并且几乎得到了最终结果,但是我似乎无法让 UI 报告进度,我已经设置了 Onpropertychanged 事件和下载的异步任务,但不会反映在 ui 中
我有下载代码,
private async Task DownloadUpdateAsync(string url, string destinationPath)
{
using (var client = new HttpClient())
{
var response = await client.GetAsync(url,
HttpCompletionOption.ResponseHeadersRead);
response.EnsureSuccessStatusCode();
var totalBytes = response.Content.Headers.ContentLength ?? 0;
var readBytes = 0L;
var buffer = new byte[8192];
using (var stream = await response.Content.ReadAsStreamAsync())
using (var fileStream = new FileStream(destinationPath, FileMode.Create,
FileAccess.Write, FileShare.None))
{
await Task.Run(async () =>
{
while (true)
{
var bytesRead = await stream.ReadAsync(buffer, 0, buffer.Length);
if (bytesRead == 0)
{
await Task.Yield();
break;
}
await fileStream.WriteAsync(buffer, 0, bytesRead);
readBytes += bytesRead;
Application.Current.Dispatcher.Invoke(() => {
DownloadProgress = (int)((readBytes / (float)totalBytes) * 100);
Process = DownloadProgress.ToString(); // Convert to string
OnPropertyChanged(nameof(DownloadProgress));
OnPropertyChanged(nameof(Process)); // Notify property change for Process
Debug.WriteLine(Process); // Print the Process value
});
}
});
}
}
}
我一直在尝试让进度条工作,但是注意到 debug.writeline 工作了,所以排除了它是 int 转换,我对文本框做了同样的事情,但仍然没有更新
Int 设置
public int DownloadProgress
{
get => downloadProgress;
set
{
if (downloadProgress != value)
{
downloadProgress = value;
OnPropertyChanged(nameof(DownloadProgress));
}
}
}
已在 onpropertyChanged 事件上设置断点行,它确实收到了更新的值,但未在 UI 中反映这一点
XAML
<Window.DataContext>
<viewmodel:UpdateViewModel/>
</Window.DataContext>
<Window.Resources>
<Style x:Key="CustomProgressBar" TargetType="ProgressBar">
<Setter Property="Foreground" Value="#DCA3FF"/>
<Setter Property="Background" Value="#7C8093"/>
<Setter Property="BorderBrush" Value="Transparent"/>
<Setter Property="BorderThickness" Value="0"/>
<Setter Property="Height" Value="20"/>
</Style>
</Window.Resources>
<Grid>
<Border Background="#7C8093" CornerRadius="5">
<StackPanel>
<TextBlock Foreground="White" Text="An update is available."/>
<TextBlock Foreground="White" Text="Change Log: update test"/>
<Button Content="Update Now" Command="{Binding UpdateCommand}" />
<ProgressBar Height="20" Value="{Binding DownloadProgress, Mode=OneWay}" />
<TextBlock Width="700" Text="{Binding Process, UpdateSourceTrigger=PropertyChanged}"/>
<Button Content="Test Progress" Command="{Binding TestProgressCommand}" />
</StackPanel>
</Border>
</Grid>
我很确定我有这个,我已经搜索过,甚至在写在这里之前使用过chatgpt,但仍然有问题,反映了下载的进度
我已尽力提供有关该问题的尽可能多的信息。
当前使用
ProgressBar
的一个问题是,您分配的值不超过 100,但没有设置栏上的 Maximum
属性(默认为 1
)。对于任何 1 或以上的值,这将导致进度条显示为 100%,从而呈现未更新的外观。
只需尝试这个:
<ProgressBar Maximum="100"
Height="20"
Value="{Binding DownloadProgress, Mode=OneWay}" />
此外(尽管不太可能是问题的原因),对您问题的评论是正确的;你不需要在这里使用
Task.Run
,如果你不使用 Task.Run
,你也不需要使用 Dispatcher.Invoke
。而且你不需要Task.Yield
;当“bytesRead”为 break
时,只是 0
。