three-game-engine
Version:
Simple light-weight game engine using three.js, three-mesh-ui and rapier
74 lines (73 loc) • 2.87 kB
JavaScript
Object.defineProperty(exports, "__esModule", { value: true });
exports.createUIComponent = void 0;
const ThreeMeshUI = require("three-mesh-ui");
const MESH_UI_ATTRIBUTE_NAMES = [
'offset',
'width', 'height',
'fontSize', 'fontKerning', 'fontColor', 'fontOpacity', 'fontSupersampling', 'fontFamily', 'fontTexture',
'padding',
'margin',
'contentDirection',
'justifyContent',
'alignItems',
'interline',
'hiddenOverflow',
'bestFit',
'backgroundColor', 'backgroundOpacity', 'backgroundTexture', 'backgroundSize',
'borderRadius', 'borderWidth', 'borderColor',
'content',
'letterSpacing',
'textAlign',
'whitespace',
'breakOn'
];
const createUIComponent = async (userInterfaceJSON, parentObject3D, assetStore) => {
const { type, children, ...attributes } = userInterfaceJSON;
// Separate attributes into attributes for the Object3D constructor, vs
// attributes that should be applied to the component (an Object3D) after construction.
const meshUIAttributes = {};
const object3DAttributes = {};
for (let attr in attributes) {
if (MESH_UI_ATTRIBUTE_NAMES.includes(attr)) {
meshUIAttributes[attr] = attributes[attr];
}
else {
object3DAttributes[attr] = attributes[attr];
}
}
// .fontFamily can be an asset path (a string)
if (typeof meshUIAttributes.fontFamily === 'string') {
const fontFamilyAsset = await assetStore.load(meshUIAttributes.fontFamily);
meshUIAttributes.fontFamily = fontFamilyAsset.data;
}
// .fontTexture can be an asset path (instead of an absolute URL)
if (typeof meshUIAttributes.fontTexture === 'string' && !meshUIAttributes.fontTexture.includes('://')) {
const fontTextureAsset = await assetStore.load(meshUIAttributes.fontTexture);
meshUIAttributes.fontTexture = await fontTextureAsset.getFullURL();
}
if (!type) {
throw new Error(`createUIComponent: type is required`);
}
const validComponentTypes = ['Text', 'Block', 'InlineBlock', 'Keyboard'];
if (!validComponentTypes.includes(type)) {
throw new Error(`createUIComponent: invalid component type: ${type}`);
}
const component = new ThreeMeshUI[type](meshUIAttributes);
for (const objAttr in object3DAttributes) {
component[objAttr] = object3DAttributes[objAttr];
}
if (!component.name) {
component.name = `mesh-ui-${type.toLowerCase()}`;
}
if (!parentObject3D) {
throw new Error(`createUIComponent: must provide an Object3D to parent this component`);
}
parentObject3D.add(component);
if (children) {
for (let child of children) {
await (0, exports.createUIComponent)(child, component, assetStore);
}
}
};
exports.createUIComponent = createUIComponent;
;