当前位置: 首页 > news >正文

【Unity3D】UI Toolkit数据动态绑定

1 前言

        本文将实现 cvs 表格数据与 UI Toolkit 元素的动态绑定。

        如果读者对 UI Toolkit 不是太了解,可以参考以下内容。

  • UI Toolkit简介
  • UI Toolkit容器
  • UI Toolkit元素
  • UI Toolkit样式选择器
  • UI Toolkit自定义元素

        本文完整资源见→UI Toolkit数据动态绑定。

2 数据动态绑定案例

2.1 UI 搭建

        样式和 UI 层级结构如下。

        MainLayout.xml

<ui:UXML xmlns:ui="UnityEngine.UIElements" xmlns:uie="UnityEditor.UIElements" xsi="http://www.w3.org/2001/XMLSchema-instance" engine="UnityEngine.UIElements" editor="UnityEditor.UIElements" noNamespaceSchemaLocation="../../../../UIElementsSchema/UIElements.xsd" editor-extension-mode="False"><Style src="project://database/Assets/Role/View/StyleSheets/RoleStyle.uss?fileID=7433441132597879392&amp;guid=d93d80f270ec5014c90e97cc8c404d1f&amp;type=3#RoleStyle" /><ui:VisualElement name="Background" style="flex-grow: 1; background-image: url(&apos;project://database/Assets/Role/Img/Background_Sky.png?fileID=2800000&amp;guid=02ebb0e77ccd96143911134d6e39e1db&amp;type=3#Background_Sky&apos;); padding-left: 4%; padding-right: 4%; padding-top: 4%; padding-bottom: 4%; -unity-background-scale-mode: scale-and-crop;"><ui:Label text="Game Role" display-tooltip-when-elided="true" name="TitleLab" style="height: 10%; margin-bottom: 1%; -unity-text-align: middle-left; font-size: 100px; -unity-font-style: italic; color: rgb(34, 34, 34);" /><ui:VisualElement name="Body" style="flex-grow: 1; flex-direction: row;"><ui:VisualElement name="RoleTemplate" style="flex-basis: 25%; margin-left: 10px; margin-right: 10px; margin-top: 10px; margin-bottom: 10px; background-color: rgba(0, 0, 0, 0.2); border-top-left-radius: 10px; border-bottom-left-radius: 10px; border-top-right-radius: 10px; border-bottom-right-radius: 10px;"><ui:VisualElement name="Image" style="flex-basis: 50%; margin-left: 5%; margin-right: 5%; margin-top: 5%; margin-bottom: 0; background-color: rgba(0, 0, 0, 0.39); border-top-left-radius: 10px; border-top-right-radius: 10px; background-image: url(&apos;project://database/Assets/Role/Img/Avatar_1.png?fileID=2800000&amp;guid=95b3aee3bc9bae64f8b70aba356b50b1&amp;type=3#Avatar_1&apos;); -unity-background-scale-mode: scale-and-crop;" /><ui:Label text="角色" display-tooltip-when-elided="true" name="NameLab" style="margin-left: 3%; margin-right: 3%; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0; background-color: rgb(255, 96, 96); border-top-left-radius: 10px; border-bottom-left-radius: 10px; border-top-right-radius: 10px; border-bottom-right-radius: 10px; flex-shrink: 1; font-size: 35px; -unity-text-align: middle-center; color: rgb(255, 254, 254);" /><ui:VisualElement name="Properties" style="flex-grow: 1; margin-left: 5%; margin-right: 5%; margin-top: 0; margin-bottom: 5%; background-color: rgba(0, 0, 0, 0.39); border-bottom-right-radius: 10px; border-bottom-left-radius: 10px;"><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="等级" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="行动力" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="最大HP" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="最大MP" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="攻击力" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="防御力" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement></ui:VisualElement></ui:VisualElement></ui:VisualElement></ui:VisualElement>
</ui:UXML>

        RoleStyle.uss

#RoleTemplate:hover {transition-duration: 0.1s;translate: 0 -20px;border-left-width: 5px;border-right-width: 5px;border-top-width: 5px;border-bottom-width: 5px;border-left-color: rgb(248, 242, 242);border-right-color: rgb(248, 242, 242);border-top-color: rgb(248, 242, 242);border-bottom-color: rgb(248, 242, 242);
}#Property Label {font-size: 25px;color: rgba(0, 0, 0, 255);-unity-text-align: middle-center;-unity-font-style: bold;
}

        显示效果如下。

2.2 创建模板

        在 Hierarchy 窗口选中 RoleTemplate 元素,右键弹出菜单,选择 Create Template,选择 Resources 目录下保存 RoleTemplate.uxml,修改 Grow 为 1。

        RoleTemplate.cs

<ui:UXML xmlns:ui="UnityEngine.UIElements" xmlns:uie="UnityEditor.UIElements" editor-extension-mode="False"><ui:VisualElement name="RoleTemplate" style="flex-basis: 25%; margin-left: 10px; margin-right: 10px; margin-top: 10px; margin-bottom: 10px; background-color: rgba(0, 0, 0, 0.2); border-top-left-radius: 10px; border-bottom-left-radius: 10px; border-top-right-radius: 10px; border-bottom-right-radius: 10px; flex-grow: 1;"><ui:VisualElement name="Image" style="flex-basis: 50%; margin-left: 5%; margin-right: 5%; margin-top: 5%; margin-bottom: 0; background-color: rgba(0, 0, 0, 0.39); border-top-left-radius: 10px; border-top-right-radius: 10px; background-image: url(&apos;project://database/Assets/Role/Img/Avatar_1.png?fileID=2800000&amp;guid=95b3aee3bc9bae64f8b70aba356b50b1&amp;type=3#Avatar_1&apos;); -unity-background-scale-mode: scale-and-crop;" /><ui:Label text="角色" display-tooltip-when-elided="true" name="NameLab" style="margin-left: 3%; margin-right: 3%; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0; background-color: rgb(255, 96, 96); border-top-left-radius: 10px; border-bottom-left-radius: 10px; border-top-right-radius: 10px; border-bottom-right-radius: 10px; flex-shrink: 1; font-size: 35px; -unity-text-align: middle-center; color: rgb(255, 254, 254);" /><ui:VisualElement name="Properties" style="flex-grow: 1; margin-left: 5%; margin-right: 5%; margin-top: 0; margin-bottom: 5%; background-color: rgba(0, 0, 0, 0.39); border-bottom-right-radius: 10px; border-bottom-left-radius: 10px;"><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="等级" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="行动力" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="最大HP" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="最大MP" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="攻击力" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement><ui:VisualElement name="Property" style="flex-direction: row; margin-left: 5px; margin-right: 5px; margin-top: 5px; margin-bottom: 5px; flex-grow: 0; justify-content: center;"><ui:Label text="防御力" display-tooltip-when-elided="true" name="Name" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(185, 251, 192); border-top-left-radius: 10px; border-bottom-left-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /><ui:Label text="1" display-tooltip-when-elided="true" name="Value" style="flex-basis: 50%; flex-shrink: 1; background-color: rgb(255, 200, 200); border-top-right-radius: 10px; border-bottom-right-radius: 10px; padding-left: 0; padding-right: 0; padding-top: 0; padding-bottom: 0;" /></ui:VisualElement></ui:VisualElement></ui:VisualElement>
</ui:UXML>

        保存模板后,删除 Hierarchy 窗口中的 RoleTemplate 元素,后面会通过脚本加载 RoleTemplate。

2.3 自定义元素

        RoleView.cs

using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UIElements;public class RoleView : VisualElement {// 便于在UI Builder中导入自定义UI, 需要有无参构造函数public new class UxmlFactory : UxmlFactory<RoleView> {}private TemplateContainer container; // 模板容器private List<VisualElement> properties; // 角色属性public RoleView() {container = Resources.Load<VisualTreeAsset>("RoleTemplate").Instantiate();container.style.flexGrow = 1;hierarchy.Add(container);properties = container.Query("Property").ToList();}public RoleView(RoleData roleData) : this() {userData = roleData;UpdateRoleData();container.RegisterCallback<MouseDownEvent>(OnClick);}private void OnClick(MouseDownEvent mouseDownEvent) { // 单击角色模板回调函数RoleData roleData = (RoleData) userData;if (mouseDownEvent.button == 0) { // 按下鼠标左键roleData.RoleLevel++;} else if (mouseDownEvent.button == 1) { // 按下鼠标右键roleData.RoleLevel--;}UpdateRoleData();}private void UpdateRoleData() { // 更新角色数据RoleData roleData = (RoleData) userData;container.Q<VisualElement>("Image").style.backgroundImage = roleData.RoleImage;container.Q<Label>("NameLab").text = roleData.RoleName;SetProperty(properties[0], roleData.RoleLevel);SetProperty(properties[1], roleData.LevelData.initiative);SetProperty(properties[2], roleData.LevelData.maxHp);SetProperty(properties[3], roleData.LevelData.maxMp);SetProperty(properties[4], roleData.LevelData.attack);SetProperty(properties[5], roleData.LevelData.defense);}private void SetProperty(VisualElement property, int value) { // 更新角色属性property.Q<Label>("Value").text = value.ToString();}
}

2.4 自定义数据

        LevelData.cs

public class LevelData { // 等级属性数据public int initiative; // 主动权(行动力/速度)public int maxHp; // 最大生命值public int maxMp; // 最大魔法值public int attack; // 攻击力public int defense; // 防御力
}

        RoleData.cs

using System.Collections.Generic;
using UnityEngine;[CreateAssetMenu(menuName = ("RoleData"), fileName = ("RoleData_"))]
public class RoleData : ScriptableObject { // 角色属性数据private const int roleMaxLevel = 10; // 最大等级[SerializeField]private TextAsset levelDataFile; // 等级数据csv文件[SerializeField]private Texture2D roleImage; // 角色头像[SerializeField]private string roleName; // 角色名[SerializeField, Range(1, roleMaxLevel)]private int roleStartLevel = 1; // 角色开始等级[SerializeField]private List<LevelData> levelDatas; // 等级数据private int roleLevel; // 角色当前等级public Texture2D RoleImage => roleImage; // 获取角色头像public string RoleName => roleName; // 获取角色名public int RoleLevel { // 获取/设置角色等级get => roleLevel;set {if (roleLevel == value || value < 1 || value > roleMaxLevel) {return;}roleLevel = value;}}public LevelData LevelData => levelDatas[roleLevel - 1]; // 获取角色等级数据private void OnEnable() {roleLevel = roleStartLevel;}private void OnValidate() {if (levelDataFile == null) {return;}if (levelDatas == null) {levelDatas = new List<LevelData>();}levelDatas.Clear();string[] textInLines = levelDataFile.text.Split('\n');for (int i = 1; i < textInLines.Length; i++) {string[] statsValues = textInLines[i].Split(",");LevelData levelData = new LevelData();levelData.initiative = int.Parse(statsValues[0]);levelData.maxHp = int.Parse(statsValues[1]);levelData.maxMp = int.Parse(statsValues[2]);levelData.attack = int.Parse(statsValues[3]);levelData.defense = int.Parse(statsValues[4]);levelDatas.Add(levelData);}}
}

        编译后,在 Assets 窗口右键,依次选择【Create→RoleData】,创建 4 个对象,对应 4 个角色的配置,分别重命名为 RoleData_1.asset、RoleData_2.asset、RoleData_3.asset、RoleData_4.asset。

        选中 ScriptableObject 配置文件后,在 Inspector 窗口配置角色属性。

        其中 LevelDataFile 是角色每个等级的属性 cvs 表,内容如下。

2.5 元素加载

        RoleLoader.cs

using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UIElements;public class RoleLoader : MonoBehaviour {[SerializeField]private List<RoleData> roleDatas; // 角色数据private VisualElement root; // 根容器private void Awake() {root = GetComponent<UIDocument>().rootVisualElement;var bodyContainer = root.Q("Body");bodyContainer.Clear();for(int i = 0; i < roleDatas.Count; i++) {RoleView roleView = new RoleView(roleDatas[i]);roleView.style.flexBasis = Length.Percent(25.0f);bodyContainer.Add(roleView);}}
}

        说明:RoleLoader 脚本组件挂在 UIDocument 对象上,并且需要将 RoleData_1.asset、RoleData_2.asset、RoleData_3.asset、RoleData_4.asset 赋给 RoleDatas,如下。

2.6 运行效果

相关文章:

【Unity3D】UI Toolkit数据动态绑定

1 前言 本文将实现 cvs 表格数据与 UI Toolkit 元素的动态绑定。 如果读者对 UI Toolkit 不是太了解&#xff0c;可以参考以下内容。 UI Toolkit简介UI Toolkit容器UI Toolkit元素UI Toolkit样式选择器UI Toolkit自定义元素 本文完整资源见→UI Toolkit数据动态绑定。 2 数据…...

微信小程序如何在切换页面后原页面状态不变

在微信小程序中&#xff0c;如果要实现在切换页面后原页面状态不变&#xff0c;可以通过以下几种方式来实现&#xff1a; 使用全局数据&#xff1a;可以将需要保持状态的数据存储在小程序的全局数据中&#xff0c;这样无论切换到哪个页面&#xff0c;都可以通过全局数据来获取…...

蓝桥杯官网填空题(生成树)

问题描述 下面是一个 8 个结点的无向图的邻接矩阵表示&#xff0c;其中第 i 行第 j 列表示结点 i 到结点 j 的边长度。当 长度为 0 时表示不存在边。 0 9 3 0 0 0 0 99 0 8 1 4 0 0 03 8 0 9 0 0 0 00 1 9 0 3 0 0 50 4 0 3 0 7 0 60 0 0 0 7 0 5 20 0 0 0 0 5 0 49 0 0 5 6 2…...

Qt Designer UI设计布局小结

目录 前言1 居中布局2 左右布局3 上下布局4 复杂页面布局总结 前言 本文总结了在开发Qt应用程序时使用 Designer 进行UI布局的一些心得体会。Qt Designer是Qt提供的一个可视化界面设计工具&#xff0c;旨在帮助开发人员快速创建和布局用户界面。它提供了丰富的布局管理器和控件…...

linux设备树节点添加新的复位属性之后设备驱动加载异常问题分析

linux设备树节点添加新的复位属性之后设备驱动加载异常问题分析 1 linux原始设备驱动信息1.1 设备树节点信息1.2 linux设备驱动1.3 makefile1.4 Kconfig1.5 对应的defconfig文件 2 修改之后的linux设备驱动2.1 修改之后的设备树节点信息2.2 原始test_fw.c出现的问题以及原因分析…...

连nil切片和空切片一不一样都不清楚?那BAT面试官只好让你回去等通知了。

连nil切片和空切片一不一样都不清楚&#xff1f;那BAT面试官只好让你回去等通知了。 问题 package mainimport ("fmt""reflect""unsafe" )func main() {var s1 []ints2 : make([]int,0)s4 : make([]int,0)fmt.Printf("s1 pointer:%v, s2 p…...

前端构建工具 webpack 笔记

1、了解 webpack 1、定义&#xff1a;本质上&#xff0c;webpack 是一个用于现代 JavaScript 应用程序的静态模块打包工具&#xff0c;当 webpack 处理应用它会在内部从一个或多个入口点构建一个依赖图(dependency graph)&#xff0c;然后将你项目中所程序时&#xff0c;需的…...

.Net MVC 使用Areas后存在相同Controller时报错的解决办法; 从上下文获取请求的Area名及Controller名

先来说个额外的问题&#xff1a;如何在请求上下文&#xff08;比如过滤器的中&#xff09;获取请求对应的Area和Controller 名字&#xff1f;&#xff08;假设请求上下文对象为 filterContext &#xff09;&#xff1a; 1. 获取Area名: (string)filterContext.RouteData.DataTo…...

docker-compose部署etcd集群

1. docker-compose.yml cat > docker-compose.yml << EOF version: "3.0"networks:etcd-net: # 网络driver: bridge # 桥接模式volumes:etcd1_data: # 挂载到本地的数据卷名driver: localetcd2_data:driver: localetcd3_data:driver:…...

微信怎么定时发圈?

定时发圈的妙用 在合适的时间点发布新的产品、促销活动&#xff0c;不仅能够及时提醒用户品牌的存在&#xff0c;还可以引发用户的兴趣&#xff0c;增加品牌的曝光率。 选择最佳的发朋友圈时间段&#xff0c;以确保推广内容得到最大的曝光和关注&#xff0c;提高广告投放的效果…...

记录造数据测试接口

一、前言 在java开发中经常需要造数据进行测试接口&#xff0c;这里记录一下常用的通过造数据测试接口的方法。 二、一般的接口传参方式 1、接口的方式最好是使用JSON或者map的方式&#xff0c;这样的好处是传参可以灵活伸缩&#xff0c;返回的结果也最好是JSON或者map的方式…...

数据结构基础7:二叉树【链式结构】实现和递归思想。

二叉树的链式结构实现 一.二叉树链式结构的实现&#xff1a;1.前置说明&#xff1a;1.创建二叉树&#xff1a;2.二叉树的结构&#xff1a; 2.二叉树的遍历&#xff1a;1.二叉树的前中后序遍历&#xff1a;2.内容拓展&#xff1a; 二.二叉树链式(题目)题目一&#xff1a;计算节点…...

[.NET 6] IHostedService 的呼叫等等我的爱——等待Web应用准备就绪

📢欢迎点赞 :👍 收藏 ⭐留言 📝 如有错误敬请指正,赐人玫瑰,手留余香!📢本文作者:由webmote 原创📢作者格言:新的征程,我们面对的不是技术而是人心,人心不可测,海水不可量,唯有技术,才是深沉黑夜中的一座闪烁的灯塔 !序言 在这篇文章中,我将介绍如何等…...

基于jeecg-boot的flowable流程自定义业务退回撤回或驳回到发起人后的再次流程提交

更多nbcio-boot功能请看演示系统 gitee源代码地址 后端代码&#xff1a; https://gitee.com/nbacheng/nbcio-boot 前端代码&#xff1a;https://gitee.com/nbacheng/nbcio-vue.git 在线演示&#xff08;包括H5&#xff09; &#xff1a; http://122.227.135.243:9888 主要…...

python如何学习

功能如此强大、高效的Python&#xff0c;却非常的简单好学&#xff0c;这让学它的同学爱不释手&#xff0c;也让越来越多的互联网企业开始用Python来做主要的开发语言&#xff0c;比如谷歌、Facebook&#xff08;现Meta&#xff09;、豆瓣、知乎等知名互联网公司都在使用Python…...

Centos7更新php7.2版本升级

之前搭建的LNMP环境php使用yum安装的版本为7.2&#xff0c;现有项目wordpress安装wp插件需要php7.4版本的支持&#xff0c;需要在原来的环境更新php版本。 一、卸载php7.2 yum remove php*原先的安装方式是yum安装直接yum remove就可以卸载否则需要rpm命令查询&#xff0c;按…...

操作系统学习笔记---计算机系统概述

目录 概念 功能和目标 特征 并发 共享&#xff08;资源共享&#xff09; 虚拟 异步 发展与分类 手工操作阶段&#xff08;无OS&#xff09; 批处理阶段 单道批处理系统 多道批处理系统 分时操作系统 实时操作系统 网络操作系统 分布式计算机系统 个人计算机操…...

uniapp H5 navigateBack无法返回上一层级

项目场景&#xff1a; 提交表单后需要返回上一级 原因分析&#xff1a; H5在PC端打开&#xff0c;当前页面重新加载的情况下&#xff0c;出现navigateBack不能返回&#xff0c;由于H5端页面刷新后返回页面栈会消失 //提交 const handleSubmit async () > {form.value?.a…...

Android性能优化之应用瘦身(APK瘦身)

关于作者&#xff1a;CSDN内容合伙人、技术专家&#xff0c; 从零开始做日活千万级APP。 专注于分享各领域原创系列文章 &#xff0c;擅长java后端、移动开发、人工智能等&#xff0c;希望大家多多支持。 目录 一、导读二、概览2.1 apk组成 三、优化方向3.1 源代码3.1.1 代码混…...

C语言数组和指针笔试题(二)(一定要看)

目录 字符数组二例题1例题2例题3例题4例题5例题6例题7总结 字符数组三例题1例题2例题3例题4例题5例题6例题7 字符数组二 char arr[] {a,b,c,d,e,f} 1:printf("%d\n", strlen(arr)); 2:printf("%d\n", strlen(arr0)); 3:printf("%d\n", strlen(…...

AI-调查研究-01-正念冥想有用吗?对健康的影响及科学指南

点一下关注吧&#xff01;&#xff01;&#xff01;非常感谢&#xff01;&#xff01;持续更新&#xff01;&#xff01;&#xff01; &#x1f680; AI篇持续更新中&#xff01;&#xff08;长期更新&#xff09; 目前2025年06月05日更新到&#xff1a; AI炼丹日志-28 - Aud…...

docker详细操作--未完待续

docker介绍 docker官网: Docker&#xff1a;加速容器应用程序开发 harbor官网&#xff1a;Harbor - Harbor 中文 使用docker加速器: Docker镜像极速下载服务 - 毫秒镜像 是什么 Docker 是一种开源的容器化平台&#xff0c;用于将应用程序及其依赖项&#xff08;如库、运行时环…...

Java 语言特性(面试系列1)

一、面向对象编程 1. 封装&#xff08;Encapsulation&#xff09; 定义&#xff1a;将数据&#xff08;属性&#xff09;和操作数据的方法绑定在一起&#xff0c;通过访问控制符&#xff08;private、protected、public&#xff09;隐藏内部实现细节。示例&#xff1a; public …...

Ascend NPU上适配Step-Audio模型

1 概述 1.1 简述 Step-Audio 是业界首个集语音理解与生成控制一体化的产品级开源实时语音对话系统&#xff0c;支持多语言对话&#xff08;如 中文&#xff0c;英文&#xff0c;日语&#xff09;&#xff0c;语音情感&#xff08;如 开心&#xff0c;悲伤&#xff09;&#x…...

NLP学习路线图(二十三):长短期记忆网络(LSTM)

在自然语言处理(NLP)领域,我们时刻面临着处理序列数据的核心挑战。无论是理解句子的结构、分析文本的情感,还是实现语言的翻译,都需要模型能够捕捉词语之间依时序产生的复杂依赖关系。传统的神经网络结构在处理这种序列依赖时显得力不从心,而循环神经网络(RNN) 曾被视为…...

技术栈RabbitMq的介绍和使用

目录 1. 什么是消息队列&#xff1f;2. 消息队列的优点3. RabbitMQ 消息队列概述4. RabbitMQ 安装5. Exchange 四种类型5.1 direct 精准匹配5.2 fanout 广播5.3 topic 正则匹配 6. RabbitMQ 队列模式6.1 简单队列模式6.2 工作队列模式6.3 发布/订阅模式6.4 路由模式6.5 主题模式…...

VM虚拟机网络配置(ubuntu24桥接模式):配置静态IP

编辑-虚拟网络编辑器-更改设置 选择桥接模式&#xff0c;然后找到相应的网卡&#xff08;可以查看自己本机的网络连接&#xff09; windows连接的网络点击查看属性 编辑虚拟机设置更改网络配置&#xff0c;选择刚才配置的桥接模式 静态ip设置&#xff1a; 我用的ubuntu24桌…...

[免费]微信小程序问卷调查系统(SpringBoot后端+Vue管理端)【论文+源码+SQL脚本】

大家好&#xff0c;我是java1234_小锋老师&#xff0c;看到一个不错的微信小程序问卷调查系统(SpringBoot后端Vue管理端)【论文源码SQL脚本】&#xff0c;分享下哈。 项目视频演示 【免费】微信小程序问卷调查系统(SpringBoot后端Vue管理端) Java毕业设计_哔哩哔哩_bilibili 项…...

接口自动化测试:HttpRunner基础

相关文档 HttpRunner V3.x中文文档 HttpRunner 用户指南 使用HttpRunner 3.x实现接口自动化测试 HttpRunner介绍 HttpRunner 是一个开源的 API 测试工具&#xff0c;支持 HTTP(S)/HTTP2/WebSocket/RPC 等网络协议&#xff0c;涵盖接口测试、性能测试、数字体验监测等测试类型…...

LRU 缓存机制详解与实现(Java版) + 力扣解决

&#x1f4cc; LRU 缓存机制详解与实现&#xff08;Java版&#xff09; 一、&#x1f4d6; 问题背景 在日常开发中&#xff0c;我们经常会使用 缓存&#xff08;Cache&#xff09; 来提升性能。但由于内存有限&#xff0c;缓存不可能无限增长&#xff0c;于是需要策略决定&am…...