Unreal Engine使用C++入门示例

转载自52VR 原文章链接 http://www.52vr.com/article-639-1.html

epic games宣布ue4免费使用之后,吸引了大批看好VRAR前景的游戏开发者。

不过国内ue4教程和资料太少,而且一大部分资料都是关于蓝图(Blueprint)的,好在官网放出了guide和demo。更多讨论,可以前往讨论区:http://www.52vr.com/forum-93-1.html


本文先演示一个如何在UnrealEngine上创建一个C++项目,然后实现一个可用按键控制物体的示例:

1. 安装Unreal Engine,在此不做详细说明。从官网上下载安装,然后注册epic games账号。如果要下源码,需要绑定Github账号,等到EpicGames自动邀请之后才能浏览源码。


2. 新建项目:

安装好之后,启动UnrealEngine,选择 新建项目-> c++ -> 基础代码

 

等加载完之后,选择文件->新建c++类,然后在如下界面选择继承Pawn(Pawn是可由玩家控制或者AI控制的物体的基类):


我在创建的时候取类名为CollidingPawn,  创建完之后会自动打开vs2012(如果没装会提示你装一个,其他版本比如vs2015也不行,只能是2012),生成一个CollidingPawn.cpp和CollidingPawn.h。

头文件如下所示, 我按照自己的理解加了注释:

CollidingPawn.h:

  

[代码]:

01#pragma once
02 
03 
04 
05#include "GameFramework/Pawn.h"
06 
07#include "CollidingPawn.generated.h"
08 
09 
10 
11UCLASS()
12 
13class DEMO__API ACollidingPawn : public APawn
14 
15{
16 
17    GENERATED_BODY()
18 
19 
20 
21public:
22 
23    // 构造函数,可在此方法中放置物体和参数
24 
25    ACollidingPawn();
26 
27 
28 
29    // 游戏开始调用此方法
30 
31    virtual void BeginPlay() override;
32 
33     
34 
35    // 如果PrimaryActorTick.bCanEverTick设置为true,则每一帧都会调用此方法。如果处于性能的考虑,可以将其关闭。
36 
37    virtual void Tick( float DeltaSeconds ) override;
38 
39 
40 
41    // 在此函数中绑定按键和方法
42 
43    virtual void SetupPlayerInputComponent(class UInputComponent* InputComponent) override;
44 
45};



接下来,我们在原来的基础上,来实现按键控制物体的小程序

先创建一个可见的球体:

在CollidingPawn.cpp的构造函数ACollidingPawn::ACollidingPawn()中添加一个球体,一个网格组件(mesh),一个弹簧臂和相机,代码如下:


[代码]:

01//创建一个球体
02 
03    USphereComponent* SphereComponent = CreateDefaultSubobject(TEXT("RootComponent"));
04 
05    //设置为根组件
06 
07    RootComponent = SphereComponent;
08 
09    //设置半径
10 
11    SphereComponent->InitSphereRadius(40.0f);
12 
13    SphereComponent->SetCollisionProfileName(TEXT("Pawn"));
14 
15 
16 
17    // 创建并放置网格物体组件,这样我们能看到球体的位置
18 
19    UStaticMeshComponent* SphereVisual = CreateDefaultSubobject(TEXT("VisualRepresentation"));
20 
21    //如果不把网格附加到SphereComponent 就看不到球体
22 
23    SphereVisual->AttachTo(RootComponent);
24 
25    static ConstructorHelpers::FObjectFinder      SphereVisualAsset(TEXT("/Game/StarterContent/Shapes/Shape_Sphere.Shape_Sphere"));
26 
27    if (SphereVisualAsset.Succeeded()){
28 
29        SphereVisual->SetStaticMesh(SphereVisualAsset.Object);
30 
31        SphereVisual->SetRelativeLocation(FVector(0.0f, 0.0f, -40.0f));
32 
33        SphereVisual->SetWorldScale3D(FVector(0.8f));
34 
35    }
36 
37 
38 
39    //  使用弹簧臂来让相机获得一种平滑、自然的运动。
40 
41    //  弹簧臂的目的是让视角跟SphereComponent保持一定距离,如果不加,效果像fps游戏的第一视角一样
42 
43    USpringArmComponent* SpringArm = CreateDefaultSubobject(TEXT("CameraAttachmentArm"));
44 
45    SpringArm->AttachTo(RootComponent);
46 
47    SpringArm->RelativeRotation = FRotator(-45.f, 0.f, 0.f); //45度角
48 
49    SpringArm->TargetArmLength = 400.0f; //弹簧臂长度
50 
51    SpringArm->bEnableCameraLag = true;
52 
53    SpringArm->CameraLagSpeed = 3.f;
54 
55 
56 
57    // 创建相机并附加到弹簧臂
58 
59    // 如果没有相机 什么都看不到
60 
61    UCameraComponent* Camera = CreateDefaultSubobject(TEXT("ActualCamera"));
62 
63    Camera->AttachTo(SpringArm, USpringArmComponent::SocketName);



然后配置按键: 打开ue编辑器, 选择编辑->项目设置-> 输入, 然后在右边的axis mappings加入如下设置:

MoveForWard,MoveRight,Turn,Turn_Y 可自定义,表示跟各个按键的绑定关系。

然后创建一个类CollidingPawnMovementComponent继承自PawnMovementComponent(控制pawn移动的组件),我们可以把WASD绑定的行为绑定到这个component上,然后把该component绑定到我们刚才创建的球体上:

CollidingPawnMovementComponent.cpp


  

[代码]:

01#include "Demo.h"
02 
03#include "CollidingPawnMovementComponent.h"
04 
05 
06 
07void UCollidingPawnMovementComponent::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction)
08 
09{
10 
11    Super::TickComponent(DeltaTime, TickType, ThisTickFunction);
12 
13 
14 
15    // Make sure that everything is still valid, and that we are allowed to move.
16 
17    if (!PawnOwner || !UpdatedComponent || ShouldSkipUpdate(DeltaTime))
18 
19    {
20 
21        return;
22 
23    }
24 
25 
26 
27    // Get (and then clear) the movement vector that we set in ACollidingPawn::Tick
28 
29    FVector DesiredMovementThisFrame = ConsumeInputVector().GetClampedToMaxSize(1.0f) * DeltaTime * 150.0f;
30 
31    if (!DesiredMovementThisFrame.IsNearlyZero())
32 
33    {
34 
35        FHitResult Hit;
36 
37        SafeMoveUpdatedComponent(DesiredMovementThisFrame, UpdatedComponent->GetComponentRotation(), true, Hit);
38 
39 
40 
41        // If we bumped into something, try to slide along it
42 
43        if (Hit.IsValidBlockingHit())
44 
45        {
46 
47            SlideAlongSurface(DesiredMovementThisFrame, 1.f - Hit.Time, Hit.Normal, Hit);
48 
49        }
50 
51    }
52 
53};


然后在CollidingPawn.h中加入如下代码:

[代码]:

1class UCollidingPawnMovementComponent* OurMovementComponent;
先将movementComponent绑定到刚才加的球体上,在CollidingPawn构造函数底部加入如下代码:

[代码]:

1// Create an instance of our movement component, and tell it to update the root.
2    OurMovementComponent = CreateDefaultSubobject<ucollidingpawnmovementcomponent>(TEXT("CustomMovementComponent"));
3    OurMovementComponent->UpdatedComponent = RootComponent;</ucollidingpawnmovementcomponent>
为了让游戏中的其他类知道CollidingPawn目前正在使用CollidingPawnMovementComponent作为移动控制组件,需要在CollidingPawn.h中加入以下代码:

[代码]:

1virtual UPawnMovementComponent* GetMovementComponent() const override;
然后在CollidingPawn.cpp中加入:

[代码]:

1UPawnMovementComponent* ACollidingPawn::GetMovementComponent() const
2{
3    return OurMovementComponent;
4}
刚才我们已经将新创建的移动控制组件绑定到了球体上,现在需要把WASD触发的函数绑定到移动组件上,在CollidingPawn中实现往前移动,往左移动,转动视角的三个方法:

[代码]:

01// 往前(后)移动
02void ACollidingPawn::MoveForward(float AxisValue)
03{
04    if (OurMovementComponent && (OurMovementComponent->UpdatedComponent == RootComponent))
05    {
06        OurMovementComponent->AddInputVector(GetActorForwardVector() * AxisValue);
07    }
08}
09 
10// 往左(右)移动
11void ACollidingPawn::MoveRight(float AxisValue)
12{
13    if (OurMovementComponent && (OurMovementComponent->UpdatedComponent == RootComponent))
14    {
15        OurMovementComponent->AddInputVector(GetActorRightVector() * AxisValue);
16    }
17}
18 
19// 左右转动视角
20void ACollidingPawn::Turn(float AxisValue)
21{
22    FRotator NewRotation = GetActorRotation();
23    NewRotation.Yaw += AxisValue;
24    SetActorRotation(NewRotation);
25}
然后将这三个方法在ACollidingPawn::SetupPlayerInputComponent中注册:

[代码]:

1void ACollidingPawn::SetupPlayerInputComponent(class UInputComponent* InputComponent)
2{
3    Super::SetupPlayerInputComponent(InputComponent);
4 
5    InputComponent->BindAxis("MoveForward", this, &ACollidingPawn::MoveForward);
6    InputComponent->BindAxis("MoveRight", this, &ACollidingPawn::MoveRight);
7    InputComponent->BindAxis("Turn", this, &ACollidingPawn::Turn);
8}
以上就完成了一个可用WASD移动和鼠标控制左右视角的球体
如果上下移动视角,可仿照以上的ACollidingPawn::Turn方法,将NewRotation.Yaw += AxisValue; 改为NewRotation.Pitch += AxisValue;即可


Unreal Engine 4 Scripting with C++ Cookbook 2016 | ISBN-10: 1785885545 | 431 pages | PDF | 7 MB Key Features A straightforward and easy-to-follow format A selection of the most important tasks and problems Carefully organized instructions to solve problems efficiently Clear explanations of what you did Solutions that can be applied to solve real-world problems Book Description Unreal Engine 4 (UE4) is a complete suite of game development tools made by game developers, for game developers. With more than 100 practical recipes, this book is a guide showcasing techniques to use the power of C++ scripting while developing games with UE4. It will start with adding and editing C++ classes from within the Unreal Editor. It will delve into one of Unreal's primary strengths, the ability for designers to customize programmer-developed actors and components. It will help you understand the benefits of when and how to use C++ as the scripting tool. With a blend of task-oriented recipes, this book will provide actionable information about scripting games with UE4, and manipulating the game and the development environment using C++. Towards the end of the book, you will be empowered to become a top-notch developer with Unreal Engine 4 using C++ as the scripting language. What you will learn Build function libraries (Blueprints) containing reusable code to reduce upkeep Move low-level functions from Blueprint into C++ to improve performance Abstract away complex implementation details to simplify designer workflows Incorporate existing libraries into your game to add extra functionality such as hardware integration Implement AI tasks and behaviors in Blueprints and C++ Generate data to control the appearance and content of UI elements
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值