221 lines
5.6 KiB
JavaScript
221 lines
5.6 KiB
JavaScript
class BBTimelineBackgroundCanvas extends BBTimelineCanvas {
|
|
constructor(parentEl, el) {
|
|
super(parentEl, el);
|
|
}
|
|
|
|
initialiseOptions() {
|
|
super.initialiseOptions();
|
|
|
|
const a = this;
|
|
|
|
a.Options = {
|
|
Axis: {
|
|
LineColour1: "#000000",
|
|
LineWidth: 1,
|
|
Font: "8pt Arial",
|
|
LabelColour: "#000000",
|
|
LabelSpacing: 6
|
|
},
|
|
XAxis: {
|
|
NoPartPerDay: 4,
|
|
HourLineSpace: 6,
|
|
HourLineHeight: 10,
|
|
HourLineColour: "#EAEAEA",
|
|
DayLineHeight: 20,
|
|
DayLineColour: "#9E9E9E",
|
|
Position: 'bottom'
|
|
}
|
|
};
|
|
}
|
|
|
|
initialiseComponents() {
|
|
super.initialiseComponents();
|
|
|
|
const a = this;
|
|
|
|
a.Invalidate();
|
|
}
|
|
|
|
|
|
get GraphRectangle() {
|
|
const a = this;
|
|
|
|
if (a.Options.XAxis.Position == 'top') {
|
|
return {
|
|
X: a.ClientRectangle.X,
|
|
Y: (a.ClientRectangle.Y + a.XAxisHeight),
|
|
W: a.ClientRectangle.W,
|
|
H: (a.ClientRectangle.H - a.XAxisHeight)
|
|
};
|
|
} else {
|
|
return {
|
|
X: a.ClientRectangle.X,
|
|
Y: a.ClientRectangle.Y,
|
|
W: a.ClientRectangle.W,
|
|
H: (a.ClientRectangle.H - a.XAxisHeight)
|
|
};
|
|
}
|
|
}
|
|
|
|
get XAxisHeight() {
|
|
const a = this;
|
|
const labelSize = a.measureText(a.Options.Axis.Font, "0");
|
|
|
|
return labelSize.H + a.Options.Axis.LabelSpacing + (a.Options.XAxis.DayLineHeight * 2);
|
|
}
|
|
|
|
get XAxisPositions() {
|
|
const a = this;
|
|
const endPosX = (a.GraphRectangle.X + a.GraphRectangle.W);
|
|
|
|
let result = [];
|
|
let x = a.GraphRectangle.X;
|
|
let date = a.Parent.ConvertToDate(a.Parent.ShowDate);
|
|
|
|
// Rollback one day
|
|
date.setDate(date.getDate() - 1);
|
|
|
|
while (true) {
|
|
if (x >= endPosX) {
|
|
break;
|
|
}
|
|
|
|
result.push({
|
|
Date: a.Parent.DateToInternalString(date),
|
|
X: x
|
|
});
|
|
|
|
x += (a.Options.XAxis.HourLineSpace * a.Options.XAxis.NoPartPerDay);
|
|
date.setDate(date.getDate() + 1);
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
|
|
Invalidate() {
|
|
const a = this;
|
|
|
|
a.Clear();
|
|
|
|
a.drawAxis();
|
|
a.drawXAxisTicks();
|
|
a.drawXAxisLabels();
|
|
|
|
if (a.Parent.Debug) a.drawRectangle(a.ClientRectangle, "red");
|
|
if (a.Parent.Debug) a.drawRectangle(a.GraphRectangle, "red");
|
|
}
|
|
|
|
|
|
drawAxis() {
|
|
const a = this;
|
|
|
|
a.CTX.beginPath();
|
|
|
|
if (a.Options.XAxis.Position == 'top') {
|
|
a.CTX.moveTo(a.GraphRectangle.X, (a.GraphRectangle.Y + a.GraphRectangle.H));
|
|
a.CTX.lineTo(a.GraphRectangle.X, a.GraphRectangle.Y);
|
|
a.CTX.lineTo((a.GraphRectangle.X + a.GraphRectangle.W), a.GraphRectangle.Y);
|
|
} else {
|
|
a.CTX.moveTo(a.GraphRectangle.X, a.GraphRectangle.Y);
|
|
a.CTX.lineTo(a.GraphRectangle.X, (a.GraphRectangle.Y +a.GraphRectangle.H));
|
|
a.CTX.lineTo((a.GraphRectangle.X + a.GraphRectangle.W), (a.GraphRectangle.Y + a.GraphRectangle.H));
|
|
}
|
|
|
|
a.CTX.lineWidth = a.Options.Axis.LineWidth;
|
|
a.CTX.strokeStyle = a.Options.Axis.LineColour1;
|
|
a.CTX.stroke();
|
|
}
|
|
|
|
drawXAxisLabels() {
|
|
const a = this;
|
|
const labelSize = a.measureText(a.Options.Axis.Font, "0");
|
|
|
|
let posY = 0;
|
|
let posDayY = 0;
|
|
let posMonthY = 0;
|
|
|
|
if (a.Options.XAxis.Position == 'top') {
|
|
posY = (a.GraphRectangle.Y - a.Options.Axis.LineWidth) - 2;
|
|
posDayY = (posY - (labelSize.H + a.Options.XAxis.DayLineHeight));
|
|
posMonthY = (posDayY - (labelSize.H + a.Options.Axis.LabelSpacing));
|
|
} else {
|
|
posY = (a.GraphRectangle.Y + a.GraphRectangle.H) + a.Options.Axis.LineWidth;
|
|
posDayY = (posY + a.Options.XAxis.DayLineHeight);
|
|
posMonthY = (posDayY + labelSize.H + a.Options.Axis.LabelSpacing);
|
|
}
|
|
|
|
a.XAxisPositions.forEach(function(e, i) {
|
|
const date = a.Parent.ConvertToDate(e.Date);
|
|
|
|
let writeLabel = false;
|
|
if ((i == 0)) {
|
|
// Don't label first entry if too close to the next month
|
|
if (date.getDate() < 25) {
|
|
writeLabel = true;
|
|
}
|
|
} else if (date.getDate() == 1) {
|
|
writeLabel = true;
|
|
}
|
|
|
|
// if (i == 0) {
|
|
// // Don't write first date
|
|
// } else {
|
|
// Write date (dd)
|
|
a.drawText(e.X, posDayY, a.Parent.DateToString(date, "dd"), a.Options.Axis.Font, a.Options.Axis.LabelColour, "center");
|
|
// }
|
|
|
|
// Write month (MMMM) on first of the month
|
|
if (writeLabel) {
|
|
a.drawText(e.X, posMonthY, a.Parent.DateToString(date, "MMMM yyyy"), a.Options.Axis.Font, a.Options.Axis.LabelColour, "left");
|
|
}
|
|
});
|
|
}
|
|
|
|
drawXAxisTicks() {
|
|
const a = this;
|
|
|
|
let startPosX = a.GraphRectangle.X;
|
|
const endPosX = (a.GraphRectangle.X + a.GraphRectangle.W);
|
|
let posY = 0;
|
|
let posDayY = 0;
|
|
let posHourY = 0;
|
|
|
|
if (a.Options.XAxis.Position == 'top') {
|
|
posY = (a.GraphRectangle.Y - a.Options.Axis.LineWidth);
|
|
posDayY = (posY - a.Options.XAxis.DayLineHeight);
|
|
posHourY = (posY - a.Options.XAxis.HourLineHeight);
|
|
} else {
|
|
posY = (a.GraphRectangle.Y + a.GraphRectangle.H) + a.Options.Axis.LineWidth;
|
|
posDayY = (posY + a.Options.XAxis.DayLineHeight);
|
|
posHourY = (posY + a.Options.XAxis.HourLineHeight);
|
|
}
|
|
|
|
let i = 0;
|
|
|
|
while (true) {
|
|
if (startPosX >= endPosX) {
|
|
break;
|
|
}
|
|
|
|
a.CTX.beginPath();
|
|
a.CTX.moveTo(startPosX, posY);
|
|
|
|
if ((i % a.Options.XAxis.NoPartPerDay) == 0) {
|
|
a.CTX.lineTo(startPosX, posDayY);
|
|
a.CTX.strokeStyle = a.Options.XAxis.DayLineColour;
|
|
} else {
|
|
a.CTX.lineTo(startPosX, posHourY);
|
|
a.CTX.strokeStyle = a.Options.XAxis.HourLineColour;
|
|
}
|
|
|
|
a.CTX.lineWidth = a.Options.Axis.LineWidth;
|
|
a.CTX.stroke();
|
|
|
|
startPosX += a.Options.XAxis.HourLineSpace;
|
|
|
|
i++;
|
|
}
|
|
}
|
|
|
|
} |