I have implemented a scatterplot using react-plotly.js I would like the chart to re-size itself when the page layout changes. But currently, the layout of the chart doesn't change by itself. If I explicitly perform some function on the chart which forces the chart to redraw itself then only the chart width changes.
I applied useResizeHandler property and have set autosize to true. But that doesn't make any difference either.
<Plot
useResizeHandler
style={{ width: '100%' }}
data={chartData}
onClick={(data) => this.handlePlotClick(data)}
type={'scatter'}
layout={this.layout} />
const layout = {
autosize: true,
dragmode: true,
margin: {
l: 5,
r: 5,
t: 10,
b: 10,
pad: 0,
autoexpand: true
},
hovermode: 'closest',
hoverlabel: {
bgcolor: 'rgba(0,0,0,1)',
bordercolor: 'rgba(200,200,200,1)'
},
height: '650',
yaxis: {
visible: false
},
xaxis: {
autorange: false,
showline: true,
fixedrange: false, // true disables range selection on main graph
rangeslider: {
range: this.state.sliderRange,
visible: true,
borderwidth: 1,
bordercolor: '#000'
}
}
};
}
As you can see in the screenshot above, the div.svg-container has same width as the main-svg. But it still leaves white space on the right. I am unable to debug why it would behave that way. If I explicitly perform zoom on the chart that will redraw the plot then it will behave correctly. But I would like it to automatically resize when the page layout changes.
I was stuck on this problem too. Try window.dispatchEvent(new Event('resize')) from http://codrate.com/questions/how-can-trigger-the-window-resize-event-manually-in-javascript
I was calling resizeHandler when my chart is resized by dragging.
resizeHandler = () => {
this.child.resizeHandler();
window.dispatchEvent(new Event('resize'));
}
The charts always autoscales when the chart is resized, so I basically trigger the window resize when my chart size is changed. So for you, when you detect the page layout changes you can trigger the window resize.
Related
I need to only show two shapes in my custom Tui image editor, a rectangle and a circle, nothing more nothing less.
I added the rectangle and it works perfectly but if I add another function to add a circle and draw either or first the and then select the other, it still draws the first item. (if you click on a circle and draw, then click on the rectangle and draw then it draws a circle)
I am not sure how I can get this to function properly.
here is my two functions for my circle and rectangle.
const onAddCircle = () => {
imageEditorRef.current.startDrawingMode('SHAPE');
if (imageEditorRef.current.getDrawingMode() !== 'SHAPE') {
const { height } = imageEditorRef.current.getCanvasSize();
imageEditorRef.current.startDrawingMode('SHAPE');
imageEditorRef.current.setDrawingShape('circle', {
fill: 'transparent',
stroke: COLOR_STATUS_ORANGE,
strokeWidth: height / 100,
isRegular: true,
});
}
};
const onAddRectangle = () => {
if (imageEditorRef.current.getDrawingMode() !== 'SHAPE') {
const { height } = imageEditorRef.current.getCanvasSize();
imageEditorRef.current.startDrawingMode('SHAPE');
imageEditorRef.current.clearObjects();
imageEditorRef.current.setDrawingShape('rect', {
fill: 'transparent',
stroke: COLOR_STATUS_ORANGE,
strokeWidth: height / 100,
isRegular: true,
});
}
};
and they are triggered by buttons
<button
onClick={onAddCircle}
color="green"
/>
<button
onClick={onAddRectangle}
color="red"
/>
I've tried adding imageEditorRef.current.clearDrawingShape(); to the beginning of the functions but it says its not a function because it doesn't exist. then I tried adding imageEditorRef.current.clearObjects(); but that clears everything that it draw by that shape.
I've looked their documentation as well and there is nothing on how to actually clear shape cache before drawing or selecting another shape.
Could someone please help ?
I fixed it!
Ive combined both functions into one added a prop called shape, and it checks if the prop is set to either or and then if it is then it uses that logic else it clears the drawing board.
const drawShape = (Shape) => {
const { height } = imageEditorRef.current.getCanvasSize();
imageEditorRef.current.startDrawingMode('SHAPE');
if (Shape === 'circle') {
imageEditorRef.current.setDrawingShape('circle', {
fill: 'transparent',
stroke: COLOR_STATUS_ORANGE,
strokeWidth: height / 100,
isRegular: true,
});
} else if (Shape === 'rectangle') {
imageEditorRef.current.setDrawingShape('rect', {
fill: 'transparent',
stroke: COLOR_STATUS_ORANGE,
strokeWidth: height / 100,
isRegular: true,
});
} else {
imageEditorRef.current.stopDrawingMode();
}
};
How to change the chart title dynamically on hover in Highcharts
JSfiddle
http://jsfiddle.net/q4b7dvmx/1/
tried with setState but its not working perfectly
tooltip:{
enabled: true,
borderRadius: 0,
borderWidth: 0,
shadow: false,
shared: true,
useHTML: true,
zIndex: 99999,
formatter() {
// ToolTip Built Here
const { x , y } = this;
let tooltipString = `<div > ${y}
</div>`;
// that.props.updateDates( this.points[0].series.userOptions.dates[this.points[0].key] );
return tooltipString;
}
}
The easiest way is to change a title text attribute in tooltip formatter function.
tooltip: {
...,
formatter(e) {
const {
x,
y
} = this;
e.chart.title.attr({
text: 'ftest' + ' x value: ' + x
});
}
}
Live demo: http://jsfiddle.net/BlackLabel/tk1avpze/
API Reference: https://api.highcharts.com/class-reference/Highcharts.SVGElement#attr
Do you mean on hover of a data-point? in that case, your demo does nothing to the chart title.
Either way, you should check this post;
How can I access a hover state in reactjs?
EDIT;
Did you see https://api.highcharts.com/highcharts/tooltip.formatter - it adresses the formatter. It seems to be the answer, from the looks of a similar question;
Highcharts.js : get specific value from data to tooltip
I am trying to have stacked bar with different color as below.
I could achive bar as below however looking for -
1. label under each block and count.
2. On click on one of the block, color for rest of the blocks should be changed (should be same as hover behaviour)
Any suggestion and help would be appreciated.
You can use stacked bar chart with enabled data labels:
plotOptions: {
bar: {
stacking: 'normal',
dataLabels: {
color: 'black',
enabled: true,
y: 80
}
}
}
Live demo: http://jsfiddle.net/BlackLabel/wg46umjp/
API Reference: https://api.highcharts.com/highcharts/plotOptions.bar.dataLabels
I'm trying to align the title to the left instead of the center (shown in the image).
I know this is possible on chartJS v3.0.0-alpha.2, but reactchartjs only goes up to 2.9.30 as far as I know.
Does anyone know how to achieve this in reactchartjs?
I thought it would be something like:
options={{
title: {
position: 'top',
align: 'left',
},
}}
Any help would be appreciated.
You should use the align parameter. This sets the alignment of the title. Your options are:
start
center
end
Your align: 'left' isn't one of the above and will not have any effect. Setting align: 'start' however will give you exactly what you want:
The full code looks like this:
<Chart
type='line'
data={dat}
options={{
plugins: {
title: {
display: true,
align: 'start',
text: 'Bitcoin Mining Difficulty'
}
}
}} />
Let me also mention that you should not confuse that with position: 'left'. position moves the whole title into one of top, left, bottom, right area of the chart. An example with a combination of position: 'left' and align: start:
The Chart.js Plugin Core API offers a range of hooks that may be used for performing custom code. You can use the afterDraw hook to draw the title yourself directly on the canvas using CanvasRenderingContext2D.fillText().
In React, you can register the plugin as follows:
componentWillMount() {
Chart.pluginService.register({
afterDraw: chart => {
let ctx = chart.chart.ctx;
ctx.save();
let xAxis = chart.scales['x-axis-0'];
ctx.textAlign = "left";
ctx.font = "14px Arial";
ctx.fillStyle = "black";
ctx.fillText("Title", xAxis.left, 10);
ctx.restore();
}
});
}
You'll also have to define some extra padding at the top of the chart to make sure, the title appears on the canvas.
options: {
layout: {
padding: {
top: 20
}
},
...
Please take a look at this StackBlitz and see how it works.
In order to have the edges of the previous/next carousel items to show within Slider, I am reducing the .swiper-slide size. There are two ways of achieving this that I have tried:
setting .swiper-slide width to 90%
setting the slidesPerView param to 1.1
Both work nicely, but the final two items in the carousel show stange visual artefacts. The background of the container appears to overlap and intersect the slider. Images below (first in each example is as it is expected to render, second is with glitch). The visual glitch is cleared with a click, but still undesirable:
These are my Slider params
const params = {
slidesPerView: 3,
spaceBetween: 50,
speed: 400,
centeredSlides: true,
initialSlide: this.props.latestQuestionIndex,
slideToClickedSlide: true,
breakpoints: {
768: {
slidesPerView: 3,
spaceBetween: 30
},
425: {
slidesPerView: 1.1,
spaceBetween: 10
}
},
on: {
slideChange: () =>
this.state.swiper && this.setState({ currentIndex: this.state.swiper.activeIndex })
}
};
Is there another method of allowing for overlap of the edges of other carousel images, or a fix for this visual glitch?