Blazor入门笔记(4)-组件的生命周期
1.环境
VS2019 16.5.1
.NET Core SDK 3.1.200
Blazor WebAssembly Templates 3.2.0-preview2.20160.5
2.简介
Blazor的生命周期与React组件的生命周期类似,也分为三个阶段:初始化阶段、运行中阶段和销毁阶段,其相关方法有10个,包括设置参数前、初始化、设置参数之后、组件渲染后以及组件的销毁,但是这些方法有些是重复的,只不过是同步与异步的区别。本文将介绍Blazor WASM的生命周期。
3.图解
首先将结果图呈现,代码位于第4部分:

Blazor生命周期方法主要包括:
| 1 | 设置参数前 | SetParametersAsync |
| 2 | 初始化 | OnInitialized/OnInitializedAsync |
| 3 | 设置参数后 | OnParametersSet/OnParametersSetAsync |
| 4 | 组件渲染呈现后 | OnAfterRender/OnAfterRenderAsync |
| 5 | 判断是否渲染组件 | ShouldRender |
| 6 | 组件删除前 | Dispose |
| 7 | 通知组件渲染 | StateHasChanged |
在所有生命周期函数中,有以下需要注意的点:
(1)前5种方法的声明都是virtual,除SetParametersAsync为public外,其他的都是protected。
(2)OnAfterRender/OnAfterRenderAsync方法有一个bool类型的形参firstRender,用于指示是否是第一次渲染(即组件初始化时的渲染)。
(3)同步方法总是先于异步方法执行。
(4)Dispose函数需要通过使用@implements指令实现IDisposable接口来实现。
(5)StateHasChanged无法被重写,可以被显示调用,以便强制实现组件刷新(如果ShouldRender返回true,并且Blazor认为需要刷新);当组件状态更改时不必显示调用此函数,也可导致组件的重新渲染(如果ShouldRender返回true),因为其已经在ComponentBase内部的处理过程(第一次初始化设置参数时、设置参数后和DOM事件处理等)中被调用。
4.代码实例
首先使用VS创建一个新Blazor WASM应用程序,其默认带有一个Count.razor组件,这个组件是示例如何使用事件和更改组件状态的,可以直接用来示例。
4.1.LifecycleTest组件
为了显示父组件更改属性导致组件渲染的这一过程中组件生命周期方法的调用过程,因此需要新建一个组件LifecycleTest.razor,将原来Count.razor组件,的所有代码都剪切到LifecycleTest.razor中,并为其添加一个组件参数Title,并在页面组件中显示:
<h3>LifecycleTest,Title:@Title</h3>
[Parameter]
public string Title { get; set; }
为了显示通过调用StateHasChanged方法使组件刷新的过程,在LifecycleTest.razor组件中添加一个新的按钮“NotifyStateHasChanged”,并为其绑定事件方法:
<button class="btn btn-secondary" @onclick="NotifyStateHasChanged">NotifyStateHasChanged</button> void NotifyStateHasChanged()
{
Console.WriteLine("NotifyStateHasChanged");
StateHasChanged();
}
此外,为了显示组件被删除时Dispose方法的执行过程,需要为组件继承IDisposable接口,并实现IDisposable的Dispose方法:
public void Dispose()
{
Console.WriteLine("Dispose");
}
最后,实现所有的生命周期函数,LifecycleTest.razor的所有的代码如下:
@implements IDisposable
<h3>LifecycleTest,Title:@Title</h3>
<p>Current count: @currentCount</p>
<button class="btn btn-primary" @onclick="IncrementCount">Click me</button>
<button class="btn btn-secondary" @onclick="NotifyStateHasChanged">NotifyStateHasChanged</button> @code { [Parameter]
public string Title { get; set; } private int currentCount = ; private void IncrementCount()
{
currentCount++;
} void NotifyStateHasChanged()
{
Console.WriteLine("NotifyStateHasChanged");
StateHasChanged();
} #region 初始化组件
protected override void OnInitialized()
{
Console.WriteLine("OnInitialized");
base.OnInitialized();
} protected override Task OnInitializedAsync()
{
Console.WriteLine("OnInitializedAsync");
return base.OnInitializedAsync();
}
#endregion /// <summary>
/// 设置参数前
/// </summary>
/// <param name="parameters"></param>
/// <returns></returns>
public override Task SetParametersAsync(ParameterView parameters)
{
Console.WriteLine("SetParametersAsync");
return base.SetParametersAsync(parameters);
} #region 设置参数之后
protected override void OnParametersSet()
{
Console.WriteLine("OnParametersSet");
base.OnParametersSet();
} protected override Task OnParametersSetAsync()
{
Console.WriteLine("OnParametersSetAsync");
return base.OnParametersSetAsync();
}
#endregion #region 组件呈现之后
protected override void OnAfterRender(bool firstRender)
{
Console.WriteLine($"OnAfterRender, firstRender:{firstRender}");
base.OnAfterRender(firstRender);
} protected override Task OnAfterRenderAsync(bool firstRender)
{
Console.WriteLine($"OnAfterRenderAsync, firstRender:{firstRender}");
return base.OnAfterRenderAsync(firstRender);
}
#endregion /// <summary>
/// 是否渲染组件
/// </summary>
/// <returns></returns>
protected override bool ShouldRender()
{
Console.WriteLine("ShouldRender");
return true;
} public void Dispose()
{
Console.WriteLine("Dispose");
}
}
4.2.Count.razor页面
现在,我们在Count.razor中引用LifecycleTest组件,为其参数Title赋值title,并在Count.razor中添加一个按钮,添加事件ChangeParamter,用于改变title的值。Count.razor的所有代码如下:
@page "/counter" <button class="btn btn-warning" @onclick="ChangeParamter">ChangeParamter</button>
<LifecycleTest Title="@title"></LifecycleTest> @code { string title = "here is the title parameter"; void ChangeParamter()
{
title = DateTime.Now.ToString("o");
}
}
4.3.执行结果
运行本应用程序,进入count页面,在浏览器的控制台上可以看到以下输出:

清空控制台,点击“ChangeParamter”按钮,可以观测到页面上的Title位置的值发生了变化,控制台的输出结果如下:

清空控制台,点击“Click me”按钮,可以看到Current count后面的值增加了1,控制台的输出结果如下:

清空控制台,点击“NotifyStateHasChanged”按钮,可以看到页面并没有发生变化,不过,控制台的输出结果如下:

本文参考:
Blazor入门笔记(4)-组件的生命周期的更多相关文章
- Blazor入门笔记(6)-组件间通信
1.环境 VS2019 16.5.1.NET Core SDK 3.1.200Blazor WebAssembly Templates 3.2.0-preview2.20160.5 2.简介 在使用B ...
- ReactJS入门(二)—— 组件的生命周期
如果你熟悉avalon,使用过 data-include-rendered 和 data-include-loaded 等回调方法,那么你会很好地理解React组件的各个生命周期. 说白了其实就是Re ...
- reactjs入门到实战(七)---- React的组件的生命周期
React的组件的生命周期有三个状态分别是:挂载(生产组件示例化.准备挂载到页面.挂载到页面).更新(更新值.更新DOM).和卸载(卸载后). >>>其他 getInitia ...
- ReactJS入门3:组件的生命周期
本文主要介绍组件的生命周期. 组建的生命周期主要分为3个:Mounting.Updating.Unmounting. 1. Mounting:组件被加载到DOM 在本阶段,主要有三个方法: 1 ...
- react 入坑笔记(六) - 组件的生命周期
React 组件生命周期 详细参考: react 组件生命周期 组件的生命周期可分为三个状态: 1.Mounting:已经挂载/插入到真实 DOM 树上: 2.Updating:正在被重新渲染: 3. ...
- 【React】学习笔记(二)——组件的生命周期、React脚手架使用
原教程视频:ttps://www.bilibili.com/video/BV1wy4y1D7JT?p=2&spm_id_from=pageDriver 目录 一.组件的生命周期 1.1.生命周 ...
- Jetpack 架构组件 Lifecycle 生命周期 MD
Markdown版本笔记 我的GitHub首页 我的博客 我的微信 我的邮箱 MyAndroidBlogs baiqiantao baiqiantao bqt20094 baiqiantao@sina ...
- react(一):组件的生命周期
最近兄弟团队让我去帮忙优化两个页面,前端用的react全家桶,后端用的python,上一次写react代码都过去一年了,顺着以前的的学习思路,再捋顺一下react的要点 组件的生命周期就是Reac的工 ...
- 【老孟Flutter】Stateful 组件的生命周期
老孟导读:关于生命周期的文章共有2篇,第一篇是介绍 Flutter 中Stateful 组件的生命周期. 博客地址:http://laomengit.com/blog/20201227/Statefu ...
随机推荐
- 简单易懂的Servlet路径问题
关于servlet路径,我看了一下网上别人的博客园,发现都有一个通病,讲的太专业了,又抓不住关键部分,往往看一眼就不想看第二眼.所以我特地准备了初学者所通识的servlet路径问题. 1.标识符 /j ...
- c++中比较好用的黑科技
切入正题,上黑科技 一.黑科技函数(常用的我就不写了,例如sort函数) 1.next_permutation(a+1,a+1+n) a[1-n]全排列 2.reverse(a+1,a+1+n) 将a ...
- Go组件学习:如何读取ini配置文件
代码示例全部保存在,欢迎star:https://github.com/EnochZg/golang-examples 安装组件 go get gopkg.in/ini.v1 使用 先创建ini后缀的 ...
- win下安装virtualenv和创建django项目
一.由于一直在Linux环境下开发,想了解一下winPython开发环境: 1.打开cmd,pip install virtualenv 2.virtualenv test 由于这样需要进入到目录下才 ...
- linux 读取 USB HID鼠标坐标和点击 在 LCD上显示
首先要,编译内核时启用了 USB HID 设备.启用了 鼠标 . 在开发板上插入usb 时会有如下提示. 可以看到,多了一个 mouse0 和 eventX 打出来的是我的 联想鼠标. 1, 在 终端 ...
- Java Grammar(二):运算符
运算符简介 计算机自打诞生以来,用作最多的就是进行计算,而计算离不开运算符,所以运算符在我们的Java语言中的地位举足轻重,我们现在就来了解一下Java给我们提供的运算符. 从运算的元素的个数来区分, ...
- 03、MySql的数据类型
MySQL中定义数据字段的类型对你数据库的优化是非常重要的. MySQL支持多种类型,大致可以分为三类:数值.日期/时间和字符串(字符)类型. 1.数字类型 类型 大小 范围(有符号) 范围(无符号) ...
- C++总结之template
函数模板 我们可以把函数模板当做一种特殊的函数,里面的参数类型可以是任意类型,这样的话我们就可以减少重复定义,从而让这个函数模板自动适应不同的参数类型,也就是说函数可以适应多种类型的参数,例如doub ...
- Python习题集(二)
每天一习题,提升Python不是问题!!有更简洁的写法请评论告知我! https://www.cnblogs.com/poloyy/category/1676599.html 题目 a = [1, 2 ...
- Http报文和Request和Response的常用方法
简述 它是HTTP应用程序之间发送的数据块.这些数据块以一些文本形式的元信息开头,这些信息描述了报文的内容及含义,后面跟着可选的数据部分.这些报文都是在客户端.服务器和代理之间流动. HTTP报文的流 ...