I am trying to create a single month Calendar Component where the starting date is flexible, therefore the first day of the month can start during any weekday (ie M, T, W). I manage to create the grid, but I am struggling to get start flexibility. Can anyone help me to figure it out?
Thank you in advance.
Logic - Image
Render result - Image
JavaScript
$(function(){ var $container = $("#container"); var boxCount = 31, rowLength = 7, boxSize = 414 / 7; for(var i=0; i<boxCount; i++){ var $box = $("<div/>") .attr("class", "box") .css({ left: i%rowLength * boxSize + "px", top: Math.floor(i/rowLength) * boxSize }) .appendTo($container); } });
#container{ position: relative; } .box{ position: absolute; width: 50px; height: 50px; background: #eee; border-radius: 1px; box-shadow: 0 1px 2px rgba(0, 0, 0, 0.1); }
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> <div id="container"></div>
ReactJS
import * as React from 'react'
import { PropertyControls, ControlType } from 'framer'
// Define type of property
interface Props {
width: number
height: number
text: string
number: number
}
export class Calendar extends React.Component<Props> {
// Set default properties
static defaultProps = {
text: 'January',
number: 31,
}
// Items shown in property panel
static propertyControls: PropertyControls = {
text: { type: ControlType.String, title: 'Month' },
number: {
type: ControlType.Number,
title: 'Number',
min: 0,
max: 100,
step: 1,
displayStepper: true,
},
}
render() {
const createCalendar = (month, number, width, height) => {
var rowLength = 7,
boxWidth = width / rowLength,
boxHeight = height / rowLength,
times = 2
// const leftPos = i => {
// console.log((i % rowLength) * boxWidth)
// var offset = boxWidth * times
// if (i < rowLength - times) {
// var offset = boxWidth * times
// return (i % rowLength) * boxWidth + offset
// } else if (i >= 5 && i <= 6) {
// return (i % (rowLength - times)) * boxWidth
// } else if (i >= rowLength) {
// return (i % rowLength) * boxWidth + offset
// }
// }
// LOGIC
const leftPos = i => {
console.log((i % rowLength) * boxWidth)
var offset = boxWidth * times
if (i < rowLength - times) {
var offset = boxWidth * times
return (i % 5) * boxWidth + offset
} else {
return (i % 5) * boxWidth
}
}
const topPos = i => {
return Math.floor(i / (rowLength - times)) * boxHeight
}
const res = [ ...Array(number) ].map((_, i) => {
return (
<div
style={{
position: 'absolute',
width: boxWidth,
height: boxHeight,
// left: (i % rowLength) * boxWidth + boxWidth * 2,
left: leftPos(i),
// top: Math.floor(i / rowLength) * boxHeight,
top: topPos(i),
display: 'flex',
alignItems: 'center',
justifyContent: 'center',
textAlign: 'center',
color: '#8855FF',
background: 'rgba(136, 85, 255, 0.1)',
overflow: 'hidden',
}}
key={i}
>
{i + 1}
</div>
)
})
return (
<div
style={{
display: 'flex',
flexDirection: 'column',
}}
>
<div
style={{
display: 'flex',
alignItems: 'center',
justifyContent: `center`,
textAlign: 'center',
width: '100%',
height: boxHeight,
color: '#8855FF',
background: 'rgba(136, 85, 255, 0.1)',
}}
>
{month}
</div>
<div style={{ position: 'relative' }}>{res}</div>
</div>
)
}
return createCalendar(this.props.text, this.props.number, this.props.width, this.props.height)
}
}
You can try a library like date-fns: https://date-fns.org/docs/Getting-Started
Start your month with dateFns.startOfWeek(dateFns.startOfMonth(new Date()))
(or start of the week of the date you want) and hide the other days with css: https://codepen.io/pen/ZwrQZg
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.