mirror of
https://github.com/pretix/pretix.git
synced 2025-12-12 04:42:28 +00:00
Compare commits
1 Commits
v4.17.0
...
widget-sea
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
3b62737d4c |
@@ -87,6 +87,18 @@ website. If you confident to have a good reason for not using SSL, you can overr
|
|||||||
|
|
||||||
<pretix-widget event="https://pretix.eu/demo/democon/" skip-ssl-check></pretix-widget>
|
<pretix-widget event="https://pretix.eu/demo/democon/" skip-ssl-check></pretix-widget>
|
||||||
|
|
||||||
|
Seating plans
|
||||||
|
-------------
|
||||||
|
|
||||||
|
By default, events with seating plans just show a button that opens the seating plan. You can also have the seating
|
||||||
|
plan embedded into the widget directly by using::
|
||||||
|
|
||||||
|
<pretix-widget event="https://pretix.eu/demo/democon/" seating-embedded></pretix-widget>
|
||||||
|
|
||||||
|
Note that the seating plan will only be embedded if the widget has enough space (currently min. 992 pixels width, may change
|
||||||
|
in the future) and that the seating plan part of the widget can unfortunately *not* be styled with CSS like the rest of
|
||||||
|
the widget.
|
||||||
|
|
||||||
Always open a new tab
|
Always open a new tab
|
||||||
---------------------
|
---------------------
|
||||||
|
|
||||||
|
|||||||
@@ -663,11 +663,15 @@ class EventIndex(EventViewMixin, EventListMixin, CartMixin, TemplateView):
|
|||||||
return context
|
return context
|
||||||
|
|
||||||
|
|
||||||
@method_decorator(allow_frame_if_namespaced, 'dispatch')
|
|
||||||
@method_decorator(iframe_entry_view_wrapper, 'dispatch')
|
@method_decorator(iframe_entry_view_wrapper, 'dispatch')
|
||||||
class SeatingPlanView(EventViewMixin, TemplateView):
|
class SeatingPlanView(EventViewMixin, TemplateView):
|
||||||
template_name = "pretixpresale/event/seatingplan.html"
|
template_name = "pretixpresale/event/seatingplan.html"
|
||||||
|
|
||||||
|
def dispatch(self, request, *args, **kwargs):
|
||||||
|
r = super().dispatch(request, *args, **kwargs)
|
||||||
|
r.xframe_options_exempt = True
|
||||||
|
return r
|
||||||
|
|
||||||
def get(self, request, *args, **kwargs):
|
def get(self, request, *args, **kwargs):
|
||||||
from pretix.presale.views.cart import get_or_create_cart_id
|
from pretix.presale.views.cart import get_or_create_cart_id
|
||||||
|
|
||||||
|
|||||||
@@ -141,18 +141,21 @@ var api = {
|
|||||||
},
|
},
|
||||||
|
|
||||||
'_postFormJSON': function (endpoint, form, callback, err_callback) {
|
'_postFormJSON': function (endpoint, form, callback, err_callback) {
|
||||||
var params = [].filter.call(form.elements, function (el) {
|
var params;
|
||||||
return (el.type !== 'checkbox' && el.type !== 'radio') || el.checked;
|
if (Array.isArray(form)) {
|
||||||
})
|
params = form
|
||||||
.filter(function (el) {
|
} else {
|
||||||
return !!el.name && !!el.value;
|
params = [].filter.call(form.elements, function (el) {
|
||||||
})
|
return (el.type !== 'checkbox' && el.type !== 'radio') || el.checked;
|
||||||
.filter(function (el) {
|
}).filter(function (el) {
|
||||||
|
return !!el.name && !!el.value;
|
||||||
|
}).filter(function (el) {
|
||||||
return !el.disabled;
|
return !el.disabled;
|
||||||
})
|
})
|
||||||
.map(function (el) {
|
}
|
||||||
return encodeURIComponent(el.name) + '=' + encodeURIComponent(el.value);
|
params = params.map(function (el) {
|
||||||
}).join('&');
|
return encodeURIComponent(el.name) + '=' + encodeURIComponent(el.value);
|
||||||
|
}).join('&');
|
||||||
|
|
||||||
var xhr = api._getXHR();
|
var xhr = api._getXHR();
|
||||||
xhr.open("POST", endpoint, true);
|
xhr.open("POST", endpoint, true);
|
||||||
@@ -522,7 +525,7 @@ Vue.component('category', {
|
|||||||
});
|
});
|
||||||
|
|
||||||
var shared_methods = {
|
var shared_methods = {
|
||||||
buy: function (event) {
|
buy: function (event, data) {
|
||||||
if (this.$root.useIframe) {
|
if (this.$root.useIframe) {
|
||||||
if (event) {
|
if (event) {
|
||||||
event.preventDefault();
|
event.preventDefault();
|
||||||
@@ -541,7 +544,7 @@ var shared_methods = {
|
|||||||
this.$root.overlay.frame_loading = true;
|
this.$root.overlay.frame_loading = true;
|
||||||
|
|
||||||
this.async_task_interval = 100;
|
this.async_task_interval = 100;
|
||||||
var form = this.$refs.form;
|
var form = data === undefined ? this.$refs.form : data;
|
||||||
if (form === undefined) {
|
if (form === undefined) {
|
||||||
form = this.$refs.formcomp.$refs.form;
|
form = this.$refs.formcomp.$refs.form;
|
||||||
}
|
}
|
||||||
@@ -663,7 +666,7 @@ var shared_methods = {
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
handleResize: function () {
|
handleResize: function () {
|
||||||
this.mobile = this.$refs.wrapper.clientWidth <= 800;
|
this.clientWidth = this.$refs.wrapper.clientWidth;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -674,7 +677,7 @@ var shared_widget_data = function () {
|
|||||||
async_task_timeout: null,
|
async_task_timeout: null,
|
||||||
async_task_interval: 100,
|
async_task_interval: 100,
|
||||||
voucher: null,
|
voucher: null,
|
||||||
mobile: false,
|
clientWidth: 1000,
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -811,11 +814,16 @@ Vue.component('pretix-widget-event-form', {
|
|||||||
+ '</div>'
|
+ '</div>'
|
||||||
|
|
||||||
// Seating plan
|
// Seating plan
|
||||||
+ '<div class="pretix-widget-seating-link-wrapper" v-if="this.$root.has_seating_plan">'
|
+ '<div class="pretix-widget-seating-link-wrapper" v-if="$root.has_seating_plan && !show_seating_plan_inline">'
|
||||||
+ '<button class="pretix-widget-seating-link" @click.prevent.stop="$root.startseating">'
|
+ '<button class="pretix-widget-seating-link" @click.prevent.stop="$root.startseating">'
|
||||||
+ strings['show_seating']
|
+ strings['show_seating']
|
||||||
+ '</button>'
|
+ '</button>'
|
||||||
+ '</div>'
|
+ '</div>'
|
||||||
|
+ '<div class="pretix-widget-seating-embed" v-else-if="$root.has_seating_plan && show_seating_plan_inline">'
|
||||||
|
+ '<iframe :key="\'seatingframe\' + $root.loadid" class="pretix-widget-seating-embed-iframe" ref="seatingframe"'
|
||||||
|
+ ' :src="seatingframe" frameborder="0" referrerpolicy="origin" allowtransparency="true">'
|
||||||
|
+ '</iframe>'
|
||||||
|
+ '</div>'
|
||||||
|
|
||||||
// Waiting list for seating plan
|
// Waiting list for seating plan
|
||||||
+ '<div class="pretix-widget-seating-waitinglist" v-if="this.$root.has_seating_plan && this.$root.has_seating_plan_waitinglist">'
|
+ '<div class="pretix-widget-seating-waitinglist" v-if="this.$root.has_seating_plan && this.$root.has_seating_plan_waitinglist">'
|
||||||
@@ -870,10 +878,14 @@ Vue.component('pretix-widget-event-form', {
|
|||||||
this.$root.$on('amounts_changed', this.calculate_buy_disabled)
|
this.$root.$on('amounts_changed', this.calculate_buy_disabled)
|
||||||
this.$root.$on('focus_voucher_field', this.focus_voucher_field)
|
this.$root.$on('focus_voucher_field', this.focus_voucher_field)
|
||||||
this.calculate_buy_disabled()
|
this.calculate_buy_disabled()
|
||||||
|
|
||||||
|
window.addEventListener('message', this.on_seat_select);
|
||||||
},
|
},
|
||||||
beforeDestroy: function() {
|
beforeDestroy: function() {
|
||||||
this.$root.$off('amounts_changed', this.calculate_buy_disabled)
|
this.$root.$off('amounts_changed', this.calculate_buy_disabled)
|
||||||
this.$root.$off('focus_voucher_field', this.focus_voucher_field)
|
this.$root.$off('focus_voucher_field', this.focus_voucher_field)
|
||||||
|
|
||||||
|
window.addEventListener('message', this.on_seat_select);
|
||||||
},
|
},
|
||||||
computed: {
|
computed: {
|
||||||
buy_label: function () {
|
buy_label: function () {
|
||||||
@@ -903,9 +915,26 @@ Vue.component('pretix-widget-event-form', {
|
|||||||
} else {
|
} else {
|
||||||
return strings.buy;
|
return strings.buy;
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
|
show_seating_plan_inline: function () {
|
||||||
|
return this.$root.seating_embedded && this.$parent.clientWidth > 992;
|
||||||
|
},
|
||||||
|
seatingframe: function () {
|
||||||
|
var seatingframe_url = this.$root.target_url;
|
||||||
|
if (this.$root.subevent){
|
||||||
|
seatingframe_url += '/' + this.$root.subevent;
|
||||||
|
}
|
||||||
|
seatingframe_url += '/seatingframe/?inline=1&locale=' + lang + '&widget_id=' + this.$root.widgetindex;
|
||||||
|
return seatingframe_url;
|
||||||
|
},
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
|
on_seat_select: function (ev) {
|
||||||
|
if (ev.data.source !== "pretix_widget_seating") return;
|
||||||
|
if (parseInt(ev.data.widget_id) !== this.$root.widgetindex) return; // In case multiple widgets are on this page
|
||||||
|
if (ev.data.action !== "buy") return;
|
||||||
|
this.$parent.buy(null, ev.data.data);
|
||||||
|
},
|
||||||
focus_voucher_field: function() {
|
focus_voucher_field: function() {
|
||||||
this.$refs.voucherinput.scrollIntoView(false)
|
this.$refs.voucherinput.scrollIntoView(false)
|
||||||
this.$refs.voucherinput.focus()
|
this.$refs.voucherinput.focus()
|
||||||
@@ -1371,9 +1400,12 @@ Vue.component('pretix-widget', {
|
|||||||
data: shared_widget_data,
|
data: shared_widget_data,
|
||||||
methods: shared_methods,
|
methods: shared_methods,
|
||||||
mounted: function () {
|
mounted: function () {
|
||||||
this.mobile = this.$refs.wrapper.clientWidth <= 600;
|
this.clientWidth = this.$refs.wrapper.clientWidth;
|
||||||
},
|
},
|
||||||
computed: {
|
computed: {
|
||||||
|
mobile: function () {
|
||||||
|
return this.clientWidth <= 600;
|
||||||
|
},
|
||||||
classObject: function () {
|
classObject: function () {
|
||||||
o = {'pretix-widget': true};
|
o = {'pretix-widget': true};
|
||||||
if (this.mobile) {
|
if (this.mobile) {
|
||||||
@@ -1536,6 +1568,7 @@ var shared_root_methods = {
|
|||||||
root.has_seating_plan_waitinglist = data.has_seating_plan_waitinglist;
|
root.has_seating_plan_waitinglist = data.has_seating_plan_waitinglist;
|
||||||
root.itemnum = data.itemnum;
|
root.itemnum = data.itemnum;
|
||||||
}
|
}
|
||||||
|
root.loadid++; // force-reload iframes
|
||||||
root.poweredby = data.poweredby;
|
root.poweredby = data.poweredby;
|
||||||
if (root.loading > 0) {
|
if (root.loading > 0) {
|
||||||
root.loading--;
|
root.loading--;
|
||||||
@@ -1674,7 +1707,7 @@ var shared_root_computed = {
|
|||||||
},
|
},
|
||||||
widget_data_json: function () {
|
widget_data_json: function () {
|
||||||
return JSON.stringify(this.widget_data);
|
return JSON.stringify(this.widget_data);
|
||||||
}
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
var create_overlay = function (app) {
|
var create_overlay = function (app) {
|
||||||
@@ -1716,7 +1749,7 @@ function get_ga_client_id(tracking_id) {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
var create_widget = function (element) {
|
var create_widget = function (element, widgetindex) {
|
||||||
var target_url = element.attributes.event.value;
|
var target_url = element.attributes.event.value;
|
||||||
if (!target_url.match(/\/$/)) {
|
if (!target_url.match(/\/$/)) {
|
||||||
target_url += "/";
|
target_url += "/";
|
||||||
@@ -1725,6 +1758,7 @@ var create_widget = function (element) {
|
|||||||
var subevent = element.attributes.subevent ? element.attributes.subevent.value : null;
|
var subevent = element.attributes.subevent ? element.attributes.subevent.value : null;
|
||||||
var style = element.attributes.style ? element.attributes.style.value : null;
|
var style = element.attributes.style ? element.attributes.style.value : null;
|
||||||
var skip_ssl = element.attributes["skip-ssl-check"] ? true : false;
|
var skip_ssl = element.attributes["skip-ssl-check"] ? true : false;
|
||||||
|
var seating_embedded = element.attributes["seating-embedded"] ? true : false;
|
||||||
var disable_iframe = element.attributes["disable-iframe"] ? true : false;
|
var disable_iframe = element.attributes["disable-iframe"] ? true : false;
|
||||||
var disable_vouchers = element.attributes["disable-vouchers"] ? true : false;
|
var disable_vouchers = element.attributes["disable-vouchers"] ? true : false;
|
||||||
var widget_data = JSON.parse(JSON.stringify(window.PretixWidget.widget_data));
|
var widget_data = JSON.parse(JSON.stringify(window.PretixWidget.widget_data));
|
||||||
@@ -1747,6 +1781,7 @@ var create_widget = function (element) {
|
|||||||
el: element,
|
el: element,
|
||||||
data: function () {
|
data: function () {
|
||||||
return {
|
return {
|
||||||
|
widgetindex: widgetindex,
|
||||||
target_url: target_url,
|
target_url: target_url,
|
||||||
parent_stack: [],
|
parent_stack: [],
|
||||||
subevent: subevent,
|
subevent: subevent,
|
||||||
@@ -1768,6 +1803,7 @@ var create_widget = function (element) {
|
|||||||
voucher_explanation_text: null,
|
voucher_explanation_text: null,
|
||||||
show_variations_expanded: !!variations,
|
show_variations_expanded: !!variations,
|
||||||
skip_ssl: skip_ssl,
|
skip_ssl: skip_ssl,
|
||||||
|
seating_embedded: seating_embedded,
|
||||||
disable_iframe: disable_iframe,
|
disable_iframe: disable_iframe,
|
||||||
style: style,
|
style: style,
|
||||||
connection_error: false,
|
connection_error: false,
|
||||||
@@ -1782,6 +1818,7 @@ var create_widget = function (element) {
|
|||||||
display_add_to_cart: false,
|
display_add_to_cart: false,
|
||||||
widget_data: widget_data,
|
widget_data: widget_data,
|
||||||
loading: 1,
|
loading: 1,
|
||||||
|
loadid: 1,
|
||||||
widget_id: 'pretix-widget-' + widget_id,
|
widget_id: 'pretix-widget-' + widget_id,
|
||||||
vouchers_exist: false,
|
vouchers_exist: false,
|
||||||
disable_vouchers: disable_vouchers,
|
disable_vouchers: disable_vouchers,
|
||||||
@@ -1882,7 +1919,7 @@ window.PretixWidget.buildWidgets = function () {
|
|||||||
var wlength = widgets.length;
|
var wlength = widgets.length;
|
||||||
for (var i = 0; i < wlength; i++) {
|
for (var i = 0; i < wlength; i++) {
|
||||||
var widget = widgets[i];
|
var widget = widgets[i];
|
||||||
widgetlist.push(create_widget(widget));
|
widgetlist.push(create_widget(widget, i + 1));
|
||||||
}
|
}
|
||||||
|
|
||||||
var buttons = document.querySelectorAll("pretix-button, div.pretix-button-compat");
|
var buttons = document.querySelectorAll("pretix-button, div.pretix-button-compat");
|
||||||
|
|||||||
@@ -331,6 +331,15 @@
|
|||||||
width: 100%;
|
width: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.pretix-widget-seating-embed {
|
||||||
|
margin: 0 -10px;
|
||||||
|
}
|
||||||
|
.pretix-widget-seating-embed-iframe {
|
||||||
|
width: 100%;
|
||||||
|
aspect-ratio: 2/1;
|
||||||
|
max-height: 60vh;
|
||||||
|
}
|
||||||
|
|
||||||
.pretix-widget-seating-waitinglist {
|
.pretix-widget-seating-waitinglist {
|
||||||
margin: 15px 0;
|
margin: 15px 0;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user