01271 Posted July 29, 2018 Share Posted July 29, 2018 So I have several buttons for on-screen controls. I can add any combination of three buttons but as soon as I add a fourth one I get the error: TypeError: rect is undefined It's really weird because if I make each button say its bounds from inside I get the following: Object { pos: Object, shapeType: "Rectangle", points: Array[4], edges: Array[4], normals: Array[4], _width: 48, _height: 48 } entities.js:322:5 Object { pos: Object, shapeType: "Rectangle", points: Array[4], edges: Array[4], normals: Array[4], _width: 48, _height: 48 } entities.js:322:5 Object { pos: Object, shapeType: "Rectangle", points: Array[4], edges: Array[4], normals: Array[4], _width: 48, _height: 48 } entities.js:322:5 Object { pos: Object, shapeType: "Rectangle", points: Array[4], edges: Array[4], normals: Array[4], _width: 48, _height: 48 } entities.js:322:5 and the pos is there and it's right. Checking in-game it's right as well, var abc = me.game.world.getChildByName('button')[3] abc.getBounds() Object { pos: Object, shapeType: "Rectangle", points: Array[4], edges: Array[4], normals: Array[4], _width: 48, _height: 48 } pos is 100, 100. Here's the stack trace: TypeError: rect is undefined[Learn More] melonjs.js:8890:13 Quadtree.prototype.getIndex http://localhost:8000/lib/melonjs.js:8890:13 Quadtree.prototype.insert http://localhost:8000/lib/melonjs.js:8993:25 Quadtree.prototype.insertContainer http://localhost:8000/lib/melonjs.js:8949:25 api.update http://localhost:8000/lib/melonjs.js:3814:21 _renderFrame http://localhost:8000/lib/melonjs.js:13807:13 How and why is this happening? Quote Link to comment Share on other sites More sharing options...
01271 Posted July 30, 2018 Author Share Posted July 30, 2018 When I change the button Entity I made into a sprite and adapt a few things, the problem goes away. However the pointer events no longer work so that's not the best trade. Quote Link to comment Share on other sites More sharing options...
01271 Posted July 30, 2018 Author Share Posted July 30, 2018 swapping out with GUI_Object has the same error. I'll post the button code now. game.ControlButtonEntity = me.Entity.extend({ init: function(x, y, settings) { settings.image = 'buttons'; settings.width = 48; settings.height = 48; // settings.framewidth = 48; // settings.frameheight = 48; this._super(me.Entity, 'init', [x, y, settings]); this.renderable.addAnimation('up',[0]); this.renderable.addAnimation('right',[1]); this.renderable.addAnimation('down',[2]); this.renderable.addAnimation('left',[3]); this.renderable.addAnimation('A',[4]); this.renderable.addAnimation('B',[5]); this.renderable.addAnimation('inventory',[6]); this.renderable.addAnimation('exitInventory',[7]); this.renderable.addAnimation('C',[8]); this.renderable.addAnimation('D',[9]); this.alwaysUpdate = true; this.body.gravity = 0; this.buttonID = settings.buttonID; this.name = 'button'; this.alwaysUpdate = true; this.body.collisionType = me.collision.types.NO_OBJECT; this.animationpause = true; // this.isPersistent = true; this.pushed = false; this.renderable.setCurrentAnimation(settings.buttonID); me.input.registerPointerEvent('pointerdown', this, this.startButtonPress.bind(this)); me.input.registerPointerEvent('pointerup', this, this.endButtonPress.bind(this)); me.input.registerPointerEvent('pointerleave', this, this.endButtonPress.bind(this)); var buttonRegistry = { up : me.input.KEY.UP, down : me.input.KEY.DOWN, left : me.input.KEY.LEFT, right : me.input.KEY.RIGHT, inventory:me.input.KEY.E, }; this.buttonCode = buttonRegistry[settings.buttonID]; }, startButtonPress: function() { me.input.triggerKeyEvent(this.buttonCode, true); }, endButtonPress: function() { me.input.triggerKeyEvent(this.buttonCode, false); }, update: function(dt) { if (this.pushed) { } // this.body.update(dt); return (this._super(me.Entity, 'update', [dt]) || true); }, }); If I have more than 3 of these on screen at once it breaks the game with the aforementioned error. // Add our HUD to the game world, add it last so that this is on top of the rest. // Can also be forced by specifying a "Infinity" z value to the addChild function. this.HUD = new game.HUD.Container(); me.game.world.addChild(this.HUD); // me.game.world.addChild(me.pool.pull('textbox')); if (!game.hasAddedTextarea) { this.HUD.addChild(new game.gui.TextArea(0, 300, 960, 250)); game.hasAddedTextarea = true; } vpw = me.game.viewport.getBounds().width; vph = me.game.viewport.getBounds().height; // multiples 48 96 144 192 me.game.world.addChild(me.pool.pull('buttonEntity', vpw - 144, vph - 144, { buttonID: 'up' })); me.game.world.addChild(me.pool.pull('buttonEntity', vpw - 96, vph - 96, { buttonID: 'right' })); me.game.world.addChild(me.pool.pull('buttonEntity', vpw - 192, vph - 96, { buttonID: 'left' })); // me.game.world.addChild(me.pool.pull('buttonEntity', vpw - 144, vph - 96, { buttonID: 'down' Quote Link to comment Share on other sites More sharing options...
obiot Posted July 30, 2018 Share Posted July 30, 2018 it's hard to understand with "just that" to be honest.... can you share how you declared your buttons, at least the constructor part ? did you use also the basic GUI_Object ? if you use me.Sprite then you have indeed to register on mouse event yourself (which is fine too, it all depends of what you need) here below is how I defined buttons for the following example : https://github.com/melonjs/melonJS/tree/master/examples/UI/js/entities more simple one from the platformer : https://github.com/melonjs/melonJS/blob/master/examples/platformer/js/entities/HUD.js hope this helps ! Quote Link to comment Share on other sites More sharing options...
obiot Posted July 30, 2018 Share Posted July 30, 2018 posted mine right after your last one, so then I would definitely suggest using GUI_Object, like in the example I provided Quote Link to comment Share on other sites More sharing options...
01271 Posted July 30, 2018 Author Share Posted July 30, 2018 Yeah I noticed I posted exactly at the same time as you, I'll try making it more like yours and see if that works out. Quote Link to comment Share on other sites More sharing options...
01271 Posted July 30, 2018 Author Share Posted July 30, 2018 No even with code for the buttons that's highly inspired by yours I don't have it working. New button: game.HUD.FSControl = me.GUI_Object.extend({ init: function(x, y, settings) { settings.image = 'buttons'; settings.framewidth = 48; settings.frameheight = 48; settings.width = 480; settings.height = 48; this._super(me.GUI_Object, "init", [x, y, settings]); this.name = 'button2'; this.addAnimation('up', [0]); this.addAnimation('right', [1]); this.addAnimation('down', [2]); this.addAnimation('left', [3]); this.addAnimation('inventory', [6]); this.setCurrentAnimation(settings.buttonID); this.animationpause = true; var buttonRegistry = { up: me.input.KEY.UP, down: me.input.KEY.DOWN, left: me.input.KEY.LEFT, right: me.input.KEY.RIGHT, inventory: me.input.KEY.E, }; this.buttonCode = buttonRegistry[settings.buttonID]; }, update: function() { if (this.updated) { if (!this.released) { me.input.triggerKeyEvent(this.buttonCode, true); } else { me.input.triggerKeyEvent(this.buttonCode, false); } } } }); It's a pretty simple button, 20 lines shorter, but if I have one too many it breaks. Quote Link to comment Share on other sites More sharing options...
01271 Posted July 30, 2018 Author Share Posted July 30, 2018 I removed some of my entities from the screen and the problem stopped. Then I added more buttons and it started again. It's not the buttons doing it it's some kind of entity limit in general. Dang, that's even more complicated. Quote Link to comment Share on other sites More sharing options...
obiot Posted July 30, 2018 Share Posted July 30, 2018 that's weird indeed... Not sure it will help, but the only reference to rect in the quadtree implementation is in the getIndex method (https://github.com/melonjs/melonJS/blob/master/src/physics/quadtree.js#L135), which means that somehow one object not defining `getBounds()` which means not inheriting at least from the me.Renderable class was added to the game world, and therefore to the quadtree. Which is even weirder since all objects from the game world are added through this function that filter those objects without a getBounds function. 01271 1 Quote Link to comment Share on other sites More sharing options...
01271 Posted July 30, 2018 Author Share Posted July 30, 2018 Oh, learning that turned out to be very helpful. I have a textarea that's beside the game and that's added to the world in the way that parasyte mentioned years ago in a github thread. Since that one is added in a weird way I commented out the part where it's added to the world and started adding my buttons and a lot of enemies and things didn't break. Turns out my problem is with a textarea rather than with buttons or enemies. Go figure :V Now I can focus on just this part. This is what it looks like by the way. game.gui.TextArea = me.Renderable.extend({ init: function() { this.textarea = document.createElement('textarea'); this.textarea.id = 'textHistory'; this.textarea.readOnly = "true"; this.textarea.disabled = "true"; me.video.getWrapper().appendChild(this.textarea); game.TextArea = this; var self = this; var videoPos = me.video.getPos(); self.textarea.style = 'width:' + (window.innerWidth - videoPos.width) + 'px; height:' + videoPos.height + 'px;'; this.isPersistent = true; me.event.subscribe(me.event.WINDOW_ONRESIZE, function() { var videoPos = me.video.getPos(); self.textarea.style = 'width:' + (window.innerWidth - videoPos.width - 10) + 'px; height:' + videoPos.height + 'px;'; }); }, addText: function(text) { this.textarea.innerHTML += '\n' + text; }, clear: function() { this.textarea.innerHTML = ''; }, destroy: function() {}, // update: function() { // videoPos = me.video.getPos(); // this.textarea.style = 'width:' + (window.innerWidth - videoPos.width) + 'px; height:' + videoPos.height + 'px;'; // } }); Shouldn't be hard to get this working. Ultimately it doesn't actually need to be managed by melonjs so I can remove it from the container outright if things get complicated. Quote Link to comment Share on other sites More sharing options...
obiot Posted July 31, 2018 Share Posted July 31, 2018 I see !!!! :):):) Note that the only (major) thing you are missing in that object then is the call to the parent constructor, that would then initialise the bounding rect used by getBounds(), and also initialise a bunch of other internal properties, like the new `isKinematic` property introduced in melonJS 5.0 (which when If true disable physic collision and input events for this renderable), that would also prevent this kind of object to be added in the first place to the quad tree (since you do not need a text object to be reactive to neither physic nor pointer events). Quote Link to comment Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.