Add another event source FullCalendar? - javascript

I try to add another event source on my FullCalendar. First, I get all events from manual function that I create own and I render all events using renderEvent function. But, I got error when I try to add another event source. So, I want to add holidays feature. I create another event source to get holidays date. That event was success to showed in my FullCalendar. But there is weird thing.
Example : If I have range of my holiday date, such as start : 2019/02/26 - end : 2019/02/28. The event content length doesn't 26 until 28, but start from 26 until 27.
What it's wrong? This is my code for to get all events.
// Get Agenda Data
function getEvents(datas) {
$("input[name=unitAgenda]").attr("value",
$("select[name=unit]").val());
var reUnit = datas.replace("- ","");
$('.calendar').fullCalendar('removeEvents');
$('.calendar').fullCalendar('refetchEvents');
$.ajax({
url: 'agendakerja/kalender/get_events',
dataType: 'JSON',
data: { unit: reUnit },
success: function(data) {
$.each(data["events"], function (index, event) {
$('.calendar').fullCalendar('renderEvent', event, true);
});
}
});
//passing unit name to function
global = reUnit;
}
And this is my code for get holidays date.
eventSources: [
{ url: 'agendakerja/kalender/get_holidays' }
]
Please help me!

Related

How do you Get and Add events to a specific source?

I was successfully able to specify multiple sources: My SQL server source, and an empty array to hold any user-generated events userAddedEvents = []. The idea was that I could use this array later to "save" new events to my server.
var userAddedEvents = []; //container for event objects that will hold user-generated content
var calendar = new FullCalendar.Calendar(calendarEl, {
eventSources: [
{
events: function (fetchInfo, successCallback, failureCallback) {
$.ajax({
url: url,
type: 'post',
contentType: "application/json; charset=utf-8", //include fetchInfo in request body instead of form-data
dataType: "json",
data: JSON.stringify(fetchInfo), //the fetchInfo object must be stringified
success: function (data) {
events = $.merge([], data.events);
successCallback(events);
}
});
}
}, //end server source
{
id: 'userAddedEvents',
events: userAddedEvents
} //end local array source
]
});
So, here's me trying to add an event to my userAddedEvents source...
select: function (info) {
// https://fullcalendar.io/docs/select-callback
console.log(info)
console.log('selected ' + info.startStr + ' to ' + info.endStr)
calendar.addEvent({
start: info.startStr,
end: info.endStr,
rendering: 'background', //v4 and v5 use different terminology
color: '#ff9f89',
selected: true, //custom, extended property
}, userAddedEvents);
calendar.unselect(); //clear the current selection
},
Anyway, long story short... when I try to dump out the results of userAddedEvents, it's empty, although, I do see new content on my calendar.
==UPDATED== with example included... I added a custom button where I attempt to get content from the userAddedEvents array.
Alternatively (also shown in the example), I've had success getting ALL events with calendar.getEvents(), then using $.grep to filter some specific property or extended property. Ultimately though, I suppose I'm trying to use a "temporary event source" for the sake of convenience -- I can act upon the userAddedEvents array, stringify it, empty it, etc. I do not know how to getEvents for a specific source object.
customButtons: {
getUserCreatedEvents: {
text: 'Get User Events',
click: function () {
console.log(calendar.getEventSources()); //both event sources are listed
console.log(calendar.getEventSourceById(userAddedEvents)); //missing the id in output {calendar, id, internalEventSource, url}
console.log(calendar.getEventSourceById('userAddedEvents')); //has the the id in output {calendar, id, internalEventSource, url}
console.log(userAddedEvents) //the array is empty
/*
events = calendar.getEvents();
// console.log(events)
var filteredResultsGREP = $.grep(events, function (event) {
return event.rendering === 'background';
});
*/
/*
https://fullcalendar.io/docs/Event-toPlainObject (version 5 only)
*/
// this WILL show any events added based on the property specified
// console.log(filteredResultsGREP);
}
}
}
How do I get the events that are new? I want to hold all user-created events before I send them to SQL for processing.
Firstly, apologies for totally forgetting about this question, having started to help with it.
After some digging it looks like you can't get the raw events for an individual event source, which is a bit annoying.
So I think actually your simplest approach is just to add the events to your separate array, without worrying about the structure in fullCalendar. Then you can just send that list to the server when you want to save them.
select: function (info) {
var evt = {
start: info.startStr,
end: info.endStr,
rendering: "background", //v4 and v5 use different terminology
color: "#ff9f89",
selected: true //custom, extended property
};
calendar.addEvent(evt);
userAddedEvents.push(evt);
calendar.unselect(); //clear the current selection
},
Demo: https://codepen.io/ADyson82/pen/abdVVNM
The only extra complication you might have is if you allow events to be dragged or resized (or otherwise edited) after they've been added, you'll have to sync that with the separate array, which is a bit of extra work.

FullCalendar event duplicate after the first even

when I select an event it's ok, after I get duplicated, quadrupled, etc.
Why? I don't undertastand why it's
This is my code in javascript
$('#calendar').fullCalendar({
snapDuration: '00:30:00',
selectable: true,
aspectRatio: 1.8,
scrollTime: '08:00', // undo default 6am scrollTime
resources: '{!! route('fullcalendar.roomall') !!}',
events: '{!! route('fullcalendar.bookingall') !!}',
select: function( start, end, jsEvent, view, resourceId) {
$('#event-modal').find('input[name=title]').val('');
// set values in inputs
$('#event-modal').find('input[name=evtStart]').val(
start.format('YYYY-MM-DD HH:mm:ss')
);
$('#event-modal').find('input[name=evtEnd]').val(
end.format('YYYY-MM-DD HH:mm:ss')
);
// show modal dialog
$('#event-modal').modal('show');
/*
bind event submit. Will perform a ajax call in order to save the event to the database.
When save is successful, close modal dialog and refresh fullcalendar.
*/
$("#event-modal").on('click','.save', function(event) {
event.preventDefault();
var id = resourceId['id'];
var roomName = resourceId['title'];
var title = $('#title').val();
var start = $('#evtStart').val();
var end = $('#evtEnd').val();
$('#event-modal').modal('hide');
$.ajax({
url: '{{ route('events.save') }}',
data: $("#event-modal").serialize(),
type: 'post',
dataType: 'json',
data: {
'_token': $('input[name=_token]').val(),
'title': title,
'start': start,
'end': end,
'roomId': id,
'roomName': roomName
},
success: function(response) {
callback(response);
$("#calendar").fullCalendar( 'refetchEvents');
}
});
});
},
});
when I select an event it's ok, after I get duplicated, quadrupled, etc.
Why? I don't undertastand why it's
The problem is because you keep on adding more and more "click" event handlers to the "save" button every time the "select" callback runs.
$("#event-modal").off("click", ".save").on('click','.save', function(event) {
should fix your issue (.off() removes the specified event handlers from the element).
Questions of this nature get asked all the time. You need to understand that adding an event handler to an element doesn't remove the previous ones, they can all exist together, and they all will continue to respond to events until you remove them.

How to prevent event overlapping when updating existing events in Full Calendar?

I have used eventOverlap: false, and selectOverlap: false, to prevent the user from overlapping events. However, I am trying to prevent the user from overlapping existing events.
In my full calendar the user can click on an event, which opens a pop up dialog and allows the user to update the date/time of the selected event. However, the user is able choose a date/time where an event is already booked. Therefore, I want to have a validation on the Save button that checks if the updated date/time has an event or not before any changes are made. These two screen shots show this problem graphically.
1. Shows that event time is being updated. 2. Shows the event is overlapping after it has been updated
var events = []; //global array where all the events are stored
function FetchEventAndRenderCalendar() {
//fetch info from database and add it to the events array
events = [];
$.ajax({
type: "GET",
url: "/SessionScheduler/GetEvents",
success: function (data) {
$.each(data, function (i, v) {
events.push({
id: v.Id,
title: v.Title,
description: v.Description,
start: moment(v.StartDate),
end: moment(v.EndDate),
tutorName: v.TutorName,
color: v.ThemeColour
});
})
//then display the calendar with the events
GenerateCalender(events);
},
error: function (error) {
alert('failed');
}
})
}
This is the Save button where I want to have a validation check. I have looked at this solution but this didn't work for me
$('#btnSave').click(function () {
//validation
var selectedStartDate = moment(document.getElementById('txtStart').value.trim(), "DD/MM/YYYY HH:mm a").toDate();
var selectedEndDate = moment(document.getElementById('txtEnd').value.trim(), "DD/MM/YYYY HH:mm a").toDate();
if (selectedStartDate > selectedEndDate) {
alert('Invalid end date');
return;
}
if (selectedStartDate.getTime() == selectedEndDate.getTime()) {
alert('Start/End dates can not be the same');
return;
}
var data = {
Id: $('#hdEventID').val(),
Title: $('#txtTitle').val(),
StartDate: $('#txtStart').val(),
EndDate: $('#txtEnd').val(),
Description: $('#txtDescription').val(),
TutorName: $('#txtTutorName').val(),
ThemeColour: $('#ddThemeColour').val()
}
SaveEvent(data);
})
SaveEvent function: Which saves the data
function SaveEvent(data) {
if (selectedEvent != null && confirm("Are you sure?")) {
$.ajax({
type: "POST",
url: '/SessionScheduler/SaveEvent',
data: data,
success: function (data) {
if (data.status) {
//refresh the calendar if the status is true else its failed
FetchEventAndRenderCalendar();
$('#myModalSave').modal('hide'); //hide modal dialog pop window
}
},
error: function () {
alert('Failed');
}
})
}
}
This function will check whether the event passed in overlaps with any other events currently displayed on the calendar.
Note this relies on the events having unique id properties, so it doesn't check itself. It also cannot, by its nature, check any events not currently displayed on the calendar, because fullCalendar doesn't return those from its clientEvents method. You should check again on the server-side before accepting the modification into your database.
//check whether or not the calendar event passed in overlaps with an existing event in the current (client-side) calendar data
//the first parameter should be the event which is being tested
//the second parameter should be a jQuery object wrapping the calendar HTML element
function isCalendarEventOverlapping(event)
{
var evts = cal.fullCalendar('clientEvents');
for (i in evts)
{
if (evts[i].id != event.id)
{
if (event.start.isBefore(evts[i].end) && event.end.isAfter(evts[i].start))
{
return true;
}
}
}
return false;
}
I did some search about this problem.
FullCalender check if selection days has an event?
How to check event is already exist for a day - fullcalendar
How to avoid events duplication on fullcalendar?
Can I prevent events with conflict time?
Everytime, they get all the events from the FC memory, and iterate over them, for searching conflict time.
Unfortunately, there is no simple solution for that.
My suggestions:
You should to make a ajax call before every modification, where your server checks the conflict (if you store the events on the server side)
If your server doesn't store your events, then you have to iterate all the events in the client side, in order to find a conflict.

My code for Full Calendar works in Chrome, Firefox but why is this breaking in Safari?

This code works in Chrome and Firefox, but on Safari the calendar does not even load on the screen.
Basically I need to pull event data automatically from another website, and then feed it into Full Calendar. The format that the other website sends event details is an array with properties "name" and "time." Full Calendar takes event details in the form of an array called "events" with properties "title" and "start." So with the code below, I tried to rename the array and the properties to follow Full Calendar's format. And then inside the code rendering the calendar, I call that array "events". It works in Chrome and Firefox, but on Safari it does not and the console is telling me that it is expecting a ":" after property name "events"? How can I get this to work with Safari?
var getEvents = function() {
$.ajax({
type: "GET",
url: API_ENDPOINT,
dataType: 'jsonp',
success: displayEvents
});
};
var displayEvents = function(data) {
var events = data.results;
function changeData(events) {
var start;
for (var i=0; i < events.length; i++) {
if (events[i].hasOwnProperty("name")) {
events[i]["title"] = events[i]["name"];
delete events[i]["name"];
}
if (events[i].hasOwnProperty("time")) {
events[i]["start"] = events[i]["time"];
delete events[i]["time"];
}
if (events[i].hasOwnProperty("start")) {
start = events[i].start;
events[i].start = new Date(start);
}
}
}
changeData(events);
console.log(events);
$('#calendar').fullCalendar({
events
});
}
getEvents();
Just change $('#calendar').fullCalendar({ events });
to $('#calendar').fullCalendar({ events: events });
where the first events is the property name of the Object you're passing to the $.fullCalendar() function, and the second events is the value, ie your previously defined variable.

FullCalendar: refetchEvents call causes to all meetings to blink during re-rendering

I play with fullCalendar and I use refetchEvents:
$('#calendar').fullCalendar('refetchEvents');
It works properly and this command calls events method with callback
events: function (start, end, timezone, callback) { /* ... */ }
however it first remove all meetings from calendar and after - renders new ones. This approach causes to all table to blink (different from google behaviour).
Is there any other way to render meetings without clear-add?
Seems like I need to add only deltas that makes work too hard, messy and not stable
Thanks,
My suggestion is to do the ajax request first (where you initially put .fullCalendar('refetchEvents')), and if it succeeds, then call refetchevents. The code will look something like this:
var events = [];
$.get('/events/get', function(result){
events = result;
});
$('#calendar').fullCalendar({
events: function (start, end, timezone, callback) {
callback(events);
}
});
Add this in your ajax parameter :
async:false,
$.ajax({
url: calendar_url + '&start'+start.unix()+'&end='+end.unix(),
dataType: 'JSON',
async:false,
success: function(response) {
}
})
Use below approach instead of refetchEvents so it's not blinking.
var events = {
url: '/getEVents',
type: 'GET',
}
$('#calendar').fullCalendar('removeEventSource', events);
$('#calendar').fullCalendar('addEventSource', events);

Categories

Resources