3

I am trying to import Blockly (via node-blockly from npm) into a VueJS component, but the javascript part of Blockly contains getElementById() calls, which causes an error as document.getElementById() is not available in VueJS.

Any idea how to get around this?

(Edit) Code Example:

<template> 
 <div class="hello"> 
   <div id="blocklyDiv" style="height: 480px; width: 600px;">
   </div> 
    <xml id="toolbox" ref=toolbox style="display: none"> 
     <block type="controls_if"></block> 
     <block type="text"></block> <block type="text_print"></block> 
    </xml> 
   </div> 
</template> 
<script> 
 import Blockly from "node-blockly" 
 export default { name: 'hello' } 
 var workspace = Blockly.inject('blocklyDiv', {toolbox: document.getElementById('toolbox')}); 
</script>
Vincent Cantin
  • 16,192
  • 2
  • 35
  • 57
Dirk Rejahl
  • 61
  • 1
  • 5
  • I'm not sure I understand. document.getElementById works fine with vue.js. Can you provide a code example of what isn't working? – retrograde Feb 14 '17 at 22:28
  • I think you are using the webpack version which has eslint? If yes then you need to allow browser in eslintrc. If this is your case then I shall post an answer. – Amresh Venugopal Feb 15 '17 at 05:04
  • I opted for no eslint when I created the webpack project (using vue cli). – Dirk Rejahl Feb 15 '17 at 08:44

3 Answers3

3

I supose is v2.

Try in mounted event

<template> 
 <div class="hello"> 
   <div id="blocklyDiv" style="height: 480px; width: 600px;">
   </div> 
    <xml id="toolbox" ref=toolbox style="display: none"> 
     <block type="controls_if"></block> 
     <block type="text"></block> <block type="text_print"></block> 
    </xml> 
   </div> 
</template> 
<script> 
 import Blockly from "node-blockly" 
 export default { 
   name: 'hello',
   data(){
     return {
       workspace: null
     }
   },
   mounted(){
     this.workspace = Blockly.inject('blocklyDiv', {toolbox: document.getElementById('toolbox')});
   }
 } 
</script>
tony19
  • 125,647
  • 18
  • 229
  • 307
David
  • 923
  • 8
  • 19
  • I am afraid that didn't make a difference. The getElementById() function when calling the inject isn't actually the problem. It is a getElementById() within the Blockly JS. I guess the additional elements (xml, toolbox etc.) need to be registered properly as child components. I will try this and post the results here.... – Dirk Rejahl Feb 15 '17 at 14:23
2

Assuming you are using VueJS version 2, you can access the reference to an element using this.$refs.myElement after tagging your element in the template.

Example:

<div ref="blocklyDiv" style="height: 480px; width: 600px;">

mounted () {
  this.workspace = Blockly.inject(this.$refs.blocklyDiv);
}

Then, just do the same for your toolbox.

Vincent Cantin
  • 16,192
  • 2
  • 35
  • 57
0

This works for me

<script>
export default {
    mounted() {
        console.log('blockly');
           var workspace = Blockly.inject('blocklyDiv', {
             toolbox: document.getElementById('toolbox')
           });

           var blocklyArea = document.getElementById('blocklyArea');
           var blocklyDiv = document.getElementById('blocklyDiv');

           var workspace = Blockly.inject(blocklyDiv, {
              toolbox: document.getElementById('toolbox')
           });

  ....
},
Dazzle
  • 2,880
  • 3
  • 25
  • 52
  • Update- this approach does not allow for the implementation of Blockly.JavaScript.workspaceToCode(workspace); Investigating. – Dazzle Feb 08 '18 at 14:54