artfully_ose 1.3.0.pre3 → 1.3.0.pre4
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/app/assets/images/loading-white.gif +0 -0
- data/app/assets/images/seating_temp/1.jpg +0 -0
- data/app/assets/images/seating_temp/10.jpg +0 -0
- data/app/assets/images/seating_temp/11.jpg +0 -0
- data/app/assets/images/seating_temp/2.jpg +0 -0
- data/app/assets/images/seating_temp/3.jpg +0 -0
- data/app/assets/images/seating_temp/4.jpg +0 -0
- data/app/assets/images/seating_temp/5.jpg +0 -0
- data/app/assets/images/seating_temp/6.jpg +0 -0
- data/app/assets/images/seating_temp/7.jpg +0 -0
- data/app/assets/images/seating_temp/8.jpg +0 -0
- data/app/assets/images/seating_temp/9.jpg +0 -0
- data/app/assets/images/seating_temp/icon_43405.png +0 -0
- data/app/assets/images/seating_temp/icon_43405.svg +3 -0
- data/app/assets/images/seating_temp/icon_43405_plus.png +0 -0
- data/app/assets/images/seating_temp/license.txt +8 -0
- data/app/assets/javascripts/application.js +1 -0
- data/app/assets/javascripts/custom/cookies.js +27 -0
- data/app/assets/javascripts/custom/inline-people-search.js +4 -0
- data/app/assets/javascripts/custom/job-monitor.js +0 -1
- data/app/assets/javascripts/exchange-seat-chart.js +5 -0
- data/app/assets/javascripts/seat-chart.js +606 -0
- data/app/assets/javascripts/show-seat-chart.js +17 -0
- data/app/assets/javascripts/store/store-seat-chart.js +76 -0
- data/app/assets/javascripts/store/store.js +14 -39
- data/app/assets/stylesheets/application.sass +49 -1
- data/app/assets/stylesheets/bootstrap-overrides.css +11 -3
- data/app/assets/stylesheets/sass/seat-chart.sass +311 -0
- data/app/assets/stylesheets/sass/store.sass +73 -19
- data/app/assets/stylesheets/storefront.css +2 -0
- data/app/concerns/pdf_generation.rb +1 -15
- data/app/controllers/advanced_searches_controller.rb +1 -3
- data/app/controllers/charts_controller.rb +14 -12
- data/app/controllers/console_sales_controller.rb +55 -0
- data/app/controllers/event_calendars_controller.rb +15 -0
- data/app/controllers/events_controller.rb +16 -5
- data/app/controllers/exchanges_controller.rb +32 -9
- data/app/controllers/export_controller.rb +8 -0
- data/app/controllers/members/sessions_controller.rb +0 -2
- data/app/controllers/membership_comps_controller.rb +2 -1
- data/app/controllers/prices_controller.rb +20 -0
- data/app/controllers/shows_controller.rb +3 -1
- data/app/controllers/store/events_controller.rb +6 -5
- data/app/controllers/store/orders_controller.rb +11 -13
- data/app/controllers/store/shows_controller.rb +1 -0
- data/app/controllers/store/store_controller.rb +11 -0
- data/app/controllers/tickets_controller.rb +0 -28
- data/app/controllers/user_memberships_controller.rb +7 -2
- data/app/controllers/venues_controller.rb +9 -0
- data/app/helpers/artfully_ose_helper.rb +18 -4
- data/app/helpers/seating_helper.rb +157 -0
- data/app/models/assigned_chart.rb +220 -0
- data/app/models/cart.rb +6 -1
- data/app/models/chart.rb +28 -17
- data/app/models/database_views/item_view.rb +76 -5
- data/app/models/discount.rb +4 -0
- data/app/models/discounts/buy_one_get_one_free_discount_type.rb +1 -1
- data/app/models/discounts/dollars_off_tickets_discount_type.rb +5 -1
- data/app/models/discounts/percentage_off_tickets_discount_type.rb +8 -4
- data/app/models/event.rb +86 -12
- data/app/models/general_admission_chart.rb +51 -0
- data/app/models/imports/events_import.rb +1 -1
- data/app/models/job/show_creator.rb +3 -10
- data/app/models/kit.rb +11 -1
- data/app/models/kits/assigned_seating_kit.rb +23 -0
- data/app/models/member_walkup.rb +1 -1
- data/app/models/order_handler.rb +22 -6
- data/app/models/organization.rb +4 -5
- data/app/models/person.rb +3 -1
- data/app/models/sale.rb +1 -1
- data/app/models/seat.rb +96 -0
- data/app/models/section.rb +1 -3
- data/app/models/show.rb +10 -17
- data/app/models/ticket.rb +30 -6
- data/app/models/ticket/locker.rb +3 -2
- data/app/models/ticket_type.rb +12 -6
- data/app/models/ticket_types_seat.rb +4 -0
- data/app/models/venue.rb +23 -0
- data/app/views/advanced_searches/filters/_birthday.html.haml +1 -0
- data/app/views/assigned_charts/_show.html.haml +12 -0
- data/app/views/console_sales/_aloha.html.haml +5 -4
- data/app/views/console_sales/new.html.haml +9 -0
- data/app/views/event_calendars/index.html.haml +34 -0
- data/app/views/events/_menu.html.haml +2 -1
- data/app/views/events/_section_fields.html.haml +13 -8
- data/app/views/events/new.html.haml +34 -4
- data/app/views/events/prices.html.haml +3 -4
- data/app/views/events/seating.html.haml +131 -0
- data/app/views/exchanges/_assigned_chart.html.haml +108 -0
- data/app/views/exchanges/_general_admission_chart.html.haml +55 -0
- data/app/views/exchanges/new.html.haml +1 -55
- data/app/views/general_admission_charts/_show.html.haml +2 -0
- data/app/views/layouts/_menu.html.haml +44 -31
- data/app/views/layouts/storefront.html.haml +72 -30
- data/app/views/membership_comps/new.html.haml +1 -0
- data/app/views/order_mailer/confirmation_for.html.haml +5 -3
- data/app/views/order_mailer/confirmation_for.text.haml +1 -2
- data/app/views/pdfs/order.html.haml +20 -6
- data/app/views/seating/_actions_menu.html.haml +10 -0
- data/app/views/seating/_chart.html.haml +15 -0
- data/app/views/seating/_chart_container.html.haml +2 -0
- data/app/views/seating/_chart_note_display.html.haml +7 -0
- data/app/views/seating/_hold_seats_modal.html.haml +39 -0
- data/app/views/seating/_layer_menu.html.haml +23 -0
- data/app/views/seating/_legend.html.haml +52 -0
- data/app/views/seating/_modify_seats_modal.html.haml +29 -0
- data/app/views/seating/_ticket_type_modals.html.haml +41 -0
- data/app/views/shows/_seat_chart.html.haml +122 -0
- data/app/views/shows/_sections_table.html.haml +3 -24
- data/app/views/shows/_ticket_table.html.haml +4 -2
- data/app/views/shows/_work_with.html.haml +4 -0
- data/app/views/shows/new.html.haml +2 -2
- data/app/views/shows/show.html.haml +93 -14
- data/app/views/store/assigned_charts/_show.html.haml +54 -0
- data/app/views/store/checkouts/shopping_cart_display/_tickets.haml +13 -0
- data/app/views/store/donations/index.html.haml +1 -1
- data/app/views/store/events/calendar.html.haml +94 -11
- data/app/views/store/events/index.html.haml +1 -1
- data/app/views/store/events/show.html.haml +36 -2
- data/app/views/store/events/single_show.html.haml +5 -4
- data/app/views/store/general_admission_charts/_show.html.haml +41 -0
- data/app/views/store/orders/show.html.haml +17 -4
- data/app/views/store/shared/_donate_form.html.haml +2 -1
- data/app/views/store/shared/_small_donate_form.html.haml +1 -1
- data/app/views/store/shows/_show.html.haml +1 -39
- data/app/views/ticket_types/edit.html.haml +1 -1
- data/app/views/user_memberships/_list.html.haml +1 -1
- data/app/views/venues/edit.html.haml +1 -1
- data/app/views/venues/show.html.haml +11 -0
- data/config/routes.rb +27 -10
- data/db/migrate/20140828174357_add_type_to_chart.rb +7 -0
- data/db/migrate/20140828195617_create_seats.rb +16 -0
- data/db/migrate/20140829135426_add_venue_to_chart.rb +5 -0
- data/db/migrate/20140829143520_add_assigned_to_event.rb +5 -0
- data/db/migrate/20140904164927_add_fields_to_seat.rb +14 -0
- data/db/migrate/20140912170010_add_note_to_seat.rb +6 -0
- data/db/migrate/20140919152307_add_seats_to_ticket.rb +5 -0
- data/db/migrate/20140930224543_add_public_note_to_chart.rb +5 -0
- data/db/migrate/20141001140737_add_seat_id_index_to_tickets.rb +5 -0
- data/db/migrate/20141001193242_associate_hold_with_person.rb +6 -0
- data/db/migrate/20141021175311_create_ticket_types_seats.rb +11 -0
- data/db/migrate/20150106161744_migrate_charts_back_to_venues.rb +18 -0
- data/db/migrate/20151105085424_add_creator_to_items_view.rb +40 -0
- data/lib/artfully_ose/version.rb +1 -1
- data/spec/factories/assigned_chart_factories.rb +18 -0
- data/spec/factories/chart_factories.rb +4 -8
- data/spec/factories/kit_factories.rb +4 -0
- data/spec/factories/seat_factories.rb +4 -0
- data/spec/factories/show_factories.rb +1 -1
- metadata +66 -5
- data/app/models/ticket/foundry.rb +0 -48
- data/app/models/ticket/template.rb +0 -40
- data/app/views/store/events/_calendar.html.haml +0 -13
@@ -3,8 +3,6 @@ class Members::SessionsController < Devise::SessionsController
|
|
3
3
|
|
4
4
|
def new
|
5
5
|
@org = Organization.find_by_name(params[:org_name])
|
6
|
-
# Store the referrer so we can send them back
|
7
|
-
# where they started after successful sign in.
|
8
6
|
session[:continue] = request.referrer
|
9
7
|
super
|
10
8
|
end
|
@@ -18,8 +18,9 @@ class MembershipCompsController < ArtfullyOseController
|
|
18
18
|
@membership_comp.send_email ||= true
|
19
19
|
@membership_comp.number_of_memberships ||= 1
|
20
20
|
@membership_comp.person_id = params[:person_id]
|
21
|
-
@membership_comp.segment_id
|
21
|
+
@membership_comp.segment_id = params[:segment_id]
|
22
22
|
@membership_comp.search_id = params[:search_id]
|
23
|
+
@membership_comp.advanced_search_id = params[:advanced_search_id]
|
23
24
|
@membership_comp.organization = current_user.current_organization
|
24
25
|
@membership_comp.find_people
|
25
26
|
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
class PricesController < ApplicationController
|
2
|
+
def update
|
3
|
+
@chart = Chart.find(params[:id])
|
4
|
+
authorize! :edit, @chart
|
5
|
+
|
6
|
+
if @chart.update_attributes_from_params(Chart.polish_params(params[:chart]))
|
7
|
+
flash[:notice] = "Prices saved."
|
8
|
+
else
|
9
|
+
flash[:error] = "Please name all of your ticket types."
|
10
|
+
redirect_to prices_event_url(@chart.event) and return
|
11
|
+
end
|
12
|
+
|
13
|
+
if user_requesting_next_step?
|
14
|
+
redirect_to seating_event_path(@chart.event)
|
15
|
+
#redirect_to image_event_path(@chart.event)
|
16
|
+
else
|
17
|
+
redirect_to prices_event_url(@chart.event)
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -33,7 +33,7 @@ class ShowsController < ArtfullyOseController
|
|
33
33
|
end
|
34
34
|
|
35
35
|
def new
|
36
|
-
@show = @event.
|
36
|
+
@show = @event.build_next_show
|
37
37
|
end
|
38
38
|
|
39
39
|
def calendar
|
@@ -85,7 +85,9 @@ class ShowsController < ArtfullyOseController
|
|
85
85
|
def show
|
86
86
|
@show = Show.includes(:event => :venue, :tickets => :section).find(params[:id])
|
87
87
|
authorize! :view, @show
|
88
|
+
@chart = Chart.includes(@show.chart.class.included_models).find(@show.chart_id)
|
88
89
|
@tickets = @show.tickets
|
90
|
+
@show.chart = @chart
|
89
91
|
end
|
90
92
|
|
91
93
|
def edit
|
@@ -6,14 +6,15 @@ class Store::EventsController < Store::StoreController
|
|
6
6
|
@shows = @event.upcoming_shows_rel.published
|
7
7
|
|
8
8
|
if @shows.count < 5
|
9
|
-
@shows = @shows.includes(:event, :chart =>
|
10
|
-
elsif
|
11
|
-
|
12
|
-
@dates_by_month = dates.group_by {|d| d.strftime("%B %Y")}
|
9
|
+
@shows = @shows.includes(:event => :events_pass_types, :chart => @event.default_chart.class.included_models)
|
10
|
+
elsif session[:last_show_uuid]
|
11
|
+
@previous_show = @event.shows.find_by_uuid(session[:last_show_uuid])
|
13
12
|
end
|
14
13
|
|
14
|
+
@current_membership_types = current_member.try(:current_membership_types)
|
15
|
+
|
15
16
|
render :single_show and return if @event.single_show?
|
16
|
-
render :calendar and return if @event.upcoming_public_shows.length > 4
|
17
|
+
render :calendar and return if @event.upcoming_public_shows.length > 4 || @event.assigned?
|
17
18
|
render :show
|
18
19
|
end
|
19
20
|
|
@@ -10,20 +10,10 @@ class Store::OrdersController < Store::StoreController
|
|
10
10
|
handler.handle_passes(params)
|
11
11
|
handler.handle_discount_or_pass_code(params)
|
12
12
|
|
13
|
-
|
14
|
-
|
13
|
+
errored = handler.error.present?
|
14
|
+
flash[:alert] = handler.error if errored
|
15
15
|
|
16
|
-
|
17
|
-
when 'storefront'
|
18
|
-
store_donate_path
|
19
|
-
else
|
20
|
-
store_order_path
|
21
|
-
end
|
22
|
-
|
23
|
-
redirect_to redirect_url
|
24
|
-
else
|
25
|
-
redirect_to store_order_path
|
26
|
-
end
|
16
|
+
redirect_to redirect_path(errored)
|
27
17
|
end
|
28
18
|
|
29
19
|
def show
|
@@ -80,4 +70,12 @@ class Store::OrdersController < Store::StoreController
|
|
80
70
|
def event
|
81
71
|
current_cart.tickets.first.event
|
82
72
|
end
|
73
|
+
|
74
|
+
def redirect_path(errored)
|
75
|
+
if errored
|
76
|
+
params[:on_error] || store_order_path(@store_organization)
|
77
|
+
else
|
78
|
+
params[:on_success] || store_order_path(@store_organization)
|
79
|
+
end
|
80
|
+
end
|
83
81
|
end
|
@@ -2,6 +2,8 @@ class Store::StoreController < ActionController::Base
|
|
2
2
|
layout "storefront"
|
3
3
|
include CartFinder
|
4
4
|
before_filter :store_organization
|
5
|
+
before_filter :save_page_location
|
6
|
+
|
5
7
|
|
6
8
|
def store_organization
|
7
9
|
@store_organization ||= load_store_organization
|
@@ -25,4 +27,13 @@ class Store::StoreController < ActionController::Base
|
|
25
27
|
nil
|
26
28
|
end
|
27
29
|
end
|
30
|
+
|
31
|
+
#
|
32
|
+
# We're saving all pages for the user
|
33
|
+
# so that if they use the modal to member login,
|
34
|
+
# devise will redirect back to what they were doing
|
35
|
+
#
|
36
|
+
def save_page_location
|
37
|
+
session[:continue] = request.original_url
|
38
|
+
end
|
28
39
|
end
|
@@ -59,34 +59,6 @@ class TicketsController < ArtfullyOseController
|
|
59
59
|
end
|
60
60
|
end
|
61
61
|
|
62
|
-
def on_sale
|
63
|
-
authorize! :bulk_edit, Ticket
|
64
|
-
with_confirmation do
|
65
|
-
@show = Show.find(params[:show_id])
|
66
|
-
@selected_tickets = params[:selected_tickets]
|
67
|
-
if @show.bulk_on_sale(@selected_tickets)
|
68
|
-
flash[:notice] = "Put #{to_plural(@selected_tickets.size, 'ticket')} on sale. "
|
69
|
-
else
|
70
|
-
flash[:error] = "Tickets that have been sold or comped can't be put on or taken off sale. A ticket that is already on sale or off sale can't be put on or off sale again."
|
71
|
-
end
|
72
|
-
redirect_to event_show_url(@show.event, @show)
|
73
|
-
end
|
74
|
-
end
|
75
|
-
|
76
|
-
def off_sale
|
77
|
-
authorize! :bulk_edit, Ticket
|
78
|
-
with_confirmation do
|
79
|
-
@show = Show.find(params[:show_id])
|
80
|
-
@selected_tickets = params[:selected_tickets]
|
81
|
-
if @show.bulk_off_sale(@selected_tickets)
|
82
|
-
flash[:notice] = "Put #{to_plural(@selected_tickets.size, 'ticket')} off sale. "
|
83
|
-
else
|
84
|
-
flash[:error] = "Tickets that have been sold or comped can't be put on or taken off sale. A ticket that is already on sale or off sale can't be put on or off sale again."
|
85
|
-
end
|
86
|
-
redirect_to event_show_url(@show.event, @show)
|
87
|
-
end
|
88
|
-
end
|
89
|
-
|
90
62
|
def delete
|
91
63
|
@show = Show.find(params[:show_id])
|
92
64
|
@selected_tickets = params[:selected_tickets]
|
@@ -11,11 +11,16 @@ class UserMembershipsController < ActionController::Base
|
|
11
11
|
build_membership(user, clean_permission, @organization) or build_errors(user, @organization)
|
12
12
|
end
|
13
13
|
|
14
|
-
|
15
|
-
|
16
14
|
redirect_to organization_url(@organization, :active_tab=>"users") and return
|
17
15
|
end
|
18
16
|
|
17
|
+
def reinvite
|
18
|
+
@organization = current_user.current_organization
|
19
|
+
@user = @organization.user_memberships.find(params[:id]).user
|
20
|
+
User.invite!({:email => @user.email}, current_user)
|
21
|
+
redirect_to organization_url(@organization, :active_tab=>"users"), :notice => "We've resent the invite to #{@user.email}." and return
|
22
|
+
end
|
23
|
+
|
19
24
|
def destroy
|
20
25
|
@organization = Organization.find(params[:organization_id])
|
21
26
|
@mship = UserMembership.find(params[:id])
|
@@ -4,6 +4,15 @@ class VenuesController < ArtfullyOseController
|
|
4
4
|
authorize! :edit, @event
|
5
5
|
@venue = @event.venue
|
6
6
|
end
|
7
|
+
|
8
|
+
#
|
9
|
+
# Used asynchronously from events/new
|
10
|
+
# For now, pass venue name as the id since we can't get it from Bootstrap's typeahead
|
11
|
+
#
|
12
|
+
def show
|
13
|
+
@venue = Venue.most_recently_named(current_organization, params[:id])
|
14
|
+
render :show, :layout => false
|
15
|
+
end
|
7
16
|
|
8
17
|
def update
|
9
18
|
@event = Event.find(params[:event_id])
|
@@ -27,6 +27,17 @@ module ArtfullyOseHelper
|
|
27
27
|
end
|
28
28
|
end
|
29
29
|
|
30
|
+
def enter_code_string
|
31
|
+
@store_organization.can?(:access, :passes) ? "Have a Discount or Pass Code?" : "Have a Discount Code?"
|
32
|
+
end
|
33
|
+
|
34
|
+
def write_membership_modal
|
35
|
+
(@store_organization.has_kit? :membership) &&
|
36
|
+
(controller_path != "store/memberships") &&
|
37
|
+
(controller_path != "store/donations") &&
|
38
|
+
!member_signed_in?
|
39
|
+
end
|
40
|
+
|
30
41
|
def current_role
|
31
42
|
current_user.permission_in(current_user.current_organization)
|
32
43
|
end
|
@@ -70,9 +81,12 @@ module ArtfullyOseHelper
|
|
70
81
|
"#{target.class.name.downcase}_#{action_path_name}_path"
|
71
82
|
end
|
72
83
|
|
73
|
-
def last_login(
|
74
|
-
|
75
|
-
|
84
|
+
def last_login(user_membership)
|
85
|
+
if user_membership.user.current_sign_in_at.nil?
|
86
|
+
link_to("Resend invite", reinvite_organization_user_membership_path(@organization, user_membership), :method => :put)
|
87
|
+
else
|
88
|
+
"Last login #{time_ago_in_words(user_membership.user.current_sign_in_at)} ago"
|
89
|
+
end
|
76
90
|
end
|
77
91
|
|
78
92
|
def time_ago_sentence(t)
|
@@ -292,7 +306,7 @@ module ArtfullyOseHelper
|
|
292
306
|
end
|
293
307
|
|
294
308
|
def nav_dropdown(text, link='#')
|
295
|
-
link_to ERB::Util.html_escape(text) + '
|
309
|
+
link_to ERB::Util.html_escape(text) + ''.html_safe, link, :class => 'dropdown-toggle', 'data-toggle' => 'dropdown'
|
296
310
|
end
|
297
311
|
|
298
312
|
def bootstrapped_type(type)
|
@@ -0,0 +1,157 @@
|
|
1
|
+
module SeatingHelper
|
2
|
+
|
3
|
+
def html_class_for(seat)
|
4
|
+
classes = ""
|
5
|
+
|
6
|
+
seat.ticket_types.each do |ticket_type|
|
7
|
+
classes = classes + "ticket-type-#{ticket_type.id} "
|
8
|
+
end
|
9
|
+
|
10
|
+
if seat.ticket && seat.ticket.sold?
|
11
|
+
classes = classes + "seat-unselectable "
|
12
|
+
else
|
13
|
+
classes = classes + "seat-selectable "
|
14
|
+
end
|
15
|
+
|
16
|
+
|
17
|
+
classes = classes + "available empty " if seat.available
|
18
|
+
#classes = classes + "sold " if seat.ticket && seat.ticket.sold?
|
19
|
+
classes = classes + "killed " if seat.killed
|
20
|
+
classes = classes + "aisle " if seat.aisle
|
21
|
+
classes = classes + "wheelchair " if seat.wheelchair
|
22
|
+
classes = classes + "wheelchair-companion " if seat.wheelchair_companion
|
23
|
+
|
24
|
+
if seat.on_hold? && (!seat.ticket || !seat.ticket.sold?)
|
25
|
+
classes = classes + "hold house-hold "
|
26
|
+
return "development-hold" if seat.development_hold
|
27
|
+
return "tech-hold" if seat.tech_hold
|
28
|
+
return "contractual-hold" if seat.contractual_hold
|
29
|
+
return "person-hold" if seat.person_hold
|
30
|
+
return "press-hold" if seat.press_hold
|
31
|
+
end
|
32
|
+
|
33
|
+
classes
|
34
|
+
end
|
35
|
+
|
36
|
+
def hold_popover_text_for(seat)
|
37
|
+
str = ""
|
38
|
+
|
39
|
+
if seat.held_for_id.present?
|
40
|
+
str += "Hold for: #{seat.held_for.to_s}"
|
41
|
+
str += "<br>"
|
42
|
+
end
|
43
|
+
|
44
|
+
str += (h seat.hold_note)
|
45
|
+
|
46
|
+
if seat.ticket.present?
|
47
|
+
str += "<br>"
|
48
|
+
str += "<br>"
|
49
|
+
str += (link_to "Sell", "javascript:showSellSeat('#{seat.id}','#{seat.label}')", :class => "btn btn-primary sell-btn", :target => "_blank")
|
50
|
+
end
|
51
|
+
|
52
|
+
str
|
53
|
+
end
|
54
|
+
|
55
|
+
def storefront_html_class_for(seat)
|
56
|
+
classes = ""
|
57
|
+
classes = classes + "seat-in-cart " if seat.ticket.cart_id == current_cart.id #current_cart.tickets.include?(seat.ticket)
|
58
|
+
classes = classes + "available empty " if seat.available_for_purchase
|
59
|
+
classes = classes + "filled " if !seat.available_for_purchase
|
60
|
+
classes = classes + "aisle " if seat.aisle
|
61
|
+
classes = classes + "wheelchair " if seat.wheelchair
|
62
|
+
classes = classes + "wheelchair-companion " if seat.wheelchair_companion
|
63
|
+
|
64
|
+
if current_cart.discount.present?
|
65
|
+
if (current_cart.discount.ticket_types & seat.ticket_types.collect(&:name)).present?
|
66
|
+
classes = classes + "member-on "
|
67
|
+
else
|
68
|
+
classes = classes + "member-off "
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
if current_cart.applied_pass.present?
|
73
|
+
if current_cart.applied_pass.applies_to? (seat)
|
74
|
+
classes = classes + "member-on "
|
75
|
+
else
|
76
|
+
classes = classes + "member-off "
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
if current_member
|
81
|
+
if seat.member_ticket_for? @current_membership_types
|
82
|
+
classes = classes + "member-on "
|
83
|
+
else
|
84
|
+
classes = classes + "member-off "
|
85
|
+
end
|
86
|
+
end
|
87
|
+
|
88
|
+
classes
|
89
|
+
end
|
90
|
+
|
91
|
+
def exchange_html_class_for(seat, ticket_type)
|
92
|
+
|
93
|
+
classes = ""
|
94
|
+
|
95
|
+
if !seat.available_for_purchase || !seat.ticket_types.include?(ticket_type)
|
96
|
+
classes = classes + "filled "
|
97
|
+
classes = classes + "seat-unselectable "
|
98
|
+
elsif seat.available_for_purchase && seat.ticket_types.include?(ticket_type)
|
99
|
+
classes = classes + "available empty "
|
100
|
+
classes = classes + "seat-selectable "
|
101
|
+
end
|
102
|
+
|
103
|
+
classes = classes + "aisle " if seat.aisle
|
104
|
+
classes = classes + "wheelchair " if seat.wheelchair
|
105
|
+
classes = classes + "wheelchair-companion " if seat.wheelchair_companion
|
106
|
+
|
107
|
+
classes
|
108
|
+
end
|
109
|
+
|
110
|
+
def storefront_html_class_for(seat)
|
111
|
+
classes = ""
|
112
|
+
classes = classes + "seat-in-cart " if seat.ticket.cart_id == current_cart.id #current_cart.tickets.include?(seat.ticket)
|
113
|
+
classes = classes + "available empty " if seat.available_for_purchase
|
114
|
+
classes = classes + "filled " if !seat.available_for_purchase
|
115
|
+
classes = classes + "aisle " if seat.aisle
|
116
|
+
classes = classes + "wheelchair " if seat.wheelchair
|
117
|
+
classes = classes + "wheelchair-companion " if seat.wheelchair_companion
|
118
|
+
|
119
|
+
if current_cart.discount.present?
|
120
|
+
if (current_cart.discount.ticket_types & seat.ticket_types.collect(&:name)).present?
|
121
|
+
classes = classes + "member-on "
|
122
|
+
else
|
123
|
+
classes = classes + "member-off "
|
124
|
+
end
|
125
|
+
end
|
126
|
+
|
127
|
+
if current_cart.applied_pass.present?
|
128
|
+
if current_cart.applied_pass.applies_to? (seat)
|
129
|
+
classes = classes + "member-on "
|
130
|
+
else
|
131
|
+
classes = classes + "member-off "
|
132
|
+
end
|
133
|
+
end
|
134
|
+
|
135
|
+
if current_member
|
136
|
+
if seat.member_ticket_for? @current_membership_types
|
137
|
+
classes = classes + "member-on "
|
138
|
+
else
|
139
|
+
classes = classes + "member-off "
|
140
|
+
end
|
141
|
+
end
|
142
|
+
|
143
|
+
classes
|
144
|
+
end
|
145
|
+
|
146
|
+
def hold_header_for(seat)
|
147
|
+
"House Hold"
|
148
|
+
end
|
149
|
+
|
150
|
+
def ticket_type_pseudo_array_for(seat)
|
151
|
+
seat.ticket_types.collect(&:id).join(",")
|
152
|
+
end
|
153
|
+
|
154
|
+
def css_class(ticket_type)
|
155
|
+
((ticket_type.name || "") + " " + (ticket_type.id || "").to_s).parameterize
|
156
|
+
end
|
157
|
+
end
|
@@ -0,0 +1,220 @@
|
|
1
|
+
class AssignedChart < Chart
|
2
|
+
has_many :seats, :foreign_key => "chart_id"
|
3
|
+
belongs_to :venue
|
4
|
+
|
5
|
+
def by_rows(row_key = :row_index)
|
6
|
+
rows = {}
|
7
|
+
self.seats.each do |seat|
|
8
|
+
seats_in_row = rows.fetch(seat.send(row_key), [])
|
9
|
+
seats_in_row << seat
|
10
|
+
rows[seat.send(row_key)] = seats_in_row
|
11
|
+
end
|
12
|
+
rows
|
13
|
+
end
|
14
|
+
|
15
|
+
#
|
16
|
+
# Suitable for chaining includes
|
17
|
+
# :chart => chart.class.included_models
|
18
|
+
#
|
19
|
+
def self.included_models
|
20
|
+
[:seats => [:held_for, :ticket, :ticket_types]]
|
21
|
+
end
|
22
|
+
|
23
|
+
def num_columns
|
24
|
+
#col_index starts with zero
|
25
|
+
self.seats.empty? ? 0 : self.seats.collect(&:col_index).max + 1
|
26
|
+
end
|
27
|
+
|
28
|
+
def create_tickets
|
29
|
+
raise "Only charts that have been assigned to shows can create tickets" if self.show.nil?
|
30
|
+
self.seats.each do |seat|
|
31
|
+
seat.create_ticket
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
def sync(seat_hash)
|
36
|
+
|
37
|
+
transaction do
|
38
|
+
updated_ids = []
|
39
|
+
Rails.logger.debug("CHARTSYNC received: #{seat_hash}")
|
40
|
+
seats = self.seats.includes(:ticket_types, :ticket).all
|
41
|
+
ticket_type_hash = {}
|
42
|
+
self.ticket_types.each {|ticket_type| ticket_type_hash[ticket_type.id] = ticket_type}
|
43
|
+
seat_hash["seatRows"].each do |seat_row|
|
44
|
+
Rails.logger.debug("CHARTSYNC handling row: #{seat_row["rowIndex"]}")
|
45
|
+
row_label = seat_row["rowLabel"]
|
46
|
+
row_index = seat_row["rowIndex"]
|
47
|
+
seat_row["seats"].each do |json_seat|
|
48
|
+
|
49
|
+
Rails.logger.debug("CHARTSYNC -")
|
50
|
+
|
51
|
+
Rails.logger.debug("CHARTSYNC handling seat: #{json_seat["colIndex"]}")
|
52
|
+
Rails.logger.debug("CHARTSYNC updating seat with id: [#{json_seat["id"]}]")
|
53
|
+
seat = seats.find{|s| s.id == json_seat["id"].to_i}
|
54
|
+
if seat.present?
|
55
|
+
Rails.logger.debug("CHARTSYNC found seat: #{seat.inspect}")
|
56
|
+
else
|
57
|
+
Rails.logger.debug("CHARTSYNC no seat found. Creating a new seat.")
|
58
|
+
seat = Seat.new if seat.nil?
|
59
|
+
end
|
60
|
+
#seat = Seat.where(:id => json_seat["id"]).first_or_initialize
|
61
|
+
updated_ids <<json_seat["id"]
|
62
|
+
seat.chart = self
|
63
|
+
seat.row_index = row_index
|
64
|
+
seat.row_label = row_label
|
65
|
+
|
66
|
+
seat.col_index = json_seat["colIndex"]
|
67
|
+
seat.col_label = (json_seat["colIndex"].to_i + 1).to_s
|
68
|
+
|
69
|
+
seat.label = json_seat["label"]
|
70
|
+
seat.available = json_seat["available"]
|
71
|
+
seat.killed = json_seat["killed"]
|
72
|
+
seat.aisle = json_seat["aisle"]
|
73
|
+
seat.wheelchair = json_seat["wheelchair"]
|
74
|
+
seat.wheelchair_companion = json_seat["wheelchairCompanion"]
|
75
|
+
|
76
|
+
seat.house_hold = json_seat["houseHold"]
|
77
|
+
seat.development_hold = json_seat["developmentHold"]
|
78
|
+
seat.tech_hold = json_seat["techHold"]
|
79
|
+
seat.contractual_hold = json_seat["contractualHold"]
|
80
|
+
seat.person_hold = json_seat["personHold"]
|
81
|
+
seat.press_hold = json_seat["pressHold"]
|
82
|
+
|
83
|
+
seat.hold_note = json_seat["holdNote"]
|
84
|
+
seat.held_for_id = json_seat["holdPersonId"]
|
85
|
+
seat.seat_note = json_seat["seatNote"]
|
86
|
+
|
87
|
+
Rails.logger.debug("CHARTSYNC ticket_types are: #{json_seat["ticketTypeIds"]}")
|
88
|
+
|
89
|
+
if (seat.ticket_types.collect(&:id) != json_seat["ticketTypeIds"].collect{|tt| tt.to_i})
|
90
|
+
seat.ticket_types_seats.destroy_all
|
91
|
+
json_seat["ticketTypeIds"].each do |ticket_type_id|
|
92
|
+
Rails.logger.debug("CHARTSYNC adding ticket_type: #{ticket_type_id}")
|
93
|
+
#seat.ticket_types << TicketType.find(ticket_type_id)
|
94
|
+
seat.ticket_types << ticket_type_hash[ticket_type_id.to_i]
|
95
|
+
end
|
96
|
+
else
|
97
|
+
Rails.logger.debug("CHARTSYNC no changes to ticket types")
|
98
|
+
end
|
99
|
+
|
100
|
+
Rails.logger.debug("CHARTSYNC saving seat: #{seat.inspect}")
|
101
|
+
seat.update_ticket
|
102
|
+
Rails.logger.debug("CHARTSYNC Changed: #{seat.changes}")
|
103
|
+
seat.save
|
104
|
+
seat.create_ticket
|
105
|
+
end
|
106
|
+
end
|
107
|
+
# deleted_ids = self.seats.collect(&:id).select{|id| updated_ids.exclude?(id)}
|
108
|
+
Rails.logger.debug("CHARTSYNC updated seats: #{updated_ids}")
|
109
|
+
self.seats.where('id not in (?)', updated_ids).destroy_all unless updated_ids.blank?
|
110
|
+
self.show.delay.refresh_stats if self.show
|
111
|
+
self.event.venue.delay.update_default_chart_from(self) if self.event
|
112
|
+
end
|
113
|
+
|
114
|
+
end
|
115
|
+
|
116
|
+
#
|
117
|
+
# Pass a venue or event
|
118
|
+
#
|
119
|
+
def self.default_chart_for(chartable)
|
120
|
+
chart = AssignedChart.where(chartable.class.name.foreign_key.to_sym => chartable.id)
|
121
|
+
.where(:is_template => true)
|
122
|
+
.first
|
123
|
+
return chart unless chart.nil?
|
124
|
+
|
125
|
+
chart = AssignedChart.new
|
126
|
+
["A","B","C","D","E","F","G","H","I","J"].each_with_index do |row_label, index|
|
127
|
+
(0..9).each do |col_index|
|
128
|
+
seat = chart.seats.build({:row_index => index,
|
129
|
+
:col_index => col_index,
|
130
|
+
:row_label => row_label,
|
131
|
+
:col_label => col_index + 1,
|
132
|
+
:label => "#{row_label}#{col_index+1}",
|
133
|
+
:available => true})
|
134
|
+
chart.seats << seat
|
135
|
+
end
|
136
|
+
end
|
137
|
+
chart.is_template = true
|
138
|
+
chart.send("#{chartable.class.name.downcase}=", chartable)
|
139
|
+
chart.name = chartable.name
|
140
|
+
chart.organization = chartable.organization
|
141
|
+
chart
|
142
|
+
end
|
143
|
+
def update_attributes_from_params(params_hash = {}, parent_chart = nil)
|
144
|
+
super(params_hash)
|
145
|
+
attach_ticket_types_to_seats(parent_chart)
|
146
|
+
end
|
147
|
+
|
148
|
+
#
|
149
|
+
# Rebuild-the ticket types from the parent_chart
|
150
|
+
#
|
151
|
+
def attach_ticket_types_to_seats(parent_chart)
|
152
|
+
return if parent_chart.nil?
|
153
|
+
seats.each do |seat|
|
154
|
+
parent_seat = parent_chart.seats
|
155
|
+
.where(:row_index => seat.row_index)
|
156
|
+
.where(:col_index => seat.col_index)
|
157
|
+
.first
|
158
|
+
|
159
|
+
Rails.logger.debug("SEATS parent_seat #{parent_seat.inspect}")
|
160
|
+
parent_seat.ticket_types.each do |parent_ticket_type|
|
161
|
+
Rails.logger.debug("SEATS parent ticket type #{parent_ticket_type.inspect}")
|
162
|
+
Rails.logger.debug("SEATS my ticket types #{self.ticket_types.inspect}")
|
163
|
+
ticket_type = self.ticket_types.find{|tt| tt.name == parent_ticket_type.name}
|
164
|
+
Rails.logger.debug("SEATS found ticket_type #{ticket_type.inspect}")
|
165
|
+
if ticket_type
|
166
|
+
seat.ticket_types << ticket_type
|
167
|
+
Rails.logger.debug seat.ticket_types.inspect
|
168
|
+
end
|
169
|
+
end
|
170
|
+
|
171
|
+
seat.save if self.persisted?
|
172
|
+
end
|
173
|
+
end
|
174
|
+
|
175
|
+
#
|
176
|
+
# Returns an array of available tickets as well as an error
|
177
|
+
# [[ ticket array ], "error message suitable for end-user display"]
|
178
|
+
#
|
179
|
+
# this method ignores ticket_limit
|
180
|
+
#
|
181
|
+
def get_available_tickets(ticket_type, ticket_limit = 4, member = nil, seat = nil, cart = nil)
|
182
|
+
#
|
183
|
+
# TODO: check member, ticket holds, etc...
|
184
|
+
#
|
185
|
+
|
186
|
+
available_to = 1
|
187
|
+
if member && ticket_type.member_ticket?
|
188
|
+
Rails.logger.debug("ASSIGNED SEATING Checking for tickets available to this member")
|
189
|
+
available_to = ticket_type.available_to(member)
|
190
|
+
Rails.logger.debug("ASSIGNED SEATING available_to #{available_to}")
|
191
|
+
already_in_cart = cart.tickets.select{|t| t.ticket_type == ticket_type}.length
|
192
|
+
Rails.logger.debug("ASSIGNED SEATING already in cart #{already_in_cart}")
|
193
|
+
available_to = available_to - already_in_cart
|
194
|
+
Rails.logger.debug("ASSIGNED SEATING available to this member #{available_to}")
|
195
|
+
end
|
196
|
+
|
197
|
+
if available_to > 0
|
198
|
+
[ Array.wrap(Ticket.available.where(:seat_id => seat.id).first), nil ]
|
199
|
+
else
|
200
|
+
[ [], "Sorry, we couldn't add any more tickets at this price level." ]
|
201
|
+
end
|
202
|
+
end
|
203
|
+
|
204
|
+
protected
|
205
|
+
|
206
|
+
def duplicate(options = {})
|
207
|
+
new_chart = super(options)
|
208
|
+
|
209
|
+
self.seats.each do |seat|
|
210
|
+
new_chart.seats << seat.dup!
|
211
|
+
end
|
212
|
+
|
213
|
+
if (!!options[:save])
|
214
|
+
new_chart.save
|
215
|
+
new_chart.attach_ticket_types_to_seats(self)
|
216
|
+
end
|
217
|
+
|
218
|
+
new_chart
|
219
|
+
end
|
220
|
+
end
|