为自定义项目运行Syncker
从性能角度说要以最大效率使用Syncker,需要节点的选择性同步化及材质。如果Syncker从脚本进行执行(究竟为世界对象,编辑器或自定义系统无关)用于对同步化进行完全控制,这种操作可行。
如果使用投影仪对应用程序进行渲染,参看使用AppProjection运行Syncker一文。
实施脚本
要运行来自世界脚本的自定义项目Syncker主站,同步节点,渲染参数及网络上的相机,更加下列指令实施脚本。请注意使用相似的逻辑来同步材质。
- 首先初始化在主计算机上运行的脚本中的Syncker。还应初始化一个控制台来激活运行主站命令行选项的能力。要在所有连接的从站上同步创建节点,使用
Unigine::Syncker::Master::createNode()函数。
// 主计算机上的unigine_project.cpp #include <core/unigine.h> #include <core/systems/syncker/syncker_master.h> #include <core/systems/syncker/syncker_master_console.h> // 将数组内的节点进行序列化处理效果会更高 // 然后将这些节点作为数据包进行传递,而不是一个接着一个的方式进行传递 ObjectMeshStatic meshes[0]; int init() { // 设置固定的FPS值保证所有计算机上的模拟一致 engine.game.setFTime(1.0f / 60.0f); // 将主控制台进行序列化处理 Unigine::Syncker::Master::Console::init(); // 使用所给的广播地址将Syncker序列化处理 Unigine::Syncker::Master::init(master_address); PlayerSpectator camera = new PlayerSpectator(); camera.setPosition(Vec3(2.0f,0.0f,1.5f)); camera.setDirection(Vec3(-1.0f,0.0f,-0.5f)); engine.game.setPlayer(camera); // 使用将被同步处理的网格对世界对象进行填充 for(int j = 0; j < 2; j++) { for(int i = 0; i < 2 - j; i++) { // 可指定其它所有网格的路径 ObjectMeshStatic mesh = node_remove(new ObjectMeshStatic("unigine_project/meshes/box.mesh")); mesh.setMaterial("mesh_base","*"); mesh.setProperty("surface_base","*"); mesh.setPosition(Vec3(i,j,j)); // 将所有从站上的创建的网格同步化处理 Unigine::Syncker::Master::createNode(mesh); meshes.append(mesh); } } return 1; }
对于将被编译的代码,将box.mesh文件 从 <Unigine SDK>/data/samples/common/meshes 文件夹拷贝到 unigine_project/data/unigine_project/meshes 文件夹。 - 实施逻辑,这样允许加载用于在主站一侧上的所有从站的世界对象,并在初始化Syncker以后在init()函数内进行调用。
看跳过此步骤并在每个从站上单独
void sync_world() { // 加载从站世界对象 Unigine::Syncker::Master::systemCall(~0,"engine.console.run",("world_load " + engine.world.getName())); // 等待从站世界 int ret[0]; float begin = clock(); while(clock() - begin < 2.0f) { int is_loaded = 1; Unigine::Syncker::Master::systemCall(~0,"engine.world.isLoaded",(),ret); foreach(int i = 0; ret) is_loaded &= i; if(is_loaded) break; } }
- 接下来指定用于控制台和Syncker的关闭逻辑:
// 主计算机上的unigine_project.cpp int shutdown() { // 在有必要的情况下,在所有从应用程序中运行控制台命令。 // 被调用的命令从从站的系统脚本处得到运行。 Unigine::Syncker::Master::systemCall(~0,"engine.console.run",("world_quit")); // 关闭控制台。 Unigine::Syncker::Master::Console::shutdown(); // 关闭 Syncker。 Unigine::Syncker::Master::shutdown(); return 1; }
- 脚本render() 函数内的同步逻辑。这种逻辑让您可以指定所有节点(在有必要的情况下,还可指定材质)。
这些节点必须同步。可在此处了解具体的函数描述。
//主计算机上的 unigine_project.cpp int render() { // 同步帧信息 Unigine::Syncker::Master::syncFrame(); // 同步相机位置 Unigine::Syncker::Master::syncPlayer(); // 同步渲染参数 Unigine::Syncker::Master::syncRender(); // 同步节点 Unigine::Syncker::Master::syncNodes(meshes); // 帧的末尾 Unigine::Syncker::Master::syncEnd(); return 1; }
如果在主站和侧站上运行相同的世界脚本,需要在代码周围标记#ifndef DEFINE_NAME ... #else ... #endif,安装如下方式进行:
DEFINE_NAME 应在应用程序开始时指定。
#include <core/unigine.h>
// 将在主机上运行的逻辑
#ifndef DEFINE_NAME
#include <core/systems/syncker/syncker_master.h>
#include <core/systems/syncker/syncker_master_console.h>
ObjectMeshStatic meshes[0];
// 上述定义的init() 函数
// 上述定义的shutdown()函数
// 上述定义的render() 函数
#else
// 将在从站上运行的逻辑
int init() {
PlayerSpectator camera = new PlayerSpectator();
camera.setPosition(Vec3(2.0f,0.0f,1.5f));
camera.setDirection(Vec3(-1.0f,0.0f,-0.5f));
engine.game.setPlayer(camera);
return 1;
}
#endif
运行Syncker
由于Syncker主站初始化,关闭逻辑,及节点的同步,材质等都在世界脚本中得到实施,没必要使用用于主站的Syncker脚本。但仍需要为从站使用Syncker脚本因为并未为其实施自定义逻辑。
在实施主站脚本以后,需按照下列方式运行脚本:
- 运行所有将与主站同步的从站应用程序。
要达到这种目的,在从站应用程序启动时指定下列选项覆盖为从站使用了Syncker脚本的默认编辑器脚本。如果在主站和从站上使用了相同的世界脚本,也许指定所需的 定义:
需要script_editor_load控制台命令来为从站加载Syncker。main_x64 -data_path "../" -editor_script "core/systems/syncker/syncker_slave.cpp" -extern_define "DEFINE_NAME" -console_command "script_editor_load"
记得加载其它所需的 启动参数。 -
如果未实施脚本中的加载逻辑则为每个从站加载世界对象:
也可在应用程序启动时执行此命令(参看上一步):
world_load unigine_project/unigine_project
如果打开了控制台,您会发现从站应用程序对两个端口进行帧听,这两个端口用于来自主站的数据包(此默认值可不进行修改):-console_command "world_load unigine_project/unigine_project"
---- Syncker::Slave ---- Name: unknown UDP: 8890 TCP: 8891
- 在将被作为主站使用的主计算机上运行 unigine_project 脚本。
然后在连接的从站命令台中会看到下列内容:
main_x64 -data_path "../" -console_command "world_load unigine_project/unigine_project"
---- Syncker::Master ---- Address: 192.168.0.255 UDP: 8890 TCP: 8891
- 更改主站的网络广播地址:
使用world_reload重新加载世界对象。然后在主站控制台中会看到从站已连接的信息:
master_address xxx.xxx.xxx.xxx
Connection to "xxx.xxx.xxx.xxx" accepted in 0.00 seconds
如果从站上的世界对象并未按程序得到加载,控制台命令world_reload或world_load与当前的加载使用了同一个世界对象但此命令不会在主站后的从站上运行。仅加载一个新的世界对象作业。
配置显示器
当在主计算机和从计算机上发布应用程序后,需要根据屏幕配置为每台从站配置视口:
- 如果使用监测器网格代表屏幕配置,执行在Syncker主要文章的更改屏幕配置篇章中指定的指令。
-
如果屏幕配置以 网格或 CAVE被呈现,通过master_mesh控制台命令为所有连接上的从站对其进行设置。
请确保每个网格面的名称与对应从站的名称相匹配。要设置从站名称,运行 slave_name 控制台命令:
master_mesh <mesh_name>
slave_name <name>
最新更新: 2017-07-03
Help improve this article
Was this article helpful?
(or select a word/phrase and press Ctrl+Enter)