add gif generator

This commit is contained in:
JuliusHerrmann 2021-12-14 00:40:22 +01:00
parent be854ddce3
commit 0559d6fac8
6 changed files with 15638 additions and 11913 deletions

22826
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -3,6 +3,7 @@
"version": "0.1.0", "version": "0.1.0",
"private": true, "private": true,
"dependencies": { "dependencies": {
"@dhdbstjr98/gif.js": "^1.0.2",
"@testing-library/jest-dom": "^5.11.4", "@testing-library/jest-dom": "^5.11.4",
"@testing-library/react": "^11.1.0", "@testing-library/react": "^11.1.0",
"@testing-library/user-event": "^12.1.10", "@testing-library/user-event": "^12.1.10",

View File

@ -0,0 +1,77 @@
import React from 'react';
import '../../css/Graph.css';
import '../../css/GIFGenerator.css';
import Slider from '../Slider';
import GIF from '@dhdbstjr98/gif.js';
class GIFGenerator extends React.Component {
constructor() {
super();
this.state = {step: 0, duration: 5, loop: true, background: "#ffffff"};
this.animationId = 0;
}
generateGIF = () => {
//clean input
this.setState({duration: Math.abs(this.state.duration)});
var gif = new GIF( {
workers: 2,
quality: 10,
repeat: this.state.loop? 0 : -1,
background: this.state.background
});
gif.on('finished', function(blob) {
window.open(URL.createObjectURL(blob));
});
let stepBehtmlFore = this.state.step;
//clear playing animation
clearInterval(this.animationId);
this.props.setState({step: 0}, () => {
this.stepTime = 1;
//this.animationId = setInterval(this.visualizeOneStep, this.stepTime);
this.animationId = setInterval(this.grabImageAndNextStep.bind(null, gif, stepBehtmlFore), this.stepTime);
this.props.setState({playing: true});
});
}
grabImageAndNextStep = (gif, stepBehtmlFore) => {
//check if we are at the end
if (this.props.state.step > this.props.animationLength) {
this.props.setState({step: stepBehtmlFore});
this.props.visualizeOneStep(false);
clearInterval(this.animationId);
gif.render();
this.props.setState({playing: false});
return;
}
this.props.visualizeOneStep();
//select the canvas (this is a bit hacky but ey it works)
gif.addFrame(document.querySelectorAll("canvas")[2],
// there is probably a minimum cap.... I'm not sure
{copy: true, delay: this.state.duration / this.props.animationLength});
}
//onChange={(e) => this.setState({loop: e.state.value})}>
render() {
return (
<div id="generateGIFPopup">
<label htmlFor="gifDuration" id="gifLengthLabel">Duration In Seconds: </label>
<input htmlFor="gifDuration" type="number" id="gifLengthInput"
value={this.state.duration} onChange={(e) => this.setState({duration: e.target.value})}/>
<label htmlFor="gifBackground" id="gifBackgroundLabel">Background Color: </label>
<input htmlFor="gifBackground" id="gifBackgroundInput" type='color'
value={this.state.background}
onChange={(e) => this.setState({background: e.target.value})}/>
<label htmlFor="gifLoop" id="gifLoopLabel">Loop: </label>
<input htmlFor="gifLoop" id="gifLoopInput" type="checkbox" checked={this.state.loop}
onChange={(e) =>
this.setState({loop: e.target.checked})}/>
<button onClick ={this.generateGIF} >Generate GIF</button>
</div>
);
}
}
export default GIFGenerator;

View File

@ -1,7 +1,9 @@
import React from 'react'; import React from 'react';
import CytoscapeComponent from 'react-cytoscapejs'; import CytoscapeComponent from 'react-cytoscapejs';
import '../../css/Graph.css' import '../../css/Graph.css';
import Slider from '../Slider'; import Slider from '../Slider';
import GIFGenerator from './GIFGenerator';
//import GIF from '@dhdbstjr98/gif.js';
class Graph extends React.Component { class Graph extends React.Component {
constructor(props) { constructor(props) {
@ -10,7 +12,7 @@ class Graph extends React.Component {
this.cy = React.createRef(); this.cy = React.createRef();
this.stepTime = 0; this.stepTime = 0;
this.neverPlayed = true; this.neverPlayed = true;
this.state ={animationDuration: 4, step: 0, playing: false}; this.state ={animationDuration: 4, step: 0, playing: false, gif: null};
} }
componentDidMount() { componentDidMount() {
@ -206,6 +208,7 @@ class Graph extends React.Component {
<Slider description="Step" min="0" max={this.props.animationLength} currentValue={this.state.step} handleChange={this.visualizeSpecificStep}/> <Slider description="Step" min="0" max={this.props.animationLength} currentValue={this.state.step} handleChange={this.visualizeSpecificStep}/>
<CytoscapeComponent id="cy" userZoomingEnabled={false} userPanningEnabled={false} <CytoscapeComponent id="cy" userZoomingEnabled={false} userPanningEnabled={false}
cy={(cy) => { this.cy = cy }} elements={this.props.graphData}/> cy={(cy) => { this.cy = cy }} elements={this.props.graphData}/>
<GIFGenerator setState={this.setState.bind(this)} state={this.state} visualizeOneStep={this.visualizeOneStep} animationLength={this.props.animationLength}/>
</div>); </div>);
} }
} }

6
src/css/GIFGenerator.css Normal file
View File

@ -0,0 +1,6 @@
#generateGIFPopup {
position: absolute;
top: 0;
left: 0;
border: solid black;
}

4608
yarn.lock

File diff suppressed because it is too large Load Diff