2017-08-05 10:53:11 qq_35534985 阅读数 6615
  • 从这里开始虚幻4-Editor介绍 v4.18

    本课程系列取名英译系列,是录制人员参考国外英文原版经典教程,结合中国人的习惯录制而成。希望能够给大家以帮助。从这里开始虚幻4系列教程,是Unreal的官方发布的入门教学,非常经典,是学习Unreal的佳入口。

    2377 人正在学习 去看看 杨石兴

《学习笔记记录》

新人接触UE4,在此发帖主要用于记录学习内容,同时希望可以帮助其他朋友

在网上看到很多AR的视频,感觉很有意思,就研究了一下,感觉UE4好像不能直接进行AR的开发。通过查找资料,看到一款UE4开发AR的插件,感觉可能很强大,就下载下来尝试一下。

插件名称:Unreal4AR

官方网址:http://www.unreal4ar.com/

打开后出现如下所示界面

此处简要介绍了一下插件的功能,说明插件可以让开发人员使用UE4的蓝图脚本进行项目开发。

点击橙色按钮“GET THE PLUGIN NOW!”获取插件。然后弹出如下界面

该界面显示了UNREAL4AR插件的特性和支持的UE4版本,及目前插件的最新版本v1.8。要想获得插件,还需选择权限,这里分为三种。


第一种Editor demo是免费的,应该只能编辑学习使用,不能打包生成。

第二种是个人开发使用,收费99欧元,用于个人开发

第三种是商业开发使用,收费249欧元,用于商业开发

我这里选择的是第一种,然后点击按钮“ADD TO CART”

然后点击“Proceed to checkout”,进行确认,下一个界面会要求填写信息,我随便写的也可以通过。

然后点击“PLACE ORDER”按钮,即可进入下载页面

然后再点击Download后面的连接就可以下载插件了。

2016-09-06 16:09:31 sgnyyy 阅读数 1624
  • 从这里开始虚幻4-Editor介绍 v4.18

    本课程系列取名英译系列,是录制人员参考国外英文原版经典教程,结合中国人的习惯录制而成。希望能够给大家以帮助。从这里开始虚幻4系列教程,是Unreal的官方发布的入门教学,非常经典,是学习Unreal的佳入口。

    2377 人正在学习 去看看 杨石兴
  FVector2D thisMouse;
    FVector2D dMouse;
    APlayerController* PController = GetWorld()->GetFirstPlayerController();
    PController->GetMousePosition( thisMouse.X, thisMouse.Y );
获取鼠标按下去的时间
float time = PController->GetInputKeyTimeDown(  EKeys::LeftMouseButton );

2014-07-24 21:11:24 u010153703 阅读数 1623
  • 从这里开始虚幻4-Editor介绍 v4.18

    本课程系列取名英译系列,是录制人员参考国外英文原版经典教程,结合中国人的习惯录制而成。希望能够给大家以帮助。从这里开始虚幻4系列教程,是Unreal的官方发布的入门教学,非常经典,是学习Unreal的佳入口。

    2377 人正在学习 去看看 杨石兴

Unreal里的动画这么理解:

动画资源:AnimSequence, AnimMontage, BlendSpace...  其中,AnimSequence是我们导入的最基础的AnimClip,AnimMontage和BlendSpace都是在Unreal的Personal里用AnimSequence进一步制作的。

动画控制:AnimationBlueprint。 

AnimationBlueprint包含两部分:Anim Graph和Event Graph。  

Anim Graph: 动画状态转换(动画状态机)、动画混合(支持简单混合,目前还没有强大的混合树功能)。

Event Graph:可以自定义一些Event。或者处理某些AnimSequence、AnimMontage里插入的某些Event。

Unreal将角色逻辑和动画逻辑分开来处理,这样子处理有他的道理,只不过用户需要多了解Character和AnimInstance的通信机制。以CharacterBlueprint和AnimationBlueprint为例。

用户输入控制行走:

CharacterBlueprint里接受用户输入,由Character的MovementComponent得到Character的Speed。 而这个Speed是决定AnimationBlueprint里Idle-Walk-Run的参数。AnimationBlueprint如何从CharacterBlueprint获取信息呢?


其实看到了两种模式,(1)Try Get Pawn Owner节点得到当前的Player,由Player可以得到Velocity设置给AnimBP的Speed; 

(2)另一个就是需要做类型转换,将获取的Character转换为我们的MyCharacter,也就是我们已经用到的CharacterBP类型,此时就能获取MyCharacter 这个CharacterBP里的成员,变量、函数、Event,只要有访问权限,都能调用。

另外Try Get Pawn Owner节点可以换为Get Owning Actor节点。Get Owning Actor获取的是使用这个AnimationBlueprint的Actor。在这里这两个节点获取的对象是相同的。


动画状态机里一些动画状态的转换条件由AnimationBlueprint的一些Variable控制。而这些Variable又经常受用户输入影响,也就是这些Variable的值需要从CharacterBlueprint获取。 本质和前文的“用户输入控制行走”无差。


不用状态机转换,用Slot来控制:

需要制作AnimMontage,在AnimGraph里将Slot连接到Final Animation Pose。那么接下来不管是在AnimationBlueprint里的Event Graph里用Montage Play节点调用Montage,还是在CharacterBlueprint里用Play Anim Montage节点调用Montage,都可行!

注意,但在CharacterBlueprint里用PlayAnimMontage节点调用带RootMotion的Montage时,播放时可能会出现角色只出现位移没有播放相应动作的现象。 建议动画的处理还是尽量放在AnimBlueprint里。CharacterBlueprint只是告诉AnimBlueprint播放什么动画就好了。



完全不用AnimationBluerpint,直接在CharacterBlueprint里用Play Animation节点调用最原始的AnimSequence

注意,Play Animation节点是可以在CharacterBlueprint里用的,不过得注意去掉Context Sensitive。








2014-07-31 18:37:23 u010153703 阅读数 1187
  • 从这里开始虚幻4-Editor介绍 v4.18

    本课程系列取名英译系列,是录制人员参考国外英文原版经典教程,结合中国人的习惯录制而成。希望能够给大家以帮助。从这里开始虚幻4系列教程,是Unreal的官方发布的入门教学,非常经典,是学习Unreal的佳入口。

    2377 人正在学习 去看看 杨石兴
Unreal里的Input被我分为两类,(1)只控制Possesed Pawn的ActionEvent和AxisEvents,需要配合设置Project Settings里的Input。(2)可以控制整个场景的任何物体。用的比较多的是KeyEvents和MouseEvents,当然,如果你用摇杆外设,用的比较多的是GamepadEvents。

(1) ActionEvent和AxisEvents
在ProjectSetting的 Input里定义一堆键盘输入来做Action和Axis的Mapping。
在ProjectSetting里的Input有两种:
Action Events和Axis Events。
AxisEvent提供对应按键的Axis Value。


Action Event则不提供额外信息,只是触发事件。



(2) KeyEvents和MouseEvents
其实,还有很有用的Input种类是:KeyEvents和MouseEvents。


Action Events和Axis Events,按键消息只被Possessed的Pawn接收,也就是你只能控制PlayerPawn/PlayerCharacter。
但KeyEvents和MouseEvents的按键消息可以被场景中任何物体接收。

噢噢噢,有了KeyEvents,用来测试多么方便多么方便呀~ 


2018-06-08 14:17:24 zp288105109a 阅读数 531
  • 从这里开始虚幻4-Editor介绍 v4.18

    本课程系列取名英译系列,是录制人员参考国外英文原版经典教程,结合中国人的习惯录制而成。希望能够给大家以帮助。从这里开始虚幻4系列教程,是Unreal的官方发布的入门教学,非常经典,是学习Unreal的佳入口。

    2377 人正在学习 去看看 杨石兴

    断断续续学习Unreal很久了,但工作用的是Unity,Unreal很多API都记不住,就分类记录下。

    C++获取UMG组件有2种方式,目前知道的,一个是通过属性宏(BindWidget),另一个则类似Unity的Transform.Find(string name),Unreal用的是UWidget* GetWidgetFromName(const FName& Name) const

    .h:

#include "CoreMinimal.h"
#include "Blueprint/UserWidget.h"
#include "Components/Button.h"
#include "StartUserWidget.generated.h"

/**
 * 
 */
UCLASS()
class RPGPROJECT_API UStartUserWidget : public UUserWidget
{
	GENERATED_BODY()
	
public:
	virtual bool Initialize() override;
	
	UFUNCTION()
		void OnStartBtnClick();
	UFUNCTION()
		void OnQuitBtnClick();

public:
	UPROPERTY()
		UButton* StartBtn;
	UPROPERTY(Meta = (BindWidget))
		UButton* QuitBtn;
};

    .cpp:

#include "UI/StartUserWidget.h"
#include "Runtime/Engine/Classes/Kismet/KismetSystemLibrary.h"

bool UStartUserWidget::Initialize()
{
	if (!Super::Initialize())
		return false;

	StartBtn = Cast<UButton>(GetWidgetFromName(TEXT("StartBtn")));
	if (StartBtn != nullptr)
		StartBtn->OnClicked.AddDynamic(this, &UStartUserWidget::OnStartBtnClick);
	if (QuitBtn != nullptr)
		QuitBtn->OnClicked.AddDynamic(this, &UStartUserWidget::OnQuitBtnClick);

	return true;
}

void UStartUserWidget::OnStartBtnClick()
{
	UE_LOG(LogTemp, Error, TEXT("OnStartBtnClick"));
}

void UStartUserWidget::OnQuitBtnClick()
{
	UE_LOG(LogTemp, Error, TEXT("OnQuitBtnClick"));

	// Quit game
	UKismetSystemLibrary::QuitGame(GetWorld(), nullptr, EQuitPreference::Quit);
}

    自己也写了个UI管理的,本来想写个单例来着,不知道Unreal怎么写,就放在GameInstance中来管理,估计随着学习还会改:

#include "GameInstance/MainGameInstance.h"
#include "Runtime/Engine/Classes/Kismet/GameplayStatics.h"
#include "UI/MessageUserWidget.h"

void UMainGameInstance::Init()
{
	UGameInstance::Init();

	FCoreUObjectDelegates::PreLoadMap.AddUObject(this, &UMainGameInstance::BeginLoadingScene);
	FCoreUObjectDelegates::PostLoadMapWithWorld.AddUObject(this, &UMainGameInstance::EndLoadingScene);

	InitializeUserWidgetMap();
	InitializeSceneMap();
	UserWidgetList.Reset();
}

void UMainGameInstance::BeginLoadingScene(const FString& Map)
{
	Release();
}

void UMainGameInstance::EndLoadingScene(UWorld* World)
{
}

UUserWidget* UMainGameInstance::ShowWidget(int UserWidgetId, bool bIsAddToViewport)
{
	if (!UserWidgetMap.Contains(UserWidgetId))
		return nullptr;

	UUserWidget* CurrentWidget = nullptr;

	if(UserWidgetList.Contains(UserWidgetId))
		CurrentWidget = UserWidgetList[UserWidgetId];
	else
	{
		const TCHAR* UserWidgetClassName = UserWidgetMap[UserWidgetId];
		CurrentWidget = CreateWidget<UUserWidget>(this, LoadClass<UUserWidget>(this, UserWidgetClassName));
	}

	if (CurrentWidget != nullptr && bIsAddToViewport && !CurrentWidget->IsInViewport())
		CurrentWidget->AddToViewport();

	if (CurrentWidget != nullptr && !UserWidgetList.Contains(UserWidgetId))
		UserWidgetList.Add(UserWidgetId, CurrentWidget);

	return CurrentWidget;
}

void UMainGameInstance::RemoveWidget(int UserWidgetId)
{
	if (!UserWidgetList.Contains(UserWidgetId))
		return;

	UUserWidget* TempUserWidget = UserWidgetList[UserWidgetId];
	if(TempUserWidget != nullptr && TempUserWidget->IsInViewport())
		TempUserWidget->RemoveFromViewport();
}

void UMainGameInstance::ShowMessageView(FString Msg)
{
	UMessageUserWidget* MessageUserWidget = Cast<UMessageUserWidget>(ShowWidget((int)EUserWidget::MessageView));
	if (MessageUserWidget != nullptr)
		MessageUserWidget->ShowMessage(Msg);
}

void UMainGameInstance::LoadScene(int SceneId)
{
	if (!SceneMap.Contains(SceneId))
		return;

	UWorld* World = GetWorld();
	if (World != nullptr)
		UGameplayStatics::OpenLevel(World, SceneMap[SceneId]);
	else
		UE_LOG(LogTemp, Error, TEXT("World == nullptr"));
}

void UMainGameInstance::Release()
{
	if (UserWidgetList.Num() > 0)
	{
		for (TMap<int, UUserWidget*>::TIterator it = UserWidgetList.CreateIterator(); it; ++it)
		{
			if (it->Value->IsInViewport())
				it->Value->RemoveFromViewport();
		}
	}
	UserWidgetList.Reset();
}

void UMainGameInstance::InitializeUserWidgetMap()
{
	UserWidgetMap.Reset();
	UserWidgetMap.Add((int)EUserWidget::StartView, TEXT("WidgetBlueprint'/Game/UI/StartView.StartView_C'"));//需要加上_C
	UserWidgetMap.Add((int)EUserWidget::MainView, TEXT("WidgetBlueprint'/Game/UI/MainView.MainView_C'"));
	UserWidgetMap.Add((int)EUserWidget::MessageView, TEXT("WidgetBlueprint'/Game/UI/MessageView.MessageView_C'"));
}

void UMainGameInstance::InitializeSceneMap()
{
	SceneMap.Reset();
	SceneMap.Add((int)EScene::StartScene, TEXT("/Game/Scene/Start"));
	SceneMap.Add((int)EScene::MainScene, TEXT("/Game/Scene/Main"));
}


unreal4 源码引言

阅读数 256

Unreal中的捏脸

阅读数 225

没有更多推荐了,返回首页