目前如果你想在 UE4 里创建一个 Program 工程的话,存在两点限制,第一需要将工程源文件都放在 Engine/Source/Programs 目录下,第二是必须使用源码版本的引擎来编译。一般来说也没什么问题,但是有些时候会带来一些问题,比如你的 Program 有着特定的用途只和特定的项目相关,放在引擎目录下稍显不合适,会污染引擎代码结构。怎么样解决这两点限制,构建更加干净的项目?

本文的示例工程地址:MyProject,测试的引擎版本为:4.24

在引擎目录外创建 Program 工程

首先随便创建一个游戏工程,如果 MyProject,目录结构如下

MyProject
|---MyProject.uproject
|---Config
|---Content
|---Source|---MyProject.Target.cs|---MyProjectEditor.Target.cs|---MyProject|---MyProject.Build.cs|---MyProject.cpp|---MyProject.h|---MyProjectGameModeBase.cpp|---MyProjectGameModeBase.h

类似引擎目录结构,在 Source 目录下新建两个子目录:Programs 用来放所有的 Program 工程模块;Runtime 用来放游戏相关的工程模块。然后将原来 Source 目录下的文件全部复制的 Runtime 目录中,并复制引擎的空工程示例 BlankProgram 工程到 Programs 目录中,并改个新名字 MyBlankProgram(UE4中各个Target名字全局不能冲突),新的结构如下

MyProject
|---MyProject.uproject
|---Config
|---Content
|---Source|---Runtime // 新建的目录,将之前的 Source 目录下的内容直接平移进来|   |---MyProject.Target.cs|   |---MyProjectEditor.Target.cs|   |---MyProject|       |---MyProject.Build.cs|       |---MyProject.cpp|       |---MyProject.h|       |---MyProjectGameModeBase.cpp|       |---MyProjectGameModeBase.h|---Programs // 新建的目录,用来放各种工具项目|---MyBlankProgram|---MyBlankProgram.Build.cs|---MyBlankProgram.Target.cs|---Private|   |---MyBlankProgram.cpp|   |---MyBlankProgram.h|---Resources|---Windows|---BlankProgram.ico

右键 MyProject.uproject 文件,选择 Generate Visual Studio project files,生成工程文件,此时就会发现 MyBlankProgram 工程正确生成到 Solution 中的 Programs 目录下,如图

如果想自定义 MyBlankProgram 在 Solution 中的目录,可以打开 MyBlankProgram.target.cs 文件,在构造函数在给 SolutionDirectory 赋个自定义值,如

[SupportedPlatforms(UnrealPlatformClass.Desktop)]
public class MyBlankProgramTarget : TargetRules
{public MyBlankProgramTarget(TargetInfo Target) : base(Target){// other codes...SolutionDirectory = "MyPrograms";// other codes...}
}

重新生成 Solution,此时 MyBlankProgram 就在 MyPrograms 目录下了,如图

注意点

在引擎的目录结构中,Engine/Source 目录下是有几个 Target.cs 文件的,如图

所以在我们的工程中,是否一样也可以把 MyProject.Target.cs 也放到 Source 根目录下呢?

答案是不行的,游戏工程搜索 Target.cs 文件和引擎是有些区别的,代码见 Source/Programs/UnrealBuildTool/System/NativeProjects.cs 中的 FindTargetFiles 函数。生成工程的时候,会搜索 uproject 文件所在目录下的所有 Target.cs 文件,但是如果在某一级目录搜索到了 Target.cs 文件,那就不会继续搜索这一级目录中的子目录了。所以如果将 MyProject.Target.cs 也放到 Source 下,那么搜索就会停在 Source 目录,所以 Source/Programs 目录中的 Target.cs 文件就会被忽略了

编译

此时编译 MyBlankProgram,会出现编译错误,如下

1>------ Build started: Project: MyBlankProgram, Configuration: Development_Program x64 ------
1>UnrealBuildTool : error : Unable to find project 'E:WorkspaceMyProjectMyBlankProgram.uproject'.

这个错误的原因是编译时调用 UBT 的命令行参数中有一个 -project 参数,参数值是有问题的,如图

有以下几种解决方法

直接修改参数

在命令行中将 #(ProjectName) 直接改为 MyProject,如图

这种方法缺点是每次重新生成工程后都得改一遍

将工程新建到引擎目录下

第二种方法是直接将工程新建到引擎目录下,见之前的文章

FlyingTree:UE4 关于工程目录结构的一个小技巧​zhuanlan.zhihu.com

将工程建到引擎目录下,生成工程时就不会在编译命令行中增加 -project 参数,此时会根据目录的层级关系在上级目录中搜索对应的 uproject

修改 UBT

最直接的方式就是改 UBT 源码,打开 Source/Programs/UnrealBuildTool/ProjectFiles/VisualStudio/VCProject.cs 文件,在 WriteConfiguration 函数中,新增一段代码,当是 IsForeignProject 的时候,优先使用命令行中传入的 uproject 文件路径,如图

其它编译错误

Program 的模块需要依赖于 LaunchEngineLoop.cpp 文件,由于现在将 Program 移到了引擎目录之外,所以在模块中添加 include 路径的地方也需要修改,打开 MyBlankProgram.Build.cs,将 PublicIncludePathsPrivateIncludePaths 添加的路径拼上引擎路径,如图

结果

通过以上修改后,编译 MyBlankProgram,就会在 MyProject/Binaries/Win64 下看到生成的可执行文件,如图

运行结果如图

不过有一点不完美的就是,运行后日志,配置等文件的生成路径是在这里

这里的初始化代码见 FGenericPlatformMisc::ProjectDir,在 Program 下写死的使用 Engine 目录,如图

如果想要修改,只能在自己的 Program 代码中,一开始初始化的时候调用 FPlatformMisc::SetOverrideProjectDir 改一下,如图

这样,Program 运行时生成的日志配置等就生成到正确的目录下,如图

非源码引擎编译 Program 工程

首先将上文的示例工程 MyProject 的引擎切换成安装版本的引擎,如图

此时生成工程会报错,报错信息如下

ERROR: Targets with a unique build environment cannot be built an installed engine

解决这个错误需要修改 MyBlankProgram.Target.cs,将 BuildEnvironment 改成 TargetBuildEnvironment.Shared,如下

[SupportedPlatforms(UnrealPlatformClass.Desktop)]
public class MyBlankProgramTarget : TargetRules
{public MyBlankProgramTarget(TargetInfo Target) : base(Target){// other codes...BuildEnvironment = TargetBuildEnvironment.Shared;// other codes...}
}

重新生成解决方案,修改后可以正常生成,如图

现在编译 MyBlankProgram,会遇到上文中同样的错误,如下

1>------ Build started: Project: MyBlankProgram, Configuration: Development_Program x64 ------
1>UnrealBuildTool : error : Unable to find project 'E:WorkspaceMyProjectMyBlankProgram.uproject'.

解决方法同上

继续编译,遇到新的错误

1>Creating makefile for MyBlankProgram (.uproject file is newer)
1>UnrealBuildTool : error : Program targets are not currently supported from this engine distribution.

这个错误的原因的安装版本的引擎能编译的配置是固定好的,并配置在 Engine/Config/BaseEngine.ini[InstalledPlatforms]

解决这个问题的方法是将 EngineBuildInstalledBuild.txt 文件重命名一下,UBT 是根据这个文件是否存在来判断是否是安装版本的引擎

此时再编译,就会正确编译 MyBlankProgram,可执行文件的输出目录是引擎目录 Engine/Binaries/Win64,如图

以上的步骤可以通过脚本来进行整合

生成工程

@ECHO OFFSET EnginePath=E:Epic GamesUE_4.24EngineCALL "%EnginePath%BuildBatchFilesBuild.bat" -ProjectFiles -Project="%~dp0MyProject.uproject" -game -progressPAUSE

编译工程

@ECHO OFFSET EnginePath=E:Epic GamesUE_4.24EngineREM 重命名 InstalledBuild.txt
IF EXIST "%EnginePath%BuildInstalledBuild.txt" (REN "%EnginePath%BuildInstalledBuild.txt" InstalledBuild1.txt
)CALL "%EnginePath%BuildBatchFilesBuild.bat" MyBlankProgram Win64 Development -Project="%~dp0MyProject.uproject" -WaitMutexREM 重命名 InstalledBuild.txt
IF EXIST "%EnginePath%BuildInstalledBuild1.txt" (REN "%EnginePath%BuildInstalledBuild1.txt" InstalledBuild.txt
)PAUSE

总结

在上文中解决这两个限制的方法,其实并不完美,但是目前好像也没有什么其它的解决方法

as工程放到源码编译_UE4 Program 类型工程的限制和解决方法相关推荐

  1. as工程放到源码编译_方舟编译器学习笔记2 源码编译

    根据方舟官方文档编译了方舟编译器的源码,在这里简单谈谈其源码的编译过程: 1.操作系统环境: 64位版本的Ubuntu(官方推荐Ubuntu 16.04).我自己本身就有Ubuntu 16.04的虚拟 ...

  2. as工程放到源码编译_Android 7.1源码编译导入AS完整教程

    本教程仅针对Android 7.1系统,为便于虚拟机备份和出现问题时的还原,本教程分为3步:初始化编译环境.源码同步.编译源码导入Android Studio. 编译源码:Android7.1.2_r ...

  3. as工程放到源码编译_关于AS高版本SDK编译生成的apk放入低版本android源码中集成编译...

    做dfu功能的时候,遇到的这样一个问题.添加了dfu的依赖之后,会要求编译的sdk为28,我的AS版本默认生成的是27.然而target版本是25. // The DFU Library is imp ...

  4. as工程放到源码编译_Flutter源码剖析(二):源码的阅读与调试环境配置

    综述 Flutter从架构上来说有3部分: 用Dart写的Framework层,面向开发者 用Java/Kotlin写的Embdder层(For Android,iOS是OC/Swift),纯Flut ...

  5. android源码编译出现No private recovery resources for TARGET_DEVICE解决方法

    mmm和mm出现No private recovery resources  for  TARGET_DEVICE 问题解决 mmm和mm出现一下提示解决方法: log: No private rec ...

  6. 编译源码时出现 Checking API: checkapi-last (unknown): error 17解决方法

    原文地址::http://www.eoeandroid.com/thread-84145-1-1.html 相关网帖 1.关于android中的checkapi----http://blog.sina ...

  7. 编译安卓系统源码jack-server问题入坑,全网最全解决方法

    编译安卓系统源码jack-server入坑,全网最全解决方法 1.权限问题 2.端口占用 3.删除 TLSv1, TLSv1.1(我的最后解决办法) 1.权限问题 运行失败时进入~/.jack-ser ...

  8. 云豹直播系统源码接入华为云存储,含问题及解决方法

    云豹直播系统源码接入华为云存储该怎么做? 一.云豹直播系统源码接入华为云存储的前期准备工作 1.注册云服务账号开通对象存储服务. (1)登录公有云网站.在页面右上角单击"注册".按 ...

  9. 工程管理系统源码-专注项目数字化管理-工程管理

    高效的工程项目管理软件不仅能够提高效率还应可以帮你节省成本提升利润 在工程行业中,管理不畅以及不良的项目执行,往往会导致项目延期.成本上升.回款拖后,最终导致项目整体盈利下降.企企管理云业财一体化的项 ...

最新文章

  1. JavaScript中,this的绑定规则
  2. 12 Java程序员面试宝典视频课程之面向对象
  3. dataimagepng php_php用header('content-type: image/png')输出验证码,但响应回来的是text/html...
  4. 【BZOJ-3262】陌上花开 CDQ分治(3维偏序)
  5. 工作区 暂存区 版本库之间的关系
  6. 第3讲--3.1旋转矩阵
  7. 无需羡慕,今后.NET开发想拿30k也可以毫不费劲!
  8. scp构造端口_指定端口号的scp
  9. centos7配置mysql其他机器访问_CentOS7安装MySQL并开启远程访问详解
  10. STM32H743+CubeMX-串口非空闲中断接收
  11. 信息学奥赛一本通 1958:【12NOIP普及组】寻宝 | OpenJudge NOI 1.12 06 | 洛谷 P1076 [NOIP2012 普及组] 寻宝
  12. html5软件下载页面源码
  13. Node.js抓取网页信息(cheerio网络爬虫)
  14. Java使用循环创建多个线程
  15. 交互式 shell 玩转 Python
  16. 浅谈今日头条关键词下拉词框优化推广的优势
  17. 简明介绍java“包”的用法
  18. Windows 技术篇-修改hosts添加域名解析实例演示,设置域名指定ip方法
  19. 使用Memberane Moniter监控HTTP SOAP requests
  20. 3月4日 与柳传志面对面(谁是这个时代的思想家)

热门文章

  1. 常用jar包之commons-beanutils使用
  2. 面试题:冒泡排序的优化
  3. 001-ant design安装及快速入门【基于纯antd的基本项目搭建】
  4. 更加优雅的iOS自动布局
  5. Java虚拟机管理的内存运行时数据区域解释
  6. Android中自定义Dialog外形,去除黑底和白色边框
  7. Silverlight实例_人立方
  8. 一级计算机考试题库25套答案,全国计算机等级考试一级试题及答案(25套)..doc
  9. 树状数组求逆序对_初识树状数组
  10. python安装后怎么配置环境变量_Python安装与环境变量的配置