首页 > 其他分享 >WPF使用Blazor的快速案例

WPF使用Blazor的快速案例

时间:2023-09-01 14:23:08浏览次数:60  
标签:文件 private Blazor 案例 value using fullName WPF

下面我们将讲解在WPF中使用Blazor,并且使用Blazor做一些文件编辑操作,下面是需要用到的东西

  • WPF
  • Blazor
  • Masa Blazor
  • Monaco

安装Masa Blazor模板

使用CMD指令安装模板

dotnet new install MASA.Template

新建Masa Blazor WPF App

  1. 找到如图的模板,然后点击下一步

  2. 下一步,新建项目名称FileEditor

添加Monaco

  1. 打开wwwroot/index.html,并且引用Monaco的依赖,将一下依赖添加到body里面的最尾部。
<script>
    var require = { paths: { 'vs': 'https://cdn.masastack.com/npm/monaco-editor/0.34.1/min/vs' } };
</script>
<script src="https://cdn.masastack.com/npm/monaco-editor/0.34.1/min/vs/loader.js"></script>
<script src="https://cdn.masastack.com/npm/monaco-editor/0.34.1/min/vs/editor/editor.main.nls.js"></script>
<script src="https://cdn.masastack.com/npm/monaco-editor/0.34.1/min/vs/editor/editor.main.js"></script>
  1. 新建Pages/Index.razor.cs文件
using System.IO;
using System.Text;
using Masa.Blazor;
using Masa.Blazor.Presets;
using Microsoft.AspNetCore.Components;
using Microsoft.JSInterop;

namespace FileEditor.Pages;

public partial class Index : IDisposable
{
    /// <summary>
    /// 文本内容
    /// </summary>
    private string value;

    private MMonacoEditor _editor;

    private DotNetObjectReference<Index>? _objRef;

    /// <summary>
    /// 定义Monaco的初始配置
    /// </summary>
    private object options = new
    {
        language = "md", // 设置语法
        automaticLayout = true, // 高度自适应
        theme = "vs-dark", // 主题
    };

    private string fullName;

    protected override void OnInitialized()
    {
        _objRef = DotNetObjectReference.Create(this);
    }

    /// <summary>
    /// 具体文件路径
    /// </summary>
    [Parameter]
    [CascadingParameter(Name = nameof(FullName))]
    public string FullName
    {
        get => fullName;
        set
        {
            fullName = value;
            UpdateValue();
        }
    }

    /// <summary>
    /// Monaco初始化事件
    /// </summary>
    private async Task InitMonaco()
    {
        // 监听CTRL+S 2097 = CTRL+S 快捷键
        // 调用Monaco的Command,传递当前对象,并且指定当触发快捷键的时候调用当签对象的指定方法。
        await _editor.AddCommandAsync(2097, _objRef, nameof(SaveValue));
    }

    /// <summary>
    /// 更新value
    /// </summary>
    private void UpdateValue()
    {
        if (string.IsNullOrEmpty(fullName))
        {
            return;
        }

        var info = new FileInfo(fullName);
        if (!info.Exists) return;
        using var fileStream = info.OpenText();
        value = fileStream.ReadToEnd();
    }

    /// <summary>
    /// 更新文件内容
    /// </summary>
    [JSInvokable]
    public async Task SaveValue()
    {
        try
        {
            await using var fileStream = File.OpenWrite(fullName);
            fileStream.Position = 0;
            await fileStream.WriteAsync(Encoding.UTF8.GetBytes(value));
            fileStream.Close();
        }
        catch (Exception e)
        {
            await PopupService.EnqueueSnackbarAsync(new SnackbarOptions()
            {
                Title = "保存文件错误",
                Content = e.Message
            });
        }
    }

    public void Dispose()
    {
        _editor.Dispose();
        _objRef?.Dispose();
    }
}

Index.razor.cs文件中我们实现了拦截FullName的set,当被set的时候说明上级组件选择了文件并且通过CascadingParameter传递了参数到当前组件。

并且对于当前的Value进行更新,

打开Index.razor

@page "/"
@inject IPopupService PopupService

<MMonacoEditor InitCompleteHandle="async () => await InitMonaco()"
               @bind-Value="value"
               Height="@("100%")"
               EditorOptions="options" @ref="_editor">
</MMonacoEditor>

我们对于cs的一些方法和参数进行了绑定,并且bind-value了value的值,我们在cs文件中更新了value就自动更新了UI的显示的值。

然后我们打开Shared/MainLayout.razor文件添加打开文件选择器,从而选择文件。

@using Microsoft.Win32
@inherits LayoutComponentBase

<MApp>
    <MAppBar App>
        <MAppBarNavIcon @onclick="() => _drawer = !_drawer"></MAppBarNavIcon>
        <MToolbarTitle>FileEditor</MToolbarTitle>
        <MButton OnClick="OpenFile">打开文件</MButton>
        <MSpacer></MSpacer>
        <MButton Text Color="primary" Target="_blank" Href="https://docs.masastack.com/blazor/introduction/why-masa-blazor">About</MButton>
    </MAppBar>

    <MNavigationDrawer App @bind-Value="_drawer">
        <MList Nav Routable>
            <MListItem Href="/" ActiveClass="primary--text">
                <MListItemIcon>
                    <MIcon>mdi-home</MIcon>
                </MListItemIcon>
                <MListItemContent>
                    <MListItemTitle>Home</MListItemTitle>
                </MListItemContent>
            </MListItem>
            <MListItem Href="/counter" ActiveClass="primary--text">
                <MListItemIcon>
                    <MIcon>mdi-plus</MIcon>
                </MListItemIcon>
                <MListItemContent>
                    <MListItemTitle>Counter</MListItemTitle>
                </MListItemContent>
            </MListItem>
            <MListItem Href="/fetchdata" ActiveClass="primary--text">
                <MListItemIcon>
                    <MIcon>mdi-list-box</MIcon>
                </MListItemIcon>
                <MListItemContent>
                    <MListItemTitle>Fetch data</MListItemTitle>
                </MListItemContent>
            </MListItem>
        </MList>
    </MNavigationDrawer>

    <MMain>
        <MContainer Fluid Style="height: 100%">
            <CascadingValue Value="fullName" Name="FullName">
                <MErrorHandler>
                    @Body
                </MErrorHandler>
            </CascadingValue>
        </MContainer>
    </MMain>
</MApp>

@code {

    private bool? _drawer;

    private string fullName;

    private void OpenFile()
    {
        var openFileDialog = new OpenFileDialog();
        openFileDialog.Title = "请选择您的文件";
        openFileDialog.Filter = "文本文件 (*.txt, *.md)|*.txt;*.md";
        bool? result = openFileDialog.ShowDialog();
        if (result == true)
        {
            fullName = openFileDialog.FileName;
        }
    }
}

在这里我们将使用Microsoft.Win32.OpenFileDialog打开文件选择器,并且指定选择文件的类型,

当前文件选择器返回true,则fullName的值,fullName则会通过CascadingValue组件的绑定传递到<CascadingValue></CascadingValue>内的所有子组件。

下面我们看看实际使用效果。

技术交流

qq群:452761192

wx:wk28u9123456789(请备注技术交流)

源码下载地址:https://code-token.oss-cn-beijing.aliyuncs.com/FileEditor.zip

标签:文件,private,Blazor,案例,value,using,fullName,WPF
From: https://www.cnblogs.com/hejiale010426/p/17671769.html

相关文章

  • WPF 动态更改启动窗体startupUri
    第一步:在App.xaml里,把StartupUri=""去掉,改成Startup="Application_Startup"第二步:在App.xaml.cs里,增加Application_Startup事件:privatevoidApplication_Startup(objectsender,StartupEventArgse){ApplicationcurrApp=Application.Current;currAp......
  • (!重要)25动态数据传递/布局综合案例
        获取自身的脚本,持有脚本调用自身的方法更新自己   ......
  • flume采集目录到HDFS案例:
    (1)采集需求:某服务器的某特定目录下,会不断产生新的文件,每当有新文件出现,就需要把文件采集到HDFS中去(2)根据需求,首先定义以下3大要素a):采集源,即source——监控文件目录:spooldirb):下沉目标,即sink——HDFS文件系统:hdfssinkc):source和sink之间的传递通道——chann......
  • 服务器数据恢复-vmware ESXI虚拟机误还原快照导致数据丢失的数据恢复案例
    服务器数据恢复环境:从物理机迁移一台虚拟机到ESXI,迁移后做了一个快照。该虚拟机上部署了一个SQLServer数据库,存放了5年左右的数据。ESXI上有数十台虚拟机,EXSI连接了一台EVA存储,所有的虚拟机都在EVA存储上。服务器故障:由于工作人员的误操作,不小心将几年前迁移数据后做的快照还原......
  • WPF Textblock标签下 Run标签-----显示空白或者消除空白
    消除Run之前的空白是将Run标签布局时头尾相连,如下:<TextBlock><RunText="A"></Run><RunText="B"></Run></TextBlock> 消除Run之间连接的空白格式,方式如下:<TextBlock><RunText="A&quo......
  • 医学案例|Cochran's Q检验
    一、案例介绍当前有一名医生拟评价药物A对50名高血压患者的降压效果。在患者服用药物A后的第3天、第5天和第7天时分别进行记录。该医生想知道服用药物A的高血压患者血压是否一直在好转。血压好转赋值为1,血压没变化赋值为0,。部分数据如下:二、问题分析比较三组或多组二分类变量......
  • Blazor下的serilog
    前段时间学习了blazor,按教程一步一步学习的,但是发现borad.razor上的游戏第一个总是对应不上,我觉得是css没有写好的原因,所以没有过多探究。近日学习了serilog,发现配置起来好像比log4net要简单,深入研究了一下,觉得挺有意思。于是想采用日志的方式把前面的问题找出来,所以又学了一系......
  • 服务器数据恢复-RAID6磁盘重组RAID5导致原RAID6数据丢失的数据恢复案例
    服务器数据恢复环境:一台存储设备中有一组由12块硬盘组建的RAID6磁盘阵列,上层采用EXT3文件系统,共划分3个LUN。服务器故障&分析:存储设备在运行过程中RAID6阵列突然不可用,管理员对故障存储进行了重新分配RAID的操作并进行了初始化。初始化一段时间后,管理员察觉有异,于是强行终止初始......
  • WPF设置传参、点击按钮改变长度
    前台代码<!--通过传递ElementName--><Buttonx:Name="btn1"Width="200"Height="27"Command="{BindingCommand}"CommandParameter="{BindingElementName=btn1}"/><!--......
  • 闰年、数字统计和成绩分析 - Java编程案例
    目录1.判断闰年2.统计数字出现次数3.成绩分析导言:最近,我在学习Java编程过程中遇到了一些有趣的问题,其中包括判断闰年、统计数字出现次数以及分析成绩等。通过编写代码并解决这些问题,我不仅加深了对Java的理解,还提高了编程能力。在本篇博客中,我将与大家分享我遇到的这些问题以及......