%= javascript_include_tag("calendar", plugin: :redmine_qbo_calendar) %> <% # Check if toggles are active via query params only_appointments = params[:only_appointments] == '1' hide_past_weeks = params[:hide_past_weeks] == '1' # Current date context today = User.current.today is_current_month = (calendar.instance_variable_get(:@month) == today.month && calendar.instance_variable_get(:@year) == today.year) # Get Redmine's configured non-working week days (e.g., ["6", "7"] for Sat/Sun) non_working_days = Setting.non_working_week_days || [] all_holidays = Holiday.all # Safely collect all unique CustomerAppointments across the entire calendar date range all_appointments = (calendar.startdt..calendar.enddt).flat_map { |date| calendar.events_on(date) }.select { |e| e.is_a?(CustomerAppointment) }.uniq # Lambda to determine if an appointment should render on a specific calendar day appointment_occurs_on = lambda do |appointment, current_day| app_datetime = appointment.respond_to?(:date) && appointment.date.present? ? appointment.date : appointment.start_date return false if app_datetime.nil? start_date = app_datetime.to_date target_date = current_day.to_date return false if target_date < start_date # Skip rendering on Redmine standard non-working days return false if non_working_days.include?(target_date.cwday.to_s) # Skip rendering on custom non-working days (Holidays) return false if all_holidays.any? { |h| h.occurs_on?(target_date) } duration = [appointment.duration.to_i, 1].max date_cursor = start_date working_days_count = 0 while date_cursor <= target_date is_standard_weekend = non_working_days.include?(date_cursor.cwday.to_s) is_custom_holiday = all_holidays.any? { |h| h.occurs_on?(date_cursor) } # Only increment duration count if it's a standard working day AND not a holiday unless is_standard_weekend || is_custom_holiday working_days_count += 1 end if date_cursor == target_date return working_days_count <= duration end date_cursor += 1 # Pure Ruby Date increment stays a Date object end false end %> <%# Calendar Status Legend Key %> <% # Collect status keys from CustomerAppointment enum statuses = CustomerAppointment::STATUSES %> <% if statuses.any? %>
style="text-decoration: none; color: inherit;"> <%= day.day %> (<%= abbr_day_name(day.cwday) %>) <% if User.current.allowed_to?(:add_customer_appointments, nil, global: true) %> <%# Only show ADD button if it's in the future, NOT a weekend, NOT a holiday, AND user has permission %> <% if day >= User.current.today && !is_standard_weekend && !is_custom_holiday && User.current.allowed_to?(:add_customer_appointments, nil, global: true) %> <%= link_to sprite_icon('add'), new_customer_appointment_path(start_date: day), class: 'icon-only icon-add', title: l(:label_appointment_new, default: 'New Appointment') %> <% end %> <% end %> <% if total_hours > 0 %> <%= total_hours.round(1) %>h <% end %>
<%# Render Holiday Name Badge if it's a holiday %> <% if is_custom_holiday %>