Adding a constructor to an injected Project Class - javascript

I'm trying to add a constructor, which I call ctor, to Project, so I can add to it some properties when it's instantiated.
Here's the (absolutely ghastly) hack I'm using on Item to make this tick:
const canvas = document.querySelector('canvas')
paper.setup(canvas)
paper.Item.inject({
ctor: function(args) {
console.log('Item constructed!')
}
})
// All Items are supposed to call `_initialize` so we "hook" there.
const Item_initialize = paper.Item.prototype._initialize
const Item_ctor = paper.Item.prototype.ctor
paper.Item.prototype._initialize = function(...args) {
const initializer = Item_initialize.apply(this, args)
if (Item_ctor) Item_ctor.apply(this)
return initializer
}
const path = new paper.Path.Line({
strokeColor: 'black',
strokeWidth: 5,
from: 100,
to: 50
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/paper.js/0.12.0/paper-core.js"></script>
<canvas></canvas>
Unfortunately the above trick doesn't work on Project:
const canvas = document.querySelector('canvas')
paper.setup(canvas)
paper.Project.inject({
ctor: function(args) {
// Not called
console.log('Project constructed!')
}
})
const Project_initialize = paper.Project.prototype._initialize
const Project_ctor = paper.Project.prototype.ctor
paper.Project.prototype._initialize = function(...args) {
const initializer = Project_initialize.apply(this, args)
if (Project_ctor) Project_ctor.apply(this)
return initializer
}
const project = new paper.Project(canvas)
<script src="https://cdnjs.cloudflare.com/ajax/libs/paper.js/0.12.0/paper-core.js"></script>
<canvas></canvas>
What am I missing here?

Related

Add prototype of a fuction

I have some question about my node.js project.
What I'm trying to do is, add additional functionality to a function.
So, I added new functionality using prototype, but it failed.
Below is my current code.
[ someFeatures.js ]
const functionFoo = new Function()
const functionBar = new Function()
module.exports = { functionFoo, functionBar }
[ addFeatures.js ]
// Import fuction
const { functionFoo, functionBar } = require('./someFeatures.js')
// Add additional feature
functionFoo.prototype.addtionalFeatureA = foo => {
return someFunction(foo)
}
// Add additional feature
functionBar.prototype.addtionalFeatureB = foo => {
return someOtherFunction(foo)
}
module.exports = { functionFoo, functionBar }
[ Other files will use this feature ]
const { functionFoo } = require('./someFeatures.js')
const aaa = new functionFoo()
aaa.addtionalFeatureA('bbb')
The result is 'TypeError: Cannot read properties of undefined (reading 'prototype')'
Is there any solution to fix this issue? Thanks in advance!
change new Function
into empty function
let yourFunction = function () {}
and change this
function.prototype.additional = foo => { ... }
to this
function.prototype.additional = function (foo) {
...
}

Not working dynamically rendering my chart on vue-chartjs

I was define my chart as below (MainChart.vue).
import { Line, mixins } from 'vue-chartjs'
const { reactiveProp } = mixins
// const brandPrimary = '#20a8d8'
export default {
extends: Line,
mixins: [reactiveProp],
props: ['options', 'chartData', 'height'],
mounted () {
this.renderChart(this.chartData, this.options)
var elements = 1
}
}
I tested this code and confirmed that it worked well.
<line-chart :chartData="myChartData"></line-chart>
but, I tried rendering chart dynamically, it is not working.
import lineChart from './MainChart';
// ...
let chartClass = Vue.extend(lineChart)
let chartInstance = new chartClass({
propsData: {
chartData: myChartData
}
})
chartInstance.$mount()
console.log(chartInstance.$el)
console.log(chartInstance.$el.querySelector("canvas").toDataURL('image/png'))
console.log(chartInstance.$refs.canvas)
console.log(chartInstance.$refs.canvas.toDataURL('image/png'))
Console messages:
I checked from the console and found that nothing was drawn in the canvas area.
How can I do render my chart dynamically?
Similar questions:
Is it possible to print a chart with vue-chartjs?
To get full image data, you have to wait until the chart is finished. Using 'Promise' is helpful.
async function addChart(d, i, w, h) {
var canvas = document.createElement("canvas")
canvas.width = 765
canvas.height = 382
//canvas.style.width = "765px"
//canvas.style.height = "382px"
//canvas.style.display = "none"
canvas.id = "dynamicChart"
document.body.appendChild(canvas)
var ctx = document.getElementById("dynamicChart").getContext('2d');
var draw = () => new Promise((resolve, reject) => {
new Chart(ctx, {
type: 'bar',
data: d,
options: {
responsive: false
}
})
setTimeout(() => resolve(), 100)
})
await draw()
let imageData = document.getElementById("dynamicChart").toDataURL("image/png")
console.log(imageData)
addImage(imageData, i, w, h)
document.body.removeChild(canvas)
}
// ...
await addChart(myChartData, 0, 400, 300)
If you want draw multiple chart for in the loop, try this:
let chartFunctions = []
myList.forEach((item) => {
chartFunctions.push(async function() {
await addChart(myChartData, 3, 160, 80)
})
}
for(let k in chartFunctions) {
await chartFunctions[k]()
}
Console messages:

VTK.js VR not display/showing an hand controller in Room

I try to use VTK VR, but When I test it, I cant see controller in room, I can get action from controller like press or somthing, but without its seen for user in VR mode, how I can fix it?
Online Demo From Here.
import 'vtk.js/Sources/favicon';
import vtkActor from 'vtk.js/Sources/Rendering/Core/Actor';
import vtkCalculator from 'vtk.js/Sources/Filters/General/Calculator';
import vtkConeSource from 'vtk.js/Sources/Filters/Sources/ConeSource';
import vtkFullScreenRenderWindow from 'vtk.js/Sources/Rendering/Misc/FullScreenRenderWindow';
import vtkMapper from 'vtk.js/Sources/Rendering/Core/Mapper';
import { AttributeTypes } from 'vtk.js/Sources/Common/DataModel/DataSetAttributes/Constants';
import { FieldDataTypes } from 'vtk.js/Sources/Common/DataModel/DataSet/Constants';
import controlPanel from './controller.html';
// ----------------------------------------------------------------------------
// Standard rendering code setup
// ----------------------------------------------------------------------------
const fullScreenRenderer = vtkFullScreenRenderWindow.newInstance({
background: [0, 0, 0],
});
const renderer = fullScreenRenderer.getRenderer();
const renderWindow = fullScreenRenderer.getRenderWindow();
// ----------------------------------------------------------------------------
// Example code
// ----------------------------------------------------------------------------
// create a filter on the fly, sort of cool, this is a random scalars
// filter we create inline, for a simple cone you would not need
// this
// ----------------------------------------------------------------------------
const coneSource = vtkConeSource.newInstance({ height: 100.0, radius: 50.0 });
// const coneSource = vtkConeSource.newInstance({ height: 1.0, radius: 0.5 });
const filter = vtkCalculator.newInstance();
filter.setInputConnection(coneSource.getOutputPort());
// filter.setFormulaSimple(FieldDataTypes.CELL, [], 'random', () => Math.random());
filter.setFormula({
getArrays: (inputDataSets) => ({
input: [],
output: [
{
location: FieldDataTypes.CELL,
name: 'Random',
dataType: 'Float32Array',
attribute: AttributeTypes.SCALARS,
},
],
}),
evaluate: (arraysIn, arraysOut) => {
const [scalars] = arraysOut.map((d) => d.getData());
for (let i = 0; i < scalars.length; i++) {
scalars[i] = Math.random();
}
},
});
const mapper = vtkMapper.newInstance();
mapper.setInputConnection(filter.getOutputPort());
const actor = vtkActor.newInstance();
actor.setMapper(mapper);
actor.setPosition(20.0, 0.0, 0.0);
renderer.addActor(actor);
renderer.resetCamera();
renderWindow.render();
// -----------------------------------------------------------
// UI control handling
// -----------------------------------------------------------
fullScreenRenderer.addController(controlPanel);
const representationSelector = document.querySelector('.representations');
const resolutionChange = document.querySelector('.resolution');
const vrbutton = document.querySelector('.vrbutton');
representationSelector.addEventListener('change', (e) => {
const newRepValue = Number(e.target.value);
actor.getProperty().setRepresentation(newRepValue);
renderWindow.render();
});
resolutionChange.addEventListener('input', (e) => {
const resolution = Number(e.target.value);
coneSource.setResolution(resolution);
renderWindow.render();
});
vrbutton.addEventListener('click', (e) => {
if (vrbutton.textContent === 'Send To VR') {
fullScreenRenderer.getOpenGLRenderWindow().startVR();
vrbutton.textContent = 'Return From VR';
} else {
fullScreenRenderer.getOpenGLRenderWindow().stopVR();
vrbutton.textContent = 'Send To VR';
}
});
// -----------------------------------------------------------
// Make some variables global so that you can inspect and
// modify objects in your browser's developer console:
// -----------------------------------------------------------
global.source = coneSource;
global.mapper = mapper;
global.actor = actor;
global.renderer = renderer;
global.renderWindow = renderWindow;
Note: Tested on Latest Version of Chrome & Firefox (64 bit). Controller Type is HTC Vive.
Update 1:
We found this option not development, so that I share updated link now Github Link

Variable is pushed, but it doesn't exist later

I have the following code:
const scenarioList = []
const randomScenario = () => {
return scenarioList[Math.floor(Math.random() * scenarioList.length--)]
}
class Scenario{
setBG(){
//screen.bg = this.bg
//screen.redraw()
}
write(text, buttons, callback){
//$('#gametext > span').html(`<span>${text}</span>`)
//input.setText(buttons)
//input.bindAll(callback)
}
constructor(imgsrc, text, actions, callback){
let img = new Image()
img.src = imgsrc
this.bg = img
this.text = text
this.actions = actions
this.callback = callback
scenarioList.push(this)
console.log(scenarioList)
}
}
I init the class the following (and this is in the global scope)
new Scenario('./bg/1.png', 'You look around and see a huge mountain, what do you do?',[
'Climb It!!',
'Walk around',
'Other Direction',
'Rest',
], [
() => {
alert('a')
},
() => {
alert('a')
},
() => {
alert('a')
},
() => {
alert('a')
},
])
And verify with console.log(scenarioList)
[Scenario]
So its appended, but when I later try to do a console.log() on the same variable it is the following:
[]
Code that causes it:
const startGame = () => {
alert('were here') // this executes at the correct time, but later then variable init.
let scn = randomScenario()
console.log(scenarioList)
scn.write()
scn.setBG()
}
I am not seeing why this would happen, anyone can give me a push in the right direction?
I've found the solution, this code actually removed the element from the array:
const randomScenario = () => {
return scenarioList[Math.floor(Math.random() * scenarioList.length--)]
}
instead I did this:
return scenarioList[Math.floor(Math.random() * scenarioList.length -1)]

Multiple export classes from same require(jsfile)

I'm currently designing an application and have some classes I'm extending. Below is a brief sample code of how it looks today, as well as where I want to go (aka one file, multiple classes and export them + consume them in main.js - or any other)..
TODAY
main.js
const UrgentTask = require('./urgentTask');
const Task = require('./task');
var ut = new UrgentTask({ name: "Some task", priority: "URGENT" });
var nt = new Task({ name: "Normal task" });
console.log(ut.toString());
console.log(nt.toString());
task.js
'use strict'
class Task {
constructor(data) {
this.name = data.name;
this.completed = false;
}
complete() {
console.log('completing task: ' + this.name);
this.completed = true;
}
save() {
console.log('Saving task: ' + this.name);
}
toString() {
return this.name + ' ' + this.completed;
}
}
module.exports = Task;
urgentTask.js
'use strict'
var Task = require('./task');
// Decorate "TASK"
class UrgentTask extends Task {
constructor(data) {
super(data);
this.priority = data.priority;
}
toString() {
return `[${this.priority}] ${super.toString()}`;
}
}
module.exports = UrgentTask;
WHAT I WOULD LIKE
main.js
const { Task, UrgentTask } = require('./task');
var ut = new UrgentTask({ name: "Some task", priority: "URGENT" });
var nt = new Task({ name: "Normal task" });
console.log(ut.toString());
console.log(nt.toString());
task.js
=> this would ideally export the two classes, but I don't know how to?
What I already tried:
module.exports = Task;
module.exports = UrgentTask;
But this blows up in node.
WHAT I WOULD LIKE
const { Task, UrgentTask } = require('./task');
That's a destructuring assignment, which assigns object properties to discrete bindings (constants, in this case).
So you need to export an object:
ES2015+ syntax (but using Node modules, not ES2015 modules):
module.exports = {Task, UrgentTask};
ES5 and earlier syntax:
module.exports = {Task: Task, UrgentTask: UrgentTask};
Actually, by default, exports already is an object so you can also do this:
module.exports.Task = Task;
module.exports.UrgentTask = UrgentTask;
But replacing it with a new object is fine too.
Simple non-Require example:
function getMyStuff() {
class Task { }
class UrgentTask extends Task { }
return {Task, UrgentTask};
}
const {Task, UrgentTask} = getMyStuff();
const ut = new UrgentTask();
console.log(ut instanceof UrgentTask); // true
console.log(ut instanceof Task); // true
NodeJS example:
mymodule.js:
class Task { }
class UrgentTask extends Task { }
module.exports = {Task, UrgentTask};
myapp.js:
const {Task, UrgentTask} = require("./mymodule.js");
const ut = new UrgentTask();
console.log(ut instanceof UrgentTask); // true
console.log(ut instanceof Task); // true

Categories