I'm trying to make a calendar of event using react-native-big-calendar
when i believe it's suppose to work with both start and end time, but somehow it's not work when i uncomment the end property
here are the codes:
const events = [
{
title: 'Meeting',
start: new Date(2020, 5, 20, 10, 0),
// end: new Date(2020, 5, 20, 22, 30),
},
{
title: 'Coffee break',
start: new Date(2020, 1, 14, 15, 45),
// end: new Date(2020, 1, 14, 16, 30),
},
{
title: 'Repair my car',
start: new Date(2020, 5, 20, 7, 45),
// end: new Date(2020, 5, 20, 13, 30),
},
]
class BookingListScreen extends Component {
constructor(props) {
super(props);
this.state = {
}
}
render() {
console.log('logged by phuognn start: ', new Date(2020, 5, 20, 10, 0));
console.log('logged by phuognn end: ',new Date(2020, 5, 20, 22, 30));
return (
<View style={{ flex: 1 }}>
<Calendar
height={Dimensions.get('window').height}
style={styles.calendar}
events={events}
height={600}
eventCellStyle={{ backgroundColor: 'blue' }}
/>
</View>
);
}
}
if I uncomment the end property of events, the calendar show no event.
Wonder why?
The end property is required on the type BaseEvent. So you must specify it!
node_modules\react-native-big-calendar\build\interfaces.d.ts
export interface BaseEvent {
start: Date;
end: Date;
title: string;
}
If what you're looking for is an event which lasts all day, use event's time.
const events = [
{
title: 'Meeting',
start: new Date(2020, 1, 11, 0, 0),
end: new Date(2020, 1, 12, 0, 0),
}
]
Related
I have an Array of Strings that I have mapped using the Map funtion and rendered a Text with each item. Now if I click any mapped Text I want to highlight that clicked Text. Moreover, I want to keep on highlighting the next Text after some delay and so on.
How to do it efficiently? So far I have witten the following code and I am able to Highlight the clicked text with the help of an extra style based on the selected page and index clicked. Now I want to have to select the next mapped item automatically after some delay.
function QiratContainer() {
const [selectedIndex, setSelectedIndex] = useState<any>(2)
const [selectedPage, setSelectedPage] = useState<number>(1)
return (
<SafeAreaView >
<FlatList
data={quranData}
showsVerticalScrollIndicator={false}
renderItem={({ item, index }) => (
<View style={styles.pageContainer}>
<PageHeader surahName={item.firstSurahName} juzzNumber={item.juz} />
<View style={{ flex: 1 }}>
{item.ayahs.map((ayah: any, index: any) => (
<>
{ayah.name !== undefined &&
<SurahHeader ayah={ayah} />
}
<Text onPress={() => playAyah(ayah, index)} style={[styles.ayahStyle, selectedIndex === index && selectedPage === ayah?.page && styles.selectedAyah]}>{ayah?.text?.replace("بِسْمِ اللَّهِ الرَّحْمَٰنِ الرَّحِيمِ", "")}</Text>
</>
))}
</View>
<PageFooter pageNumber={item.page} />
</View>
)}
/>
</SafeAreaView>
)
function playAyah(ayah: any, index: any) {
console.log(ayah.audio)
//Setting the Selected Index and the specific page of that index to highlight the selected ayah...
console.log(index)
// console.log(ayah.page)
setSelectedIndex(index)
setSelectedAyah(ayah)
}
}
const styles = StyleSheet.create({
ayahStyle: {
fontSize: 24,
fontWeight: 'bold',
marginVertical: 8,
color: 'black'
},
selectedAyah: {
backgroundColor: 'grey'
},
pageContainer: {
width: width,
height: height - 20,
},
})
Following is my JSON Array that is used in the FlatList and Map
[
{
"juz": 1,
"page": 1,
"firstSurahName": "سورة الفاتحة",
"ayahs": [
{
"number": 1,
"name": "سورة الفاتحة",
"englishName": "Al-Faatiha",
"englishNameTranslation": "The Opening",
"revelationType": "Meccan",
"numberInPage": 0,
"ayahsNumber": 7
},
{
"number": 1,
"text": "بِسْمِ اللَّهِ الرَّحْمَٰنِ الرَّحِيمِ",
"numberInSurah": 1,
"juz": 1,
"page": 1,
"hizbQuarter": 1,
"ayahsNumber": 7,
"surahNumber": 1,
"numberInPage": 1,
"audio": "https://everyayah.com/data/ahmed_ibn_ali_al_ajamy_128kbps/001001.mp3"
},
{
"number": 2,
"text": "الْحَمْدُ لِلَّهِ رَبِّ الْعَالَمِينَ",
"numberInSurah": 2,
"juz": 1,
"page": 1,
"hizbQuarter": 1,
"ayahsNumber": 7,
"surahNumber": 1,
"numberInPage": 2,
"audio": "https://everyayah.com/data/ahmed_ibn_ali_al_ajamy_128kbps/001002.mp3"
},
{
"number": 3,
"text": "الرَّحْمَٰنِ الرَّحِيمِ",
"numberInSurah": 3,
"juz": 1,
"page": 1,
"hizbQuarter": 1,
"ayahsNumber": 7,
"surahNumber": 1,
"numberInPage": 3,
"audio": "https://everyayah.com/data/ahmed_ibn_ali_al_ajamy_128kbps/001003.mp3"
},
{
"number": 4,
"text": "مَالِكِ يَوْمِ الدِّينِ",
"numberInSurah": 4,
"juz": 1,
"page": 1,
"hizbQuarter": 1,
"ayahsNumber": 7,
"surahNumber": 1,
"numberInPage": 4,
"audio": "https://everyayah.com/data/ahmed_ibn_ali_al_ajamy_128kbps/001004.mp3"
},
{
"number": 5,
"text": "إِيَّاكَ نَعْبُدُ وَإِيَّاكَ نَسْتَعِينُ",
"numberInSurah": 5,
"juz": 1,
"page": 1,
"hizbQuarter": 1,
"ayahsNumber": 7,
"surahNumber": 1,
"numberInPage": 5,
"audio": "https://everyayah.com/data/ahmed_ibn_ali_al_ajamy_128kbps/001005.mp3"
},
{
"number": 6,
"text": "اهْدِنَا الصِّرَاطَ الْمُسْتَقِيمَ",
"numberInSurah": 6,
"juz": 1,
"page": 1,
"hizbQuarter": 1,
"ayahsNumber": 7,
"surahNumber": 1,
"numberInPage": 6,
"audio": "https://everyayah.com/data/ahmed_ibn_ali_al_ajamy_128kbps/001006.mp3"
},
{
"number": 7,
"text": "صِرَاطَ الَّذِينَ أَنْعَمْتَ عَلَيْهِمْ غَيْرِ الْمَغْضُوبِ عَلَيْهِمْ وَلَا الضَّالِّينَ",
"numberInSurah": 7,
"juz": 1,
"page": 1,
"hizbQuarter": 1,
"ayahsNumber": 7,
"surahNumber": 1,
"numberInPage": 7,
"audio": "https://everyayah.com/data/ahmed_ibn_ali_al_ajamy_128kbps/001007.mp3"
}
],
"number": 1,
"counter": 1
}
]
I always do this stuff by creating a state called "selected" and I save the ID of the selected .map child component in it.
In the .map children components I put classname={selected == id ? "cssSelected" : "cssNotSelected"}
And when I click on a .map child component: onClick={() => setSelected(id)}
Need help with chart js
ACTUALLY, I'M USING VUE-CHARTJS BUT IT'S JUST A WRAPPER
in the line chart on the left side, the number is increasing by 5(0, 5, 10, 15, etc) I want it to increase by 10 and also decrease the height of the chart so the aspect ratio is something like 16/9
also is it possible to make the left number say 5k+, 10k+, 15k+ instead of just 5, 10, 15
here's my code for the chart
<script>
import { Line } from 'vue-chartjs'
export default {
extends: Line,
data: () => ({
chartdata: {
labels: ['January', 'February', 'March', 'April', 'May','Jun'],
datasets: [
{
data: [12, 20, 27, 22, 14, 10],
borderColor: "#135193",
pointBackgroundColor: "#135193",
pointBorderColor: "#135193",
backgroundColor: 'rgba(255, 255, 255, 0)'
},
{
data: [3, 12, 17, 20, 30, 40],
borderColor: "#FF8811",
pointBackgroundColor: "#FF8811",
pointBorderColor: "#FF8811",
backgroundColor: 'rgba(255, 255, 255, 0)'
}
]
},
options: {
responsive: true,
legend: {
display: false
}
}
}),
mounted () {
this.renderChart(this.chartdata, this.options)
}
}
</script>
Yes, you can just use CSS to set the dimensions of the canvas and set maintainAspectRatio to false in the options, for the ticks you can use the tick callback:
const labels = ["Red", "Blue", "Yellow", "Green", "Purple", "Orange"];
const options = {
type: 'line',
data: {
labels,
datasets: [{
label: '# of Votes',
data: [12, 19, 3, 5, 2, 3],
borderColor: 'red',
backgroundColor: 'pink'
}]
},
options: {
maintainAspectRatio: false,
scales: {
yAxes: [{
ticks: {
callback: (val) => (`${val}K`)
}
}]
}
}
}
const ctx = document.getElementById('chartJSContainer').getContext('2d');
new Chart(ctx, options);
canvas {
max-height: 180px;
max-width: 320px;
}
<body>
<canvas id="chartJSContainer" width="600" height="400"></canvas>
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.9.4/Chart.js"></script>
</body>
Okay it turns out its as simple as wrapping the chart with a container and set height of that container as needed
I created a line graph with vue apexcharts and I'm trying to enable the selection tool in the toolbar (as explain here :https://apexcharts.com/docs/options/chart/toolbar/ )
But even if I set :
selection: true,
It doesn't appear on the graph.
Here is my vue component :
<template>
<div class="container">
<apexchart :type="typechart" height="350" :options="options" :series="series"></apexchart>
</div>
</template>
<script lang="ts">
import { Vue, Component } from "vue-property-decorator";
import VueApexCharts from "vue-apexcharts";
Vue.component("apexchart", VueApexCharts);
#Component({
components: { MyPlot }
})
export default class MyPlot extends Vue {
witdhgraph: string = "500";
typechart: string = "line";
options: any = {
chart: {
id: "vuechart-example",
toolbar: {
show: true,
offsetX: 0,
offsetY: 0,
tools: {
download: true,
selection: true,
zoom: true,
zoomin: true,
zoomout: true,
pan: true
}
},
autoSelected: "selection"
},
stroke: {
curve: "smooth"
},
colors: ["#00205b"],
xaxis: {
type: "numeric",
categories: [
0,
1,
2,
3,
4,
5,
6,
7,
8,
9,
10,
11,
12,
13,
14,
15,
16,
17,
18,
19,
20,
21,
22,
23,
24,
25,
26,
27,
28,
29,
30,
31,
32,
33,
34,
35,
36,
37,
38,
39,
40,
41,
42,
43,
44,
45,
46,
47,
48,
49
]
},
annotations: {
position: "back",
xaxis: [
{
x: 28,
x2: 32,
strokeDashArray: 1,
borderColor: "#c2c2c2",
fillColor: "#c2c2c2",
opacity: 0.3,
offsetX: 0,
offsetY: 0,
label: {
borderColor: "#c2c2c2",
borderWidth: 1,
borderRadius: 2,
text: "test ",
textAnchor: "middle",
position: "top",
orientation: "horizontal",
offsetX: 0,
offsetY: 0,
style: {
background: "#fff",
color: "#777",
fontSize: "12px",
fontWeight: 400,
fontFamily: undefined,
cssClass: "apexcharts-xaxis-annotation-label"
}
}
}
]
}
};
series: any = [
{
name: "series-1",
data: [
67,
93,
4,
39,
31,
62,
39,
4,
63,
51,
28,
73,
75,
80,
47,
17,
6,
55,
36,
18,
85,
64,
99,
21,
100,
14,
18,
12,
70,
44,
44,
87,
8,
37,
72,
67,
20,
7,
5,
33,
36,
41,
30,
30,
88,
31,
47,
77,
74,
35
]
}
];
}
</script>
You also need to enable
chart: {
selection: {
enabled: true
}
}
This was not mentioned in the docs which have been corrected now: https://apexcharts.com/docs/options/chart/toolbar/#selection
I previously used the label formatter to customise the Y-Axis labels in a chart, but I'm not sure how to do this using highcharts-vue because of scope.
See the following pseudo code;
export default {
data () {
return {
currencySymbol: '$',
title: 'My Chart',
points: [10, 0, 8, 2, 6, 4, 5, 5],
chartType: 'Spline',
chartOptions: {
chart: {
type: 'spline'
},
title: {
text: 'Sin chart'
},
yAxis: {
gridLineDashStyle: 'Dot',
labels: {
style: {
color: '#fff'
},
formatter: function () {
return this.currencySymbol + this.axis.defaultLabelFormatter.call(this)
}
},
series: [{
data: [10, 0, 8, 2, 6, 4, 5, 5],
color: '#6fcd98'
}]
}
}
}
In the full app, the currencySymbol property is updated in the response of an AJAX call.
Is there an elegant way of achieving this?
The most recommended way would be to use Computed Properties, JS Arrow function, and call Highcharts.Axis.prototype.defaultLabelFormatter.
First of all we need to move a whole chart configuration inside of a computed property, e.g called chartOptions. Then we just need to refactor the formatter function a bit, so that it would be arrow function, and create the variable with symbol defined in component data (!important). After that, the this keyword will indicate on the component object, and refer the symbol direcly by calling the variable created on the top of the function. I prepared the example, so please take a lok on it.
Live example: https://codesandbox.io/s/highcharts-vue-demo-icuzw
Code:
data() {
return {
currencySymbol: "$",
title: "My Chart",
points: [10, 0, 8, 2, 6, 4, 5, 5],
chartType: "Spline"
};
},
computed: {
chartOptions() {
var symbol = this.currencySymbol;
return {
chart: {
type: "spline"
},
title: {
text: "Sin chart"
},
yAxis: {
gridLineDashStyle: "Dot",
labels: {
style: {
color: "#000"
},
formatter: label => {
return (
symbol + Highcharts.Axis.prototype.defaultLabelFormatter.call(label)
);
}
}
},
series: [
{
data: [10, 0, 8, 2, 6, 4, 5, 5],
color: "#6fcd98"
}
]
};
}
}
Kind regards!
I would like to have three inputs which add data to each data array.
Input looks like this:
<input type="range" min="0" max="10" step="1" v-model="newData">{{ newData }}
<button #click="addData(newData, 'first')">Add</button>
and script
const app = new Vue({
el: '#app',
data: {
newData: 5,
dimensions: [
{
title: 'first',
data: [0, 2, 5, 9, 5, 10, 3, 5, 0, 0, 1, 8, 2, 9, 0]
},
{
title: 'second',
data: [1, 3, 8, 1, 2, 3, 3, 3, 5, 1, 9, 2, 4, 6, 0]
},
{
title: 'third',
data: [6, 1, 6, 1, 2, 5, 3, 9, 5, 1, 0, 2, 4, 4, 10]
}]
},
methods: {
addData() {
???
}
}
})
What kind of should my addData method be? I can't push to particular dimension. I just manage to add new one.
I'm glad if anyone can help me :)
Change your addData() method to accept two parameters, the data and the dimension to which to push. Then it should look like the following:
addData(mData, mDimension) {
this.dimensions.forEach((dimension) => {
if (dimension['title'] === mDimension) {
dimension['data'].push(parseInt(mData));
}
});
}
Don't forget to pass the data and dimension in your method call.