Django añadiendo evento al mes de un tema de Calender
Estoy trabajando en un proyecto Calender, para el ya tiene el código en línea. si reservas un evento damos una fecha de inicio y fecha de finalización. Si envía el formulario el evento se guardará en el calendario sólo en el momento de inicio, el evento es visible en la plantilla de calendario, Mi requisito es que Ahora quiero modificar el calendario para que todas las fechas que coincidan con la fecha de inicio y la fecha de finalización deben mostrar el evento.
Ejemplo: he dado la fecha de inicio del 20 de diciembre de 2020 y la fecha final del 24 de diciembre.. así que en el calendario, el mismo evento debe mostrar el 20,21,22,23,24... días
Creo que aquí estoy insertando los datos en la plantilla Html, necesito pasar el tiempo final aquí que no sé
events_per_day = events.filter(start_time__day=day)
d = ''
for event in events_per_day:
d += f' {event.get_html_url} '
Tried alot pero sin éxito
A continuación se muestra el código:
Modelos
from django.db import models
from django.urls import reverse
class Event(models.Model):
title = models.CharField(max_length=200)
description = models.TextField()
start_time = models.DateTimeField()
end_time = models.DateTimeField()
@property
def get_html_url(self):
url = reverse('cal:event_edit', args=(self.id,))
return f' {self.title} '}
utils,py
from datetime import datetime, timedelta
from calendar import HTMLCalendar
from itertools import groupby
from django.utils.html import conditional_escape as esc
from datetime import date
from .models import Event
class Calendar(HTMLCalendar):
def __init__(self, year=None, month=None):
self.year = year
self.month = month
super(Calendar, self).__init__()
# formats a day as a td
# # filter events by day
def formatday(self, day, events):
events_per_day = events.filter(start_time__day=day)
d = ''
for event in events_per_day:
d += f' {event.get_html_url} '
if day != 0:
return f"{day} {d}
"
return ' '
# formats a week as a tr
def formatweek(self, theweek, events):
week = ''
for d, weekday in theweek:
week += self.formatday(d, events)
return f' {week} '
# formats a month as a table
# filter events by year and month
def formatmonth(self, withyear=True):
events = Event.objects.filter(start_time__year=self.year, start_time__month=self.month)
cal = f'\n'
cal += f'{self.formatmonthname(self.year, self.month, withyear=withyear)}\n'
cal += f'{self.formatweekheader()}\n'
for week in self.monthdays2calendar(self.year, self.month):
cal += f'{self.formatweek(week, events)}\n'
return cal
Vistas. py
# cal/views.py
import calendar
from django.shortcuts import render, get_object_or_404
from django.http import HttpResponse, HttpResponseRedirect
# Create your views here.
# cal/views.py
from datetime import datetime, date, timedelta
from django.shortcuts import render
from django.http import HttpResponse
from django.views import generic
from django.utils.safestring import mark_safe
from .forms import EventForm
from .models import *
from .utils import Calendar
#Calendar
class CalendarView(generic.ListView):
model = Event
template_name = 'cal/calendar.html'
def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
# use today's date for the calendar
d = get_date(self.request.GET.get('month', None))
print('d',d)
context['prev_month'] = prev_month(d)
context['next_month'] = next_month(d)
#print('html_cal', cal)
# Instantiate our calendar class with today's year and date
cal = Calendar(d.year, d.month)
print('cal', cal)
# Call the formatmonth method, which returns our calendar as a table
html_cal = cal.formatmonth(withyear=True)
print('html_cal',html_cal)
# print('html_cal1', html_cal)
context['calendar'] = mark_safe(html_cal)
return context
def get_date(req_day):
if req_day:
year, month = (int(x) for x in req_day.split('-'))
return date(year, month, day=1)
return datetime.today()
def index(request):
return HttpResponse('hello')
def prev_month(d):
first = d.replace(day=1)
prev_month = first - timedelta(days=1)
month = 'month=' + str(prev_month.year) + '-' + str(prev_month.month)
print('month',month)
return month
def next_month(d):
days_in_month = calendar.monthrange(d.year, d.month)[1]
last = d.replace(day=days_in_month)
next_month = last + timedelta(days=1)
month = 'month=' + str(next_month.year) + '-' + str(next_month.month)
return month
def event(request, event_id=None):
instance = Event()
if event_id:
instance = get_object_or_404(Event, pk=event_id)
else:
instance = Event()
form = EventForm(request.POST or None, instance=instance)
if request.POST and form.is_valid():
print('form',form)
form.save()
return HttpResponseRedirect(reverse('cal:calendar'))
return render(request, 'cal/event.html', {'form': form})
Pregunta hecha hace 3 años, 4 meses, 29 días - Por codechampion
3 Respuestas:
-
Usted puede utilizar más grande o igual a " menos o igual al filtrado
events_per_day = events.filter(start_time__day__gte=day, end_time__day__lte=day)
Respondida el Dec 18, 2020 a las 03:58 - por techwizkid
Votos positivos: 0 | Votos negativos: 0 -
Para lograr que un evento se muestre en todas las fechas entre la fecha de inicio y la fecha de finalización en el calendario, necesitas modificar la lógica en tu método
formatday
dentro de la claseCalendar
en tu archivoutils.py
.Aquí hay una sugerencia de cómo puedes modificar el método
formatday
para lograr este resultado:python class Calendar(HTMLCalendar): def __init__(self, year=None, month=None): self.year = year self.month = month super(Calendar, self).__init__() def formatday(self, day, events): events_per_day = events.filter(start_time__day=day) d = '' for event in events_per_day: if event.start_time.day <= day <= event.end_time.day: d += f'
- {event.get_html_url}
{day} " return '- {d}
' En esta modificación, estamos iterando sobre los eventos filtrados por día y solo agregando el evento a la lista
d
si el día está dentro del rango de la fecha de inicio y la fecha de finalización del evento.Con este cambio, cuando se genere el calendario en la plantilla HTML, el evento se mostrará en todas las fechas entre la fecha de inicio y la fecha de finalización.
Espero que esta solución te ayude a lograr el resultado deseado en tu proyecto de Django Calendar. ¡Déjame saber si tienes alguna otra pregunta o duda!
Respondida el Dec 19, 2020 a las 03:58 - por Gpt
Votos positivos: 0 | Votos negativos: 0 -
Para mostrar el evento en todas las fechas que coinciden con la fecha de inicio y finalización en el calendario, debes modificar el método
formatday
en el archivoutils.py
de la siguiente manera:python def formatday(self, day, events): events_per_day = events.filter(start_time__day=day) d = '' start_date = events_per_day.first().start_time.date() end_date = events_per_day.first().end_time.date() for event in events_per_day: d += f'
- {event.get_html_url}
{day} " return '- {d}
' Los cambios realizados:
- Obtiene el primer evento del día para obtener la fecha de inicio y finalización.
- Comprueba si la fecha actual está dentro del rango de fechas de inicio y finalización.
- Si la fecha está dentro del rango, muestra el evento; de lo contrario, muestra una celda vacía.
Con estos cambios, el calendario mostrará el evento en todas las fechas que coincidan con la fecha de inicio y finalización.
Respondida el Dec 19, 2020 a las 04:13 - por Gemini
Votos positivos: 0 | Votos negativos: 0