第三章 流程控制

第一节 C++和蓝图循环

ForLoop蓝图节点相当于C++中的for循环,ForeLoopWithBreak节点相当于for循环体中加了break语句,当触发某个条件时直接结束。

for()
{
if(xxx)
break;
}

WhileLoop节点相当于C++中的while语句

while()
{ }

第二节 C++和蓝图结构体

UE4可以右键空白处选择蓝图,创建结构体,方便管理数据。C++中如下。

struct MyStruct
{
bool one;
int Two;
};
void main()
{
MyStruct str;
str.one = true;
str.two = 0;
cout<<str.one<<endl;
system("pause");
}

同结构体一样,在UE中同样可以右键空白处,然后选择枚举或者Enumeration来快速创建一个枚举蓝图。之后在具体要用的蓝图中新建一个变量,在变量类型中选择类型为自己刚刚创建的枚举名即可。

enum ETr{
Monster,
Kill,
Hello
};
void main()
{
ETr tr;
//即在几种类型之中选择一种
tr = ETr::Kill;
case Monster:
break;
case Kill:
break;
case Hello:
break;
default:
break;
}

第三节 DoOnceDelay

在流程控制节点中,branch节点相当于if语句。Delay节点相当于Sleep语句。DoOnce节点意思是只执行一次,DoOnce中startclosed选项要是勾上了,则刚开始就不执行,reset用于重置DoOnce。 Gate阀门,可以通过事件来调用。FlipFlow可以控制第一帧走上面的第二帧走下面的,来回往复。MultiGate用于emm,Gate加强版,一次性可以有很多输出,还可以设置从第几个开始,可以设置是否循环是否随机,以及Gate也有的重设。

第四节 SequenceDoOnce

这玩意只要下个信号传过来就会刷新等待时间,所以如果在tick中使用的话,就会无限阻塞。

sequence序列很有用,可以一次同时执行很多事件。

第五节 C++实现蓝图控制

实现Branch

void TureCondition()
{
//这种情况下要实现的功能
}
void FalseCondition()
{
//这种情况下要实现的功能
}
void Branch(bool Condition)
{
if(Condition)
{
TrueCondition();
}
else
{
FalseCondition();
}
}

实现Delay

void DelayCompleted()
{
//要完成的事件逻辑
}
void Delay(float Duration)
{
//sleep函数的单位是ms
Sleep(Duration * 1000);
DelayCompleted();
}

实现DoN

static bool bReset = false;
void Reset()
{
bReset = false;
}
void DoThing(int i)
{
//要执行的逻辑
}
void DoN(int N)
{
if(!bReset)
{
for(int i=0;i<N;i++)
{
DoThing(i);
}
//循环次数完成,关闭循环条件
bReset = true;
}
}

实现DoOnce

static bool bDoOnce = false;
void Reset()
{
bDoOnce = false;
}
void DoOnce(bool StartClosed)
{
if(!bDoOnce)
{
bDoOnce = false;
Completed();
}
}

第四章 事件接口

第一节 封装逻辑蓝图代理

函数中禁止使用delay,会造成线程阻塞,函数要求执行快,执行完就释放临时变量。宏里面可以包含事件,宏里面可以用delay。

代理(发报机、委托)蓝图中绑定和解绑操作如下

C++中差不多这样就行

void print()
{
printf("hello world");
}
void main()
{
print();
system("pause");
}

第二节 Actor事件接口

在蓝图中找到function选项,选择override下拉列表,可看到如下函数功能

Actor生命周期中,有Event Tick、Event BeginPlay、Event Destroyed、Event End Play四个函数。

特别注意,有两个叫ActorEndCursorOver和ActorBeginCursorOver的函数,可以判断场景中鼠标是否和Actor重叠

Event OnEndViewTarget和Event OnBecomeViewTarget函数用于切换视角,一个在切换到某个物体的视角时执行,另一个在离开某个物体的视角时执行。在编辑器窗口中可使用,Vew ACTOR名称 命令来切换观察的物体。

对于伤害函数来说,有RadialDamage和Point Damage、带衰减的半径伤害等形式。

第三节 Character接口

EventOnWalkingOffLedge函数,当人物离开正在行走的表面时就会激活,下面几个参数分别是,离开面的法线(Previous Floor Impact Normal),接触面的法线(Previous Floor Contact Normal),在哪个位置结束的函数(Previous Location),时间增量(Time Delta)。

可以用这个办法切换角色。

第四节 服务端事件接口

GameMode接口:

第五节 UMG接口

获取鼠标位置

这里有个宝藏教程,关于UI中,槽和拖拽的做法,一看就可以用来做背包。我详细纪录一下步骤。

没搞明白。

第五章 蓝图间的访问

第一节 通过实例访问

现在关卡编辑器中,选中要访问的蓝图类,然后在关卡蓝图中右键空白处创建一个对实例蓝图的引用,然后调用TestA事件。

还有一种方法,通过遍历场景中所有的actor,找到选择的TestA类数组,因为场上只有一个TestA,所以选中数组中的第一个元素,调用其TestA事件。

第二节 管理模式访问

创建一个实例蓝图,通过在蓝图中创建或生成另一个蓝图进行管理。

尽量不要用第一节中GetWorld后遍历的方式操作类。

第三节 蓝图接口访问

在C++中通过接口访问的话,举例如下

class Actor
{
public:
}
class IInterface
{
public:
virtual void prinit_f() = 0; private: };
//在接口中抽象实现后必须在子类中继承
class A : public IInterface,public Actor
{
public:
virtual void print_f()
{
cout<<"Hello"<<endl;
}
}; void main()
{
IInterface * S_a = new A();
//调用接口
S_a->print_f();
system("pause");
}

在蓝图中这样创建接口

我们知道,在C++中,如果S_a多继承了IInterface接口和Actor类,那么在创建的时候,是无法进行如下操作的。

    Actor * S_a = new A();
//调用IInterface的接口
S_a->print_f();
//无法调用,因为S_a是Actor的类

但是在蓝图中可以这样操作,在要继承的类的class setting中添加上面自行创建的蓝图接口后。

然后在侧边栏新增的接口菜单中进入接口的蓝图面板,在其中实现接口的功能。

最后在管理类中,创建接口变量,从生成类的蓝图节点的返回值获得接口的引用。

第四节 UMG访问正确方式

通过获取Controller后获取HUD访问,不能通过UMG直接访问pawn,character。HUD的实例存在于Player Controller。因为在服务端或其他客户端根本不存在你的UMG数据,但是有玩家控制器,所以直接修改UMG是错误的,无法同步的,要通过controller访问。

第六章 组件

第一节 基础组件

静态网格体,骨骼网格体,移动组件,抛射物组件,球形,盒型,粒子组件,没啥特别的。

第二节 渲染组件自定义

有一个缆索组件,英文名是cable,可以模拟一段绳子悬挂的物理效果。可以设置绳子长度,起始点和终止点。末端可以附加到Actor的组件上,也可以附加到插槽上。更改分段数可以改变模拟物理效果的平滑程度。

如果是文本渲染组件的话,叫TextRender组件,如果想显示中文内容,需要使用支持中文的字体,不然会乱码,TextRender本质是使用材质进行贴图。

还有一个重要的组件叫程序化网格体组件(Procedual Mesh),可以用这个组件自定义网格模型,并进行布尔运算,不过都需要自己去写。

如果要画一个面出来,首先要设置四个顶点Vertices,取决于你所用的相对坐标轴。计算机中以三角形绘制一个平面,因此画一个矩形的时候需要画两次。四个点用六次画两个三角形拼出一个矩形。绘制时顺时针或逆时针方向则决定了法线(Normal)的方向,所以画完了要是没看到图像可能是法线的问题,翻转一下就可以解决。

在单独创建一个用于这个Mesh的材质并应用后,即可设置Vertex Color顶点颜色。

也可以借此手动创建一个立体模型。

第三节 渲染组件系列

向量场(VectorField)可以决定粒子是怎么发射的。样条线组件(SplineMesh),可以让模型按想要的样子发生变化。MediaPlane,和Camera组件一起使用,专门给摄像机播放媒体用的。 还比如InstancedStaticMesh,实例化静态网格体组件,可以用来处理渲染同个网格体但是多个实例的情况,可以优化场景渲染的速度。

第四节 AI组件和算法

先往场景里拖一个导航网格体,Nav mesh bounds volume。如果不想要某个地方成为导航网格体的一部分,可以使用Nav Modifier Volume,被覆盖的区域将不会计入导航网格体覆盖范围。如果想要AI从跳跃路线走的话,那就使用Nav Link Proxy,这样AI也会判断是从大路走离目标近还是从某个点在场景中进行跳跃离目标近。

AI通过A*搜寻算法在地图中找到一条最短路径,主要问题是判断路径是否阻塞。在蓝图中添加AIPerception(AI感知组件),与视力和听力有关。PawnNoiseEmitter(Pawn噪点发射器组件)可以发射一种只有AI能听见的信号让AI感知到。NavModifer(导航修改器组件),可以手动标记一段区域的优先级,比如不想要AI优先走某段路但又不想把这条路彻底堵死,可以用这个方式;又比如说可以让AI优先走某条实际上更远的路(通常是大路)。

第七章 数据库搭建

第一节 基于Save增删查改

蓝图类型Save Game本质上是UE的一种本地数据库。SaveGame用GameInstance承载,因为游戏实例不随关卡的变化而变化,只有关掉游戏的时候游戏实例才会释放。

第二节 CSV和Jsob

感觉没啥好讲的,省略一下讲后面的重点吧

第八章 搭建局域网Session

第一节 用户界面菜单、动画、效果的实现

先弄个UMG,也就用户控件。然后随便摆摆控件或者做个按钮动画啥的,我拿我自己的举例子。我先创建了一个WBP_选择联机模式

点击这个按钮可以打开具体的局域网查找界面。对鼠标停留在按钮上,按钮产生悬浮动画感兴趣的可以参考这个蓝图实现。

因为我点击第一个按钮选择局域网模式之后,会播放一个动画来加载出新的用户控件,这个动画跟怎么制作局域网无关,不过纪录在此。

关闭所有UI交互是自己写的一个蓝图函数,目的是关闭在父级用户控件时子级用户控件的交互性。

之后创建了WBP_单机局域网蓝图。

用到了一个垂直框,用来装里面的三个按钮和三个文本框。一个滚动框,后面用于显示创建的房间信息。一个循环动态浏览图示,英文是circular throbber,就是一个一直转圈圈的控件,用于在点击查找房间这种按钮后,显示出来给用户一种程序正在工作的反馈。那么菜单这边就做到这。

第二节 创建会话

上节倒数第二张图中,有个创建服务器按钮。那个按钮就是创建局域网会话按钮,其背后对应的蓝图如下。

这样子就可以在本地局域网上创建一个可供被搜索被加入的在线会话了,至于进入具体的地图后如何操作,那就是关卡蓝图和GameMode的事情了。而上图中开始游戏按钮是用来单人游戏的,点了之后直接跳转到关卡去而不创建会话。

第三节 查找并加入会话

局域网中一台主机创建会话(即一场在线游戏)后,其他的机器就可以寻找并加入这个会话。那么我在查找房间按钮中实现这个查找并加入的功能。蓝图实现如下。

在这个功能中,点击按钮后,首先清除滚动框中的所有子项,即如果之前里面有信息就都给删了。之后设置转圈圈控件的可视性为可视,这样用户就知道程序在工作了。之后寻找会话,这里设置Max Result为10的话,那么程序在局域网中最多只会找到十个可供加入的会话,一般在本地局域网游戏中这肯定是够的。之后蓝图节点将找到的会话存储为数组,我们将其提升为变量,之后循环遍历数组中所有的会话,分别将创建为_WBP_房间条控件,注意两点,每一个会话的信息都被传到了WBP_房间条控件中,另一个则是,WBP_房间条控件是被添加到滚动框中成为WBP_单机局域网中成为一个子项的

WBP_房间条的实现很简单,布局只需要一个按钮和一个文本就够,连画布面板都不需要。蓝图实现如下。

按钮点击时:

Update事件:

格式化文本是个好东西,里面用{}括住你想要的文本变量后回车,下面就能自动生成你在{}中写的属性。update事件将在本节开头的图中提到,会将按钮添加到滚动框中后刷新按钮上显示的文字,就能告诉用户这个会话中的玩家数量、Ping以及房间名,用户点击这个按钮就能加入会话。

第四节 最后效果

在编辑器中网络模式选择以客户端运行,限于机能所限,这里开启两个会话进行演示。右图为已经点击了创建服务器进入等待大厅的角色,左侧还没进行操作。

左图此时点击查找房间按钮,屏幕中心的滚动框中就会加载按钮,并更新房间信息,此时玩家点击按钮就能直接加入会话。若是一个局域网中同时存在多个会话,这里也会刷新多个按钮出来。

此时两名玩家就加入了同一个会话之中。

到这里,关于搭建局域网会话的内容就结束了。

UEC++学习(1)的更多相关文章

  1. Android学习——windows下搭建NDK_r9环境

    1. NDK(Native Development Kit) 1.1 NDK简介 Android NDK是一套允许开发人员使用本地代码(如C/C++)进行Android APP功能开发的工具,通过这个 ...

  2. linux内核数据结构学习总结

    目录 . 进程相关数据结构 ) struct task_struct ) struct cred ) struct pid_link ) struct pid ) struct signal_stru ...

  3. 用深度学习做命名实体识别(二):文本标注工具brat

    本篇文章,将带你一步步的安装文本标注工具brat. brat是一个文本标注工具,可以标注实体,事件.关系.属性等,只支持在linux下安装,其使用需要webserver,官方给出的教程使用的是Apac ...

  4. 从直播编程到直播教育:LiveEdu.tv开启多元化的在线学习直播时代

    2015年9月,一个叫Livecoding.tv的网站在互联网上引起了编程界的注意.缘于Pingwest品玩的一位编辑在上网时无意中发现了这个网站,并写了一篇文章<一个比直播睡觉更奇怪的网站:直 ...

  5. Angular2学习笔记(1)

    Angular2学习笔记(1) 1. 写在前面 之前基于Electron写过一个Markdown编辑器.就其功能而言,主要功能已经实现,一些小的不影响使用的功能由于时间关系还没有完成:但就代码而言,之 ...

  6. ABP入门系列(1)——学习Abp框架之实操演练

    作为.Net工地搬砖长工一名,一直致力于挖坑(Bug)填坑(Debug),但技术却不见长进.也曾热情于新技术的学习,憧憬过成为技术大拿.从前端到后端,从bootstrap到javascript,从py ...

  7. 消息队列——RabbitMQ学习笔记

    消息队列--RabbitMQ学习笔记 1. 写在前面 昨天简单学习了一个消息队列项目--RabbitMQ,今天趁热打铁,将学到的东西记录下来. 学习的资料主要是官网给出的6个基本的消息发送/接收模型, ...

  8. js学习笔记:webpack基础入门(一)

    之前听说过webpack,今天想正式的接触一下,先跟着webpack的官方用户指南走: 在这里有: 如何安装webpack 如何使用webpack 如何使用loader 如何使用webpack的开发者 ...

  9. Unity3d学习 制作地形

    这周学习了如何在unity中制作地形,就是在一个Terrain的对象上盖几座小山,在山底种几棵树,那就讲一下如何完成上述内容. 1.在新键得项目的游戏的Hierarchy目录中新键一个Terrain对 ...

  10. 《Django By Example》第四章 中文 翻译 (个人学习,渣翻)

    书籍出处:https://www.packtpub.com/web-development/django-example 原作者:Antonio Melé (译者注:祝大家新年快乐,这次带来<D ...

随机推荐

  1. 00_k8s_learn

    10本 Kubernetes 学习书籍推荐 - 知乎 https://zhuanlan.zhihu.com/p/468291559 Helm 的安装使用 · 从 Docker 到 Kubernetes ...

  2. 如何用python脚本采集某网图片

    一.前言: 今天学了两个工具urlopen  和etree,这两个小工具至关重要.urllib.request模块提供了最基本的构造HTTP请求的方法,利用它可以模拟浏览器的一个请求发起过程,同时它还 ...

  3. clickhouse-数据副本踩坑

    数据副本--失败,看日志 vim /var/log/clickhouse-server/clickhouse-server.err.log select * from system.replicati ...

  4. python39

    Python pass 是空语句,是为了保持程序结构的完整性. pass 不做任何事情,一般用做占位语句. Python 语言 pass 语句语法格式如下: pass 测试实例: 实例 #!/usr/ ...

  5. iOS笔记 - Runtime 01:前期准备(isa结构 | Class结构 | 方法缓存)

    前言 1 - OC机制很多都是基于 Runtime实现的,比如指针的弱引用.OC的消息机制属于 Runtime的一部分 2 - OC是一门动态语言,在程序运行过程中就可以修改已经编译好的代码 3 -  ...

  6. 【git】3.3 git分支-分支管理

    资料来源 (1) https://git-scm.com/book/zh/v2/Git-%E5%88%86%E6%94%AF-%E5%88%86%E6%94%AF%E7%AE%A1%E7%90%86 ...

  7. win10安装MAT并单独配置jdk11

    1.下载MAT 2.下载jdk11 3.配置jdk11 MAT解压后,在MemoryAnalyzer.ini配置文件开头添加配置指向jdk11,如下: -vm C:\Program Files\Jav ...

  8. .Net Core 中使用NLog替代默认日志

    1.添加引用nlog.config和Nlog.Web.AspNetCore 2.配置NLog 配置文件 添加一个Web配置文件xxxx.Config <?xml version="1. ...

  9. 微信公众号 H5授权登录

    首先微信公众号 必须是服务号,订阅号没有 "网页授权获取用户基本信息" 没有这个权限.服务号也必须认证后才有这个权限

  10. uniapp 跳转链接

    安装 uni-link 超链接 组件在异步里需要 跳转页面 或者 app里打开浏览器,不能自动跳转, 如充值:增加一个弹窗,获取到地址之后,手动点击link,打开app <uni-link :h ...