Fullcalendar select and unselect days - javascript

I am working with a fullcalendar and the idea is: When I click on a day, it is saved in the database. After It must load the calendar with the saved selections and according to of certain conditions It must allow the selection or unselection of the days.
My problem begin: when I select one day or multiple days and then I select another day, I lose the previous selection and I must keep it, as well as according to certain conditions enable or not a day to be selected or unselected.
I am using version 5.3.2.I tried solutions of other questions but I suppose because of the version they do not work
I would appreciate any suggestions.
This is my code:
document.addEventListener('DOMContentLoaded', function() {
var calendarEl = document.getElementById('calendar');
var calendar = new FullCalendar.Calendar(calendarEl, {
selectable: true,
unselectAuto: false,
headerToolbar: {
left: 'title',
right: 'prev,next',
},
dateClick: function(info) {
$(".fc-highlight").css("background", "green");
},
select: function(info) {
$(".fc-highlight").css("background", "green");
}
});
calendar.render();
});

Related

How can I create an event with addEvent with select: scroll?

I wanted to ask this question I had while messing about with fullcalendar. What I'm trying to achieve here is that a user has a calendar and has an option to select which dates they want by dragging their mouse and selecting. We can do this with selectable: true, but that's not the issue. The issue is I'm having trouble adding the event after the dates have been triggered.
The issue I think I'm having is that I can't properly define the start and end points. The code I saw in examples had components where you manually wrote the date but this is determined by scroll. So can anyone help?
This is my code.
var calendarEl = document.getElementById('calendar');
var calendar = new FullCalendar.Calendar(calendarEl, {
initialView: 'dayGridMonth',
themeSystem: 'Lumen',
selectable: 'true',
headerToolbar: {
left: 'prev,next today',
center: 'title',
right: 'dayGridMonth,timeGridWeek,timeGridDay'
},
select: function(start, end) {
var title = prompt("Event Content:");
var eventData;
if (title) {
eventData = {
title: title,
start: start,
end: end
};
}
if(eventData) {
calendar.addEvent({
title: title,
start: start,
end: end,
allDay: true
});
}
},
});
calendar.render();
});
I'll explain what's going on here. The select function asks for a prompt when you select dates, which works! But the if statements what I'm trying to do is write down the data in an array with eventData. But when I have calendar.addEvent, I'm struggling determining the start and end points. Instead of the bars popping up to signify an event, it does nothing.
Can anyone help? Thanks in advance, lemme know if you need more info.

FullCalendar : Ignore events during select

I've created a monthly calendar using fullCalendar month view.
On my calendar, I've displayed only one event per day. This event is used to display user's status (available, not available, busy...)
Because I'll always have 1 event per day, I've set eventLimit to true to avoid multiple events and because this event is about the entire day, I've also set editable to false to prevent events' drag & drop .
Here is my code:
$('#calendar').fullCalendar({
editable: false, // Prevent event drag & drop
events: '/json/calendar', // Get all events using a json feed
selectable: true,
eventLimit: true, // Only 1 event per day
header: {
left: 'prev,next',
center: 'title',
right: 'today'
},
select: function(start, end) {
window.location.hash = '#oModal-calendar'; // Display some popup with a form
end.subtract(1, 'days');
$('#checkboxButton').data('start', start);
$('#checkboxButton').data('end', end);
$('#calendar').fullCalendar('unselect');
}
});
I want my user to be able to select days directly from the calendar so I've set selectable: true in the calendar's option. However, I've got many feedback that "it didn't worked".
After some investigation, I found that users often click on the event block instead of the day.
Because events are draggable by default, a click on an event doesn't trigger the select and because I've set editable to false it doesn't do anything anymore.
This combination leads my users to think that there is a bug.
I would like the fullCalendar select to work like there was no event on the calendar. How can I achieve this behavior ?
Edit: here is a jsfiddle based on full calendar example and my code
I finally found the solution.
FullCalendar event's click is bind to the css class fc-day-grid-event.
It's possible to simply ignore it with one css line pointer-events: none;.
.fc-day-grid-event {
pointer-events: none;
}
Here is the Jsfiddle updated.
One way to do this would be to allow the user to click on event's through the eventClick callback, but when they click on them trigger the "select" function through FullCalendar's API $('#calendar').fullCalendar('select', start, end).
I updated your jsfiddle example with the relevant code.
HTML
<div id="calendar"></div>
Javascript
$('#calendar').fullCalendar({
editable: false, // Prevent event drag & drop
defaultDate: '2015-02-12',
events: [{
title: 'All Day Event',
start: '2015-02-01'
}, {
title: 'Lunch',
start: '2015-02-12T12:00:00'
}],
selectable: true,
eventLimit: true, // Only 1 event per day
header: {
left: 'prev,next',
center: 'title',
right: 'today'
},
select: function (start, end) {
var title = prompt('Event Title:');
var eventData;
if (title) {
eventData = {
title: title,
start: start,
end: end
};
$('#calendar').fullCalendar('renderEvent', eventData, true); // stick? = true
}
$('#calendar').fullCalendar('unselect');
},
eventClick: function(calEvent, jsEvent, view) {
var start = calEvent.start;
var end = calEvent.end;
$('#calendar').fullCalendar('select', start, end);
}
});

Add Italian holidays into fullcalendar

I use FullCalendar in my application and its working.
Now I need to change the color of Italian holidays into red. I did it for weekends but:
I don't know how to add holidays in calendar.
How can i change their color.
This is my code :
<script>
var calendar = $('#calendar').fullCalendar({
header: {
left: 'prev',
center: 'title',
right: 'next',
},
defaultView: 'month',
lang: 'it',
height: 600,
dayClick: function(date, jsEvent, view) {
// Changing BG color
$(this).css('background-color', 'green');
//Create modal here
$('#myModal').modal();
// Show Date in SPAN
$('#spnDate').html(date.format('DD/MM/YYYY'));
// Put Date value in a variable
$('#date').attr('value', date.format('DD/MM/YYYY'));
},
editable: true,
});
</script>
You should use another eventSource that provides the holidays. These events can have a property like holiday, that specify that the event is indeed a holiday.
Based on this holiday, you can change the background color of the day with eventRender
You will have to add the following code to var calendar = $('#calendar').fullCalendar({:
eventSources: [
{
url: 'fullcalendar/holidays' // url to get holiday events
}
// any other sources...
],
eventRender: function(event, element, view) {
// lets test if the event has a property called holiday.
// If so and it matches '1', change the background of the correct day
if (event.holiday == '1') {
var dateString = event.start.format("YYYY-MM-DD");
$(view.el[0]).find('.fc-day[data-date=' + dateString + ']')
.css('background-color', '#FAA732');
}
},
Your JSON object should look like this:
[{"title":"Christmas","start":"2014-12-25","holiday":"1"},{"title":"Another holiday","start":"2014-10-14","holiday":"1"}]

Fullcalendar does not Re-render Events when calendar is not visible

I am trying to update my calendar (fullcalendar.js) dynamically, however it is not rerendering the events when the calendar is not visible. I'm also using javascript tabs in my web app so by 'not visible' I mean that it is on a different tab. I've set up a jsfiddle to demonstrate the behavior:
http://jsfiddle.net/35kU5/10/
If you click the Add button while you are on the tab that contains the calendar, the events will be added and immediately visible.
However, if you click the Add button while you are on the second (empty) tab, then switch back to the first tab with the calendar, the 'added' events are not there until you force the calendar to repaint them by some action such as switching the view from week to month, or switching days/weeks/months, then going back.
I've tried the
$("#calendar").fullcalendar('refetchEvents');
$("#calendar").fullcalendar('rerenderEvents');
methods, neither of these solve the issue....Can anyone tell me what I'm doing wrong here? Or is this simply not possible?
Please see the Adam Shaw's full calendar selectable demo. It shows that new events will be added by selecting the date.
The full calendar starts with this code which includes the select event. I use ColdFusion and this is how I retrieve data from my database server:
$myCalendar = $('#myCalendar').fullCalendar({
header: {
left: 'prev,next today',
center: 'title',
right: ''
},
theme: true,
selectable: true,
selectHelper: true,
height: 500,
events:'events.cfc?method=getevents',
select: function(start, end, allDay) {
alert('select function chosen');
// set the dialog date to the date selected on the calendar
// commented out the dates below when we changed to datetimepicker
// $('#eventStart').val(start);
// $('#eventEnd').val(end);
// added the info below to support the datetimepicker
$('#eventStart').datetimepicker("setDate", new Date(start));
$('#eventEnd').datetimepicker("setDate", new Date(end));
//clear out the contents of the event title and the event id
$('#eventTitle').val('');
$('#ID').val('');
//default the value of all day to halfday value 1,
all day is valued at 2
$('#eventallday').val(1);
$('#calEventDialog').dialog('open');
},...........
Here is the code I use for the select function. This is placed at the bottom of my js code. I reference additional fields you may not use.
var title = $('#eventTitle');
var start = $('#eventStart');
var end = $('#eventEnd');
$('#calEventDialog').dialog({
resizable: false,
autoOpen: false,
title: 'Add Event',
width: 400,
buttons: {
Save: function() {
if ($('input:radio[name=allday]:checked').val() == "1") {
eventClass = "gbcs-halfday-event";
color = "#9E6320";
end.val(start.val());
}
else {
eventClass = "gbcs-allday-event";
color = "#875DA8";
}
if (title.val() !== '') {
$myCalendar.fullCalendar('renderEvent', {
title: title.val(),
start: start.val(),
end: end.val(),
allDay: true,
className: eventClass,
color: color
}, true // make the event "stick"
);
$('calendar').fullCalendar('renderEvent', {
title: ($("#eventTitle").val()),
start: ($("#eventStart").val()),
end:($("#eventEnd").val()),
allDay: ($("#allday").val()),
color:($("background-Color").val())
}, true // make the event "stick"
);
$.ajax({
url: 'events.cfc?method=add_events',
data: 'title='+ ($("#eventTitle").val())+
'&start='+ ($("#eventStart").val()) +'
&end='+ ($("#eventEnd").val()) +
'&id='+ 0 ,
type: "POST",
success: function(json) {
alert('Updated Successfully');
}
})
}
$myCalendar.fullCalendar('unselect');
$(this).dialog('close');
},
Cancel: function() {
$(this).dialog('close');
}
}
});
});// JavaScript Document
I hope this points you in the right direction. Thanks for posting your question. You showed me how to use tabs!.

How to set full calendar to a specific start date when it's initialized for the 1st time?

I would like to set the initial month to an arbitrary month when I call the function to display the calendar.
Say for example the user selects a date last june (June 2011) somewhere else and I want fullcalendar to show up with a month display of April before (April 2010). And yes, this is just to make a case, not to make sense ;-) )
I tried to call 'gotodate' before I then subsequently call the display function but this doesn't seem to work
$('#calendar').fullCalendar( 'gotoDate', currentdate);
$('#calendar').fullCalendar({
header: {left: 'prevYear,prev,today,next,nextYear',
center: 'title', right: 'month,basicWeek,basicDay' etc...}
Could someone eventually please provide an example how to do this properly?
You should use the options 'year', 'month', and 'date' when initializing to specify the initial date value used by fullcalendar:
$('#calendar').fullCalendar({
year: 2012,
month: 4,
date: 25
}); // This will initialize for May 25th, 2012.
See the function setYMD(date,y,m,d) in the fullcalendar.js file; note that the JavaScript setMonth, setDate, and setFullYear functions are used, so your month value needs to be 0-based (Jan is 0).
UPDATE: As others have noted in the comments, the correct way now (V3 as of writing this edit) is to initialize the defaultDate property to a value that is
anything the Moment constructor accepts, including an ISO8601 date
string like "2014-02-01"
as it uses Moment.js. Documentation here.
Updated example:
$('#calendar').fullCalendar({
defaultDate: "2012-05-25"
}); // This will initialize for May 25th, 2012.
UPDATE: in the V5, defaultDate parameter has been renamed to initialDate.
You have it backwards. Display the calendar first, and then call gotoDate.
$('#calendar').fullCalendar({
// Options
});
$('#calendar').fullCalendar('gotoDate', currentDate);
As per machineAddict's comment, as of version 2 and later, year, month and day have been replaced by defaultDate, which is a Moment, supporting constructors such as an ISO 8601 date string or a Unix Epoch.
So e.g. to initialize the calendar with a given date:
$('#calendar').fullCalendar({
defaultDate: moment('2014-09-01'),
...
});
You can just pass a Date object:
For current date:
$('#calendar').fullCalendar({
defaultDate: new Date()
});
For specific date '2016-05-20':
$('#calendar').fullCalendar({
defaultDate: new Date(2016, 4, 20)
});
For v5 please use initialDate instead of defaultDate. Simply renamed option
eg
var calendarEl = document.getElementById('calendar');
var calendar = new FullCalendar.Calendar(calendarEl, {
...
initialDate: '2020-09-02',
...
});
I've had better luck with calling the gotoDate in the viewRender callback:
$('#calendar').fullCalendar({
firstDay: 0,
defaultView: 'basicWeek',
header: {
left: '',
center: 'basicDay,basicWeek,month',
right: 'today prev,next'
},
viewRender: function(view, element) {
$('#calendar').fullCalendar( 'gotoDate', 2014, 4, 24 );
}
});
Calling gotoDate outside of the callback didn't have the expected results due to a race condition.
In version 2.1.1 this works :
$('#calendar').fullCalendar({
// your calendar settings...
});
$('#calendar').fullCalendar('gotoDate', '2014-05-01');
Documentation about moment time/date format : http://fullcalendar.io/docs/utilities/Moment/
Documentation about the upgrades in version 2 : https://github.com/arshaw/fullcalendar/wiki/Upgrading-to-v2
This can be used in v5.3.2 to goto a date after initialization
calendar.gotoDate( '2020-09-12' );
eg on datepicker change
var calendarEl = document.getElementById('calendar');
var calendar = new FullCalendar.Calendar(calendarEl, {
...
initialDate: '2020-09-02',
...
});
$(".date-picker").change(function(){
var date = $(this).val();
calendar.gotoDate( date );
});
If you don't want to load the calendar twice and you don't have a version where defaultDate is implemented, do the following:
Change the following method:
function Calendar(element, options, eventSources) {
...
var date = new Date();
...
}
to:
function Calendar(element, options, eventSources) {
...
var date = options.defaultDate ? options.defaultDate : new Date();
...
}
document.addEventListener('DOMContentLoaded', function () {
var calendarEl = document.getElementById('calendar');
var calendar = new FullCalendar.Calendar(calendarEl, {
headerToolbar: {
left: 'prev,next today',
center: 'title',
right: 'dayGridMonth,timeGridWeek,timeGridDay,listWeek'
},
initialView: 'dayGridMonth',
initialDate: '2020-09-12',
navLinks: true, // can click day/week names to navigate views
selectable: true,
nowIndicator: true,
dayMaxEvents: true, // allow "more" link when too many events
editable: true,
selectable: true,
businessHours: true,
dayMaxEvents: true, // allow "more" link when too many events
events: [{
title: 'All Day Event',
start: '2020-09-01',
}]
});
calendar.render();
});
Just simply add that particular date to initialDate key.

Categories