HighCharts Series Space - reactjs

Hi im trying to remove an empty space between series.
Im using Highcharts with react.
I got a dynamic chart area and i need to remove the gap between the walls.
See the example below
Link: https://jsfiddle.net/dczv0u53/13/
Code:
xAxis: {
tickPositions: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
},
series: [
{
groupPadding: 1,
type: `area`,
data: [
[0, 1],
[1, 3],
[2, 2],
],
states: {
inactive: {
opacity: 0.8
}
}
},
{
type: `area`,
groupPadding: 1,
data: [
[5, 4],
[8, 3],
[10, 3]
],
states: {
inactive: {
opacity: 0.8
}
}
},
]
});

You can use breaks:
xAxis: {
...,
breaks: [{
from: 2,
to: 5,
breakSize: 0
}]
}
Live demo: https://jsfiddle.net/BlackLabel/tb4czrfx/
API Reference: https://api.highcharts.com/highcharts/xAxis.breaks

Related

How to update config in HighChart with React hooks?

I want to change options of HighChart by useState.
Then I could use a button click to re-render the chart.
Here is my code:
const options = {
title: {
text: "My chart",
},
series: [
{
data: [1, 2, 3, 7, 2, 3, 1, 0],
},
{
data: [1, 2, 1, 7, 3, 3, 3, 0],
},
],
};
export default function HighChartContainer() {
const [chartOptions, setChartOptions] = useState(options);
const handleChangeOptions = () => {
const newLineData = [
{
data: [1, 2, 1, 4, 2, 3, 7, 0],
},
{
data: [1, 2, 1, 6, 3, 5, 2, 0],
},
];
const newOptions = { ...chartOptions, series: newLineData };
setChartOptions(newOptions);
};
return (
<div>
<ChartWrapper>
<HighchartsReact
highcharts={Highcharts}
options={chartOptions}
/>
</ChartWrapper>
<div>
<button type="button" onClick={handleChangeOptions}>
Click me
</button>
</div>
</div>
);
}
It didn't work. I tried google but couldn't find anyone who wrote code in this pattern.
Is there anything wrong?
My code sandbox:
https://codesandbox.io/s/serene-framework-jjoh4?file=/src/App.js
You need to remove handleChangeOptions from the callback to see the effect. Additionally it is enough to update the chart with only new options:
const handleChangeOptions = () => {
const newLineData = [
{
data: [...]
},
{
data: [...]
}
];
const newOptions = { series: newLineData };
setChartOptions(newOptions);
};
Live demo: https://codesandbox.io/s/angry-johnson-gpv99?file=/src/App.js
Docs: https://github.com/highcharts/highcharts-react#optimal-way-to-update
After you update question. I saw the problem is you pass callback={handleChangeOptions} in HighchartsReact. So you just remove it. everything will work normally.

How to assign different color for each vertex in a buffer geometry? Three.js

I am new to Three.js and
I have found a few answers on the topic but none have used buffer geometry. I am making a 3D terrain project of Europe on React and I want to be able to change the water levels depending on some values. In order to do that my coloring has to be done vertex by vertex instead of adding a texture from an image where the coloring will not change if I change the vertices' values. So, depending on the "height" of the vertex I want to assign different colors.
Here's my componentDidMount function:
const SIZE_AMPLIFIER = 15;
var container = document.getElementById("main_map");
var scene, camera, renderer, controls;
var data, plane;
//load map data from bin file
function loadTerrain(file) {
var xhr = new XMLHttpRequest();
xhr.responseType = 'arraybuffer';
xhr.open('GET', file, true);
xhr.onload = function (evt) {
if (xhr.response) {
data = new Uint16Array(xhr.response)
init()
}
};
xhr.send(null);
}
loadTerrain('stats.bin');
function init() {
// initialize camera
camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, .1, 100000);
camera.position.set(10000, 4000, 0);
// initialize scene
scene = new THREE.Scene();
// initialize directional light (sun)
var sun = new THREE.DirectionalLight(0xFFFFFF, 1.0);
sun.position.set(300, 400, 300);
sun.distance = 1000;
scene.add(sun);
var frame = new THREE.SpotLightHelper(sun);
scene.add(frame);
// initialize renderer
renderer = new THREE.WebGLRenderer();
renderer.setClearColor(0x000000);
renderer.setPixelRatio(window.devicePixelRatio);
renderer.setSize(window.innerWidth, window.innerHeight);
container.append(renderer.domElement);
//initialize controls
controls = new OrbitControls(camera, renderer.domElement);
controls.enableDamping = true;
controls.dampingFactor = 1;
controls.rotateSpeed = .8;
controls.maxPolarAngle = Math.PI / 2 - .3;
// initialize plane
plane = new THREE.PlaneBufferGeometry(1500 * SIZE_AMPLIFIER, 1500 * SIZE_AMPLIFIER, 999 , 999);
plane.castShadow = true;
plane.receiveShadow = true;
var vertices = plane.attributes.position.array;
console.log(data)
// apply height map to vertices of plane
// assign different color depending on the value??
for (let i = 0, j = 2; i < data.length; i += 1, j += 3) {
if(data[i] == 0){
vertices[j] = 0
}else {
vertices[j] = data[i] / 65535 * 325 + 10
}
}
// Add texture image
var material = new THREE.MeshLambertMaterial({
map:THREE.ImageUtils.loadTexture('stats_color.png')
})
var mesh = new THREE.Mesh(plane, material);
mesh.rotation.x = - Math.PI / 2;
mesh.matrixAutoUpdate = false;
mesh.updateMatrix();
plane.computeFaceNormals();
plane.computeVertexNormals();
scene.add(mesh);
animate();
}
function animate() {
requestAnimationFrame(animate);
renderer.render(scene, camera);
//controls.update();
}
The result after this (it is satisfying for me but unfortunately not effective for the purpose of the application):
Here is an article on how to use BufferGeometry
To add colors you make a Float32Array of colors and add it as an attribute called 'color'.
geometry.setAttribute(
'color',
new THREE.BufferAttribute(new Float32Array(colors), uvNumComponents));
You then set material.vertexColors to true;
const material = new THREE.MeshPhongMaterial({
vertexColors: true,
});
body {
margin: 0;
}
#c {
width: 100vw;
height: 100vh;
display: block;
}
<canvas id="c"></canvas>
<script type="module">
import * as THREE from 'https://threejsfundamentals.org/threejs/resources/threejs/r115/build/three.module.js';
function main() {
const canvas = document.querySelector('#c');
const renderer = new THREE.WebGLRenderer({canvas});
const fov = 75;
const aspect = 2; // the canvas default
const near = 0.1;
const far = 100;
const camera = new THREE.PerspectiveCamera(fov, aspect, near, far);
camera.position.z = 3;
const scene = new THREE.Scene();
{
const color = 0xFFFFFF;
const intensity = 1;
const light = new THREE.DirectionalLight(color, intensity);
light.position.set(-1, 2, 4);
scene.add(light);
}
// NOT A GOOD EXAMPLE OF HOW TO MAKE A CUBE!
// Only trying to make it clear most vertices are unique
const vertices = [
// front
{ pos: [-1, -1, 1], norm: [ 0, 0, 1], uv: [0, 1], },
{ pos: [ 1, -1, 1], norm: [ 0, 0, 1], uv: [1, 1], },
{ pos: [-1, 1, 1], norm: [ 0, 0, 1], uv: [0, 0], },
{ pos: [-1, 1, 1], norm: [ 0, 0, 1], uv: [0, 0], },
{ pos: [ 1, -1, 1], norm: [ 0, 0, 1], uv: [1, 1], },
{ pos: [ 1, 1, 1], norm: [ 0, 0, 1], uv: [1, 0], },
// right
{ pos: [ 1, -1, 1], norm: [ 1, 0, 0], uv: [0, 1], },
{ pos: [ 1, -1, -1], norm: [ 1, 0, 0], uv: [1, 1], },
{ pos: [ 1, 1, 1], norm: [ 1, 0, 0], uv: [0, 0], },
{ pos: [ 1, 1, 1], norm: [ 1, 0, 0], uv: [0, 0], },
{ pos: [ 1, -1, -1], norm: [ 1, 0, 0], uv: [1, 1], },
{ pos: [ 1, 1, -1], norm: [ 1, 0, 0], uv: [1, 0], },
// back
{ pos: [ 1, -1, -1], norm: [ 0, 0, -1], uv: [0, 1], },
{ pos: [-1, -1, -1], norm: [ 0, 0, -1], uv: [1, 1], },
{ pos: [ 1, 1, -1], norm: [ 0, 0, -1], uv: [0, 0], },
{ pos: [ 1, 1, -1], norm: [ 0, 0, -1], uv: [0, 0], },
{ pos: [-1, -1, -1], norm: [ 0, 0, -1], uv: [1, 1], },
{ pos: [-1, 1, -1], norm: [ 0, 0, -1], uv: [1, 0], },
// left
{ pos: [-1, -1, -1], norm: [-1, 0, 0], uv: [0, 1], },
{ pos: [-1, -1, 1], norm: [-1, 0, 0], uv: [1, 1], },
{ pos: [-1, 1, -1], norm: [-1, 0, 0], uv: [0, 0], },
{ pos: [-1, 1, -1], norm: [-1, 0, 0], uv: [0, 0], },
{ pos: [-1, -1, 1], norm: [-1, 0, 0], uv: [1, 1], },
{ pos: [-1, 1, 1], norm: [-1, 0, 0], uv: [1, 0], },
// top
{ pos: [ 1, 1, -1], norm: [ 0, 1, 0], uv: [0, 1], },
{ pos: [-1, 1, -1], norm: [ 0, 1, 0], uv: [1, 1], },
{ pos: [ 1, 1, 1], norm: [ 0, 1, 0], uv: [0, 0], },
{ pos: [ 1, 1, 1], norm: [ 0, 1, 0], uv: [0, 0], },
{ pos: [-1, 1, -1], norm: [ 0, 1, 0], uv: [1, 1], },
{ pos: [-1, 1, 1], norm: [ 0, 1, 0], uv: [1, 0], },
// bottom
{ pos: [ 1, -1, 1], norm: [ 0, -1, 0], uv: [0, 1], },
{ pos: [-1, -1, 1], norm: [ 0, -1, 0], uv: [1, 1], },
{ pos: [ 1, -1, -1], norm: [ 0, -1, 0], uv: [0, 0], },
{ pos: [ 1, -1, -1], norm: [ 0, -1, 0], uv: [0, 0], },
{ pos: [-1, -1, 1], norm: [ 0, -1, 0], uv: [1, 1], },
{ pos: [-1, -1, -1], norm: [ 0, -1, 0], uv: [1, 0], },
];
const positions = [];
const normals = [];
const uvs = [];
const colors = [];
for (const vertex of vertices) {
positions.push(...vertex.pos);
normals.push(...vertex.norm);
uvs.push(...vertex.uv);
colors.push(Math.random(), Math.random(), Math.random());
}
const geometry = new THREE.BufferGeometry();
const positionNumComponents = 3;
const normalNumComponents = 3;
const uvNumComponents = 2;
const colorNumComponents = 3;
geometry.setAttribute(
'position',
new THREE.BufferAttribute(new Float32Array(positions), positionNumComponents));
geometry.setAttribute(
'normal',
new THREE.BufferAttribute(new Float32Array(normals), normalNumComponents));
geometry.setAttribute(
'uv',
new THREE.BufferAttribute(new Float32Array(uvs), uvNumComponents));
geometry.setAttribute(
'color',
new THREE.BufferAttribute(new Float32Array(colors), colorNumComponents));
const material = new THREE.MeshPhongMaterial({
vertexColors: true,
});
const cube = new THREE.Mesh(geometry, material);
scene.add(cube);
function resizeRendererToDisplaySize(renderer) {
const canvas = renderer.domElement;
const width = canvas.clientWidth;
const height = canvas.clientHeight;
const needResize = canvas.width !== width || canvas.height !== height;
if (needResize) {
renderer.setSize(width, height, false);
}
return needResize;
}
function render(time) {
time *= 0.001;
if (resizeRendererToDisplaySize(renderer)) {
const canvas = renderer.domElement;
camera.aspect = canvas.clientWidth / canvas.clientHeight;
camera.updateProjectionMatrix();
}
cube.rotation.x = time;
cube.rotation.y = time;
renderer.render(scene, camera);
requestAnimationFrame(render);
}
requestAnimationFrame(render);
}
main();
</script>

Working with Charts in motion [Animating chart]

I have created a areaspline chart using highcharts library and making it animated with play/pause button transition between weeks of data
Ref. https://www.highcharts.com/blog/tutorials/176-charts-in-motion/
jsfiddle Ref. https://jsfiddle.net/larsac07/wkev75nL/?utm_source=website&utm_medium=embed&utm_campaign=wkev75nL
in the above example, we are animating the chart week wise
dataSet used :
dataSequence = [
{
name: 'Week 1',
data: [1, 2, 2, 1, 1, 2, 2]
}, {
name: 'Week 2',
data: [6, 12, 2, 3, 3, 2, 2]
}, {
name: 'Week 3',
data: [4, 5, 6, 5, 5, 4, 9]
}, {
name: 'Week 4',
data: [5, 5, 6, 6, 5, 6, 6]
}, {
name: 'Week 5',
data: [6, 7, 7, 6, 6, 6, 7]
}, {
name: 'Week 6',
data: [8, 9, 9, 8, 8, 8, 9]
}, {
name: 'Week 7',
data: [9, 10, 4, 10, 9, 9, 9]
}, {
name: 'Week 8',
data: [1, 10, 10, 10, 10, 11, 11]
}, {
name: 'Week 9',
data: [11, 11, 12, 12, 12, 11, 11]
}
]
I don't want change chart
on play button click I want animate the data points 11 data point for week1 to same data point but different value on y axis for week2
xAxis = ["week1", "Week2", ..... ],
yAxis = [[1,2,3,4,5,6,7,8,9,10,11], [3,5,7,8,2,1,5,7,6,1,10], ....]
on the play button it would transit between week1 then will go to week 2 and so till last week number available.
Trying to have something like this Ref. https://aatishb.com/covidtrends/
this chart is plotted using this dataset for series
Highcharts.chart("container", {
chart: {
type: "areaspline"
},
tooltip: {
shared: true,
valueSuffix: " units"
},
xAxis: {
categories: [
"Week 1",
"Week 2",
"Week 3",
"Week 4",
"Week 5",
"Week 6",
"Week 7"
]
},
yAxis: {
title: {
text: "Index"
}
},
legend: {
layout: "horizontal",
align: "right",
verticalAlign: "top",
x: 50,
y: 50,
floating: true,
borderWidth: 1,
backgroundColor:
(Highcharts.theme && Highcharts.theme.legendBackgroundColor) ||
"#FFFFFF"
},
plotOptions: {
areaspline: {
fillOpacity: 0.5
}
},
credits: {
enabled: false
},
series: [
{
name: "By week",
data: dataSequence[value].data.slice()
},
{
type: "spline",
name: "Topic 1",
data: [3, 2, 1, 3, 4, 7, 8]
},
{
type: "spline",
name: "Topic 2",
data: [1, 5, 1, 3, 4, 7, 8]
},
{
type: "spline",
name: "Topic 3",
data: [3, 7, 1, 3, 4, 7, 8]
},
{
type: "spline",
name: "Topic 4",
data: [5, 1, 1, 3, 4, 7, 8]
},
{
type: "spline",
name: "Topic 5",
data: [7, 3, 1, 3, 4, 7, 8]
},
{
type: "spline",
name: "Topic 6",
data: [9, 2, 1, 3, 4, 7, 8]
},
{
type: "spline",
name: "Topic 7",
data: [11, 8, 1, 3, 4, 7, 8]
},
{
type: "spline",
name: "Topic 8",
data: [13, 11, 1, 3, 4, 7, 8]
},
{
type: "spline",
name: "Topic 9",
data: [15, 7, 1, 3, 4, 7, 8]
},
{
type: "spline",
name: "Topic 10",
data: [7, 5, 1, 3, 4, 7, 8]
}
],
title: {
text: ""
},
subtitle: {
text: "Efficiency Index of Topics"
}
});
this my update function in react
update(increment) {
var input = $("#play-range")[0];
var output = $("#play-output")[0];
if (increment) {
input.value = parseInt(input.value) + increment;
}
output.innerHTML = this.state.dataSequence[input.value].name;
this.setState({
value: input.value
});
if (input.value >= input.max) {
// Auto-pause
this.pause();
this.setState(
{
value: 0
},
() => {
output.innerHTML = this.state.dataSequence[0].name;
}
);
}
}
the whole chart is plotted at once, I need something that it should transit
first, it plots all data points for week1 then week 2 after that week 3 when I click on the play button
You need to start with an empty data and use addPoint method in the update function:
function update(increment) {
var input = $('#play-range')[0],
output = $('#play-output')[0],
increment;
chart.series[0].addPoint(dataSequence[input.value].data[actualPointIndex]);
actualPointIndex += increment;
if (actualPointIndex === 6) {
actualPointIndex = 0;
input.value = parseInt(input.value) + increment;
}
output.innerHTML = dataSequence[input.value].name; // Output value
if (input.value >= input.max) { // Auto-pause
pause($('#play-pause-button')[0]);
}
}
Live demo: https://jsfiddle.net/BlackLabel/stpxyfca/
API Reference: https://api.highcharts.com/class-reference/Highcharts.Series#addPoint

Vertical line within bars of a stacked bar chart using recharts or highcharts

How do I add a line like the one in first bar. It will be on percentage basis i.e. full width of the bar is 100%. Any clue will be helpful. My current chart is based on the code from this simple example
I'm OK to switch to highcharts if it works with that.
You can easily draw those line by using the Highcharts library.
To do it you will need to define those line as a new series, where you will need to define x and y values to fit the line on the chart.
Demo: https://jsfiddle.net/BlackLabel/v3gmph9w/
series: [{
name: 'John',
data: [5, 3, 4, 7, 2]
}, {
name: 'Jane',
data: [2, 2, 3, 2, 1]
}, {
name: 'Joe',
data: [3, 4, 4, 2, 5]
}, {
type: 'line',
enableMouseTracking: false,
data: [{x:0, y: 3}, {x: 0, y: 5}]
}]
API: https://api.highcharts.com/highcharts/series.line.data

Adding labels to both ends of axis google charts

I've built a bubble chart on quadrant graph using google-charts in reactjs but I can only had two labels on my axis and I need four.
I've tried fiddling with the code but unsuccessfully. I don't want to append dummy data and additional series elements. Is overlay the only option to add axis?
<Chart
width={"800px"}
height={"600px"}
chartType="BubbleChart"
loader={<div>Loading Chart</div>}
data={[
["Age", "Weight", "4", "Group", "Size"],
["Name", -12, 34, 1, 7],
["Name", -5.5, 6, 1, 8],
["Name", 22, 35, 1, 4],
["Name", 14, 4, 2, 5],
["Name", -5, -5, 2, 6],
["Name", 15, 34, 3, 1],
["Name4", 7, -21, 4, 22]
]}
options={{
bubble: {},
chartArea: { left: 20, top: 0, width: "90%", height: "95%" },
colors: ["red", "green", "yellow", "blue"],
hAxis: {
title: "Low Importance",
ticks: "none",
baseline: 0,
ticks: ["none"],
minValue: -50,
gridlines: { count: 0 },
maxValue: 50
},
vAxis: {
title: "Low Urgency",
baseline: 0,
ticks: ["none"],
minValue: -50,
gridlines: { count: 0 },
maxValue: 50
},
legend: "none"
}}
/>;
As you can see in the graph below, I can only get left and bottom labels but not top and right. Any ideas how I could achieve that using google-chart library for reactjs?

Resources