diff --git a/src/pretix/presale/templates/pretixpresale/widget_dummy.v1.html b/src/pretix/presale/templates/pretixpresale/widget_dummy.v1.html
deleted file mode 100644
index 72f58a9066..0000000000
--- a/src/pretix/presale/templates/pretixpresale/widget_dummy.v1.html
+++ /dev/null
@@ -1,5 +0,0 @@
-{% load compress %}
-{% load static %}
-{% compress css %}
-
-{% endcompress %}
diff --git a/src/pretix/presale/views/widget.py b/src/pretix/presale/views/widget.py
index d95624acf0..f99e83527b 100644
--- a/src/pretix/presale/views/widget.py
+++ b/src/pretix/presale/views/widget.py
@@ -83,7 +83,7 @@ logger = logging.getLogger(__name__)
# we never change static source without restart, so we can cache this thread-wise
_source_cache_key = None
-version_min = 1
+version_min = 2
version_max = 2
version_default = 2 # used for output in widget-embed-code
@@ -109,6 +109,8 @@ def indent(s):
def widget_css_etag(request, version, **kwargs):
+ if version < version_min:
+ version = version_min
# This makes sure a new version of the theme is loaded whenever settings or the source files have changed
if hasattr(request, 'event'):
return (f'{_get_source_cache_key(version)}-'
@@ -130,11 +132,7 @@ def widget_css(request, version, **kwargs):
if version > version_max:
raise Http404()
if version < version_min:
- return redirect(reverse('presale:event.widget.css' if hasattr(request, 'event') else 'organizer.widget.css', kwargs={
- 'version': version_min,
- 'organizer': request.organizer.slug,
- 'event': request.event.slug if hasattr(request, 'event') else None,
- }))
+ version = version_min
o = getattr(request, 'event', request.organizer)
template_path = 'pretixpresale/widget_dummy.html' if version == version_max else 'pretixpresale/widget_dummy.v{}.html'.format(version)
@@ -145,7 +143,7 @@ def widget_css(request, version, **kwargs):
widget_css = f.read()
theme_css = get_theme_vars_css(o, widget=True)
- css = theme_css + widget_css
+ css = f"/* v{version} */\n" + theme_css + widget_css
resp = FileResponse(css, content_type='text/css')
resp._csp_ignore = True
@@ -202,7 +200,7 @@ def generate_widget_js(version, lang):
code.append('})({});\n')
code = ''.join(code)
code = rJSMinFilter(content=code).output()
- return code
+ return f"/* v{version} */\n" + code
@gzip_page
@@ -212,10 +210,7 @@ def widget_js(request, version, lang, **kwargs):
raise Http404()
if version < version_min:
- return redirect(reverse('presale:widget.js', kwargs={
- 'version': version_min,
- 'lang': lang,
- }))
+ version = version_min
cached_js = cache.get('widget_js_data_v{}_{}'.format(version, lang))
if cached_js and not settings.DEBUG:
diff --git a/src/pretix/static/pretixpresale/js/widget/widget.v1.js b/src/pretix/static/pretixpresale/js/widget/widget.v1.js
deleted file mode 100644
index 260606e946..0000000000
--- a/src/pretix/static/pretixpresale/js/widget/widget.v1.js
+++ /dev/null
@@ -1,2504 +0,0 @@
-/*global siteglobals, module, lang, django*/
-/* PRETIX WIDGET BEGINS HERE */
-/* This is embedded in an isolation wrapper that exposes siteglobals as the global
- scope. */
-
-window.PretixWidget = {
- 'build_widgets': true,
- 'widget_data': {
- 'referer': location.href
- }
-};
-
-var Vue = module.exports;
-
-var strings = {
- 'quantity': django.pgettext('widget', 'Quantity'),
- 'quantity_dec': django.pgettext('widget', 'Decrease quantity'),
- 'quantity_inc': django.pgettext('widget', 'Increase quantity'),
- 'price': django.pgettext('widget', 'Price'),
- 'original_price': django.pgettext('widget', 'Original price: %s'),
- 'new_price': django.pgettext('widget', 'New price: %s'),
- 'select': django.pgettext('widget', 'Select'),
- 'select_item': django.pgettext('widget', 'Select %s'),
- 'select_variant': django.pgettext('widget', 'Select variant %s'),
- 'sold_out': django.pgettext('widget', 'Sold out'),
- 'buy': django.pgettext('widget', 'Buy'),
- 'register': django.pgettext('widget', 'Register'),
- 'reserved': django.pgettext('widget', 'Reserved'),
- 'free': django.pgettext('widget', 'FREE'),
- 'price_from': django.pgettext('widget', 'from %(currency)s %(price)s'),
- 'image_of': django.pgettext('widget', 'Image of %s'),
- 'tax_incl': django.pgettext('widget', 'incl. %(rate)s% %(taxname)s'),
- 'tax_plus': django.pgettext('widget', 'plus %(rate)s% %(taxname)s'),
- 'tax_incl_mixed': django.pgettext('widget', 'incl. taxes'),
- 'tax_plus_mixed': django.pgettext('widget', 'plus taxes'),
- 'quota_left': django.pgettext('widget', 'currently available: %s'),
- 'unavailable_require_voucher': django.pgettext('widget', 'Only available with a voucher'),
- 'unavailable_available_from': django.pgettext('widget', 'Not yet available'),
- 'unavailable_available_until': django.pgettext('widget', 'Not available anymore'),
- 'unavailable_active': django.pgettext('widget', 'Currently not available'),
- 'unavailable_hidden_if_item_available': django.pgettext('widget', 'Not yet available'),
- 'order_min': django.pgettext('widget', 'minimum amount to order: %s'),
- 'exit': django.pgettext('widget', 'Close ticket shop'),
- 'loading_error': django.pgettext('widget', 'The ticket shop could not be loaded.'),
- 'loading_error_429': django.pgettext('widget', 'There are currently a lot of users in this ticket shop. Please ' +
- 'open the shop in a new tab to continue.'),
- 'open_new_tab': django.pgettext('widget', 'Open ticket shop'),
- 'checkout': django.pgettext('widget', 'Checkout'),
- 'cart_error': django.pgettext('widget', 'The cart could not be created. Please try again later'),
- 'cart_error_429': django.pgettext('widget', 'We could not create your cart, since there are currently too many ' +
- 'users in this ticket shop. Please click "Continue" to retry in a new tab.'),
- 'waiting_list': django.pgettext('widget', 'Waiting list'),
- 'cart_exists': django.pgettext('widget', 'You currently have an active cart for this event. If you select more' +
- ' products, they will be added to your existing cart.'),
- 'resume_checkout': django.pgettext('widget', 'Resume checkout'),
- 'redeem_voucher': django.pgettext('widget', 'Redeem a voucher'),
- 'redeem': django.pgettext('widget', 'Redeem'),
- 'voucher_code': django.pgettext('widget', 'Voucher code'),
- 'close': django.pgettext('widget', 'Close'),
- 'continue': django.pgettext('widget', 'Continue'),
- 'variations': django.pgettext('widget', 'Show variants'),
- 'hide_variations': django.pgettext('widget', 'Hide variants'),
- 'back_to_list': django.pgettext('widget', 'Choose a different event'),
- 'back_to_dates': django.pgettext('widget', 'Choose a different date'),
- 'back': django.pgettext('widget', 'Back'),
- 'next_month': django.pgettext('widget', 'Next month'),
- 'previous_month': django.pgettext('widget', 'Previous month'),
- 'next_week': django.pgettext('widget', 'Next week'),
- 'previous_week': django.pgettext('widget', 'Previous week'),
- 'show_seating': django.pgettext('widget', 'Open seat selection'),
- 'seating_plan_waiting_list': django.pgettext('widget', 'Some or all ticket categories are currently sold out. If you want, you can add yourself to the waiting list. We will then notify if seats are available again.'),
- 'load_more': django.pgettext('widget', 'Load more'),
- 'days': {
- 'MO': django.gettext('Mo'),
- 'TU': django.gettext('Tu'),
- 'WE': django.gettext('We'),
- 'TH': django.gettext('Th'),
- 'FR': django.gettext('Fr'),
- 'SA': django.gettext('Sa'),
- 'SU': django.gettext('Su'),
- 'MONDAY': django.gettext('Monday'),
- 'TUESDAY': django.gettext('Tuesday'),
- 'WEDNESDAY': django.gettext('Wednesday'),
- 'THURSDAY': django.gettext('Thursday'),
- 'FRIDAY': django.gettext('Friday'),
- 'SATURDAY': django.gettext('Saturday'),
- 'SUNDAY': django.gettext('Sunday'),
- },
- 'months': {
- '01': django.gettext('January'),
- '02': django.gettext('February'),
- '03': django.gettext('March'),
- '04': django.gettext('April'),
- '05': django.gettext('May'),
- '06': django.gettext('June'),
- '07': django.gettext('July'),
- '08': django.gettext('August'),
- '09': django.gettext('September'),
- '10': django.gettext('October'),
- '11': django.gettext('November'),
- '12': django.gettext('December'),
- }
-};
-
-var setCookie = function (cname, cvalue, exdays) {
- var d = new Date();
- d.setTime(d.getTime() + (exdays * 24 * 60 * 60 * 1000));
- var expires = "expires=" + d.toUTCString();
- document.cookie = cname + "=" + cvalue + ";" + expires + ";path=/";
-};
-var getCookie = function (name) {
- var value = "; " + document.cookie;
- var parts = value.split("; " + name + "=");
- if (parts.length == 2) return parts.pop().split(";").shift() || null;
- else return null;
-};
-
-var padNumber = function(number, size) {
- var s = String(number);
- while (s.length < (size || 2)) {s = "0" + s;}
- return s;
-};
-
-var getISOWeeks = function (y) {
- var d, isLeap;
-
- d = new Date(y, 0, 1);
- isLeap = new Date(y, 1, 29).getMonth() === 1;
-
- //check for a Jan 1 that's a Thursday or a leap year that has a
- //Wednesday jan 1. Otherwise it's 52
- return d.getDay() === 4 || isLeap && d.getDay() === 3 ? 53 : 52
-};
-
-/* HTTP API Call helpers */
-var api = {
- '_getJSON': function (endpoint, callback, err_callback) {
- var xhr = new window.XMLHttpRequest();
- xhr.open("GET", endpoint, true);
- xhr.onload = function (e) {
- if (xhr.readyState === 4) {
- if (xhr.status === 200) {
- callback(JSON.parse(xhr.responseText), xhr);
- } else {
- err_callback(xhr, e);
- }
- }
- };
- xhr.onerror = function (e) {
- console.error(xhr.statusText);
- err_callback(xhr, e);
- };
- xhr.send(null);
- },
-
- '_postFormJSON': function (endpoint, form, callback, err_callback) {
- var params = [].filter.call(form.elements, function (el) {
- return (el.type !== 'checkbox' && el.type !== 'radio') || el.checked;
- })
- .filter(function (el) {
- return !!el.name && !!el.value;
- })
- .filter(function (el) {
- return !el.disabled;
- })
- .map(function (el) {
- return encodeURIComponent(el.name) + '=' + encodeURIComponent(el.value);
- }).join('&');
-
- var xhr = new window.XMLHttpRequest();
- xhr.open("POST", endpoint, true);
- xhr.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
- xhr.onload = function (e) {
- if (xhr.readyState === 4) {
- if (xhr.status === 200) {
- callback(JSON.parse(xhr.responseText));
- } else {
- err_callback(xhr, e);
- }
- }
- };
- xhr.onerror = function (e) {
- err_callback(xhr, e);
- };
- xhr.send(params);
- }
-};
-
-var makeid = function (length) {
- var text = "";
- var possible = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
-
- for (var i = 0; i < length; i++) {
- text += possible.charAt(Math.floor(Math.random() * possible.length));
- }
-
- return text;
-};
-
-var site_is_secure = function () {
- return /https.*/.test(document.location.protocol)
-};
-
-var widget_id = makeid(16);
-
-/* Vue Components */
-Vue.component('availbox', {
- template: ('
'),
- props: {
- item: Object,
- variation: Object
- },
- mounted: function() {
- if (this.item.has_variations) {
- this.$set(this.variation, 'amount_selected', 0);
- } else {
- // Automatically set the only available item to be selected.
- this.$set(this.item, 'amount_selected', this.$root.itemnum === 1 && !this.$root.has_seating_plan ? 1 : 0);
- }
- this.$root.$emit('amounts_changed')
- },
- computed: {
- aria_labelledby: function () {
- return this.$root.html_id + '-item-label-' + this.item.id;
- },
- dec_label: function () {
- return '- ' + (this.item.has_variations ? this.variation.value : this.item.name) + ': ' + strings.quantity_dec;
- },
- inc_label: function () {
- return '+ ' + (this.item.has_variations ? this.variation.value : this.item.name) + ': ' + strings.quantity_inc;
- },
- count_group_classes: function () {
- return {
- 'pretix-widget-item-count-group': !this.$root.use_native_spinners
- }
- },
- unavailability_reason_message: function () {
- var reason = this.item.current_unavailability_reason || this.variation?.current_unavailability_reason;
- if (reason) {
- return strings["unavailable_" + reason] || reason;
- }
- return "";
- },
- amount_selected: {
- cache: false,
- get: function () {
- var selected = this.item.has_variations ? this.variation.amount_selected : this.item.amount_selected
- if (selected === 0) return undefined;
- return selected
- },
- set: function (value) {
- // Unary operator to force boolean to integer conversion, as the HTML form submission
- // needs the value to be integer for all products.
- value = (+value);
- if (this.item.has_variations) {
- this.variation.amount_selected = value;
- } else {
- this.item.amount_selected = value;
- }
- if (this.$refs.quantity) {
- // manually set value on quantity as on reload somehow v-model binding breaks
- this.$refs.quantity.value = value;
- }
- this.$root.$emit("amounts_changed")
- }
- },
- label_select_item: function () {
- return this.item.has_variations
- ? strings.select_variant.replace("%s", this.variation.value)
- : strings.select_item.replace("%s", this.item.name)
- },
- input_name: function () {
- if (this.item.has_variations) {
- return 'variation_' + this.item.id + '_' + this.variation.id;
- } else {
- return 'item_' + this.item.id;
- }
- },
- order_max: function () {
- return this.item.has_variations ? this.variation.order_max : this.item.order_max;
- },
- avail: function () {
- return this.item.has_variations ? this.variation.avail : this.item.avail;
- },
- waiting_list_show: function () {
- return this.avail[0] < 100 && this.$root.waiting_list_enabled && this.item.allow_waitinglist;
- },
- waiting_list_url: function () {
- var u
- if (this.item.has_variations) {
- u = this.$root.target_url + 'w/' + widget_id + '/waitinglist/?item=' + this.item.id + '&var=' + this.variation.id + '&widget_data=' + encodeURIComponent(this.$root.widget_data_json) + this.$root.consent_parameter;
- } else {
- u = this.$root.target_url + 'w/' + widget_id + '/waitinglist/?item=' + this.item.id + '&widget_data=' + encodeURIComponent(this.$root.widget_data_json) + this.$root.consent_parameter;
- }
- if (this.$root.subevent) {
- u += '&subevent=' + this.$root.subevent
- }
- return u
- }
- },
- methods: {
- focus_voucher_field: function () {
- this.$root.$emit('focus_voucher_field')
- },
- on_step: function (e) {
- var t = e.target.tagName == 'BUTTON' ? e.target : e.target.closest('button');
- var step = parseFloat(t.getAttribute("data-step"));
- var controls = document.getElementById(t.getAttribute("data-controls"));
- this.amount_selected = Math.max(controls.min, Math.min(controls.max || Number.MAX_SAFE_INTEGER, (this.amount_selected || 0) + step));
- }
- }
-});
-Vue.component('pricebox', {
- template: (''),
- props: {
- price: Object,
- free_price: Boolean,
- field_name: String,
- suggested_price: Object,
- original_price: String,
- mandatory_priced_addons: Boolean,
- item_id: Number,
- },
- methods: {
- stripHTML: function (s) {
- var div = document.createElement('div');
- div.innerHTML = s;
- return div.textContent || div.innerText || '';
- },
- },
- computed: {
- aria_labelledby: function () {
- return [
- this.$root.html_id + '-item-label-' + this.item_id,
- this.price_box_id
- ].join(" ");
- },
- price_box_id: function () {
- return this.$root.html_id + '-item-pricebox-' + this.item_id;
- },
- price_desc_id: function () {
- return this.$root.html_id + '-item-pricedesc-' + this.item_id;
- },
- display_price: function () {
- if (this.$root.display_net_prices) {
- return floatformat(parseFloat(this.price.net), 2);
- } else {
- return floatformat(parseFloat(this.price.gross), 2);
- }
- },
- display_price_nonlocalized: function () {
- if (this.$root.display_net_prices) {
- return parseFloat(this.price.net).toFixed(2);
- } else {
- return parseFloat(this.price.gross).toFixed(2);
- }
- },
- suggested_price_nonlocalized: function () {
- var price = this.suggested_price;
- if (price === null) {
- price = this.price;
- }
- if (this.$root.display_net_prices) {
- return parseFloat(price.net).toFixed(2);
- } else {
- return parseFloat(price.gross).toFixed(2);
- }
- },
- original_price_aria_label: function () {
- return django.interpolate(strings.original_price, [this.stripHTML(this.original_line)]);
- },
- new_price_aria_label: function () {
- return django.interpolate(strings.new_price, [this.stripHTML(this.priceline)]);
- },
- original_line: function () {
- return '' + this.$root.currency + " " + floatformat(parseFloat(this.original_price), 2);
- },
- priceline: function () {
- if (this.price.gross === "0.00") {
- if (this.mandatory_priced_addons && !this.original_price) {
- return "\xA0"; // nbsp, because an empty string would cause the HTML element to collapse
- }
- return strings.free;
- } else {
- return '' + this.$root.currency + " " + this.display_price;
- }
- },
- taxline: function () {
- if (this.$root.display_net_prices) {
- if (this.price.includes_mixed_tax_rate) {
- return strings.tax_plus_mixed;
- } else {
- return django.interpolate(strings.tax_plus, {
- 'rate': autofloatformat(this.price.rate, 2),
- 'taxname': this.price.name
- }, true);
- }
- } else {
- if (this.price.includes_mixed_tax_rate) {
- return strings.tax_incl_mixed;
- } else {
- return django.interpolate(strings.tax_incl, {
- 'rate': autofloatformat(this.price.rate, 2),
- 'taxname': this.price.name
- }, true);
- }
- }
- }
- }
-});
-Vue.component('variation', {
- template: (''),
- props: {
- variation: Object,
- item: Object,
- category: Object,
- },
- computed: {
- orig_price: function () {
- if (this.variation.original_price) {
- return this.variation.original_price;
- }
- return this.item.original_price;
- },
- quota_left_str: function () {
- return django.interpolate(strings["quota_left"], [this.variation.avail[1]]);
- },
- variation_label_id: function () {
- return this.$root.html_id + '-variation-label-' + this.item.id + '-' + this.variation.id;
- },
- variation_desc_id: function () {
- return this.$root.html_id + '-variation-desc-' + this.item.id + '-' + this.variation.id;
- },
- variation_price_id: function () {
- return this.$root.html_id + '-variation-price-' + this.item.id + '-' + this.variation.id;
- },
- aria_labelledby: function () {
- return [this.variation_label_id, this.variation_price_id].join(" ");
- },
- headingLevel: function () {
- return this.category.name ? '5' : '4';
- },
- }
-});
-Vue.component('item', {
- template: (''
- + '
'
-
- // Product description
- + '
'
-
- // Price
- + '
'
-
- // Availability
- + '
'
-
- + '
'
- + '
'
-
- // Variations
- + '
'
- + ''
- + ''
- + '
'
-
- + '
'),
- props: {
- item: Object,
- category: Object,
- },
- data: function () {
- return {
- expanded: this.$root.show_variations_expanded
- };
- },
- mounted: function () {
- if (this.$refs.variations) {
- if (!this.expanded) {
- var $this = this;
- this.$refs.variations.hidden = true;
- this.$refs.variations.addEventListener('transitionend', function (event) {
- if (event.target == this) {
- this.hidden = !$this.expanded;
- this.style.maxHeight = 'none';
- }
- });
- this.$watch('expanded', function (newValue) {
- var v = this.$refs.variations;
- v.hidden = false;
- v.style.maxHeight = (newValue ? 0 : v.scrollHeight) + 'px';
- // Vue.nextTick does not work here
- window.setTimeout(function () {
- v.style.maxHeight = (!newValue ? 0 : v.scrollHeight) + 'px';
- }, 50);
- })
- }
- }
- },
- methods: {
- expand: function () {
- this.expanded = !this.expanded;
- },
- lightbox: function () {
- this.$root.overlay.lightbox = {
- image: this.item.picture_fullsize,
- description: this.item.name,
- }
- }
- },
- computed: {
- classObject: function () {
- return {
- 'pretix-widget-item': true,
- 'pretix-widget-item-with-picture': !!this.item.picture,
- 'pretix-widget-item-with-variations': this.item.has_variations
- }
- },
- varClasses: function () {
- return {
- 'pretix-widget-item-variations': true,
- 'pretix-widget-item-variations-expanded': this.expanded,
- }
- },
- picture_alt_text: function () {
- return django.interpolate(strings["image_of"], [this.item.name]);
- },
- headingLevel: function () {
- return this.category.name ? '4' : '3';
- },
- item_label_id: function () {
- return this.$root.html_id + '-item-label-' + this.item.id;
- },
- item_desc_id: function () {
- return this.$root.html_id + '-item-desc-' + this.item.id;
- },
- item_price_id: function () {
- return this.$root.html_id + '-item-price-' + this.item.id;
- },
- aria_labelledby: function () {
- return [this.item_label_id, this.item_price_id].join(" ");
- },
- min_order_str: function () {
- return django.interpolate(strings["order_min"], [this.item.order_min]);
- },
- quota_left_str: function () {
- return django.interpolate(strings["quota_left"], [this.item.avail[1]]);
- },
- show_toggle: function () {
- return this.item.has_variations && !this.$root.show_variations_expanded;
- },
- pricerange: function () {
- if (this.item.free_price) {
- return django.interpolate(strings.price_from, {
- 'currency': this.$root.currency,
- 'price': floatformat(this.item.min_price, 2)
- }, true).replace(this.$root.currency, '' + this.$root.currency + '');
- } else if (this.item.min_price !== this.item.max_price) {
- return '' + this.$root.currency + " "
- + floatformat(this.item.min_price, 2) + " – "
- + floatformat(this.item.max_price, 2);
- } else if (this.item.min_price === "0.00" && this.item.max_price === "0.00") {
- if (this.item.mandatory_priced_addons) {
- return "\xA0"; // nbsp, because an empty string would cause the HTML element to collapse
- }
- return strings.free;
- } else {
- return '' + this.$root.currency + " " + floatformat(this.item.min_price, 2);
- }
- },
- variationsToggleLabel: function () {
- return this.expanded ? strings.hide_variations : strings.variations;
- },
- }
-});
-Vue.component('category', {
- template: (''),
- props: {
- category: Object
- }
-});
-
-var shared_methods = {
- buy: function (event) {
- if (this.$root.useIframe) {
- if (event) {
- event.preventDefault();
- }
- } else {
- return;
- }
- if (this.$root.is_button && this.$root.items.length === 0) {
- if (this.$root.voucher_code) {
- this.voucher_open(this.$root.voucher_code);
- } else {
- this.resume();
- }
- } else {
- var url = this.$root.formAction + "&locale=" + lang + "&ajax=1";
- this.$root.overlay.frame_loading = true;
-
- this.async_task_interval = 100;
- var form = this.$refs.form;
- if (form === undefined) {
- form = this.$refs.formcomp.$refs.form;
- }
- api._postFormJSON(url, form, this.buy_callback, this.buy_error_callback);
- }
- },
- buy_error_callback: function (xhr, data) {
- if (xhr.status === 429 && typeof xhr.responseURL !== "undefined") {
- this.$root.overlay.error_message = strings['cart_error_429'];
- this.$root.overlay.frame_loading = false;
- this.$root.overlay.error_url_after = this.$root.newTabTarget;
- this.$root.overlay.error_url_after_new_tab = true;
- return;
- }
- if (xhr.status === 405 && typeof xhr.responseURL !== "undefined") {
- // Likely a redirect!
- this.$root.target_url = xhr.responseURL.substr(0, xhr.responseURL.indexOf("/cart/add") - 18);
- this.$root.overlay.frame_loading = false;
- this.buy();
- return;
- }
- this.$root.overlay.error_message = strings['cart_error'];
- this.$root.overlay.frame_loading = false;
- },
- buy_check_error_callback: function (xhr, data) {
- if (xhr.status == 200 || (xhr.status >= 400 && xhr.status < 500)) {
- this.$root.overlay.error_message = strings['cart_error'];
- this.$root.overlay.frame_loading = false;
- } else {
- this.async_task_timeout = window.setTimeout(this.buy_check, 1000);
- }
- },
- buy_callback: function (data) {
- if (data.redirect) {
- if (data.cart_id) {
- this.$root.cart_id = data.cart_id;
- setCookie(this.$root.cookieName, data.cart_id, 30);
- }
- if (data.redirect.substr(0, 1) === '/') {
- data.redirect = this.$root.target_url.replace(/^([^\/]+:\/\/[^\/]+)\/.*$/, "$1") + data.redirect;
- }
- var url = data.redirect;
- if (url.indexOf('?')) {
- url = url + '&iframe=1&locale=' + lang + '&take_cart_id=' + this.$root.cart_id;
- } else {
- url = url + '?iframe=1&locale=' + lang + '&take_cart_id=' + this.$root.cart_id;
- }
- url += this.$root.consent_parameter;
- if (this.$root.additionalURLParams) {
- url += '&' + this.$root.additionalURLParams;
- }
- if (data.success === false) {
- url = url.replace(/checkout\/start/g, "");
- this.$root.overlay.error_message = data.message;
- if (data.has_cart) {
- this.$root.overlay.error_url_after = url;
- }
- this.$root.overlay.frame_loading = false;
- } else {
- this.$root.overlay.frame_src = url;
- }
- } else {
- this.async_task_id = data.async_id;
- if (data.check_url) {
- this.async_task_check_url = this.$root.target_url.replace(/^([^\/]+:\/\/[^\/]+)\/.*$/, "$1") + data.check_url;
- }
- this.async_task_timeout = window.setTimeout(this.buy_check, this.async_task_interval);
- this.async_task_interval = 250;
- }
- },
- buy_check: function () {
- api._getJSON(this.async_task_check_url, this.buy_callback, this.buy_check_error_callback);
- },
- redeem: function (event) {
- if (this.$root.useIframe) {
- event.preventDefault();
- this.voucher_open(this.voucher);
- }
- },
- voucher_open: function (voucher) {
- var redirect_url = this.$root.voucherFormTarget + '&voucher=' + encodeURIComponent(voucher);
- if (this.$root.useIframe) {
- this.$root.overlay.frame_src = redirect_url;
- } else {
- window.open(redirect_url);
- }
- },
- resume: function () {
- var redirect_url;
- redirect_url = this.$root.target_url + 'w/' + widget_id + '/';
- if (this.$root.subevent && !this.$root.cart_id) {
- // button with subevent but no items
- redirect_url += this.$root.subevent + '/';
- }
- redirect_url += '?iframe=1&locale=' + lang;
- if (this.$root.cart_id) {
- redirect_url += '&take_cart_id=' + this.$root.cart_id;
- }
- if (this.$root.widget_data) {
- redirect_url += '&widget_data=' + encodeURIComponent(this.$root.widget_data_json);
- }
- redirect_url += this.$root.consent_parameter;
- if (this.$root.additionalURLParams) {
- redirect_url += '&' + this.$root.additionalURLParams;
- }
- if (this.$root.useIframe) {
- this.$root.overlay.frame_src = redirect_url;
- } else {
- window.open(redirect_url);
- }
- },
-};
-
-var shared_widget_data = function () {
- return {
- async_task_id: null,
- async_task_check_url: null,
- async_task_timeout: null,
- async_task_interval: 100,
- voucher: null,
- mobile: false,
- }
-};
-
-var shared_loading_fragment = (
- ''
-);
-
-var shared_iframe_fragment = (
- ''
-);
-
-var shared_alert_fragment = (
- ''
- + '
'
- + ''
- + ''
- + '
'
- + '
'
-);
-
-var shared_lightbox_fragment = (
- ''
-);
-
-Vue.component('pretix-overlay', {
- template: (''
- + shared_iframe_fragment
- + shared_alert_fragment
- + shared_lightbox_fragment
- + '
'
- ),
- watch: {
- '$root.lightbox': function (newValue, oldValue) {
- if (newValue) {
- if (newValue.image != oldValue?.image) {
- this.$set(newValue, "loading", true);
- }
- if (!oldValue) {
- window.addEventListener('keyup', this.lightboxCloseOnKeyup);
- }
- } else {
- window.removeEventListener('keyup', this.lightboxCloseOnKeyup);
- }
- }
- },
- computed: {
- frameClasses: function () {
- return {
- 'pretix-widget-frame-holder': true,
- 'pretix-widget-frame-shown': this.$root.frame_shown || this.$root.frame_loading,
- };
- },
- alertClasses: function () {
- return {
- 'pretix-widget-alert-holder': true,
- 'pretix-widget-alert-shown': this.$root.error_message,
- };
- },
- lightboxClasses: function () {
- return {
- 'pretix-widget-lightbox-holder': true,
- 'pretix-widget-lightbox-shown': this.$root.lightbox,
- 'pretix-widget-lightbox-isloading': this.$root.lightbox?.loading,
- };
- },
- },
- methods: {
- lightboxCloseOnKeyup: function (event) {
- if (event.keyCode === 27) {
- // abort on ESC-key
- this.lightboxClose();
- }
- },
- lightboxClose: function () {
- this.$root.lightbox = null;
- },
- lightboxLoaded: function () {
- this.$root.lightbox.loading = false;
- },
- errorClose: function () {
- this.$root.error_message = null;
- this.$root.error_url_after = null;
- this.$root.error_url_after_new_tab = false;
- },
- errorContinue: function () {
- if (this.$root.error_url_after_new_tab) {
- window.open(this.$root.error_url_after);
- return;
- }
- this.$root.overlay.frame_src = this.$root.error_url_after;
- this.$root.frame_loading = true;
- this.$root.error_message = null;
- this.$root.error_url_after = null;
- },
- close: function () {
- this.$root.frame_shown = false;
- this.$root.parent.frame_dismissed = true;
- this.$root.frame_src = "";
- this.$root.parent.reload();
- this.$root.parent.trigger_close_callback();
- },
- iframeLoaded: function () {
- if (this.$root.frame_loading) {
- this.$root.frame_loading = false;
- if (this.$root.frame_src) {
- this.$root.frame_shown = true;
- }
- }
- },
- focusButton: function () {
- this.$el.querySelector(".pretix-widget-alert-box button").focus();
- },
-
- }
-});
-
-Vue.component('pretix-widget-event-form', {
- template: (''
- ),
- mounted: function() {
- this.$root.$on('focus_voucher_field', this.focus_voucher_field)
- },
- beforeDestroy: function() {
- this.$root.$off('focus_voucher_field', this.focus_voucher_field)
- },
- computed: {
- aria_labelledby: function() {
- return this.$root.html_id + '-voucher-headline';
- },
- display_event_info: function () {
- return this.$root.display_event_info || (this.$root.display_event_info === null && (this.$root.events || this.$root.weeks || this.$root.days));
- },
- id_cart_exists_msg: function () {
- return this.$root.html_id + '-cart-exists';
- },
- buy_label: function () {
- var i, j, k, all_free = true;
- for (i = 0; i < this.$root.categories.length; i++) {
- var cat = this.$root.categories[i];
- for (j = 0; j < cat.items.length; j++) {
- var item = cat.items[j];
- for (k = 0; k < item.variations.length; k++) {
- var v = item.variations[k];
- if (v.price.gross !== "0.00") {
- all_free = false;
- break;
- }
- }
- if ((item.variations.length === 0 && item.price.gross !== "0.00") || item.mandatory_priced_addons) {
- all_free = false;
- break;
- }
- }
- if (!all_free) {
- break;
- }
- }
- if (all_free) {
- return strings.register;
- } else {
- return strings.buy;
- }
- },
- hiddenParams: function () {
- var params = new URL(this.$root.voucherFormTarget).searchParams;
- params.delete("iframe");
- params.delete("take_cart_id");
- return [...params.entries()];
- },
- },
- methods: {
- focus_voucher_field: function() {
- this.$refs.voucherinput.scrollIntoView(false)
- this.$refs.voucherinput.focus()
- },
- back_to_list: function() {
- this.$root.target_url = this.$root.parent_stack.pop();
- this.$root.error = null;
- if (!this.$root.subevent) {
- // reset if we are not in a series
- this.$root.name = null;
- this.$root.frontpage_text = null;
- }
- this.$root.subevent = null;
- this.$root.offset = 0;
- this.$root.append_events = false;
- this.$root.trigger_load_callback();
- if (this.$root.events !== undefined && this.$root.events !== null) {
- this.$root.view = "events";
- } else if (this.$root.days !== undefined && this.$root.days !== null) {
- this.$root.view = "days";
- } else {
- this.$root.view = "weeks";
- }
-
- var $el = this.$root.$el;
- this.$root.$nextTick(function() {
- // wait for redraw, then focus content element for better a11y
- $el.focus();
- });
- },
- }
-});
-
-Vue.component('pretix-widget-event-list-filter-field', {
- template: (''
- + ''
- + ''
- + '
'),
- props: {
- field: Object
- },
- methods: {
- onChange: function(event) {
- var filterParams = new URLSearchParams(this.$root.filter);
- if (event.target.value) {
- filterParams.set(this.field.key, event.target.value);
- } else {
- filterParams.delete(this.field.key);
- }
- this.$root.filter = filterParams.toString();
- this.$root.loading++;
- this.$root.reload();
- },
- },
- computed: {
- id: function () {
- return widget_id + "_" + this.field.key;
- },
- currentValue: function () {
- var filterParams = new URLSearchParams(this.$root.filter);
- return filterParams.get(this.field.key) || "";
- },
- },
-});
-
-Vue.component('pretix-widget-event-list-filter-form', {
- template: (''),
-});
-
-Vue.component('pretix-widget-event-list-entry', {
- template: (''
- + '{{ event.name }}
'
- + '{{ event.date_range }}
'
- + '{{ location }}
' // hidden by css for now, but
- // used by a few people
- + '{{ event.availability.text }}
'
- + ''),
- props: {
- event: Object
- },
- computed: {
- classObject: function () {
- var o = {
- 'pretix-widget-event-list-entry': true
- };
- o['pretix-widget-event-availability-' + this.event.availability.color] = true;
- if (this.event.availability.reason) {
- o['pretix-widget-event-availability-' + this.event.availability.reason] = true;
- }
- return o
- },
- location: function () {
- return this.event.location.replace(/\s*\n\s*/g, ', ');
- }
- },
- methods: {
- select: function () {
- this.$root.parent_stack.push(this.$root.target_url);
- this.$root.target_url = this.event.event_url;
- this.$root.error = null;
- this.$root.subevent = this.event.subevent;
- this.$root.loading++;
- this.$root.reload();
- }
- }
-});
-
-Vue.component('pretix-widget-event-list', {
- template: (''),
- computed: {
- display_event_info: function () {
- return this.$root.display_event_info || (this.$root.display_event_info === null && this.$root.parent_stack.length > 0);
- },
- },
- methods: {
- back_to_calendar: function () {
- // make sure to always focus content element
- this.$nextTick(function () {
- this.$root.$el.focus();
- });
- this.$root.offset = 0;
- this.$root.append_events = false;
- if (this.$root.weeks) {
- this.$root.events = undefined;
- this.$root.view = "weeks";
- this.$root.name = null;
- this.$root.frontpage_text = null;
- } else {
- this.$root.loading++;
- this.$root.target_url = this.$root.parent_stack.pop();
- this.$root.error = null;
- this.$root.reload();
- }
- },
- load_more: function () {
- this.$root.append_events = true;
- this.$root.offset += 50;
- this.$root.loading++;
- this.$root.reload();
- }
- }
-});
-
-Vue.component('pretix-widget-event-calendar-event', {
- template: (''
- + ''
- + '{{ event.name }}'
- + ''
- + '{{ event.time }}
'
- + '{{ event.availability.text }}
'
- + ''),
- props: {
- event: Object,
- describedby: String,
- },
- computed: {
- classObject: function () {
- var o = {
- 'pretix-widget-event-calendar-event': true
- };
- o['pretix-widget-event-availability-' + this.event.availability.color] = true;
- if (this.event.availability.reason) {
- o['pretix-widget-event-availability-' + this.event.availability.reason] = true;
- }
- return o
- }
- },
- methods: {
- select: function () {
- this.$root.parent_stack.push(this.$root.target_url);
- this.$root.target_url = this.event.event_url;
- this.$root.error = null;
- this.$root.subevent = this.event.subevent;
- this.$root.loading++;
- this.$root.reload();
- }
- }
-});
-
-Vue.component('pretix-widget-event-week-cell', {
- template: (''
- + '
'
- + '{{ dayhead }}'
- + '
'
- + '
'
- + '
'),
- props: {
- day: Object,
- },
- methods: {
- selectDay: function () {
- if (!this.day || !this.day.events.length || !this.$parent.$parent.$parent.mobile) {
- return;
- }
- if (this.day.events.length === 1) {
- var ev = this.day.events[0];
- this.$root.parent_stack.push(this.$root.target_url);
- this.$root.target_url = ev.event_url;
- this.$root.error = null;
- this.$root.subevent = ev.subevent;
- this.$root.loading++;
- this.$root.reload();
- } else {
- this.$root.events = this.day.events;
- this.$root.view = "events";
- }
- }
- },
- computed: {
- id: function () {
- return this.day ? this.$root.html_id + '-' + this.day.date : '';
- },
- dayhead: function () {
- if (!this.day) {
- return;
- }
- return this.day.day_formatted;
- },
- classObject: function () {
- var o = {};
- if (this.day && this.day.events.length > 0) {
- o['pretix-widget-has-events'] = true;
- var best = 'red';
- var all_low = true;
- for (var i = 0; i < this.day.events.length; i++) {
- var ev = this.day.events[i];
- if (ev.availability.color === 'green') {
- best = 'green';
- if (ev.availability.reason !== 'low') {
- all_low = false;
- }
- } else if (ev.availability.color === 'orange' && best !== 'green') {
- best = 'orange'
- }
- }
- o['pretix-widget-day-availability-' + best] = true;
- if (best === 'green' && all_low) {
- o['pretix-widget-day-availability-low'] = true;
- }
- }
- return o
- }
- }
-});
-
-Vue.component('pretix-widget-event-calendar-cell', {
- template: (''
- + ' '
- + '{{ daynum }}'
- + ' '
- + ''
- + ' | '),
- props: {
- day: Object,
- },
- methods: {
- selectDay: function (e) {
- if (!this.day || !this.day.events.length || !this.$parent.$parent.$parent.mobile) {
- return;
- }
- e.preventDefault();
- e.stopPropagation();
- if (this.day.events.length === 1) {
- var ev = this.day.events[0];
- this.$root.parent_stack.push(this.$root.target_url);
- this.$root.target_url = ev.event_url;
- this.$root.error = null;
- this.$root.subevent = ev.subevent;
- this.$root.loading++;
- this.$root.reload();
- } else {
- this.$root.events = this.day.events;
- this.$root.view = "events";
- }
- },
- onKeyDown: function (e) {
- var keyDown = e.key !== undefined ? e.key : e.keyCode;
- if ( (keyDown === 'Enter' || keyDown === 13) || (['Spacebar', ' '].indexOf(keyDown) >= 0 || keyDown === 32)) {
- // (prevent default so the page doesn't scroll when pressing space)
- e.preventDefault();
- this.selectDay(e);
- }
- },
- },
- mounted: function () {
- if (this.role == 'button') {
- this.$el.addEventListener("click", this.selectDay);
- this.$el.addEventListener("keydown", this.onKeyDown);
- }
- },
- watch: {
- role: function (newValue) {
- if (newValue == 'button') {
- this.$el.addEventListener("click", this.selectDay);
- this.$el.addEventListener("keydown", this.onKeyDown);
- } else {
- this.$el.removeEventListener("click", this.selectDay);
- this.$el.removeEventListener("keydown", this.onKeyDown);
- }
- }
- },
- computed: {
- role: function () {
- return (!this.day || !this.day.events.length || !this.$parent.$parent.$parent.mobile) ? 'cell' : 'button';
- },
- tabindex: function () {
- return this.role == 'button' ? '0' : '-1';
- },
- daynum: function () {
- if (!this.day) {
- return;
- }
- return this.day.date.substr(8);
- },
- date: function () {
- return this.day ? (new Date(this.day.date)).toLocaleDateString() : '';
- },
- classObject: function () {
- var o = {};
- if (this.day && this.day.events.length > 0) {
- o['pretix-widget-has-events'] = true;
- var best = 'red';
- var all_low = true;
- for (var i = 0; i < this.day.events.length; i++) {
- var ev = this.day.events[i];
- if (ev.availability.color === 'green') {
- best = 'green';
- if (ev.availability.reason !== 'low') {
- all_low = false;
- }
- } else if (ev.availability.color === 'orange' && best !== 'green') {
- best = 'orange'
- }
- }
- o['pretix-widget-day-availability-' + best] = true;
- if (best === 'green' && all_low) {
- o['pretix-widget-day-availability-low'] = true;
- }
- }
- return o
- }
- }
-});
-
-Vue.component('pretix-widget-event-calendar-row', {
- template: (''
- + ''
- + '
'),
- props: {
- week: Array
- },
-});
-
-Vue.component('pretix-widget-event-calendar', {
- template: (''),
- computed: {
- display_event_info: function () {
- return this.$root.display_event_info || (this.$root.display_event_info === null && this.$root.parent_stack.length > 0);
- },
- monthname: function () {
- return strings['months'][this.$root.date.substr(5, 2)] + ' ' + this.$root.date.substr(0, 4);
- },
- id: function () {
- return this.$root.html_id + "-event-calendar-table";
- },
- },
- methods: {
- back_to_list: function () {
- this.$root.weeks = undefined;
- this.$root.view = "events";
- this.$root.name = null;
- this.$root.frontpage_text = null;
- },
- prevmonth: function () {
- var curMonth = parseInt(this.$root.date.substr(5, 2));
- var curYear = parseInt(this.$root.date.substr(0, 4));
- curMonth--;
- if (curMonth < 1) {
- curMonth = 12;
- curYear--;
- }
- this.$root.date = String(curYear) + "-" + padNumber(curMonth, 2) + "-01";
- this.$root.loading++;
- this.$root.reload({focus: '#'+this.id});
- },
- nextmonth: function () {
- var curMonth = parseInt(this.$root.date.substr(5, 2));
- var curYear = parseInt(this.$root.date.substr(0, 4));
- curMonth++;
- if (curMonth > 12) {
- curMonth = 1;
- curYear++;
- }
- this.$root.date = String(curYear) + "-" + padNumber(curMonth, 2) + "-01";
- this.$root.loading++;
- this.$root.reload({focus: '#'+this.id});
- }
- },
-});
-
-Vue.component('pretix-widget-event-week-calendar', {
- template: (''
- + ''),
- computed: {
- display_event_info: function () {
- return this.$root.display_event_info || (this.$root.display_event_info === null && this.$root.parent_stack.length > 0);
- },
- weekname: function () {
- var curWeek = this.$root.week[1];
- var curYear = this.$root.week[0];
- return curWeek + ' / ' + curYear;
- },
- id: function () {
- return this.$root.html_id + "-event-week-table";
- },
- },
- methods: {
- back_to_list: function () {
- this.$root.weeks = undefined;
- this.$root.name = null;
- this.$root.frontpage_text = null;
- this.$root.view = "events";
- },
- prevweek: function () {
- var curWeek = this.$root.week[1];
- var curYear = this.$root.week[0];
- curWeek--;
- if (curWeek < 1) {
- curYear--;
- curWeek = getISOWeeks(curYear);
- }
- this.$root.week = [curYear, curWeek];
- this.$root.loading++;
- this.$root.reload({focus: '#'+this.id});
- },
- nextweek: function () {
- var curWeek = this.$root.week[1];
- var curYear = this.$root.week[0];
- curWeek++;
- if (curWeek > getISOWeeks(curYear)) {
- curWeek = 1;
- curYear++;
- }
- this.$root.week = [curYear, curWeek];
- this.$root.loading++;
- this.$root.reload({focus: '#'+this.id});
- }
- },
-});
-
-Vue.component('pretix-widget', {
- template: (''
- + ''
- ),
- data: shared_widget_data,
- methods: shared_methods,
- mounted: function () {
- var thisObj = this;
- if ("ResizeObserver" in window) {
- var resizeObserver = new ResizeObserver(function(entries) {
- thisObj.mobile = entries[0].contentRect.width <= 800;
- });
- resizeObserver.observe(this.$refs.wrapper);
- } else {
- this.mobile = this.$refs.wrapper.clientWidth <= 800;
- var debounce;
- window.addEventListener("resize", function() {
- if (debounce) clearTimeout(debounce);
- debounce = setTimeout(function () {
- thisObj.mobile = thisObj.$refs.wrapper.clientWidth <= 800;
- }, 100);
- });
- }
- },
- computed: {
- classObject: function () {
- return {
- 'pretix-widget': true,
- 'pretix-widget-mobile': this.mobile,
- 'pretix-widget-use-custom-spinners': !this.$root.use_native_spinners
- };
- }
- }
-});
-
-Vue.component('pretix-button', {
- template: (''
- + ''
- ),
- data: shared_widget_data,
- methods: shared_methods,
-});
-
-/* Function to create the actual Vue instances */
-
-var shared_root_methods = {
- open_link_in_frame: function (event) {
- var url = event.target.attributes.href.value;
- if (this.$root.additionalURLParams) {
- if (url.indexOf('?')) {
- url += '&' + this.$root.additionalURLParams;
- } else {
- url += '?' + this.$root.additionalURLParams;
- }
- }
- if (this.$root.useIframe) {
- event.preventDefault();
- if (url.indexOf('?')) {
- url += '&iframe=1';
- } else {
- url += '?iframe=1';
- }
- this.$root.overlay.frame_src = url;
- } else {
- event.target.href = url;
- return;
- }
- },
- trigger_load_callback: function () {
- this.$nextTick(function () {
- for (var i = 0; i < window.PretixWidget._loaded.length; i++) {
- window.PretixWidget._loaded[i]()
- }
- });
- },
- trigger_close_callback: function () {
- this.$nextTick(function () {
- for (var i = 0; i < window.PretixWidget._closed.length; i++) {
- window.PretixWidget._closed[i]()
- }
- });
- },
- reload: function (opt = {}) {
- var url;
- if (this.$root.is_button) {
- return;
- }
- if (this.$root.subevent) {
- url = this.$root.target_url + this.$root.subevent + '/widget/product_list?lang=' + lang;
- } else {
- url = this.$root.target_url + 'widget/product_list?lang=' + lang;
- }
- if (this.$root.offset) {
- url += '&offset=' + this.$root.offset;
- }
- if (this.$root.filter) {
- url += '&' + this.$root.filter;
- }
- if (this.$root.item_filter) {
- url += '&items=' + encodeURIComponent(this.$root.item_filter);
- }
- if (this.$root.category_filter) {
- url += '&categories=' + encodeURIComponent(this.$root.category_filter);
- }
- if (this.$root.variation_filter) {
- url += '&variations=' + encodeURIComponent(this.$root.variation_filter);
- }
- var cart_id = getCookie(this.cookieName);
- if (this.$root.voucher_code) {
- url += '&voucher=' + encodeURIComponent(this.$root.voucher_code);
- }
- if (cart_id) {
- url += "&cart_id=" + encodeURIComponent(cart_id);
- }
- if (this.$root.date !== null) {
- url += "&date=" + this.$root.date.substr(0, 7);
- } else if (this.$root.week !== null) {
- url += "&date=" + this.$root.week[0] + "-W" + this.$root.week[1];
- }
- if (this.$root.style !== null) {
- url = url + '&style=' + encodeURIComponent(this.$root.style);
- }
- var root = this.$root;
- api._getJSON(url, function (data, xhr) {
- if (typeof xhr.responseURL !== "undefined") {
- var new_url = xhr.responseURL.substr(0, xhr.responseURL.indexOf("/widget/product_list?") + 1);
- var old_url = url.substr(0, url.indexOf("/widget/product_list?") + 1);
- if (new_url !== old_url) {
- if (root.subevent) {
- new_url = new_url.substr(0, new_url.lastIndexOf("/", new_url.length - 1) + 1);
- }
- root.target_url = new_url;
- root.reload();
- return;
- }
- }
- root.connection_error = false;
- if (data.weeks !== undefined) {
- root.weeks = data.weeks;
- root.date = data.date;
- root.week = null;
- root.events = undefined;
- root.view = "weeks";
- root.name = data.name;
- root.frontpage_text = data.frontpage_text;
- root.meta_filter_fields = data.meta_filter_fields;
- } else if (data.days !== undefined) {
- root.days = data.days;
- root.date = null;
- root.week = data.week;
- root.events = undefined;
- root.view = "days";
- root.name = data.name;
- root.frontpage_text = data.frontpage_text;
- root.meta_filter_fields = data.meta_filter_fields;
- } else if (data.events !== undefined) {
- root.events = root.append_events && root.events ? root.events.concat(data.events) : data.events;
- root.append_events = false;
- root.weeks = undefined;
- root.view = "events";
- root.name = data.name;
- root.frontpage_text = data.frontpage_text;
- root.has_more_events = data.has_more_events;
- root.meta_filter_fields = data.meta_filter_fields;
- } else {
- root.view = "event";
- // Replace target_url and subevent with canonical values in case they were slightly wrong
- root.target_url = data.target_url;
- root.subevent = data.subevent;
- // Event data
- root.name = data.name;
- root.frontpage_text = data.frontpage_text;
- root.date_range = data.date_range;
- root.location = data.location;
- root.categories = data.items_by_category;
- root.currency = data.currency;
- root.display_net_prices = data.display_net_prices;
- root.use_native_spinners = data.use_native_spinners;
- root.voucher_explanation_text = data.voucher_explanation_text;
- root.error = data.error;
- root.display_add_to_cart = data.display_add_to_cart;
- root.waiting_list_enabled = data.waiting_list_enabled;
- root.show_variations_expanded = data.show_variations_expanded || !!root.variation_filter;
- root.cart_id = cart_id;
- root.cart_exists = data.cart_exists;
- root.vouchers_exist = data.vouchers_exist;
- root.has_seating_plan = data.has_seating_plan;
- root.has_seating_plan_waitinglist = data.has_seating_plan_waitinglist;
- root.itemnum = data.itemnum;
- }
- root.poweredby = data.poweredby;
- if (root.loading > 0) {
- root.loading--;
- root.trigger_load_callback();
- }
- if (root.parent_stack.length > 0 && root.has_seating_plan && root.categories.length === 0 && !root.frame_dismissed && root.useIframe && !root.error && !root.has_seating_plan_waitinglist) {
- // If we're on desktop and someone selects a seating-only event in a calendar, let's open it right away,
- // but only if the person didn't close it before.
- root.startseating()
- } else {
- // make sure to only move focus to content element when it had focus before the reload/click
- // this is needed because reload is also called on initial load and we do not want to move focus on initial load
- if (root.$el.contains(document.activeElement)) {
- root.$nextTick(function() {
- // wait for redraw, then focus content element for better a11y
- (opt.focus ? document.querySelector(opt.focus) : root.$el).focus();
- });
- }
- }
- }, function (error) {
- root.categories = [];
- root.currency = '';
- if (error.status === 429) {
- root.error = strings['loading_error_429'];
- root.connection_error = true;
- } else {
- root.error = strings['loading_error'];
- root.connection_error = true;
- }
- if (root.loading > 0) {
- root.loading--;
- root.trigger_load_callback();
- }
- });
- },
- startwaiting: function () {
- var redirect_url = this.$root.target_url + 'w/' + widget_id + '/waitinglist/?iframe=1&locale=' + lang;
- if (this.$root.subevent){
- redirect_url += '&subevent=' + this.$root.subevent;
- }
- if (this.$root.additionalURLParams) {
- redirect_url += '&' + this.$root.additionalURLParams;
- }
- if (this.$root.useIframe) {
- this.$root.overlay.frame_src = redirect_url;
- } else {
- window.open(redirect_url);
- }
- },
- startseating: function () {
- var redirect_url = this.$root.target_url + 'w/' + widget_id;
- if (this.$root.subevent){
- redirect_url += '/' + this.$root.subevent;
- }
- redirect_url += '/seatingframe/?iframe=1&locale=' + lang;
- if (this.$root.voucher_code) {
- redirect_url += '&voucher=' + encodeURIComponent(this.$root.voucher_code);
- }
- if (this.$root.cart_id) {
- redirect_url += '&take_cart_id=' + this.$root.cart_id;
- }
- if (this.$root.widget_data) {
- redirect_url += '&widget_data=' + encodeURIComponent(this.$root.widget_data_json);
- }
- if (this.$root.additionalURLParams) {
- redirect_url += '&' + this.$root.additionalURLParams;
- }
- redirect_url += this.$root.consent_parameter;
- if (this.$root.useIframe) {
- this.$root.overlay.frame_src = redirect_url;
- } else {
- window.open(redirect_url);
- }
- },
- choose_event: function (event) {
- this.$root.target_url = event.event_url;
- this.$root.error = null;
- this.$root.connection_error = false;
- this.$root.subevent = event.subevent;
- this.$root.loading++;
- this.$root.reload();
- }
-};
-
-var shared_root_computed = {
- cookieName: function () {
- return "pretix_widget_" + this.target_url.replace(/[^a-zA-Z0-9]+/g, "_");
- },
- formTarget: function () {
- var is_firefox = navigator.userAgent.toLowerCase().indexOf('firefox') > -1;
- var is_android = navigator.userAgent.toLowerCase().indexOf("android") > -1;
- if (is_android && is_firefox) {
- // Opening a POST form in a new browser fails in Firefox. This is supposed to be fixed since FF 76
- // but for some reason, it is still the case in FF for Android.
- // https://bugzilla.mozilla.org/show_bug.cgi?id=1629441
- // https://github.com/pretix/pretix/issues/1040
- return "_top";
- } else {
- return "_blank";
- }
- },
- voucherFormTarget: function () {
- var form_target = this.target_url + 'w/' + widget_id + '/redeem?iframe=1&locale=' + lang;
- var cookie = getCookie(this.cookieName);
- if (cookie) {
- form_target += "&take_cart_id=" + cookie;
- }
- if (this.subevent) {
- form_target += "&subevent=" + this.subevent;
- }
- if (this.$root.widget_data) {
- form_target += '&widget_data=' + encodeURIComponent(this.$root.widget_data_json);
- }
- form_target += this.$root.consent_parameter;
- if (this.$root.additionalURLParams) {
- form_target += '&' + this.$root.additionalURLParams;
- }
- return form_target;
- },
- formMethod: function () {
- if (!this.useIframe && this.is_button && this.items.length === 0) {
- return 'get';
- }
- return 'post';
- },
- formAction: function () {
- if (!this.useIframe && this.is_button && this.items.length === 0) {
- var target;
- if (this.voucher_code) {
- target = this.target_url + 'redeem';
- } else if (this.subevent) {
- target = this.target_url + this.subevent + '/';
- } else {
- target = this.target_url;
- }
- return target;
- }
- var checkout_url = "/" + this.target_url.replace(/^[^\/]+:\/\/([^\/]+)\//, "") + "w/" + widget_id + "/";
- if (!this.$root.cart_exists) {
- checkout_url += "checkout/start";
- }
- if (this.$root.additionalURLParams) {
- checkout_url += '?' + this.$root.additionalURLParams;
- }
- var form_target = this.target_url + 'w/' + widget_id + '/cart/add?iframe=1&next=' + encodeURIComponent(checkout_url);
- var cookie = getCookie(this.cookieName);
- if (cookie) {
- form_target += "&take_cart_id=" + cookie;
- }
- form_target += this.$root.consent_parameter
- return form_target
- },
- newTabTarget: function () {
- var target = this.target_url;
- if (this.subevent) {
- target = this.target_url + this.subevent + '/';
- }
- return target;
- },
- useIframe: function () {
- if (window.crossOriginIsolated === true) {
- console.warn("pretix Widget cannot use iframe due to Cross-Origin-Embed-Policy")
- return false;
- }
- return !this.disable_iframe && (this.skip_ssl || site_is_secure());
- },
- showPrices: function () {
- var has_priced = false;
- var cnt_items = 0;
- for (var i = 0; i < this.categories.length; i++) {
- for (var j = 0; j < this.categories[i].items.length; j++) {
- var item = this.categories[i].items[j];
- if (item.has_variations) {
- cnt_items += item.variations.length;
- has_priced = true;
- } else {
- cnt_items++;
- has_priced = has_priced || item.price.gross != "0.00" || item.free_price;
- }
- }
- }
- return has_priced || cnt_items > 1;
- },
- consent_parameter_value: function () {
- if (typeof this.widget_data["consent"] !== "undefined") {
- return encodeURIComponent(this.widget_data["consent"]);
- }
- return "";
- },
- consent_parameter: function () {
- if (typeof this.widget_data["consent"] !== "undefined") {
- return "&consent=" + encodeURIComponent(this.widget_data["consent"]);
- }
- return "";
- },
- widget_data_json: function () {
- var cloned_data = Object.assign({}, this.widget_data);
- if (typeof cloned_data["consent"] !== "undefined") {
- // Remove consent as we pass it differently. We still keep it as widget_data in the input to avoid breaking
- // the JS API of the widget.
- delete cloned_data["consent"];
- }
- return JSON.stringify(cloned_data);
- },
- additionalURLParams: function () {
- if (!window.location.search.indexOf('utm_')) {
- return '';
- }
- var params = new URLSearchParams(window.location.search);
- for (var [key, value] of params.entries()) {
- if (!key.startsWith('utm_')) {
- params.delete(key);
- }
- }
- return params.toString();
- },
-};
-
-var create_overlay = function (app) {
- var elem = document.createElement('pretix-overlay');
- document.body.appendChild(elem);
-
- var framechild = new Vue({
- el: elem,
- data: function () {
- return {
- parent: app,
- frame_loading: false,
- frame_shown: false,
- error_url_after: null,
- error_url_after_new_tab: true,
- error_message: null,
- lightbox: null,
- prevActiveElement: null,
- }
- },
- props: {
- frame_src: String,
- },
- methods: {
- },
- watch: {
- frame_src: function (newValue, oldValue) {
- // show loading spinner only when previously no frame_src was set
- if (newValue && !oldValue) {
- this.frame_loading = true;
- }
- // to close and unload the iframe, frame_src can be empty -> make it valid HTML with about:blank
- this.$el.querySelector("iframe").src = newValue || "about:blank";
- },
- frame_shown: function (newValue) {
- if (newValue) {
- this.prevActiveElement = document.activeElement;
- var btn = this.$el?.querySelector(".pretix-widget-frame-close a");
- this.$nextTick(function () {
- btn?.focus();
- });
- } else {
- this.prevActiveElement?.focus();
- }
- },
- error_message: function (newValue) {
- if (newValue) {
- this.prevActiveElement = document.activeElement;
- } else {
- this.prevActiveElement?.focus();
- }
- },
- }
- });
- app.$root.overlay = framechild;
-};
-
-function get_ga_client_id(tracking_id) {
- if (typeof ga === "undefined") {
- return null;
- }
- try {
- var trackers = ga.getAll();
- var i, len;
- for (i = 0, len = trackers.length; i < len; i += 1) {
- if (trackers[i].get('trackingId') === tracking_id) {
- return trackers[i].get('clientId');
- }
- }
- } catch (e) {
- }
- return null;
-}
-
-var create_widget = function (element, html_id=null) {
- var target_url = element.attributes.event.value;
- if (!target_url.match(/\/$/)) {
- target_url += "/";
- }
- var voucher = element.attributes.voucher ? element.attributes.voucher.value : null;
- var subevent = element.attributes.subevent ? element.attributes.subevent.value : null;
- var style = element.attributes["list-type"] ? element.attributes["list-type"].value : (element.attributes.style ? element.attributes.style.value : null);
- var skip_ssl = element.attributes["skip-ssl-check"] ? true : false;
- var disable_iframe = element.attributes["disable-iframe"] ? true : false;
- var disable_vouchers = element.attributes["disable-vouchers"] ? true : false;
- var disable_filters = element.attributes["disable-filters"] ? true : false;
- var display_event_info = element.getAttribute("display-event-info"); // null means "auto" (as before), everything other than "false" is true
- if (display_event_info !== null && display_event_info !== "auto") {
- display_event_info = display_event_info !== "false";
- } else {
- display_event_info = null;
- }
- var widget_data = JSON.parse(JSON.stringify(window.PretixWidget.widget_data));
- var filter = element.attributes.filter ? element.attributes.filter.value : null;
- var items = element.attributes.items ? element.attributes.items.value : null;
- var variations = element.attributes.variations ? element.attributes.variations.value : null;
- var categories = element.attributes.categories ? element.attributes.categories.value : null;
- var single_item_select = element.getAttribute("single-item-select") || "checkbox";
- for (var i = 0; i < element.attributes.length; i++) {
- var attrib = element.attributes[i];
- if (attrib.name.match(/^data-.*$/)) {
- widget_data[attrib.name.replace(/^data-/, '')] = attrib.value;
- }
- }
- html_id = html_id || element.id || makeid(16);
-
- var observer = new MutationObserver((mutationList) => {
- mutationList.forEach((mutation) => {
- if (mutation.type == "attributes" && mutation.attributeName.startsWith("data-")) {
- Vue.set(app.widget_data, mutation.attributeName.substring(5), mutation.target.getAttribute(mutation.attributeName));
- }
- });
- });
- var observerOptions = { attributes: true };
-
- if (element.tagName !== "pretix-widget") {
- element.innerHTML = "";
- // we need to watch the container as well as the replaced root-node (see mounted())
- observer.observe(element, observerOptions);
- }
-
- var app = new Vue({
- el: element,
- data: function () {
- return {
- target_url: target_url,
- parent_stack: [],
- subevent: subevent,
- is_button: false,
- categories: null,
- currency: null,
- name: null,
- date_range: null,
- location: null,
- offset: 0,
- has_more_events: false,
- append_events: false,
- frontpage_text: null,
- filter: filter,
- item_filter: items,
- category_filter: categories,
- variation_filter: variations,
- voucher_code: voucher,
- display_net_prices: false,
- use_native_spinners: false,
- single_item_select: single_item_select,
- voucher_explanation_text: null,
- show_variations_expanded: !!variations,
- skip_ssl: skip_ssl,
- disable_iframe: disable_iframe,
- style: style,
- connection_error: false,
- error: null,
- weeks: null,
- days: null,
- date: null,
- week: null,
- frame_dismissed: false,
- events: null,
- view: null,
- display_add_to_cart: false,
- widget_data: widget_data,
- loading: 1,
- widget_id: 'pretix-widget-' + widget_id,
- html_id: html_id,
- vouchers_exist: false,
- disable_vouchers: disable_vouchers,
- disable_filters: disable_filters,
- display_event_info: display_event_info,
- cart_exists: false,
- itemcount: 0,
- overlay: null,
- poweredby: "",
- has_seating_plan: false,
- has_seating_plan_waitinglist: false,
- meta_filter_fields: [],
- }
- },
- created: function () {
- this.reload();
- },
- mounted: function () {
- observer.observe(this.$el, observerOptions);
- },
- computed: shared_root_computed,
- methods: shared_root_methods,
- watch: {
- 'view': function (newValue, oldValue) {
- if (oldValue) {
- // always make sure the widget is scrolled to the top
- // as we only check top, we do not need to wait for a redraw
- var rect = this.$el.getBoundingClientRect();
- if (rect.top < 0) {
- this.$el.scrollIntoView();
- }
- }
- }
- }
- });
- create_overlay(app);
- return app;
-};
-
-var create_button = function (element, html_id=null) {
- var target_url = element.attributes.event.value;
- if (!target_url.match(/\/$/)) {
- target_url += "/";
- }
- var voucher = element.attributes.voucher ? element.attributes.voucher.value : null;
- var subevent = element.attributes.subevent ? element.attributes.subevent.value : null;
- var raw_items = element.attributes.items ? element.attributes.items.value : "";
- var skip_ssl = element.attributes["skip-ssl-check"] ? true : false;
- var disable_iframe = element.attributes["disable-iframe"] ? true : false;
- var button_text = element.innerHTML;
- var widget_data = JSON.parse(JSON.stringify(window.PretixWidget.widget_data));
- for (var i = 0; i < element.attributes.length; i++) {
- var attrib = element.attributes[i];
- if (attrib.name.match(/^data-.*$/)) {
- widget_data[attrib.name.replace(/^data-/, '')] = attrib.value;
- }
- }
- html_id = html_id || element.id || makeid(16);
-
- var observer = new MutationObserver((mutationList) => {
- mutationList.forEach((mutation) => {
- if (mutation.type == "attributes" && mutation.attributeName.startsWith("data-")) {
- Vue.set(app.widget_data, mutation.attributeName.substring(5), mutation.target.getAttribute(mutation.attributeName));
- }
- });
- });
- var observerOptions = { attributes: true };
-
- if (element.tagName !== "pretix-button") {
- element.innerHTML = "" + element.innerHTML + "";
- // Vue does not replace the container, so watch container as well
- observer.observe(element, observerOptions);
- }
-
- var itemsplit = raw_items.split(",");
- var items = [];
- for (var i = 0; i < itemsplit.length; i++) {
- if (itemsplit[i].indexOf("=") > 0 ) {
- var splitthis = itemsplit[i].split("=");
- items.push({'item': splitthis[0], 'count': splitthis[1]})
- }
- }
-
- var app = new Vue({
- el: element,
- data: function () {
- return {
- target_url: target_url,
- subevent: subevent,
- is_button: true,
- skip_ssl: skip_ssl,
- disable_iframe: disable_iframe,
- voucher_code: voucher,
- items: items,
- error: null,
- filter: null,
- frame_dismissed: false,
- widget_data: widget_data,
- widget_id: 'pretix-widget-' + widget_id,
- html_id: html_id,
- button_text: button_text
- }
- },
- created: function () {
- },
- mounted: function () {
- observer.observe(this.$el, observerOptions);
- },
- computed: shared_root_computed,
- methods: shared_root_methods
- });
- create_overlay(app);
- return app;
-};
-
-/* Find all widgets on the page and render them */
-widgetlist = [];
-buttonlist = [];
-window.PretixWidget._loaded = [];
-window.PretixWidget._closed = [];
-window.PretixWidget.addLoadListener = function (f) {
- window.PretixWidget._loaded.push(f);
-}
-window.PretixWidget.addCloseListener = function (f) {
- window.PretixWidget._closed.push(f);
-}
-window.PretixWidget.buildWidgets = function () {
- document.createElement("pretix-widget");
- document.createElement("pretix-button");
- docReady(function () {
- var widgets = document.querySelectorAll("pretix-widget, div.pretix-widget-compat");
- var wlength = widgets.length;
- for (var i = 0; i < wlength; i++) {
- var widget = widgets[i];
- widgetlist.push(create_widget(widget, widget.id || "pretix-widget-"+i));
- }
-
- var buttons = document.querySelectorAll("pretix-button, div.pretix-button-compat");
- var blength = buttons.length;
- for (var i = 0; i < blength; i++) {
- var button = buttons[i];
- buttonlist.push(create_button(button, button.id || "pretix-button-"+i));
- }
- });
-};
-
-window.PretixWidget.open = function (target_url, voucher, subevent, items, widget_data, skip_ssl_check, disable_iframe) {
- if (!target_url.match(/\/$/)) {
- target_url += "/";
- }
-
- var all_widget_data = JSON.parse(JSON.stringify(window.PretixWidget.widget_data));
- if (widget_data) {
- Object.keys(widget_data).forEach(function(key) { all_widget_data[key] = widget_data[key]; });
- }
- var root = document.createElement("div");
- document.body.appendChild(root);
- root.classList.add("pretix-widget-hidden");
- root.innerHTML = "";
- var app = new Vue({
- el: root,
- data: function () {
- return {
- target_url: target_url,
- subevent: subevent || null,
- is_button: true,
- skip_ssl: skip_ssl_check || false,
- disable_iframe: disable_iframe || false,
- voucher_code: voucher || null,
- items: items || [],
- error: null,
- filter: null,
- frame_dismissed: false,
- widget_data: all_widget_data,
- widget_id: 'pretix-widget-' + widget_id,
- button_text: ""
- }
- },
- created: function () {
- },
- computed: shared_root_computed,
- methods: shared_root_methods
- });
- create_overlay(app);
- app.$nextTick(function () {
- if (this.$root.useIframe) {
- this.$refs.btn.buy();
- } else {
- this.$refs.btn.$refs.form.submit();
- }
- })
-};
-
-if (typeof window.pretixWidgetCallback !== "undefined") {
- window.pretixWidgetCallback();
-}
-if (window.PretixWidget.build_widgets) {
- window.PretixWidget.buildWidgets();
-}
-
-/* Set a global variable for debugging. In DEBUG mode, siteglobals will be window, otherwise it will be something
- unnamed. */
-siteglobals.pretixwidget_debug = {
- 'Vue': Vue,
- 'widgets': widgetlist,
- 'buttons': buttonlist
-};
diff --git a/src/pretix/static/pretixpresale/scss/widget.v1.scss b/src/pretix/static/pretixpresale/scss/widget.v1.scss
deleted file mode 100644
index 900b153691..0000000000
--- a/src/pretix/static/pretixpresale/scss/widget.v1.scss
+++ /dev/null
@@ -1,1088 +0,0 @@
-// not included, will be dynamically prepended @import "../../pretixbase/scss/_theme_variables.scss";
-@import "../../pretixbase/scss/_bootstrap_vars.scss";
-@import "../../bootstrap/scss/bootstrap/variables";
-@import "../../bootstrap/scss/bootstrap/mixins";
-
-.pretix-widget-hidden {
- display: none;
-}
-.pretix-widget, .pretix-widget-alert-box {
- a {
- color: $link-color;
- text-decoration: none;
-
- &:hover,
- &:focus {
- color: $link-hover-color;
- text-decoration: $link-hover-decoration;
- }
- &:focus {
- outline: thin dotted;
- outline: 5px auto -webkit-focus-ring-color;
- outline-offset: -2px;
- }
- }
- img {
- border: 0;
- }
- b, strong {
- font-weight: bold;
- }
- h3 {
- font-size: $font-size-h3;
- font-weight: bold;
- padding: 0 15px;
- }
- button, input[type="button"], a.pretix-widget-button {
- overflow: visible;
- text-transform: none;
- cursor: pointer;
- display: inline-block;
- margin-bottom: 0;
- text-align: center;
- vertical-align: middle;
- touch-action: manipulation;
- background-image: none;
- border: 1px solid transparent;
- white-space: nowrap;
- text-decoration: none;
- @include button-size($padding-base-vertical, $padding-base-horizontal, $font-size-base, $line-height-base, $btn-border-radius-base);
- @include user-select(none);
- @include button-variant($btn-primary-color, $btn-primary-bg, $btn-primary-border, $btn-primary-background-active, $btn-primary-border-active, $btn-primary-border-hover);
-
- &,
- &:active,
- &.active {
- &:focus,
- &.focus {
- text-decoration: none;
- @include tab-focus;
- }
- }
- &.disabled,
- &[disabled],
- fieldset[disabled] & {
- cursor: $cursor-disabled;
- @include opacity(.65);
- @include box-shadow(none);
- }
- &.pretix-widget-btn-default {
- @include button-variant($btn-default-color, $btn-default-bg, $btn-default-border, darken($btn-default-bg, 10%), darken($btn-default-border, 25%), darken($btn-default-border, 12%));
- }
- }
- label.pretix-widget-btn-checkbox {
- @include button-variant($btn-default-color, $btn-default-bg, $btn-default-border, darken($btn-default-bg, 10%), darken($btn-default-border, 25%), darken($btn-default-border, 12%));
- border-width: 1px;
- border-style: solid;
- position: relative;
- cursor: pointer;
- padding: 6px 24px;
- min-height: 32px;
- box-sizing: border-box;
- color: #333;
- input {
- position: absolute;
- left: 10px;
- }
- &:has(input:checked) {
- background-color: #e6e6e6;
- border-color: #adadad;
- }
- }
- .pretix-widget-icon-cart {
- display: inline-block;
- width: 1em;
- height: 1em;
- vertical-align: text-bottom;
- fill: #333;
- background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Cpath d='M2.267 6.756c0-.312-.202-.563-.453-.563-.252 0-.454.251-.454.563 0 .312.202.563.454.563.251 0 .453-.251.453-.563Zm3.174 0c0-.312-.202-.563-.454-.563-.251 0-.453.251-.453.563 0 .312.202.563.453.563.252 0 .454-.251.454-.563Zm.453-4.785c0-.154-.103-.282-.227-.282H1.413c-.035-.211-.039-.563-.28-.563H.227c-.124 0-.227.128-.227.282 0 .153.103.281.227.281h.722l.627 3.62c-.049.127-.216.466-.216.603 0 .153.103.281.227.281h3.627c.124 0 .227-.128.227-.281 0-.154-.103-.282-.227-.282H1.955c.036-.088.085-.18.085-.281 0-.102-.032-.212-.046-.308l3.698-.537c.117-.018.202-.141.202-.281V1.971Z' transform='matrix(2.52069 0 0 2.02994 -.035 -.523)'/%3E%3C/svg%3E%0A");
- }
- input:checked + .pretix-widget-icon-cart {
- background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Cpath d='M4.534 3.097a.317.317 0 0 1-.067.197L3.56 4.42a.207.207 0 0 1-.16.084.207.207 0 0 1-.159-.084l-.907-1.126a.317.317 0 0 1-.067-.197c0-.154.103-.282.227-.282.06 0 .117.031.159.084l.521.642V2.252c0-.154.102-.281.226-.281.124 0 .227.127.227.281v1.289l.521-.642a.205.205 0 0 1 .159-.084c.124 0 .227.128.227.282ZM2.267 6.756c0-.312-.202-.563-.453-.563-.252 0-.454.251-.454.563 0 .312.202.563.454.563.251 0 .453-.251.453-.563Zm3.174 0c0-.312-.202-.563-.454-.563-.251 0-.453.251-.453.563 0 .312.202.563.453.563.252 0 .454-.251.454-.563Zm.453-4.785c0-.154-.103-.282-.227-.282H1.413c-.035-.211-.039-.563-.28-.563H.227c-.124 0-.227.128-.227.282 0 .153.103.281.227.281h.722l.627 3.62c-.049.127-.216.466-.216.603 0 .153.103.281.227.281h3.627c.124 0 .227-.128.227-.281 0-.154-.103-.282-.227-.282H1.955c.036-.088.085-.18.085-.281 0-.102-.032-.212-.046-.308l3.698-.537c.117-.018.202-.141.202-.281V1.971Z' transform='matrix(2.52069 0 0 2.02994 -.035 -.523)'/%3E%3C/svg%3E%0A");
- }
- input[type="text"], input[type="number"], select {
- line-height: normal;
- border: 1px solid $input-border;
- border-radius: $input-border-radius;
- height: $input-height-base;
- padding: $padding-base-vertical $padding-base-horizontal;
- color: $input-color;
- background-color: $input-bg;
- @include box-shadow(inset 0 1px 1px rgba(0, 0, 0, .075));
- @include transition(border-color ease-in-out .15s, box-shadow ease-in-out .15s);
- @include placeholder;
- $color-rgba: rgba(red($input-border-focus), green($input-border-focus), blue($input-border-focus), .6);
-
- &:focus {
- border-color: $input-border-focus;
- outline: 0;
- @include box-shadow(inset 0 1px 1px rgba(0, 0, 0, .075), 0 0 8px $color-rgba);
- }
- }
- input[type=number] {
- padding-right: 0; // Setting the padding-right to zero, as some versions Firefox render the arrow-buttons on number inputs useless.
- }
- input[type="checkbox"],
- input[type="radio"] {
- box-sizing: border-box; // 1
- padding: 0; // 2
- &:focus {
- outline: thin dotted;
- outline: 5px auto -webkit-focus-ring-color;
- outline-offset: -2px;
- }
- }
-}
-.pretix-widget-use-custom-spinners input[type=number] {
- padding-right: $padding-base-horizontal;
- -moz-appearance: textfield;
-}
-.pretix-widget-use-custom-spinners input[type=number]::-webkit-outer-spin-button,
-.pretix-widget-use-custom-spinners input[type=number]::-webkit-inner-spin-button {
- -webkit-appearance: none;
- margin: 0;
-}
-.pretix-widget {
- margin: 10px 0;
- padding: 0 10px;
- border: 1px solid #ccc;
- position: relative;
- min-height: 208px;
- border-radius: $input-border-radius;
-
- .pretix-widget-resume-button {
- float: right;
- margin-left: 10px;
- }
-
- .pretix-widget-clickable {
- cursor: pointer;
- }
-
- .pretix-widget-info-message {
- padding: 10px;
- text-align: left;
- margin: 10px 0;
- background-color: white;
- border: 2px solid $brand-info;
- color: $state-info-text;
- border-radius: $alert-border-radius;
- }
-
- .pretix-widget-error-message {
- padding: 10px;
- text-align: center;
- margin: 10px 0;
- background-color: white;
- border: 2px solid $brand-danger;
- color: $state-danger-text;
- border-radius: $alert-border-radius;
- }
-
- .pretix-widget-error-action {
- padding: 10px;
- text-align: center;
- }
-
- .pretix-widget-loading {
- position: absolute;
- left: 0;
- top: 0;
- width: 100%;
- height: 100%;
- background: rgba(255, 255, 255, .8);
- text-align: center;
- }
-
- @-moz-keyframes pretix-widget-spin {
- 100% {
- -moz-transform: rotate(360deg);
- }
- }
-
- @-webkit-keyframes pretix-widget-spin {
- 100% {
- -webkit-transform: rotate(360deg);
- }
- }
-
- @keyframes pretix-widget-spin {
- 100% {
- -webkit-transform: rotate(360deg);
- transform: rotate(360deg);
- }
- }
-
- .pretix-widget-loading svg {
- margin: 40px;
- /*Fallback*/
- position: absolute;
- top: 50%;
- margin-top: -64px;
- /*Sticky*/
- position: -webkit-sticky;
- position: sticky;
- top: Min(50vh, 50%);/* use uppercase M to use CSS-min and not SASS-min*/
-
- -webkit-animation: pretix-widget-spin 6s linear infinite;
- -moz-animation: pretix-widget-spin 6s linear infinite;
- animation: pretix-widget-spin 6s linear infinite;
- }
-
- .pretix-widget-item-row, .pretix-widget-category {
- clear: both;
- }
-
- .pretix-widget-item-title {
- font-weight: bold;
- }
-
- .pretix-widget-item-row {
- padding: 10px 0;
- }
-
- .pretix-widget-category {
- margin: 10px 0;
- }
-
- .pretix-widget-category-description {
- padding: 0 15px;
- }
-
- .pretix-widget-category-name {
- margin: 10px 0 0 0;
- }
-
- .pretix-widget-item-info-col {
- width: 50%;
- float: left;
- padding: 0 15px;
- box-sizing: border-box;
- }
-
- .pretix-widget-item-price-col, .pretix-widget-item-availability-col {
- width: 25%;
- float: left;
- padding: 0 15px;
- box-sizing: border-box;
- }
-
- .pretix-widget-item-description p, .pretix-widget-item-meta {
- margin: 0;
- }
-
- .pretix-widget-item-price-col {
- text-align: right;
- }
-
- del.pretix-widget-pricebox-original-price {
- color: $text-muted;
- }
-
- ins.pretix-widget-pricebox-new-price {
- font-size: 120%;
- font-weight: bold;
- text-decoration: none;
- }
-
- .pretix-widget-clear {
- clear: both;
- }
-
- .pretix-widget-category-description p {
- margin: 0 0 10px;
- }
-
- .pretix-widget-pricebox-tax {
- display: block;
- }
-
- .pretix-widget-item-count-group {
- display: flex;
- }
-
- .pretix-widget-item-count-group input {
- border-radius: 0;
- border-left: none;
- border-right: none;
- }
-
- .pretix-widget-item-count-group button span {
- vertical-align: 25%;
- line-height: 0.5;
- }
-
- .pretix-widget-item-count-dec {
- border-top-right-radius: 0;
- border-bottom-right-radius: 0;
- width: 2.5em;
- z-index: 2;
- }
-
- .pretix-widget-item-count-inc {
- border-top-left-radius: 0;
- border-bottom-left-radius: 0;
- width: 2.5em;
- }
-
- .pretix-widget-item-count-multiple {
- display: block;
- width: 100%;
- box-sizing: border-box;
- padding: 5px;
- text-align: center;
- }
-
- .pretix-widget-pricebox-price-input {
- display: inline;
- width: 100px;
- box-sizing: border-box;
- text-align: right;
- }
-
- .pretix-widget-item-count-single-label {
- display: block;
- text-align: center;
- width: 100%;
- }
-
- .pretix-widget-attribution {
- padding: 10px 15px;
- text-align: center;
- font-size: 12px;
- }
-
- .pretix-widget-item-picture {
- width: 60px;
- height: 60px;
- margin-right: 10px;
- float: left;
- }
-
- .pretix-widget-action {
- margin-left: 75%;
- width: 25%;
- padding: 0 15px;
- box-sizing: border-box;
- }
-
- .pretix-widget-action button {
- width: 100%;
- }
-
- .pretix-widget-voucher-text {
- margin: 10px 0;
- padding: 0 15px;
- }
-
- .pretix-widget-voucher-headline {
- margin: 10px 0 0 0;
- }
-
- .pretix-widget-voucher-input-wrap {
- padding: 0 15px;
- width: 75%;
- box-sizing: border-box;
- float: left;
- }
-
- .pretix-widget-voucher input {
- width: 100%;
- box-sizing: border-box;
- }
-
- .pretix-widget-voucher-button-wrap {
- padding: 0 15px;
- width: 25%;
- box-sizing: border-box;
- float: left;
- }
-
- .pretix-widget-voucher button {
- width: 100%;
- }
-
- .pretix-widget-seating-waitinglist {
- margin: 15px 0;
- }
-
- .pretix-widget-seating-waitinglist-text {
- padding: 0 15px;
- width: 75%;
- box-sizing: border-box;
- float: left;
- }
-
- .pretix-widget-seating-waitinglist-button-wrap {
- padding: 0 15px;
- width: 25%;
- box-sizing: border-box;
- float: left;
- }
-
- .pretix-widget-seating-waitinglist-button {
- width: 100%;
- }
-
- .pretix-widget-item-with-picture .pretix-widget-main-item-row .pretix-widget-item-title-and-description {
- margin-left: 70px;
- }
-
- .pretix-widget-item-availability-col {
- text-align: center;
-
- .pretix-widget-collapse-indicator::before {
- content: "";
- display: inline-block;
- width: $font-size-base;
- height: $font-size-base;
- background: url("data:image/svg+xml,%3Csvg viewBox='0 0 14 14' xmlns='http://www.w3.org/2000/svg' xml:space='preserve'%3E%3Cpath fill='#{url-friendly-colour($link-color)}' d='M6.395 4.151a.268.268 0 0 0-.177.077l-.386.386a.259.259 0 0 0-.077.177c.002.067.029.13.077.179l3.033 3.031-3.033 3.032a.255.255 0 0 0-.077.177.253.253 0 0 0 .077.178l.386.385a.268.268 0 0 0 .177.077.27.27 0 0 0 .178-.077l3.595-3.595a.259.259 0 0 0 .077-.177.255.255 0 0 0-.077-.176L6.573 4.228a.257.257 0 0 0-.178-.077Z'/%3E%3C/svg%3E");
- transition: transform .5s;
- }
-
- .pretix-widget-collapse-indicator[aria-expanded=true]::before {
- transform: rotate(90deg);
- }
- }
-
- .pretix-widget-availability-gone {
- font-weight: bold;
- color: $brand-danger;
- text-transform: uppercase;
- }
-
- .pretix-widget-availability-unavailable {
- color: $brand-danger;
- }
-
- .pretix-widget-item-variations {
- overflow: hidden;
- padding-top: 0;
- padding-bottom: 0;
- margin-top: 0;
- margin-bottom: 0;
- -moz-transition-duration: 0.5s;
- -webkit-transition-duration: 0.5s;
- -o-transition-duration: 0.5s;
- transition-duration: 0.5s;
- -moz-transition-timing-function: ease-in-out;
- -webkit-transition-timing-function: ease-in-out;
- -o-transition-timing-function: ease-in-out;
- transition-timing-function: ease-in-out;
- }
- .pretix-widget-event-header {
- padding-top: 10px;
- text-align: center;
- }
- .pretix-widget-event-details {
- padding-top: 10px;
- text-align: center;
- }
- .pretix-widget-event-location {
- display: none;
- padding-top: 10px;
- text-align: center;
- }
- .pretix-widget-event-description {
- padding: 0 15px;
- }
- .pretix-widget-event-list-back {
- padding-top: 10px;
- text-align: center;
- display: block;
- a {
- display: block;
- }
- }
- .pretix-widget-back {
- padding-bottom: 10px;
- text-align: center;
- display: block;
- a {
- display: block;
- }
- }
-
- .pretix-widget-event-list {
- padding: 10px 0;
- cursor: pointer;
- }
- .pretix-widget-event-list-entry {
- display: flex;
- flex-direction: row;
- padding: 5px 0;
- flex-wrap: wrap;
- color: $text-color;
-
- &:hover, &:active, &:focus {
- background: $gray-lighter;
- text-decoration: none;
- }
-
- .pretix-widget-event-list-entry-name {
- width: 50%;
- padding: 5px;
- box-sizing: border-box;
- }
- .pretix-widget-event-list-entry-location {
- padding: 5px;
- box-sizing: border-box;
- display: none;
- }
- .pretix-widget-event-list-entry-date {
- width: 25%;
- padding: 5px;
- box-sizing: border-box;
- }
- .pretix-widget-event-list-entry-availability {
- width: 25%;
- text-align: right;
- padding: 7px 5px 3px;
- box-sizing: border-box;
- span {
- display: inline;
- padding: 2px 6px 3px;
- font-size: 75%;
- font-weight: bold;
- line-height: 1;
- color: #fff;
- text-align: center;
- white-space: nowrap;
- vertical-align: baseline;
- border-radius: 4px;
- }
- }
- }
-
- .pretix-widget-event-availability-orange .pretix-widget-event-list-entry-availability span,
- .pretix-widget-event-availability-orange.pretix-widget-event-calendar-event {
- background-color: $brand-warning;
- }
- .pretix-widget-event-availability-none .pretix-widget-event-list-entry-availability span,
- .pretix-widget-event-availability-none.pretix-widget-event-calendar-event {
- background-color: $brand-primary;
- }
- .pretix-widget-event-availability-green .pretix-widget-event-list-entry-availability span,
- .pretix-widget-event-availability-green.pretix-widget-event-calendar-event {
- background-color: $brand-success;
- }
- .pretix-widget-event-availability-red .pretix-widget-event-list-entry-availability span,
- .pretix-widget-event-availability-red.pretix-widget-event-calendar-event {
- background-color: $brand-danger;
- }
- .pretix-widget-event-availability-low .pretix-widget-event-list-entry-availability span {
- border-left: 10px solid $brand-warning;
- }
- .pretix-widget-event-availability-low.pretix-widget-event-calendar-event {
- border-right: 10px solid $brand-warning;
- }
-
- .pretix-widget-event-calendar {
- padding-top: 10px;
- word-break: break-word;
-
- .pretix-widget-event-week-table {
- display: flex;
- flex-direction: row;
-
- .pretix-widget-event-week-col {
- flex: 1;
- margin: 0 5px;
-
- &:first-child {
- margin-left: 0;
- }
- &:last-child {
- margin-right: 0;
- }
- }
- }
-
- .pretix-widget-event-calendar-head {
- display: flex;
- flex-direction: row;
-
- strong {
- width: 50%;
- text-align: center;
- display: block;
- }
- .pretix-widget-event-calendar-next-month, .pretix-widget-event-calendar-previous-month {
- display: block;
- width: 25%;
- }
- .pretix-widget-event-calendar-next-month {
- text-align: right;
- }
- }
- .pretix-widget-event-calendar-event {
- display: block;
- border-radius: 4px;
- padding: 5px;
- color: white;
- cursor: pointer;
- margin-bottom: 5px;
- &:last-child {
- margin-bottom: 0;
- }
- &:hover {
- text-decoration: none;
- }
- }
-
- .pretix-widget-event-calendar-table {
- width: 100%;
-
- th, td {
- width: 14.285714285714286%;
- vertical-align: top;
- padding: 10px 5px;
- }
- }
- .pretix-widget-event-calendar-day {
- font-weight: bold;
- }
- }
-
- .pretix-widget-seating-link-wrapper {
- padding: 0 15px;
- margin: 15px 0 10px;
- }
- .pretix-widget-seating-link {
- display: block;
- width: 100%;
- }
-}
-
-
-.pretix-widget-event-list-filter-form {
- display: flex;
- flex-direction: row;
- align-items: end;
- margin-bottom: 15px;
-
- .pretix-widget-event-list-filter-field {
- display: block;
- width: 100%;
- margin: 0 15px 0 0;
-
- label {
- display: inline-block;
- font-weight: bold;
- margin-bottom: 5px;
- }
-
- select {
- display: block;
- width: 100%;
- }
- }
- .pretix-widget-event-list-filter-field:last-child {
- margin: 0;
- }
-}
-.pretix-widget.pretix-widget-mobile .pretix-widget-event-list-filter-form {
- display: block;
-
- .pretix-widget-event-list-filter-field {
- display: block;
- margin: 0 0 5px;
- }
-}
-
-@keyframes pretix-widget-bounce-in {
- 0% {
- transform: scale(0);
- }
- 50% {
- transform: scale(1.5);
- }
- 100% {
- transform: scale(1);
- }
-}
-.pretix-widget-alert-holder {
- position: fixed;
- left: 0;
- top: 0;
- width: 100%;
- height: 100%;
- background: rgba(255, 255, 255, 0.8);
- z-index: 16777271;
- visibility: hidden;
- opacity: 0;
- transition: opacity 0.5s; /* do not animate visibility or we'll have a flashing thing on load */
-
- &.pretix-widget-alert-shown {
- visibility: visible;
- opacity: 1;
- transition: opacity 0.5s, visibility 0.5s;
- }
-
- .bounce-enter-active {
- animation: pretix-widget-bounce-in .5s;
- }
- .bounce-leave-active {
- animation: pretix-widget-bounce-in .5s reverse;
- }
-
- .pretix-widget-alert-box {
- position: fixed;
- left: 50%;
- width: 600px;
- margin-left: -300px;
- top: 100px;
- background: white;
- border-radius: 5px 5px 5px 5px;
- -moz-border-radius: 5px 5px 5px 5px;
- -webkit-border-radius: 5px 5px 5px 5px;
- box-shadow: 0 4px 18px 0 rgba(0, 0, 0, 0.1), 0 6px 20px 0 rgba(0, 0, 0, 0.09);
- -webkit-box-shadow: 0 4px 18px 0 rgba(0, 0, 0, 0.1), 0 6px 20px 0 rgba(0, 0, 0, 0.09);
- -moz-box-shadow: 0 4px 18px 0 rgba(0, 0, 0, 0.1), 0 6px 20px 0 rgba(0, 0, 0, 0.09);
- box-sizing: border-box;
- padding: 42px 20px 20px 20px;
- text-align: center;
- font-size: 20px;
-
- p:first-child {
- margin-top: 0;
- }
- p:last-child {
- margin-bottom: 0;
- }
- }
- .pretix-widget-alert-icon {
- position: fixed;
- left: 50%;
- width: 64px;
- margin-left: -32px;
- top: 68px;
- }
-}
-.pretix-widget-frame-holder {
- position: fixed;
- left: 0;
- top: 0;
- width: 100%;
- height: 100%;
- background: rgba(255, 255, 255, 0.8);
- z-index: 16777271;
- visibility: hidden;
- opacity: 0;
- transition: opacity 0.5s, visibility 0.5s;
-
- .pretix-widget-frame-loading {
- text-align: center;
- display: flex;
- align-items: center;
- justify-content: center;
- height: 100%;
- width: 100%;
- position: fixed;
- left: 0;
- top: 0;
- }
-
- .pretix-widget-frame-loading svg {
- margin: 40px;
- -webkit-animation: pretix-widget-spin 6s linear infinite;
- -moz-animation: pretix-widget-spin 6s linear infinite;
- animation: pretix-widget-spin 6s linear infinite;
- }
-
- &.pretix-widget-frame-shown {
- visibility: visible;
- opacity: 1;
- transition: opacity 0.5s, visibility 0.5s;
- }
-
- .pretix-widget-frame-inner {
- position: fixed;
- left: 10%;
- width: 80%;
- height: 80%;
- top: 10%;
- background: white;
- border-radius: 5px 5px 5px 5px;
- -moz-border-radius: 5px 5px 5px 5px;
- -webkit-border-radius: 5px 5px 5px 5px;
- box-shadow: 0 4px 18px 0 rgba(0, 0, 0, 0.1), 0 6px 20px 0 rgba(0, 0, 0, 0.09);
- -webkit-box-shadow: 0 4px 18px 0 rgba(0, 0, 0, 0.1), 0 6px 20px 0 rgba(0, 0, 0, 0.09);
- -moz-box-shadow: 0 4px 18px 0 rgba(0, 0, 0, 0.1), 0 6px 20px 0 rgba(0, 0, 0, 0.09);
- box-sizing: border-box;
- padding: 10px;
- }
-
- .pretix-widget-frame-close {
- position: fixed;
- right: 10%;
- top: 10%;
- width: 24px;
- height: 24px;
- background: $brand-primary;
- margin: -12px -12px 0 0;
- border-radius: 12px;
- -moz-border-radius: 12px;
- -webkit-border-radius: 12px;
- text-align: center;
- }
-
- .pretix-widget-frame-close a {
- color: white;
- font-weight: bold;
- font-family: sans-serif;
- text-decoration: none;
- padding: 4px 0;
- display: inline-block;
- line-height: 16px;
- }
-
- .pretix-widget-frame-close svg {
- display: inline-block;
- border: none;
- }
-
- .pretix-widget-frame-inner iframe {
- width: 100% !important;
- height: 100% !important;
- }
-}
-
-.pretix-widget-lightbox-holder {
- position: fixed;
- left: 0;
- top: 0;
- width: 100%;
- height: 100%;
- background: rgba(255, 255, 255, 0.8);
- z-index: 16777271;
- visibility: hidden;
- opacity: 0;
- transition: opacity 0.5s, visibility 0.5s;
- display: flex;
- align-items: center;
- justify-content: center;
-
- .pretix-widget-lightbox-loading svg {
- margin: 40px;
- -webkit-animation: pretix-widget-spin 6s linear infinite;
- -moz-animation: pretix-widget-spin 6s linear infinite;
- animation: pretix-widget-spin 6s linear infinite;
- }
-
- &.pretix-widget-lightbox-shown {
- visibility: visible;
- opacity: 1;
- transition: opacity 0.5s, visibility 0.5s;
- }
-
- .pretix-widget-lightbox-inner {
- position: relative;
- background: white;
- border-radius: 5px 5px 5px 5px;
- -moz-border-radius: 5px 5px 5px 5px;
- -webkit-border-radius: 5px 5px 5px 5px;
- box-shadow: 0 4px 18px 0 rgba(0, 0, 0, 0.1), 0 6px 20px 0 rgba(0, 0, 0, 0.09);
- -webkit-box-shadow: 0 4px 18px 0 rgba(0, 0, 0, 0.1), 0 6px 20px 0 rgba(0, 0, 0, 0.09);
- -moz-box-shadow: 0 4px 18px 0 rgba(0, 0, 0, 0.1), 0 6px 20px 0 rgba(0, 0, 0, 0.09);
- box-sizing: border-box;
- padding: 10px;
- max-width: 90%;
- max-height: 90%;
- }
- &.pretix-widget-lightbox-isloading .pretix-widget-lightbox-inner {
- position: absolute;
- width: 1px;
- height: 1px;
- padding: 0;
- margin: -1px;
- overflow: hidden;
- clip: rect(0,0,0,0);
- border: 0;
- }
-
- .pretix-widget-lightbox-image {
- margin: 0;
- padding: 0;
- text-align: center;
- }
- .pretix-widget-lightbox-image img {
- max-width: 80vw;
- max-height: 80vh;
- object-fit: scale-down;
- }
- .pretix-widget-lightbox-image figcaption {
- margin: 0.5em 0 0;
- }
-
- .pretix-widget-lightbox-close {
- position: absolute;
- right: -12px;
- top: -12px;
- width: 24px;
- height: 24px;
- background: $brand-primary;
- margin: 0;
- border: none;
- border-radius: 12px;
- -moz-border-radius: 12px;
- -webkit-border-radius: 12px;
- text-align: center;
- color: white;
- font-weight: bold;
- font-family: sans-serif;
- text-decoration: none;
- padding: 4px 0;
- display: inline-block;
- line-height: 16px;
- cursor: pointer;
- }
-
- .pretix-widget-lightbox-close svg {
- display: inline-block;
- border: none;
- }
-}
-
-.pretix-widget-primary-color {
- /* in SVG */
- fill: $brand-primary;
-}
-
-.pretix-widget-event-list-load-more {
- text-align: center;
-}
-
-.pretix-widget.pretix-widget-mobile {
- .pretix-widget-event-week-table {
- display: block;
-
- .pretix-widget-event-week-col {
- flex: 1;
- margin: 10px 0;
- }
- }
-
- .pretix-widget-item-info-col {
- width: 100%;
- float: none;
- margin-bottom: 5px;
- }
- .pretix-widget-item-info-col:after {
- display: block;
- content: "";
- clear: both;
- }
- .pretix-widget-item-price-col, .pretix-widget-item-availability-col {
- width: 50%;
- min-width: 140px;
- }
- .pretix-widget-action {
- width: 100%;
- margin-left: 0;
- }
- .pretix-widget-voucher-input-wrap {
- width: 100%;
- float: none;
- }
- .pretix-widget-voucher-button-wrap {
- width: 100%;
- float: none;
- margin-top: 10px;
- }
-
- .pretix-widget-event-list-entry {
- .pretix-widget-event-list-entry-name {
- width: 100%;
- }
- .pretix-widget-event-list-entry-location {
- width: 100%;
- }
- .pretix-widget-event-list-entry-date {
- width: 50%;
- }
- .pretix-widget-event-list-entry-availability {
- width: 50%;
- }
- }
-
- .pretix-widget-event-calendar {
- .pretix-widget-event-calendar-events {
- display: none;
- }
- .pretix-widget-event-week-table {
- .pretix-widget-event-calendar-events {
- display: block;
- }
- }
- td.pretix-widget-has-events {
- background: $brand-primary;
- color: white;
- cursor: pointer;
- &.pretix-widget-day-availability-red {
- background: $brand-danger;
- }
- &.pretix-widget-day-availability-green {
- background: $brand-success;
- }
- &.pretix-widget-day-availability-low {
- border-right: 5px solid $brand-warning;
- }
- &.pretix-widget-day-availability-orange {
- background: $brand-warning;
- }
- }
-
- .pretix-widget-event-calendar-head {
- display: block;
- strong {
- width: 100%;
- display: block;
- }
- .pretix-widget-event-calendar-next-month, .pretix-widget-event-calendar-previous-month {
- display: block;
- width: 100%;
- text-align: center;
- }
- }
- }
-}
-
-@media (min-width: 1200px) {
- .pretix-widget-frame-holder {
- .pretix-widget-frame-inner {
- left: 50%;
- margin-left: -540px;
- width: 1080px;
- }
- .pretix-widget-frame-close {
- left: 50%;
- margin-left: 528px;
- }
- }
-}
-
-@media (max-width: 800px) {
- .pretix-widget-frame-holder .pretix-widget-frame-inner {
- left: 0;
- width: 100%;
- height: 100%;
- top: 0;
- background: $brand-primary;
- border-radius: 0;
- -moz-border-radius: 0;
- -webkit-border-radius: 0;
- box-shadow: none;
- -webkit-box-shadow: none;
- -moz-box-shadow: none;
- padding: 40px 0 0 0;
- }
- .pretix-widget-frame-holder .pretix-widget-frame-close {
- right: 20px;
- top: 20px;
- background: white;
- svg path {
- fill: $brand-primary;
- }
- }
-}
diff --git a/src/tests/presale/test_widget.py b/src/tests/presale/test_widget.py
index ac606dacca..a11b3c9099 100644
--- a/src/tests/presale/test_widget.py
+++ b/src/tests/presale/test_widget.py
@@ -542,7 +542,7 @@ class WidgetCartTest(CartTestMixin, TestCase):
@override_settings(COMPRESS_PRECOMPILERS=settings.COMPRESS_PRECOMPILERS_ORIGINAL)
def test_css_customized(self):
- response = self.client.get('/%s/%s/widget/v1.css' % (self.orga.slug, self.event.slug))
+ response = self.client.get('/%s/%s/widget/v2.css' % (self.orga.slug, self.event.slug))
c = b"".join(response.streaming_content).decode()
assert '#8E44B3' in c
assert '#33c33c' not in c
@@ -550,7 +550,7 @@ class WidgetCartTest(CartTestMixin, TestCase):
self.orga.settings.primary_color = "#33c33c"
self.orga.cache.clear()
- response = self.client.get('/%s/%s/widget/v1.css' % (self.orga.slug, self.event.slug))
+ response = self.client.get('/%s/%s/widget/v2.css' % (self.orga.slug, self.event.slug))
c = b"".join(response.streaming_content).decode()
assert '#8E44B3' not in c
assert '#33c33c' in c
@@ -558,18 +558,18 @@ class WidgetCartTest(CartTestMixin, TestCase):
self.event.settings.primary_color = "#34c34c"
self.event.cache.clear()
- response = self.client.get('/%s/%s/widget/v1.css' % (self.orga.slug, self.event.slug))
+ response = self.client.get('/%s/%s/widget/v2.css' % (self.orga.slug, self.event.slug))
c = b"".join(response.streaming_content).decode()
assert '#8E44B3' not in c
assert '#33c33c' not in c
assert '#34c34c' in c
def test_js_localized(self):
- response = self.client.get('/widget/v1.en.js')
+ response = self.client.get('/widget/v2.en.js')
c = response.content.decode()
assert '%m/%d/%Y' in c
assert '%d.%m.%Y' not in c
- response = self.client.get('/widget/v1.de.js')
+ response = self.client.get('/widget/v2.de.js')
c = response.content.decode()
assert '%m/%d/%Y' not in c
assert '%d.%m.%Y' in c