networked-aframe 为新用户分配不同的位置
networked-aframe assign different position to new user
我在使用 networked-aframe 设置的多人 A-Frame 环境中遇到问题。
我希望前三个连接的用户具有不同的生成位置,并且任何其他用户都在第三个位置生成,但我无法让它工作。这是我目前在 Html 中的内容:
<a-entity id="player"
networked="template:#avatar-template;showLocalTemplate:true;"
camera
positioner=""
wasd-controls
look-controls>
<a-cursor></a-cursor>
</a-entity>
这是它的 JS 组件:
AFRAME.registerComponent('positioner', {
init: function() {
var el = this.el,
counter = 0;
if (counter == 0) {
el.setAttribute('position', {x:-16, y:6, z:-10});
counter++;
}
else if(counter == 1) {
el.setAttribute('position', {x:-10, y:6, z:-10});
counter++;
}
else {
el.setAttribute('position', {x:-5, y:6, z:-10});
counter++;
}
}
});
我发现我必须像这样同步其他组件:
var avatarSchema = {
template: '#avatar-template',
components: [
'positioner',
'position',
'rotation',
'scale',
{
selector: '.head',
component: 'material'
},
{
selector: '.hairs',
component: 'show-child'
}
]
};
NAF.schemas.add(avatarSchema);
这是一个大项目,因此代码较多。如果您需要其他任何东西,例如场景设置或头像设置,请告诉我,我会添加它。
我有一个解决方法,因为我不完全了解该组件的工作原理。
我发现在引用NAF.entities.entities
下有一个玩家列表
我制作了一个附加到场景的组件:
AFRAME.registerComponent('foo',{
init:function(){
setTimeout(function(){
console.log(Object.keys(NAF.entities.entities));
console.log(Object.keys(NAF.entities.entities)[0]);
console.log(Object.keys(NAF.entities.entities).length);
},5000);
}
});
第一个日志给了我一组玩家 ID。
第二个给出第一个元素的 id。
最后一个给我玩家的数量。
你可以查看加载的玩家数量,根据哪个玩家加载,你可以设置他的位置属性。
if(NAF.. == 1) this.el.setAttribute('position',firstPos);
if(NAF.. == 2) this.el.setAttribute('position',secondPos);
if(NAF.. > 2) this.el.setAttribute('position',third);
此处的工作故障:故障。com/edit/#!/sudden-antler
当然,与其等待 5 秒,我应该听一个已加载的事件,我会在我不那么忙的时候调查它。
如果有人设法用这个组件正确地做到这一点,请发表评论,因为我试图在连接上做这个位置(太早了,其他玩家实体仍然没有加载),试着等到场景加载,但我得到的最接近的是在固定时间后,当我获得玩家数量时动态创建玩家。
我在下面想出了一个有点 hack 的解决方案,但我现在想出了一个干净的方法来确定何时连接。
let connectionResolve;
let connectionPromise = new Promise((resolve, reject) => {
connectionResolve = resolve;
})
<a-scene networked-scene="onConnect:connectionResolve">
connectionPromise.then(() => {
// now you can access NAF.connection.getConnectedClients() safely here
// do stuff
})
您可以将回调传递给联网场景组件的onConnect。它会在您连接时调用该回调。通过将承诺的解析器传递给它,您就可以安全地调用任何东西,并且知道只有在连接时才会调用它。
旧答案
请注意,您应该使用 NAF.connection.getConnectedClients()
,而不是实体,因为实体是用户之间共享的任何东西——它只是对应,因为在一个粗略的例子中,化身的数量(仅共享实体)与数量匹配用户数。
function onConnected(callback) {
setTimeout(() => {
if (NAF.connection.isConnected()) {
callback(NAF.connection.getConnectedClients())
}
else onConnected(callback)
}, 100)
}
(这只是给你一个想法。)
docs 似乎并没有为此提供一个好的事件,但他们确实提到了这些功能,我们可以以一种不太 hacky(如果不是很优雅)的方式使用这些功能。
我在使用 networked-aframe 设置的多人 A-Frame 环境中遇到问题。
我希望前三个连接的用户具有不同的生成位置,并且任何其他用户都在第三个位置生成,但我无法让它工作。这是我目前在 Html 中的内容:
<a-entity id="player"
networked="template:#avatar-template;showLocalTemplate:true;"
camera
positioner=""
wasd-controls
look-controls>
<a-cursor></a-cursor>
</a-entity>
这是它的 JS 组件:
AFRAME.registerComponent('positioner', {
init: function() {
var el = this.el,
counter = 0;
if (counter == 0) {
el.setAttribute('position', {x:-16, y:6, z:-10});
counter++;
}
else if(counter == 1) {
el.setAttribute('position', {x:-10, y:6, z:-10});
counter++;
}
else {
el.setAttribute('position', {x:-5, y:6, z:-10});
counter++;
}
}
});
我发现我必须像这样同步其他组件:
var avatarSchema = {
template: '#avatar-template',
components: [
'positioner',
'position',
'rotation',
'scale',
{
selector: '.head',
component: 'material'
},
{
selector: '.hairs',
component: 'show-child'
}
]
};
NAF.schemas.add(avatarSchema);
这是一个大项目,因此代码较多。如果您需要其他任何东西,例如场景设置或头像设置,请告诉我,我会添加它。
我有一个解决方法,因为我不完全了解该组件的工作原理。
我发现在引用NAF.entities.entities
下有一个玩家列表
我制作了一个附加到场景的组件:
AFRAME.registerComponent('foo',{
init:function(){
setTimeout(function(){
console.log(Object.keys(NAF.entities.entities));
console.log(Object.keys(NAF.entities.entities)[0]);
console.log(Object.keys(NAF.entities.entities).length);
},5000);
}
});
第一个日志给了我一组玩家 ID。
第二个给出第一个元素的 id。
最后一个给我玩家的数量。
你可以查看加载的玩家数量,根据哪个玩家加载,你可以设置他的位置属性。
if(NAF.. == 1) this.el.setAttribute('position',firstPos);
if(NAF.. == 2) this.el.setAttribute('position',secondPos);
if(NAF.. > 2) this.el.setAttribute('position',third);
此处的工作故障:故障。com/edit/#!/sudden-antler
当然,与其等待 5 秒,我应该听一个已加载的事件,我会在我不那么忙的时候调查它。
如果有人设法用这个组件正确地做到这一点,请发表评论,因为我试图在连接上做这个位置(太早了,其他玩家实体仍然没有加载),试着等到场景加载,但我得到的最接近的是在固定时间后,当我获得玩家数量时动态创建玩家。
我在下面想出了一个有点 hack 的解决方案,但我现在想出了一个干净的方法来确定何时连接。
let connectionResolve;
let connectionPromise = new Promise((resolve, reject) => {
connectionResolve = resolve;
})
<a-scene networked-scene="onConnect:connectionResolve">
connectionPromise.then(() => {
// now you can access NAF.connection.getConnectedClients() safely here
// do stuff
})
您可以将回调传递给联网场景组件的onConnect。它会在您连接时调用该回调。通过将承诺的解析器传递给它,您就可以安全地调用任何东西,并且知道只有在连接时才会调用它。
旧答案
请注意,您应该使用 NAF.connection.getConnectedClients()
,而不是实体,因为实体是用户之间共享的任何东西——它只是对应,因为在一个粗略的例子中,化身的数量(仅共享实体)与数量匹配用户数。
function onConnected(callback) {
setTimeout(() => {
if (NAF.connection.isConnected()) {
callback(NAF.connection.getConnectedClients())
}
else onConnected(callback)
}, 100)
}
(这只是给你一个想法。)
docs 似乎并没有为此提供一个好的事件,但他们确实提到了这些功能,我们可以以一种不太 hacky(如果不是很优雅)的方式使用这些功能。