本文内容为UE4.27的文档教程

GameMode确定

新建的项目会自动生成GameMode,如果有更改,而不是使用默认的GameMode类,就需要在引擎的设置中更改

角色的实现

前后左右移动

//前后 MoveForward
void AFPSCharacter::MoveForward(float value)
{
//利用控制器方向寻找前进的方向就是角色朝向
FVector Direction = FRotationMatrix(Controller->GetControlRotation()).GetScaledAxis(EAxis::X);
AddMovementInput(Direction, value);
}
//左右MoveRight
void AFPSCharacter::MoveRight(float value)
{
//
FVector Direction = FRotationMatrix(Controller->GetControlRotation()).GetScaledAxis(EAxis::Y);
AddMovementInput(Direction, value);
}

利用AddMovementInput函数传入方向

在模板自带的PlayerInputComponent方法下,绑定行为函数

void AFPSCharacter::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent)
{
Super::SetupPlayerInputComponent(PlayerInputComponent); PlayerInputComponent->BindAxis("MoveForward", this, &AFPSCharacter::MoveForward);
PlayerInputComponent->BindAxis("MoveRight", this, &AFPSCharacter::MoveRight);
}

绑定轴的移动:BindAxis

鼠标控制视角的转动

PlayerInputComponent->BindAxis("Turn", this, &AFPSCharacter::AddControllerYawInput);
PlayerInputComponent->BindAxis("LookUp", this, &AFPSCharacter::AddControllerPitchInput);

AddControllerYawInput,AddControllerPitchInput为基类自带可以直接使用来控制视角的转动

跳跃

跳跃与bPressedJump绑定这是模板基类设置好的。所以在Character的源文件和头文件中定义两个函数来控制这个变量值

void AFPSCharacter::StartJump()
{
bPressedJump = true;
} void AFPSCharacter::StopJump()
{
bPressedJump = false;
}

在模板自带的PlayerInputComponent方法下,绑定行为函数

PlayerInputComponent->BindAction("Jump", IE_Pressed, this, &AFPSCharacter::StartJump);
PlayerInputComponent->BindAction("Jump", IE_Released, this, &AFPSCharacter::StopJump);

绑定按键操作:BindAction,IE_Pressed表示设置的按键按下,IE_Released表示设置的按键松开

实现第一人称视角

FPS游戏常见的方法就是使用两个分开的角色网格体,一个是全身网格,一个是“武器和手部”的局部网格,全身网格可以用于第三人称视角,局部网格用于第一人称视角。

主要操作,摄像机组件Attach在全身网格下,局部网格Attach在摄像机下。禁用某些阴影更加真实(防止第一个网格体的影响)

FPSMesh->bCastDynamicShadow = false;
FPSMesh->CastShadow = false;

发射物的实现

设置一个球状发射物利用USphereComponent,利用UProjectileMovementComponent确定发射物的移动,定义一个函数用于管理发射物的发射

//传入发射方向,在角色类中获取,乘以发射速度
void AFPSProjectile::FireInDirection(const FVector& ShootDirection)
{
ProjectileMovementComponent->Velocity = ShootDirection * ProjectileMovementComponent->InitialSpeed;
}

在角色类中利用BindAction绑定按键,并且编写Fire函数,在角色类中需要新增一个变量用来确定角色需要发射哪一类发射物虽然现在只有1类。

BindAction需要一个角色类中的操作(函数),所以需要在角色类中再写一个Fire函数,其中调用发射物类中的发射函数

//在头文件中
UPROPERTY(EditDefaultsOnly, Category = Projectile)
TSubclassOf<class AFPSProjectile> ProjectileClass;

实现射击

在角色类的头文件中include发射物头文件,编写Fire函数,利用SpawnActor方法来生成发射物,调用发射物类中的发射函数实现发射。

void AFPSCharacter::Fire()
{
// 试图发射发射物。
if (ProjectileClass)
{
// 获取摄像机变换。
FVector CameraLocation;
FRotator CameraRotation;
GetActorEyesViewPoint(CameraLocation, CameraRotation); // 设置MuzzleOffset,在略靠近摄像机前生成发射物。
MuzzleOffset.Set(100.0f, 0.0f, 0.0f); // 将MuzzleOffset从摄像机空间变换到世界空间。
FVector MuzzleLocation = CameraLocation + FTransform(CameraRotation).TransformVector(MuzzleOffset); // 使目标方向略向上倾斜。
FRotator MuzzleRotation = CameraRotation;
MuzzleRotation.Pitch += 10.0f; UWorld* World = GetWorld();
if (World)
{
FActorSpawnParameters SpawnParams;
SpawnParams.Owner = this;
SpawnParams.Instigator = GetInstigator(); // 在枪口位置生成发射物。
AFPSProjectile* Projectile = World->SpawnActor<AFPSProjectile>(ProjectileClass, MuzzleLocation, MuzzleRotation, SpawnParams);
if (Projectile)
{
// 设置发射物的初始轨迹。
FVector LaunchDirection = MuzzleRotation.Vector();
Projectile->FireInDirection(LaunchDirection);
}
}
}
}

设置发射物的生命和碰撞

在发射物类的源文件中的构造函数中利用InitialLifeSpan设置生命周期

在引擎设置Collision中自定义Collision文件,在源文件构造函数中对SphereComp绑定该文件

SphereComp->BodyInstance.SetCollisionProfileName(TEXT("Projectile"));

当发射物碰撞物体消失

利用OnComponentHit事件,在发射物类中

SphereComponet->OnComponentHit.AddDynamic(this, &AFPSProjectile::OnHit);

void AFPSProjectile::OnHit(UPrimitiveComponent* HitComponent, AActor* OtherActor, UPrimitiveComponent* OtherComponent, FVector NormalImpulse, const FHitResult& Hit)
{
if (OtherActor != this && OtherComponent->IsSimulatingPhysics())
{
OtherComponent->AddImpulseAtLocation(ProjectileMovementComponent->Velocity * 100.0f, Hit.ImpactPoint);
} Destroy();
}

简单c++构建第一人称的更多相关文章

  1. D3D游戏编程系列(六):自己动手编写第一人称射击游戏之第一人称视角的构建

    说起第一人称射击游戏,不得不提第一人称视角啊,没有这个,那么这个第一就无从谈起啊,我作为一个观察者究竟如何在这个地图上顺利的移动和观察呢,那么,我们一起来研究下. 我们首先来看下CDXCamera类: ...

  2. 开发一个最简单的Cardboard虚拟现实应用(四)做一个Cardboard第一人称控制器

    [开源互助-原创文章,转载请说明出处]第三帖中已经创建了一个cardboard自带的demo应用,但它是不能移动的,玩家只能站在原地,通过头部转动来观察四周,除此之外,玩家并没有更多的手段与游戏场景进 ...

  3. 【转】265行JavaScript代码的第一人称3D H5游戏Demo

    译文:http://blog.jobbole.com/70956/ 原文:http://www.playfuljs.com/a-first-person-engine-in-265-lines/ 这是 ...

  4. 如何使用threejs实现第一人称视角的移动

    在数据可视化领域利用webgl来创建三维场景或VR已经越来越普遍,各种开发框架也应运而生.今天我们就通过最基本的threejs来完成第一人称视角的场景巡检功能.如果你是一位threejs的初学者或正打 ...

  5. ThingJS平台制作第一人称视角下的巡更效果

    今天想要做一个类似巡更的过程,就像是在学校保安巡更,小区保安巡更一样.巡更需要用到相应的场景,比如说:园区.学校.超市以及工厂等等,然后需要规划好路线也就是巡更的路线,并且视角要跟随路线来变换,从而达 ...

  6. Introduction to 3D Game Programming with DirectX 12 学习笔记之 --- 第十五章:第一人称摄像机和动态索引

    原文:Introduction to 3D Game Programming with DirectX 12 学习笔记之 --- 第十五章:第一人称摄像机和动态索引 代码工程地址: https://g ...

  7. Microsoft Hyperlapse——让第一人称视频更快更流畅

    Hyperlapse--让第一人称视频更快更流畅" title="Microsoft Hyperlapse--让第一人称视频更快更流畅"> 职业摄影师Nick Di ...

  8. 【Unity3D】Unity自带组件—完成第一人称人物控制

    1.导入unity自带的Character Controllers包 2.可以看到First Person Controller组件的构成 Mouse Look() : 随鼠标的移动而使所属物体发生旋 ...

  9. 基于HTML5及WebGL开发的2D3D第一人称漫游进行碰撞检测

    为了实现一个基于HTML5的场景小游戏,我采用了HT for Web来实现,短短200行代码,我就能实现用“第一人称”来操作前进后退上下左右,并且实现了碰撞检测. 先来看下实现的效果:http://h ...

  10. unity中制作模拟第一人称视角下的指南针

    private int zRotation; public GameObject obj; public void Update() { //obj = GameObject.Find("C ...

随机推荐

  1. Laravel入坑指南(4)——数据库(Mysql)

    来来来,新的一节出炉了.这一节大家一起了解,Laravel如何对Mysql进行CURD. 我们回顾一下,PHP操作Mysql无非就是通过五个要素:host(地址).username(用户名).pass ...

  2. 盘点 Udemy 上最受欢迎的免费编程课程

    之前给大家推荐过一些油管上的免费学习资源,如果您还没有看过的话可以点击这里前往. 今天再给大家推荐一批Udemy上超高质量并且免费的编程课程,有需要的小伙伴可以学起来了. 1. JavaScript ...

  3. 大白菜方式制作win10 PE启动U盘

    说明 最近帮朋友安装下win10,用了2种制作U盘启动盘的方式.记录一下也方便大家少走弯路. 准备的工具: 1.大白菜软件 2.win10镜像 3.1个U盘,U盘容量 > 8G即可. 制作PE启 ...

  4. ORACLE ROLLUP和CUBE介绍

    http://blog.csdn.net/wanghai__/article/details/4817920 ------------------ ROLLUP,是GROUP BY子句的一种扩展,可以 ...

  5. 搭建docker swarm集群

    环境介绍 管理节点    swarm01 192.168.5.140 工作节点   swarm02 192.168.5.141 管理节点执行 docker swarm init --advertise ...

  6. Spring rce CVE-2022-22965

    原理大致是这样:spring框架在传参的时候会与对应实体类自动参数绑定,通过"."还可以访问对应实体类的引用类型变量.使用getClass方法,通过反射机制最终获取tomcat的日 ...

  7. 用Taro写一个微信小程序——引入外部字体

    小程序直接用.ttf字体文件,在开发工具看没有问题,但是打包编译会提示这个字体文件打包上传不成功. 一.字体文件转换为css 1.打开https://transfonter.org/ 注意选择Base ...

  8. ASP.NET 上传文件导入Excel

    前言 本文对应的场景是导入Excel数据,Excel对应的字段都配置在xml文件中.截图如下: 代码实战 工具类 实体类:XMLReadModel.cs public class XMLReadMod ...

  9. 【Azure 云服务】当Windows系统发布新的安全漏洞后,如何查看Azure云服务(Cloud Service)的实例是否也更新了安全补丁呢?

    问题描述 当Windows发布新的安全漏洞后,会根据安全漏洞的级别分类来确定是紧急打补丁升级,还是每一月的补丁日( 每月第二周的星期二)来统一推送补丁. 比如最近的一个安全漏洞(9月13号发布)  C ...

  10. GaussDB(DWS)集群通信:详解pooler连接池

    本文分享自华为云社区<GaussDB(DWS) 集群通信系列一:pooler连接池>,作者:半岛里有个小铁盒. 1.前言 适用版本:[8.1.0(及以上)] GaussDB(DWS) 为M ...