hr-design-system-handlebars 1.108.0 → 1.109.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (39) hide show
  1. package/.storybook/main.js +1 -0
  2. package/CHANGELOG.md +24 -0
  3. package/dist/assets/index.css +11 -6
  4. package/dist/assets/js/alpine.js +2 -1
  5. package/dist/assets/js/components/forms/contactForm.alpine.js +181 -18
  6. package/dist/assets/js/components/forms/inputHandler.alpine.js +52 -5
  7. package/dist/views/components/content_nav/content_nav_container.hbs +1 -1
  8. package/dist/views/components/forms/controls.hbs +3 -2
  9. package/dist/views/components/forms/input.hbs +4 -0
  10. package/dist/views/components/forms/webform.hbs +37 -29
  11. package/dist/views/components/horizontal_scroll_container/horizontal_scroll_container.hbs +2 -2
  12. package/dist/views/components/horizontal_scroll_container/horizontal_scroll_container_example.hbs +2 -2
  13. package/dist/views/components/site_header/brand_navigation/brand_navigation.hbs +1 -1
  14. package/dist/views/components/site_header/section_navigation/section_navigation.hbs +1 -1
  15. package/dist/views_static/components/content_nav/content_nav_container.hbs +1 -1
  16. package/dist/views_static/components/forms/controls.hbs +3 -2
  17. package/dist/views_static/components/forms/input.hbs +4 -0
  18. package/dist/views_static/components/forms/webform.hbs +37 -29
  19. package/dist/views_static/components/horizontal_scroll_container/horizontal_scroll_container.hbs +2 -2
  20. package/dist/views_static/components/horizontal_scroll_container/horizontal_scroll_container_example.hbs +2 -2
  21. package/dist/views_static/components/site_header/brand_navigation/brand_navigation.hbs +1 -1
  22. package/dist/views_static/components/site_header/section_navigation/section_navigation.hbs +1 -1
  23. package/package.json +2 -1
  24. package/src/assets/fixtures/content/copytext/copytext_webform.json +5 -58
  25. package/src/assets/js/alpine.js +2 -1
  26. package/src/stories/views/components/content/copytext/copytext-form.stories.js +41 -0
  27. package/src/stories/views/components/content/copytext/copytext.stories.js +0 -7
  28. package/src/stories/views/components/content/copytext/fixtures/copytext_webform.json +1 -1
  29. package/src/stories/views/components/content_nav/content_nav_container.hbs +1 -1
  30. package/src/stories/views/components/forms/contactForm.alpine.js +181 -18
  31. package/src/stories/views/components/forms/controls.hbs +3 -2
  32. package/src/stories/views/components/forms/input.hbs +4 -0
  33. package/src/stories/views/components/forms/inputHandler.alpine.js +52 -5
  34. package/src/stories/views/components/forms/webform.hbs +37 -29
  35. package/src/stories/views/components/horizontal_scroll_container/horizontal_scroll_container.hbs +2 -2
  36. package/src/stories/views/components/horizontal_scroll_container/horizontal_scroll_container_example.hbs +2 -2
  37. package/src/stories/views/components/site_header/brand_navigation/brand_navigation.hbs +1 -1
  38. package/src/stories/views/components/site_header/section_navigation/section_navigation.hbs +1 -1
  39. package/tailwind.config.js +1 -0
@@ -5,38 +5,46 @@
5
5
  <h3 class="mb-6 text-2xl font-headingSerif sm:mb-12">
6
6
  {{this.title}}
7
7
  </h3>
8
-
9
- <form
10
- x-ref="form{{nextRandom}}"
11
- ax-load
12
- x-data="contactForm('form{{getRandom}}')"
13
- x-init="formInit()"
14
- x-ignore
8
+ <div id="formWrapper">
9
+ <form
10
+ x-ref="form{{nextRandom}}"
11
+ ax-load
12
+ x-data="contactForm('form{{getRandom}}','{{this.jsonURL}}','{{this.errorMessages}}','{{this.isMultipart}}','{{this.trackingInformations}}')"
13
+ x-init="formInit()"
14
+ x-ignore
15
15
 
16
- @submit.prevent="submitData"
17
- id="form{{getRandom}}"
18
- class="relative flex flex-col justify-center overflow-hidden group"
19
- action="{{this.url}}"
20
- method="post"
21
- enctype="{{if this.isMultipart 'multipart/form-data' 'application/x-www-form-urlencoded'}}"
22
- accept-charset="utf-8"
23
-
24
- >
25
-
26
- <div class="">
27
- <div class="px-4 py-2 font-bold text-white bg-red-500 rounded-t">
28
- DEBUG
16
+ @submit.prevent="submitData"
17
+ id="form{{getRandom}}"
18
+ class="relative flex flex-col justify-center overflow-hidden group"
19
+ action="{{this.url}}"
20
+ method="post"
21
+ enctype="{{if this.isMultipart 'multipart/form-data' 'application/x-www-form-urlencoded'}}"
22
+ accept-charset="utf-8"
23
+
24
+ >
25
+
26
+ <div class="">
27
+ <div class="px-4 py-2 font-bold text-white bg-red-500 rounded-t">
28
+ DEBUG
29
+ </div>
30
+ <div class="px-4 py-3 text-red-700 bg-red-100 border border-t-0 border-red-400 rounded-b">
31
+ <div>submissionAttempted[form{{getRandom}}]:<span x-text="getSubmissionAttempted()" class="font-bold" :class="getSubmissionAttempted() ? 'text-green-800' : 'text-red-700'"></span></div>
32
+ <div>isPosting:<span x-text="isPosting" class="font-bold" :class="isPosting ? 'text-green-800' : 'text-red-700'"></span></div>
33
+
34
+ </div>
29
35
  </div>
30
- <div class="px-4 py-3 text-red-700 bg-red-100 border border-t-0 border-red-400 rounded-b">
31
- <div>submissionAttempted[form{{getRandom}}]:<span x-text="getSubmissionAttempted()" class="font-bold" :class="getSubmissionAttempted() ? 'text-green-800' : 'text-red-700'"></span></div>
32
- </div>
33
- </div>
34
- {{> components/forms/fields _formId=(joinStrings 'form' (getRandom)) }}
36
+ {{> components/forms/fields _formId=(joinStrings 'form' (getRandom)) }}
35
37
 
36
- {{> components/forms/controls }}
37
-
38
- </form>
39
-
38
+ {{> components/forms/controls }}
39
+ <template id="successMessage">
40
+ <h2>SUPER DAS HAT ALLES FUNKTIONIERT</h2>
41
+ </template>
42
+ <template id="errorMessage">
43
+ <h2>DAS HAT LEIDER NICHT FUNKTIONIERT</h2>
44
+ </template>
45
+
46
+ </form>
47
+ </div>
40
48
  {{/components/forms/backgroundBox }}
41
49
  {{~else~}}
42
50
  {{> content/webform/components/webform _addClass="print:hidden copytext__clearBox marginTrailer--m"}}
@@ -9,12 +9,12 @@
9
9
  <button style="background-image: linear-gradient(90deg, {{_bgcolor}} 50%, transparent);" class="absolute left-0 z-10 flex items-center justify-start w-10 h-full text-{{_iconcolor}} disabled:hidden" @click="prev($refs.scrollContainer_{{getRandom}})" :disabled="!arrowLeftDisplay" tabindex="-1" aria-hidden="true" >
10
10
  {{> components/base/image/icon _icon="arrow-left" _iconmap="icons" _addClass="w-3.5 h-3.5 fill-current" }}
11
11
  </button>
12
- <button style="background-image: linear-gradient(270deg, {{_bgcolor}} 50%, transparent);" class="bg-gradient-to-l from-[{{_bgcolor}}] absolute right-0 z-10 flex items-center justify-end w-10 h-full text-{{_iconcolor}} disabled:hidden group" @click="next($refs.scrollContainer_{{getRandom}})" :disabled="!arrowRightDisplay" tabindex="-1" aria-hidden="true">
12
+ <button style="background-image: linear-gradient(270deg, {{_bgcolor}} 50%, transparent);" class="bg-gradient-to-l absolute right-0 z-10 flex items-center justify-end w-10 h-full text-{{_iconcolor}} disabled:hidden group{{_css}}" @click="next($refs.scrollContainer_{{getRandom}})" :disabled="!arrowRightDisplay" tabindex="-1" aria-hidden="true">
13
13
  {{> components/base/image/icon _icon="arrow-right" _iconmap="icons" _addClass="w-3.5 h-3.5 fill-current" }}
14
14
  </button>
15
15
  </div>
16
16
  </template>
17
- <div x-ref="scrollContainer_{{getRandom}}" @scroll="updateIndex($event.target)" class="w-full overflow-hidden overflow-x-scroll transition-all duration-300 ease-in-out cursor-default hide-scroll-bar align-center">
17
+ <div x-ref="scrollContainer_{{getRandom}}" @scroll="updateIndex($event.target)" class="w-full overflow-hidden overflow-x-scroll transition-all duration-300 ease-in-out cursor-default hide-scroll-bar">
18
18
  {{> @partial-block }}
19
19
  </div>
20
20
  </div>
@@ -1,5 +1,5 @@
1
1
  <div class="w-full h-auto mb-10">
2
- {{#> components/horizontal_scroll_container/horizontal_scroll_container _viewport="xs" _onDarkBackground="true" _bgcolor="var(--color-navigation-bg)" _iconcolor="navigation-icons"}}
2
+ {{#> components/horizontal_scroll_container/horizontal_scroll_container _viewport="xs" _onDarkBackground="true" _css=" from-[--color-navigation-bg]" _bgcolor="var(--color-navigation-bg)" _iconcolor="navigation-icons"}}
3
3
 
4
4
  <div class="flex h-auto p-4 pr-10 text-lg leading-6 text-white bg-primary">
5
5
  <p class="whitespace-nowrap ">Guten Tag. Dieses Div kann mittels click auf die Pfeiltasten verschoben werden kann. Die Pfeile werden dynamisch angezeigt/ausgeblendet sobald der Rand des Inhalts erreicht ist. </p>
@@ -8,7 +8,7 @@
8
8
  {{/components/horizontal_scroll_container/horizontal_scroll_container}}
9
9
  </div>
10
10
  <div class="w-full h-auto mb-10">
11
- {{#> components/horizontal_scroll_container/horizontal_scroll_container _viewport="xs" _onDarkBackground="true" _bgcolor="var(--color-navigation-bg)" _iconcolor="navigation-icons"}}
11
+ {{#> components/horizontal_scroll_container/horizontal_scroll_container _viewport="xs" _onDarkBackground="true" _css=" from-[--color-navigation-bg]" _bgcolor="var(--color-navigation-bg)" _iconcolor="navigation-icons"}}
12
12
 
13
13
  <div class="flex h-auto p-4 pr-10 text-lg leading-6 text-white bg-primary">
14
14
  <p class="whitespace-nowrap ">Guten Tag. Dieses Div kann mittels click auf die Pfeiltasten verschoben werden kann.</p>
@@ -1,5 +1,5 @@
1
1
  <div class="grid-cols-12 px-5 lg:px-10 col-full sm:col-main">
2
- {{#> components/horizontal_scroll_container/horizontal_scroll_container _viewport="xs" _bgcolor="var(--color-brandnavigation-bg)" _iconcolor="primary" }}
2
+ {{#> components/horizontal_scroll_container/horizontal_scroll_container _viewport="xs" _css=" from-[--color-brandnavigation-bg]" _bgcolor="var(--color-brandnavigation-bg)" _iconcolor="primary" }}
3
3
  <nav class="flex w-full text-xs list-none text-grey-scorpion">
4
4
  <span id="brandNavHeading" class="hidden">Navigation der Marken des Hessischen Rundfunks</span>
5
5
  {{#with this.brandNavigationItems}}
@@ -3,7 +3,7 @@
3
3
  class="w-full px-0 mt-10 sb-section-navigation md:mt-0 lg:grid-cols-12 lg:px-10 lg:col-main "
4
4
  x-effect="$el.setAttribute('aria-expanded', $store.burgeropen || $screen('lg')); $el.setAttribute('aria-hidden', ! ($store.burgeropen || $screen('lg')))"
5
5
  >
6
- {{#> components/horizontal_scroll_container/horizontal_scroll_container _viewport="lg" _bgcolor="var(--color-navigation-bg)" _iconcolor="navigation-icons"}}
6
+ {{#> components/horizontal_scroll_container/horizontal_scroll_container _viewport="lg" _css=" from-[--color-navigation-bg]" _bgcolor="var(--color-navigation-bg)" _iconcolor="navigation-icons"}}
7
7
  <div class="flex w-full">
8
8
  <span id="sectionNavHeadline" class="hidden">Bereichsnavigation</span>
9
9
 
package/package.json CHANGED
@@ -6,7 +6,7 @@
6
6
  "license": "MIT",
7
7
  "main": "dist/index.js",
8
8
  "repository": "https://github.com/szuelch/hr-design-system-handlebars",
9
- "version": "1.108.0",
9
+ "version": "1.109.0",
10
10
  "scripts": {
11
11
  "test": "echo \"Error: no test specified\" && exit 1",
12
12
  "storybook": "storybook dev -p 6006 public",
@@ -102,6 +102,7 @@
102
102
  "remark-gfm": "^4.0.0",
103
103
  "rimraf": "^3.0.2",
104
104
  "storybook": "^8.2.6",
105
+ "storybook-addon-mock": "^5.0.0",
105
106
  "storybook-conditional-toolbar-selector": "^1.0.3",
106
107
  "style-loader": "^4.0.0",
107
108
  "tailwindcss": "^3.0.23",
@@ -9,6 +9,10 @@
9
9
  "isWebForm": true,
10
10
  "hasNewWebForm": true,
11
11
  "title": "Kontaktformular",
12
+ "jsonURL": "https://ugc-hessenschau.dev-ext.hrcms.gcp.cloud.hr.de",
13
+ "errorMessages": "errorMessages",
14
+ "isMultipart": "isMultipart",
15
+ "trackingInformations": "trackingInformations",
12
16
  "fields":[
13
17
  {
14
18
  "@->jsoninclude": "forms/form_fields.inc.json",
@@ -30,65 +34,8 @@
30
34
  }
31
35
  ]
32
36
 
33
- }
34
- },
35
- {
36
- "isHeadline": true,
37
- "text": "Noch ein Formular"
38
- },
39
- {
40
- "paragraphBoxItem": {
41
- "isWebForm": true,
42
- "hasNewWebForm": true,
43
- "title": "Kontaktformular",
44
- "fields":[
45
- {
46
- "@->jsoninclude": "forms/form_fields.inc.json",
47
- "@->contentpath": "input-text-vorname"
48
- },
49
- {
50
- "@->jsoninclude": "forms/form_fields.inc.json",
51
- "@->contentpath": "input-text-vorname-required"
52
- },
53
- {
54
- "@->jsoninclude": "forms/form_fields.inc.json",
55
- "@->contentpath": "input-text-nachname-required"
56
- },
57
- {
58
- "@->jsoninclude": "forms/form_fields.inc.json",
59
- "@->contentpath": "select"
60
- },
61
- {
62
- "@->jsoninclude": "forms/form_fields.inc.json",
63
- "@->contentpath": "input-email",
64
- "@->overrides": [
65
- {
66
- "@->contentpath": "isRequired",
67
- "@->value": false
68
- }
69
- ]
70
- },
71
- {
72
- "@->jsoninclude": "forms/form_fields.inc.json",
73
- "@->contentpath": "input-email"
74
- },
75
- {
76
- "@->jsoninclude": "forms/form_fields.inc.json",
77
- "@->contentpath": "textarea"
78
- },
79
- {
80
- "@->jsoninclude": "forms/form_fields.inc.json",
81
- "@->contentpath": "checkbox",
82
- "@->overrides": [
83
- {
84
- "@->contentpath": "label",
85
- "@->value": "Ich bin damit einverstanden, dass der hr die von mir im vorstehenden Formular angegebenen personenbezogenen Daten für den Zweck der Kontaktaufnahme mit Upload verarbeitet. Eine Weitergabe an Dritte findet nicht statt, es sei denn, es wird ausdrücklich darauf hingewiesen. Unsere Datenschutzerklärung mit sämtlichen Informationen gemäß Art 13 DSGVO zur Datenverarbeitung durch den hr und zu Ihren Rechten können Sie unter Datenschutzerklärung einsehen. Den Datenschutzbeauftragten des hr erreichen Sie unter datenschutz@hr.de."
86
- }
87
- ]
88
- }
89
- ]
90
-
91
37
  }
92
38
  }
39
+
93
40
  ]
94
41
  }
@@ -53,7 +53,8 @@ Alpine.store('sharingBottomPos', {
53
53
  current: '0'
54
54
  })
55
55
  Alpine.store('forms', {
56
- submissionAttempted: []
56
+ submissionAttempted: [],
57
+ serverErrorFields: []
57
58
  })
58
59
  // Initialization of data handlers
59
60
  Alpine.data('mainNavigationHandler', mainNavigationHandler)
@@ -0,0 +1,41 @@
1
+ import copytext from './copytext.hbs'
2
+
3
+ import copytext_webform_json from './fixtures/copytext_webform.json'
4
+
5
+ const Template = ({ ...args }) => {
6
+ return copytext({ ...args })
7
+ }
8
+
9
+ export default {
10
+ title: 'Komponenten/Content/Copytext',
11
+ decorators: [
12
+ (Story) => {
13
+ return `<div class="grid grid-page">
14
+ <div class="grid bg-white grid-article">
15
+ ${Story()}
16
+ </div>
17
+ </div>`
18
+ },
19
+ ],
20
+ parameters: {
21
+ mockData: [
22
+ {
23
+ url: 'https://ugc-hessenschau.dev-ext.hrcms.gcp.cloud.hr.de',
24
+ method: 'POST',
25
+ status: 200,
26
+ response: {
27
+ "status":"VALIDATION_ERROR","errors":{"vorname":"form_error_required"},
28
+ },
29
+ },
30
+ ],
31
+ layout: 'fullscreen',
32
+ chromatic: { disableSnapshot: true }
33
+ }
34
+ }
35
+
36
+ export const WithWebform = {
37
+ render: Template.bind({}),
38
+ name: 'Formular',
39
+ args: copytext_webform_json,
40
+ }
41
+
@@ -17,7 +17,6 @@ import copytext_video_json from './fixtures/copytext_video.json'
17
17
  import copytext_audio_json from './fixtures/copytext_audio.json'
18
18
  import copytext_audio_event_stream_json from './fixtures/copytext_audio_livestream.json'
19
19
  import copytext_livestream_json from './fixtures/copytext_livestream.json'
20
- import copytext_webform_json from './fixtures/copytext_webform.json'
21
20
 
22
21
  const Template = ({ ...args }) => {
23
22
  return copytext({ ...args })
@@ -67,12 +66,6 @@ export const WithFiledownload = {
67
66
  args: copytext_filedownload_json,
68
67
  }
69
68
 
70
- export const WithWebform = {
71
- render: Template.bind({}),
72
- name: 'Formular',
73
- args: copytext_webform_json,
74
- }
75
-
76
69
  export const WithImage = {
77
70
  render: Template.bind({}),
78
71
  name: 'Image',
@@ -1 +1 @@
1
- {"copytextParagraph":[{"isHeadline":true,"text":"Copytext mit Formular"},{"paragraphBoxItem":{"isWebForm":true,"hasNewWebForm":true,"title":"Kontaktformular","fields":[{"type":{"isText":true,"asString":"text"},"name":"vorname","label":"Vorname","description":"Das ist der Beschreibungstext (*Pflichtfeld)","defaultValue":"","isHidden":false,"isRequired":true,"maxLength":"140"},{"type":{"isText":true,"asString":"text"},"name":"nachname","label":"Nachname","description":"","defaultValue":"","isHidden":false,"isRequired":true,"maxLength":"140"},{"isGrouped":false,"type":{"isChoice":true,"asString":"checkbox"},"name":"checkbox","label":"Ich bin damit einverstanden, dass der hr die von mir im vorstehenden Formular angegebenen personenbezogenen Daten für den Zweck der Kontaktaufnahme mit Upload verarbeitet. Eine Weitergabe an Dritte findet nicht statt, es sei denn, es wird ausdrücklich darauf hingewiesen. Unsere Datenschutzerklärung mit sämtlichen Informationen gemäß Art 13 DSGVO zur Datenverarbeitung durch den hr und zu Ihren Rechten können Sie unter Datenschutzerklärung einsehen. Den Datenschutzbeauftragten des hr erreichen Sie unter datenschutz@hr.de.","isMeta":false,"description":"Das ist der Beschreibungstext von Checkbox","isRequired":true}]}},{"isHeadline":true,"text":"Noch ein Formular"},{"paragraphBoxItem":{"isWebForm":true,"hasNewWebForm":true,"title":"Kontaktformular","fields":[{"type":{"isText":true,"asString":"text"},"name":"vorname","label":"Vorname","description":"Das ist der Beschreibungstext von Vorname","defaultValue":"","isHidden":false,"isRequired":false},{"type":{"isText":true,"asString":"text"},"name":"vorname","label":"Vorname","description":"Das ist der Beschreibungstext (*Pflichtfeld)","defaultValue":"","isHidden":false,"isRequired":true,"maxLength":"140"},{"type":{"isText":true,"asString":"text"},"name":"nachname","label":"Nachname","description":"","defaultValue":"","isHidden":false,"isRequired":true,"maxLength":"140"},{"type":{"isSelect":true,"asString":"select"},"name":"Select Name","label":"Wen möchten Sie erreichen?","description":"Das ist der Beschreibungstext von Select","defaultValue":"","isHidden":false,"isRequired":true,"options":[{"id":"option1","value":"option1","selected":false,"label":"Option 1"},{"id":"option2","value":"option2","selected":false,"label":"Option 2"},{"id":"option3","value":"option3","selected":false,"label":"Option 3"},{"id":"option4","value":"option4","selected":false,"label":"Option 4"}]},{"type":{"isText":true,"isEmail":true,"asString":"email"},"name":"email","label":"Email","description":"Das ist der Beschreibungstext von Email","defaultValue":"","isHidden":false,"isRequired":false,"maxLength":"140"},{"type":{"isText":true,"isEmail":true,"asString":"email"},"name":"email","label":"Email","description":"Das ist der Beschreibungstext von Email","defaultValue":"","isHidden":false,"isRequired":true,"maxLength":"140"},{"type":{"isTextarea":true,"asString":"textarea"},"name":"textarea","label":"Textarea","description":"Das ist der Beschreibungstext von Textarea","defaultValue":"","isHidden":false,"isRequired":true,"maxLength":"300","columns":"30","rows":"10","counter":true},{"isGrouped":false,"type":{"isChoice":true,"asString":"checkbox"},"name":"checkbox","label":"Ich bin damit einverstanden, dass der hr die von mir im vorstehenden Formular angegebenen personenbezogenen Daten für den Zweck der Kontaktaufnahme mit Upload verarbeitet. Eine Weitergabe an Dritte findet nicht statt, es sei denn, es wird ausdrücklich darauf hingewiesen. Unsere Datenschutzerklärung mit sämtlichen Informationen gemäß Art 13 DSGVO zur Datenverarbeitung durch den hr und zu Ihren Rechten können Sie unter Datenschutzerklärung einsehen. Den Datenschutzbeauftragten des hr erreichen Sie unter datenschutz@hr.de.","isMeta":false,"description":"Das ist der Beschreibungstext von Checkbox","isRequired":true}]}}]}
1
+ {"copytextParagraph":[{"isHeadline":true,"text":"Copytext mit Formular"},{"paragraphBoxItem":{"isWebForm":true,"hasNewWebForm":true,"title":"Kontaktformular","jsonURL":"https://ugc-hessenschau.dev-ext.hrcms.gcp.cloud.hr.de","errorMessages":"errorMessages","isMultipart":"isMultipart","trackingInformations":"trackingInformations","fields":[{"type":{"isText":true,"asString":"text"},"name":"vorname","label":"Vorname","description":"Das ist der Beschreibungstext (*Pflichtfeld)","defaultValue":"","isHidden":false,"isRequired":true,"maxLength":"140"},{"type":{"isText":true,"asString":"text"},"name":"nachname","label":"Nachname","description":"","defaultValue":"","isHidden":false,"isRequired":true,"maxLength":"140"},{"isGrouped":false,"type":{"isChoice":true,"asString":"checkbox"},"name":"checkbox","label":"Ich bin damit einverstanden, dass der hr die von mir im vorstehenden Formular angegebenen personenbezogenen Daten für den Zweck der Kontaktaufnahme mit Upload verarbeitet. Eine Weitergabe an Dritte findet nicht statt, es sei denn, es wird ausdrücklich darauf hingewiesen. Unsere Datenschutzerklärung mit sämtlichen Informationen gemäß Art 13 DSGVO zur Datenverarbeitung durch den hr und zu Ihren Rechten können Sie unter Datenschutzerklärung einsehen. Den Datenschutzbeauftragten des hr erreichen Sie unter datenschutz@hr.de.","isMeta":false,"description":"Das ist der Beschreibungstext von Checkbox","isRequired":true}]}}]}
@@ -4,7 +4,7 @@
4
4
  {{/if}}
5
5
  >
6
6
  {{#if this.isAutosuggest}}
7
- <div class="flex mx-0 w-full h-10 border-primary {{#if _autoSuggestContainerCss}} {{_autoSuggestContainerCss}}{{/if}}">
7
+ <div class="flex mx-0 w-full h-10 border-primary{{#if _autoSuggestContainerCss}} {{_autoSuggestContainerCss}}{{/if}}">
8
8
  <input x-ref="autosuggestInput"
9
9
  class="{{#if _inputclass }}{{_inputclass}}{{/if}} w-full h-10 pl-2 border-b-8 border-white bg-gray-alabaster text-gray-dark placeholder:text-gray-dark focus:outline-none js-autosuggest-input"
10
10
  type="text"
@@ -1,36 +1,199 @@
1
- export default function contactForm(formId) {
1
+ export default function contactForm(formId, jsonURL, errorMessages, multipart, trackingInformations, jsonp = false) {
2
2
  return {
3
+ isPosting: false,
4
+ isWebview:false,
5
+ ajaxTimeout: 60 * 1000,
6
+ form: this.$refs[formId],
7
+ formWrapper: this.$refs[formId].closest("#formWrapper"),
8
+ actionUrl: this.form && this.form.getAttribute('action'),
9
+ checkForJsonURL () {
10
+ if (jsonURL) {
11
+ this.actionUrl = jsonURL
12
+ }
13
+ },
3
14
  formInit(){
4
- this.$store.forms.submissionAttempted[formId] = false;
5
- console.log("this.$store.forms.submissionAttempted",this.$store.forms.submissionAttempted[formId]);
15
+ this.checkForJsonURL()
16
+ console.log("%cformId:", 'color: green' ,formId);
17
+ console.log("%cform:", 'color: green' ,this.form);
18
+ console.log("%cformWrapper:", 'color: green' ,this.formWrapper);
19
+ console.log("%cactionUrl:", 'color: green' ,this.actionUrl);
20
+ console.log("%cjsonURL:", 'color: green', jsonURL);
21
+ console.log("%cerrorMessages:", 'color: green', errorMessages);
22
+ console.log("%cmultipart:", 'color: green', multipart);
23
+ console.log("%ctrackingInformations:", 'color: green', trackingInformations);
24
+
25
+ this.$store.forms.submissionAttempted[formId] = false;
6
26
  },
7
- clickHandler() {
8
- console.log('check for Error:',formId);
9
- const form = this.$refs[formId];
10
- console.log('form',form);
11
- const formData = new FormData(form);
12
- const fields = Array.from(form.elements); // Array of all form fields
13
-
14
- // Loop through each field, focus it, blur it, and serialize the data
15
-
16
- if(form.reportValidity()){
17
- this.submitData();
27
+ clickHandler(event) {
28
+ console.log("event:",event);
29
+ console.log('check for Error:',formId);
30
+ console.log('form:',this.form);
31
+
32
+ if(this.form.reportValidity()){
33
+ // this.logData(event,form);
34
+ this.handleSubmit(event,this.form)
18
35
  } else {
19
36
  this.$store.forms.submissionAttempted[formId] = true;
20
37
  }
21
38
  },
22
- submitData() {
23
- const formData = new FormData(this.$refs[formId]);
39
+ logData(event,form) {
40
+ // TODO - FOR DEBUGGIN CN BE REMOVED AT THE END
41
+ const formData = new FormData(form);
42
+ const fields = Array.from(form.elements);
43
+ // Log the serialized form data
44
+ console.log(fields);
45
+
24
46
  // Convert the FormData to a serialized string
25
47
  const serializedData = Array.from(formData.entries())
26
48
  .map(([key, value]) => `${encodeURIComponent(key)}=${encodeURIComponent(value)}`)
27
49
  .join('&');
28
50
 
29
51
  // Log the serialized form data
30
- console.log('DATA: ' + serializedData);
52
+ console.log('serialized DATA: ' + serializedData);
53
+ console.log('DATA:', new URLSearchParams(new FormData(form)).toString());
54
+
55
+ },
56
+ // TODO - Validation error handler (adapt to your case)
57
+ handleValidationErrors(errors) {
58
+ console.log('Validation Errors:', errors);
59
+ this.$store.forms.serverErrorFields[formId] = errors;
60
+ console.log('Validation Errors in Store:', this.$store.forms.serverErrorFields);
61
+ },
62
+ resetValidationErrors() {
63
+ this.$store.forms.serverErrorFields[formId] = {}
64
+ },
65
+
66
+ handleSubmit(event, form ) {
67
+ event.preventDefault();
68
+
69
+ if (!this.isWebview) {
70
+ //uxAction(trackingInformations); // Assuming this is a tracking library
71
+ }
72
+
73
+ if (this.isPosting) return;
74
+ this.isPosting = true;
75
+
76
+ // TODO mit alpine umsetzen
77
+ //const preloadIcon = formWrapper.querySelector('.js-preloadIcon');
78
+ //const loadingIcon = formWrapper.querySelector('.js-loadingIcon');
79
+
80
+ // Show loading indicator
81
+ //preloadIcon.classList.add('-isHidden');
82
+ //loadingIcon.classList.remove('-isHidden');
83
+
84
+ console.log('DATA:', new URLSearchParams(new FormData(form)).toString());
85
+
86
+ // Define ajaxOptions based on form type (without jQuery $.ajax)
87
+ let ajaxOptions = {
88
+ method: jsonp ? 'GET' : 'POST',
89
+ headers: {
90
+ 'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8'
91
+ },
92
+ timeout: this.ajaxTimeout,
93
+ body: new URLSearchParams(new FormData(form)),
94
+ };
95
+
96
+ if (jsonp) {
97
+ ajaxOptions.url = this.actionUrl;
98
+ ajaxOptions.headers['Content-Type'] = 'application/json; charset=utf-8';
99
+ ajaxOptions.body = new URLSearchParams(new FormData(form)).toString(); // For JSONP case
100
+ } else if (multipart) {
101
+ ajaxOptions = {
102
+ method: 'POST',
103
+ url: this.actionUrl,
104
+ timeout: 600 * 1000,
105
+ body: new FormData(form), // No URLSearchParams, we use FormData for multipart
106
+ processData: false,
107
+ headers: {}
108
+ };
109
+ } else {
110
+ ajaxOptions.url = `${this.actionUrl}?${responseFormatParam}`;
111
+ }
112
+
113
+ // Using fetch API instead of $.ajax
114
+ fetch(ajaxOptions.url, ajaxOptions)
115
+ .then(async (response) => {
116
+ const data = await response.text(); // Assuming the rponse is text or JSON
117
+ if (response.ok) {
118
+ console.log('Done');
119
+ console.log(data);
120
+ if (jsonURL) {
121
+ const responseData = JSON.parse(data);
122
+ switch (responseData.status) {
123
+ case 'VALIDATION_ERROR':
124
+ this.resetValidationErrors();
125
+ this.handleValidationErrors(responseData.errors);
126
+ break;
127
+ case 'OK':
128
+ console.log("OK");
129
+ this.replaceAnimated(
130
+ this.formWrapper,
131
+ this.form.querySelector('#successMessage').innerHTML,
132
+ true
133
+ );
134
+ break;
135
+ default:
136
+ console.log("default");
137
+ replaceAnimated(
138
+ this.formWrapper,
139
+ this.form.querySelector('#errorMessage').innerHTML,
140
+ true
141
+ );
142
+ break;
143
+ }
144
+ } else {
145
+ replaceAnimated(this.formWrapper, data, true);
146
+ }
147
+ /*
148
+ if (eventOnSuccess) {
149
+ fireEvent(eventOnSuccess, true);
150
+ } */
151
+
152
+ /* if (rootElement.id) {
153
+ window.location.hash = rootElement.id;
154
+ } */
155
+ } else {
156
+ throw new Error('Network response was not ok.');
157
+ }
158
+ })
159
+ .catch((error) => {
160
+ console.error('Fail:', error);
161
+ replaceAnimated(
162
+ this.formWrapper,
163
+ '<div class="c-form success">Das hat leider nicht funktioniert!</div>',
164
+ true
165
+ );
166
+ })
167
+ .finally(() => {
168
+ console.log('Always');
169
+ // TODO MIT ALPINE UMSETZEN
170
+ //preloadIcon.classList.remove('-isHidden');
171
+ //loadingIcon.classList.add('-isHidden');
172
+ this.isPosting = false;
173
+ });
174
+ },
175
+ // Helper function to replace content with animation (replacing hrQuery's replaceAnimated)
176
+ replaceAnimated(wrapper, newContent, withFade = true) {
177
+ if (withFade) {
178
+ wrapper.style.opacity = 0;
179
+ setTimeout(() => {
180
+ wrapper.innerHTML = newContent;
181
+ wrapper.style.opacity = 1;
182
+ }, 300);
183
+ } else {
184
+ wrapper.innerHTML = newContent;
185
+ }
186
+ },
187
+ // Fire event utility (could be Alpine.js specific or custom)
188
+ fireEvent(eventName, success){
189
+ const event = new CustomEvent(eventName, { detail: success });
190
+ document.dispatchEvent(event);
31
191
  },
32
192
  getSubmissionAttempted() {
33
193
  return this.$store.forms.submissionAttempted[formId]
34
194
  }
195
+
35
196
  }
36
- }
197
+ }
198
+
199
+
@@ -2,8 +2,9 @@
2
2
  <div class="text-xs text-gray-500 font-headingSerif">Pflichtfeld*</div>
3
3
  <div class="flex items-center">
4
4
  <label class="order-2 cursor-pointer {{> components/button/utilities/button_base_classes}} {{> components/button/utilities/button_variation_classes _variant='primary'}} {{> components/button/utilities/button_dimension_classes _size='lg'}}">
5
- {{> components/base/image/icon _icon="send-ds" _addClass="w-5 h-5 fill-white dark:fill-text-dark "}}
6
- <input type="submit" class="pl-2 cursor-pointer" value="Absenden" @click.prevent="clickHandler"/>
5
+ <span class="hidden" :class="{'hidden': !isPosting}">{{> components/base/image/icon _icon="reload" _addClass="w-5 h-5 fill-white dark:fill-text-dark animate-spin"}}</span>
6
+ <span class="" :class="{'hidden': isPosting}">{{> components/base/image/icon _icon="send-ds" _addClass="w-5 h-5 fill-white dark:fill-text-dark "}}</span>
7
+ <input type="submit" class="pl-2 cursor-pointer" value="Absenden" @click.prevent="clickHandler($event)"/>
7
8
  </label>
8
9
 
9
10
  {{#> components/button/button _variant="tertiary"_size="lg" _css="order-1 mr-4" _type="reset"}}
@@ -77,6 +77,7 @@
77
77
  DEBUG
78
78
  </div>
79
79
  <div class="px-4 py-3 text-red-700 bg-red-100 border border-t-0 border-red-400 rounded-b">
80
+ <div>name:<span x-text="name" class="font-bold" ></span></div>
80
81
  <div>isFocused:<span x-text="isFocused" class="font-bold" :class="isFocused ? 'text-green-800' : 'text-red-700'"></span></div>
81
82
  <div>wasFocused:<span x-text="wasFocused" class="font-bold" :class="wasFocused ? 'text-green-800' : 'text-red-700'"></span></div>
82
83
  <div>valid:<span x-text="valid" class="font-bold" :class="valid ? 'text-green-800' : 'text-red-700'"></span></div>
@@ -88,6 +89,9 @@
88
89
  <div>errorMessage:<span x-text="errorMessage" class="font-bold" ></span></div>
89
90
  <div>valueMissing:<span x-text="valueMissing" class="font-bold" ></span></div>
90
91
  <div>typeMismatch:<span x-text="typeMismatch" class="font-bold" ></span></div>
92
+ <div>serverErrorFields[form{{getRandom}}][name]:<span x-text="getServerErrorFields('{{_name}}')" class="font-bold" ></span></div>
93
+ <div>submissionAttempted[form{{getRandom}}]:<span x-text="getSubmissionAttempted()" class="font-bold" :class="getSubmissionAttempted() ? 'text-green-800' : 'text-red-700'"></span></div>
94
+
91
95
  </div>
92
96
  </div>
93
97
  </div>