C++ Programming Tutorials_1翻译

来源:互联网 发布:java synchronized 块 编辑:程序博客网 时间:2024/05/24 04:24


所在原文目录结构位置:

C++ Programming Guide

 |_____Programming Quick Start Guide

 |_____Introduction to C++ Programming in UE4

 |_____C++ Programming Tutorials

 |_____Managing Game Code

 |_____Development Setup

 |_____Gameplay Programming

 |_____Engine Architecture

 |_____Console Manager: Console Variables in C++

 |_____Command-Line Arguments

 |_____Assertions

 |_____Blueprint Function Libraries

 |_____Unreal Build System

 |_____Plugins

 |_____Coding Standard

 |_____Symbol Debugger


原文地址:Programming Tutorials


-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

C++ Programming Tutorials

C++编程教程


1.Player Input and Pawns 玩家输入和Pawn(个人感觉Pawn是副角色,配角) 

 Over the course of this tutorial, you will learn to react to player input by extending the Pawn class.

通过这节教程,你将要学习通过对扩展Pawn 类对玩家的输入作出反应

Steps:步骤:

(1).Customize A Pawn 设定一个Pawn

       If you are new to Unreal Engine 4, you might want to read ourProgramming Quick Start tutorial first. For this tutorial, we will assume you are familiar with creating a      project, adding C++ code to it, and compiling your code.

      如果你是新手,那么看前面翻译的文章Programming Quick Start Guide,在本节教程,我们假定你已经对创建一个项目,添加C++代码和编译你的代码熟悉了.

      ①We will begin by creating a new, Basic Code project, with starter content, named "HowTo_PlayerInput". Then, we'll add a customizedPawn class, which we will call "MyPawn", to the project.

      我们从创建一个新的,基础代码项目,开始内容命名为"HowTo_PlayerInput". 然后,我们在项目添加一个特定的Pawn类,我们叫它"MyPawn"

               !!!A Pawn is a type of Actor that is designed to be controlled by human players or AI.

               !!!Pawn是Actor的一种类型,被设计成由人类控制或人工智能

        ②The first thing we're going to do is set our MyPawn to respond to player input automatically upon the game starting. ThePawn class provides a variable we can set during initialization that handles this for us. InMyPawn.cpp, add the following code to AMyPawn::AMyPawn:

           我们要做的第一件事情就是设置MyPawn来自动响应游戏一开始后玩家的输入.Pawn类提供一个变量,我们能在初始化的时候设置这个变量.在MyPawn.cpp中,在AMyPawn::AMyPawn中添加如下代码:

 

// Set this pawn to be controlled by the lowest-numbered player//设置这个Pawn能被最底层的玩家控制AutoPossessPlayer = EAutoReceiveInput::Player0;

       ③Next, we'll build a few basic Components. If you want to learn more about adding and managingComponents in code, as well as some common types ofComponents you will encounter, try reading ourComponents And Collision tutorial. In order to keep track of the Component we will create, we should add the following code toMyPawn.h, at the bottom of our class definition:

          下一步,我们要创建一些基础的组件.如果你想学习更多关于在代码中添加和管理组件,以及你会遇到一些常见的类型的组件,阅读我们的Components And Collision tutorial.为了跟踪我们创建的组件,我们应该在MyPawn.h中,在类定义的底部添加如下代码:

UPROPERTY(EditAnywhere)USceneComponent* OurVisibleComponent;

          !!!This variable is tagged as a UPROPERTY so that it will be visible toUnreal Engine. This is important because it prevents the variable from being reset when the game is launched, or when the project or level is closed and reloaded.
          !!!这个变量被标记为UPROPERTY ,因此,它将被暴露在虚幻引擎中,这是非常重要的,因为它能防止在游戏启动,关卡被关闭或者重新加载的时候被重置,

      And back in MyPawn.cpp, we should add the following code toAMyPawn::AMyPawn:

       再看MyPawn.cpp,我们应该在AMyPawn::AMyPawn中添加如下代码:

// Create a dummy root component we can attach things to.// 创建一个虚拟根组件,我们可以附加东西。RootComponent = CreateDefaultSubobject<USceneComponent>(TEXT("RootComponent"));// Create a camera and a visible object// 创建一个摄像机和一个可见的对象UCameraComponent* OurCamera = CreateDefaultSubobject<UCameraComponent>(TEXT("OurCamera"));OurVisibleComponent = CreateDefaultSubobject<UStaticMeshComponent>(TEXT("OurVisibleComponent"));// Attach our camera and visible object to our root component. Offset and rotate the camera.//附上我们的相机和可见的对象到根组件,偏移和旋转相机OurCamera->AttachTo(RootComponent);OurCamera->SetRelativeLocation(FVector(-250.0f, 0.0f, 250.0f));OurCamera->SetRelativeRotation(FRotator(-45.0f, 0.0f, 0.0f));OurVisibleComponent->AttachTo(RootComponent);

      ④We are now ready to save our changes and compile with the Build command in Visual Studio or the Compile button in theUnreal Engine editor

        现在,我们就可以准备保存和编译我们的项目了,在vs中的build或者UE编译按钮都可以.

Now that we have a customizedPawn to react to our game's input, we'll need to define what that input will be. To do this, we'll configure our project'sInput Settings in the Unreal Engine editor.

既然我们已经设定了一个Pawn来响应我们游戏的输入,我们需要定义输入是什么,因此,我们要在虚幻编辑器中配置我们的项目输入设置


MyPawn.h代码:

// Copyright 1998-2015 Epic Games, Inc. All Rights Reserved.#pragma once#include "GameFramework/Pawn.h"#include "MyPawn.generated.h"UCLASS()class HOWTO_PLAYERINPUT_API AMyPawn : public APawn{    GENERATED_BODY()public:    // Sets default values    AMyPawn();    // Called when the game starts or when spawned    virtual void BeginPlay() override;    // Called every frame    virtual void Tick( float DeltaSeconds ) override;    // Called to bind functionality to input    virtual void SetupPlayerInputComponent(class UInputComponent* InputComponent) override;    UPROPERTY(EditAnywhere)    USceneComponent* OurVisibleComponent;};

MyPawn.cpp代码:

// Copyright 1998-2015 Epic Games, Inc. All Rights Reserved.#include "HowTo_PlayerInput.h"#include "MyPawn.h"// Sets default valuesAMyPawn::AMyPawn(){    // Set this pawn to call Tick() every frame.  You can turn this off to improve performance if you don't need it.    PrimaryActorTick.bCanEverTick = true;    // Set this pawn to be controlled by the lowest-numbered player    AutoPossessPlayer = EAutoReceiveInput::Player0;    // Create a dummy root component we can attach things to.    RootComponent = CreateDefaultSubobject<USceneComponent>(TEXT("RootComponent"));    // Create a camera and a visible object    UCameraComponent* OurCamera = CreateDefaultSubobject<UCameraComponent>(TEXT("OurCamera"));    OurVisibleComponent = CreateDefaultSubobject<UStaticMeshComponent>(TEXT("OurVisibleComponent"));    // Attach our camera and visible object to our root component. Offset and rotate the camera.    OurCamera->AttachTo(RootComponent);    OurCamera->SetRelativeLocation(FVector(-250.0f, 0.0f, 250.0f));    OurCamera->SetRelativeRotation(FRotator(-45.0f, 0.0f, 0.0f));    OurVisibleComponent->AttachTo(RootComponent);}// Called when the game starts or when spawnedvoid AMyPawn::BeginPlay(){    Super::BeginPlay();}// Called every framevoid AMyPawn::Tick( float DeltaTime ){    Super::Tick( DeltaTime );}// Called to bind functionality to inputvoid AMyPawn::SetupPlayerInputComponent(class UInputComponent* InputComponent){    Super::SetupPlayerInputComponent(InputComponent);}
</pre><pre class="cpp" name="code">

(2).Configure Game Input 配置游戏输入

         !!!There are two types of input mappings: Action and Axis.

             Action Mappings are useful to think of as "yes or no" inputs, like the buttons on a mouse or joystick. They report when they are pressed, released, double-clicked, or held down for a short time. Discrete actions like jumping, shooting, or interacting with objects are good candidates for this type of mapping.

             Axis Mappings are continuous - think of them as "how much" inputs, like the stick on a joystick, or the position of a mouse cursor. They report their value every frame, even if they're not moving. Things with magnitude or direction, such as walking, looking around, and steering a vehicle are usually handled this way.

             While input mappings can be defined directly in code, the usual method is to define them in theUnreal Engine editor, so that's how we'll do it in this tutorial.

 

          !!!这儿有两种输入映射:Action(动作) 和 Axis(轴)

             动作映射是有用的,被认为是"是或者否"的输入,像按钮在鼠标或操纵杆.它们在短时间内反馈被单击,释放,双击或者按住.不连续跳跃等操作、射击、或与对象交互适合使用这种类型的映射。

             轴映射是连续的,认为它们是“多少”输入,像按在操纵杆上或鼠标光标的位置,它们每一帧都返回数据,即使它们没有移动.有大小和方向,就像走路,环顾四周和车辆转向通常用这种映射

             在代码中可以定义直接输入映射,通常的办法是在虚幻编辑器中定义它们,本教程中,我们将这么做


       ①In the Unreal Engine editor, under the Edit dropdown menu, we'll click the Project Settings option.

         在虚幻编辑器中, Edit (编辑)->Project Settings (项目设置)->Input(输入)

    ②From there, we'll select the Input option from theEngine section on the left. We can then expand theBindings category that appears on the right, and add oneAction Mapping and twoAxis Mappings.

The plus sign next to the Action Mapping or Axis Mapping section headings will add a new mapping. The expander arrow on the left can be used to show or hide our mappings. To add an additional input to a mapping, click the plus sign next to that mapping. Following are the mappings and inputs we will need. Take note of the negative values for the "S" and A" inputs.

选输入后,按相应的加号增加,如下所示:


       ③Now that our input is configured, let's set up a MyPawn in our level. The MyPawn class will appear in ourContent Browser, and is ready to be dragged into theLevel Editor.

          既然我们已经配置了输入,让我们在关卡中设置MyPawn ,MyPawn 类将出现在我们的Content Browser(内容浏览器)中,准备好被拖到关卡编辑器中了.

     ④One more step is needed to set up our MyPawn. We'll need to give it aStatic Mesh so that we can see it in the game. We can do this by selecting theMyPawn we just created, selecting the component called "OurVisibleComponent (Inherited)" in theDetails Panel, and assigning an asset to it through the dropdown box in theStatic Mesh category. For this tutorial, "Shape_Cylinder" is a good asset to use.

      我们要多做一步来设置我们的MyPawn,我们要给他一个静态的网格模型以便我们可以在游戏中看到他,确保你已经把它拖到世界中后,在右边 Details Panel中,设置Static Mesh ,这节教材中"Shape_Cylinder"(圆柱体)是一个不错的选择

       ⑤We can now save our level and return to Visual Studio to write code that will make the MyPawn we placed react to the inputs we defined.

          现在我们能保存下我们的关卡然后返回到VS中写代码让MyPawn 响应我们定义的输入

We're now ready to finish coding our MyPawn class in Visual Studio.

我们现在已经在VS,MyPawn类中完成了我们的代码.

MyPawn.h

<strong>// Copyright 1998-2015 Epic Games, Inc. All Rights Reserved.#pragma once#include "GameFramework/Pawn.h"#include "MyPawn.generated.h"UCLASS()class HOWTO_PLAYERINPUT_API AMyPawn : public APawn{    GENERATED_BODY()public:    // Sets default values    AMyPawn();    // Called when the game starts or when spawned    virtual void BeginPlay() override;    // Called every frame    virtual void Tick( float DeltaSeconds ) override;    // Called to bind functionality to input    virtual void SetupPlayerInputComponent(class UInputComponent* InputComponent) override;    UPROPERTY(EditAnywhere)    USceneComponent* OurVisibleComponent;};</strong>

MyPawn.cpp

// Copyright 1998-2015 Epic Games, Inc. All Rights Reserved.#include "HowTo_PlayerInput.h"#include "MyPawn.h"// Sets default valuesAMyPawn::AMyPawn(){    // Set this pawn to call Tick() every frame.  You can turn this off to improve performance if you don't need it.    PrimaryActorTick.bCanEverTick = true;    // Set this pawn to be controlled by the lowest-numbered player    AutoPossessPlayer = EAutoReceiveInput::Player0;    // Create a dummy root component we can attach things to.    RootComponent = CreateDefaultSubobject<USceneComponent>(TEXT("RootComponent"));    // Create a camera and a visible object    UCameraComponent* OurCamera = CreateDefaultSubobject<UCameraComponent>(TEXT("OurCamera"));    OurVisibleComponent = CreateDefaultSubobject<UStaticMeshComponent>(TEXT("OurVisibleComponent"));    // Attach our camera and visible object to our root component. Offset and rotate the camera.    OurCamera->AttachTo(RootComponent);    OurCamera->SetRelativeLocation(FVector(-250.0f, 0.0f, 250.0f));    OurCamera->SetRelativeRotation(FRotator(-45.0f, 0.0f, 0.0f));    OurVisibleComponent->AttachTo(RootComponent);}// Called when the game starts or when spawnedvoid AMyPawn::BeginPlay(){    Super::BeginPlay();}// Called every framevoid AMyPawn::Tick( float DeltaTime ){    Super::Tick( DeltaTime );}// Called to bind functionality to inputvoid AMyPawn::SetupPlayerInputComponent(class UInputComponent* InputComponent){    Super::SetupPlayerInputComponent(InputComponent);}


(3).Program and Bind Game Actions

      ①In Visual Studio, open MyPawn.h and add the following code to the bottom of MyPawn's class definition:

         在VS中打开MyPawn.h,添加以下代码到MyPawn的类的定义的底部

    

//Input functionsvoid Move_XAxis(float AxisValue);void Move_YAxis(float AxisValue);void StartGrowing();void StopGrowing();//Input variablesFVector CurrentVelocity;bool bGrowing;

     !!!The four input functions are going to be bound to our input events. When they run, they will update the values stored in our new input variables, which MyPawn will use to determine what it should do during in the game.

     !!!这四个输入函数将被绑定到我们的输入事件.当它们运行的时候,他们将更新存储在我们的新输入变量的值,MyPawn将用于确定在游戏中应该做什么

  ②We'll switch over to MyPawn.cpp and program the four functions we just declared. Add the following code:

   我们切换到MyPawn.cpp ,定义我们前面声明的函数.代码如下:

void AMyPawn::Move_XAxis(float AxisValue){    // Move at 100 units per second forward or backward    CurrentVelocity.X = FMath::Clamp(AxisValue, -1.0f, 1.0f) * 100.0f;}void AMyPawn::Move_YAxis(float AxisValue){    // Move at 100 units per second right or left    CurrentVelocity.Y = FMath::Clamp(AxisValue, -1.0f, 1.0f) * 100.0f;}void AMyPawn::StartGrowing(){    bGrowing = true;}void AMyPawn::StopGrowing(){    bGrowing = false;}

We use FMath::Clamp to constrain the values we get from our inputs to the range of -1 to +1. Although it's not an issue in this example, if there were multiple keys that could affect an axis in the same way, the values would be added together if a player pressed those inputs at the same time. For example, if both W and Up Arrow were mapped to MoveX with scales of 1.0, pressing both would result in an AxisValue of 2.0, which would let the player move at double speed if we didn't clamp it.
我们用FMath::Clamp 函数来限制值在-1~1.虽然在这个例子中这不是一个问题,但是如果这儿有很多按键同样的也许会影响轴映射,如果一个玩家同一时间按下一些按键,这些值就加到一起,举个例子,如果W和向上箭头映射尺度为1.0(w和向上都是前进按键),同时按住这两个键就是2.0,如果我们不限制,玩家就是2倍的移动速度!!(人家不就相当于开了加速外挂了吗?)

    !!!You may notice that the two "Move" functions take axis values as floats, while the "Grow" functions do not. This is because they will be mapped to MoveX and MoveY, which are Axis Mappings, and therefore will have a floating-point parameter. Action Mappings do not have this parameter.

    !!!你也许注意到了,两个 Move函数值是float类型,而Grow不是,这是因为他们要被映射到MoveX和MoveY,是轴映射,因此是float,动作映射没有这个参数

   ③Now that we have our input functions defined, we'll need to bind them so that they will react to the appropriate inputs. Add the following code inside ofAMyPawn::SetupPlayerInputComponent:

    既然我们已经定义好了输入函数,我们需要绑定他们,这样他们会反应到适当的输入,添加以下代码到AMyPawn::SetupPlayerInputComponent: 内

// Respond when our "Grow" key is pressed or released.InputComponent->BindAction("Grow", IE_Pressed, this, &AMyPawn::StartGrowing);InputComponent->BindAction("Grow", IE_Released, this, &AMyPawn::StopGrowing);// Respond every frame to the values of our two movement axes, "MoveX" and "MoveY".InputComponent->BindAxis("MoveX", this, &AMyPawn::Move_XAxis);InputComponent->BindAxis("MoveY", this, &AMyPawn::Move_YAxis);

    ④We now have variables that are updated by the inputs we configured. All we have left to do is write code to do something with them. Let's add the following code toAMyPawn::Tick:

    我们现在有更新我们配置的输入变量.剩下我们要做的就是为他们写一些代码,在AMyPawn::Tick中添加如下代码:

<strong>// Handle growing and shrinking based on our "Grow" action{    float CurrentScale = OurVisibleComponent->GetComponentScale().X;    if (bGrowing)    {        // Grow to double size over the course of one second        CurrentScale += DeltaTime;    }    else    {        // Shrink half as fast as we grow        CurrentScale -= (DeltaTime * 0.5f);    }    // Make sure we never drop below our starting size, or increase past double size.    CurrentScale = FMath::Clamp(CurrentScale, 1.0f, 2.0f);    OurVisibleComponent->SetWorldScale3D(FVector(CurrentScale));}// Handle movement based on our "MoveX" and "MoveY" axes{    if (!CurrentVelocity.IsZero())    {        FVector NewLocation = GetActorLocation() + (CurrentVelocity * DeltaTime);        SetActorLocation(NewLocation);    }}</strong>
      ⑤After compling our code, we can return to theUnreal Editor and press Play. We should have control of ourPawn with the WASD keys, and we should be able to make it grow by holding Space Bar, and watch it shrink when we let go.

       编译代码后,我们回到虚幻编辑器,点Play运行,WASD控制方向,空格键控制增长,松开缩小.

完整的代码:

MyPawn.h

// Copyright 1998-2015 Epic Games, Inc. All Rights Reserved.#pragma once#include "GameFramework/Pawn.h"#include "MyPawn.generated.h"UCLASS()class HOWTO_PLAYERINPUT_API AMyPawn : public APawn{    GENERATED_BODY()public:    // Sets default values    AMyPawn();    // Called when the game starts or when spawned    virtual void BeginPlay() override;    // Called every frame    virtual void Tick(float DeltaSeconds) override;    // Called to bind functionality to input    virtual void SetupPlayerInputComponent(class UInputComponent* InputComponent) override;    UPROPERTY(EditAnywhere)    USceneComponent* OurVisibleComponent;    // Input functions    void Move_XAxis(float AxisValue);    void Move_YAxis(float AxisValue);    void StartGrowing();    void StopGrowing();    // Input variables    FVector CurrentVelocity;    bool bGrowing;};


MyPawn.cpp

// Copyright 1998-2015 Epic Games, Inc. All Rights Reserved.#include "HowTo_PlayerInput.h"#include "MyPawn.h"// Sets default valuesAMyPawn::AMyPawn(){    // Set this pawn to call Tick() every frame.  You can turn this off to improve performance if you don't need it.    PrimaryActorTick.bCanEverTick = true;    // Set this pawn to be controlled by the lowest-numbered player    AutoPossessPlayer = EAutoReceiveInput::Player0;    // Create a dummy root component we can attach things to.    RootComponent = CreateDefaultSubobject<USceneComponent>(TEXT("RootComponent"));    // Create a camera and a visible object    UCameraComponent* OurCamera = CreateDefaultSubobject<UCameraComponent>(TEXT("OurCamera"));    OurVisibleComponent = CreateDefaultSubobject<UStaticMeshComponent>(TEXT("OurVisibleComponent"));    // Attach our camera and visible object to our root component. Offset and rotate the camera.    OurCamera->AttachTo(RootComponent);    OurCamera->SetRelativeLocation(FVector(-250.0f, 0.0f, 250.0f));    OurCamera->SetRelativeRotation(FRotator(-45.0f, 0.0f, 0.0f));    OurVisibleComponent->AttachTo(RootComponent);}// Called when the game starts or when spawnedvoid AMyPawn::BeginPlay(){    Super::BeginPlay();}// Called every framevoid AMyPawn::Tick(float DeltaTime){    Super::Tick(DeltaTime);    // Handle growing and shrinking based on our "Grow" action    {        float CurrentScale = OurVisibleComponent->GetComponentScale().X;        if (bGrowing)        {            // Grow to double size over the course of one second            CurrentScale += DeltaTime;        }        else        {            // Shrink half as fast as we grow            CurrentScale -= (DeltaTime * 0.5f);        }        // Make sure we never drop below our starting size, or increase past double size.        CurrentScale = FMath::Clamp(CurrentScale, 1.0f, 2.0f);        OurVisibleComponent->SetWorldScale3D(FVector(CurrentScale));    }    // Handle movement based on our "MoveX" and "MoveY" axes    {        if (!CurrentVelocity.IsZero())        {            FVector NewLocation = GetActorLocation() + (CurrentVelocity * DeltaTime);            SetActorLocation(NewLocation);        }    }}// Called to bind functionality to inputvoid AMyPawn::SetupPlayerInputComponent(class UInputComponent* InputComponent){    Super::SetupPlayerInputComponent(InputComponent);    // Respond when our "Grow" key is pressed or released.    InputComponent->BindAction("Grow", IE_Pressed, this, &AMyPawn::StartGrowing);    InputComponent->BindAction("Grow", IE_Released, this, &AMyPawn::StopGrowing);    // Respond every frame to the values of our two movement axes, "MoveX" and "MoveY".    InputComponent->BindAxis("MoveX", this, &AMyPawn::Move_XAxis);    InputComponent->BindAxis("MoveY", this, &AMyPawn::Move_YAxis);}void AMyPawn::Move_XAxis(float AxisValue){    // Move at 100 units per second forward or backward    CurrentVelocity.X = FMath::Clamp(AxisValue, -1.0f, 1.0f) * 100.0f;}void AMyPawn::Move_YAxis(float AxisValue){    // Move at 100 units per second right or left    CurrentVelocity.Y = FMath::Clamp(AxisValue, -1.0f, 1.0f) * 100.0f;}void AMyPawn::StartGrowing(){    bGrowing = true;}void AMyPawn::StopGrowing(){    bGrowing = false;}


(4).On Your Own! 靠自己做!

Using what you have learned, try to do the following:

根据你学到的,尝试着做以下的内容:

     ●Implement directional controls that increase speed after being held for a certain period of time.

        实现方向控制时,按住一段时间,速度暴涨(比如前进按钮w,按下3秒后,速度变成原来的10倍)

     ●Create a special input sequence that instantly expands the object to full scale when the user presses anAction Mapping immediately after starting to press an Axis Mapping.

          创建一个指定的输入序列,立即将对象缩放到指定倍数,也就是用动作映射和轴映射实现对象的增长/缩小

As for the specifics covered in this tutorial:至于本教程中介绍的细节:

     ●For more information about Input, try the Input page. 关于输入的更多信息,点此链接

     ●For further tutorials, see the C++ Programming Tutorials page.  进一步的教程,点此链接


//以下代码为本人的作业,仅供参考

      --------------------------------解决第一个: 3秒后10倍速度的问题--------------------------------

   第一步:添加变量:    float m_TimeAdd; //时间累加

   第二步:AMyPawn构造函数中初始化为0:   m_TimeAdd = 0.0f;  //时间累计

   第三步:修改AMyPawn::Tick函数:

 

void AMyPawn::Tick( float DeltaTime ){Super::Tick( DeltaTime );// "Grow" 模块{float CurrentScale = OurVisibleComponent->GetComponentScale().X;if (bGrowing){// Grow to double size over the course of one secondCurrentScale += DeltaTime;}else{// Shrink half as fast as we growCurrentScale -= (DeltaTime * 0.5f);}// Make sure we never drop below our starting size, or increase past double size.CurrentScale = FMath::Clamp(CurrentScale, 1.0f, 2.0f);OurVisibleComponent->SetWorldScale3D(FVector(CurrentScale));}// WASD移动模块{if (!CurrentVelocity.IsZero()){if (m_TimeAdd >= 3.0f){//10倍的速度FVector NewLocation = GetActorLocation() + (CurrentVelocity * DeltaTime) * 10;SetActorLocation(NewLocation);}else{//还是原来的速度FVector NewLocation = GetActorLocation() + (CurrentVelocity * DeltaTime);SetActorLocation(NewLocation);}//加上时间间隔m_TimeAdd += DeltaTime;}else{//只要有停顿,从新开始累加时间m_TimeAdd = 0.0f;}}}


      ------------------------------ 按空格键立马变大问题--------------------------------


// "Grow" 模块{float CurrentScale;if (bGrowing){//空格键按住,直接长大为两倍CurrentScale = 2.0f;OurVisibleComponent->SetWorldScale3D(FVector(CurrentScale));}else{//空格键松开,直接变为原大小CurrentScale = 0.5f;OurVisibleComponent->SetWorldScale3D(FVector(CurrentScale));}}

动作映射和轴映射的额区别见上面

2.Game-Controlled Cameras 游戏控制摄像机

3.Variables, Timers, and Events 变量,定时器和事件

4.Player-Controlled Cameras 玩家控制摄像机

5.Components And Collision 组件和碰撞
































0 0