@dcodegroup-au/page-builder 0.3.5 → 0.3.7
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.
- package/dist/page-builder.css +2 -2
- package/dist/page-builder.es.js +8408 -8298
- package/dist/page-builder.umd.js +47 -47
- package/example/src/App.vue +7 -5
- package/example/src/pages/BestLife.js +3 -4
- package/example/src/pages/Home.js +18 -11
- package/example/src/pages/OurVision.js +148 -0
- package/package.json +1 -1
- package/src/components/ItemEdit.vue +7 -4
- package/src/components/LinkCardEdit.vue +7 -2
- package/src/components/PageBuilder.vue +2 -0
- package/src/components/PageRender.vue +2 -0
- package/src/components/builders/Header.vue +5 -9
- package/src/components/builders/Links.vue +9 -2
- package/src/components/common/Button.vue +1 -1
- package/src/components/helpers/common.js +6 -1
- package/src/components/helpers/defaultProps.js +1 -1
- package/src/components/helpers/pageBuilderFactory.js +13 -3
- package/src/components/presenters/components/CarouselPresenter.vue +7 -8
- package/src/components/presenters/components/CollectionGridPresenter.vue +4 -3
- package/src/components/presenters/components/SliderPresenter.vue +1 -4
- package/src/components/presenters/components/VerticalTabPresenter.vue +1 -1
- package/src/components/presenters/modules/Callout.vue +32 -0
- package/src/components/presenters/modules/CollectionGrid.vue +5 -5
- package/src/components/presenters/modules/LinkCard.vue +3 -2
- package/src/components/presenters/modules/LinkList.vue +2 -1
- package/src/components/presenters/modules/LogoCloud.vue +1 -1
- package/src/components/presenters/modules/TwoColumnsImageContent.vue +37 -2
- package/src/components/presenters/overridables/VCarouselPrimaryButton.vue +1 -4
- package/tailwind.config.js +3 -0
|
@@ -31,7 +31,10 @@
|
|
|
31
31
|
</span>
|
|
32
32
|
</div>
|
|
33
33
|
<h3 class="my-3">
|
|
34
|
-
<a class="text-[24px] font-semibold text-gray-900 leading-[32px] hover:underline"
|
|
34
|
+
<a class="text-[24px] font-semibold text-gray-900 leading-[32px] hover:underline"
|
|
35
|
+
:href="formatUrl(slide.url)" target="_blank">
|
|
36
|
+
{{ slide?.title }}
|
|
37
|
+
</a>
|
|
35
38
|
</h3>
|
|
36
39
|
<p
|
|
37
40
|
class="text-base font-normal text-gray-600 leading-[24px] multiline-ellipsis"
|
|
@@ -79,8 +82,8 @@
|
|
|
79
82
|
<div v-if="component?.button" class="flex justify-center mb-[40px]">
|
|
80
83
|
<a
|
|
81
84
|
class="border-brand-300 hover:border-brand-700 border text-brand-700 h-[44px] rounded-full px-[14px] py-[10px] inline-flex gap-1.5 items-center font-semibold text-base"
|
|
82
|
-
:href="component.button.url"
|
|
83
|
-
:target="component.button.
|
|
85
|
+
:href="formatUrl(component.button.url)"
|
|
86
|
+
:target="component.button.open_in_new_tab ? '_blank' : ''">
|
|
84
87
|
{{ component.button.title }}
|
|
85
88
|
<ArrowUpRight class="w-5 h-5"></ArrowUpRight>
|
|
86
89
|
</a>
|
|
@@ -96,6 +99,7 @@ import ChevronLeft from "@/assets/img/icons/chevron-left.svg";
|
|
|
96
99
|
import ArrowUpRight from "@/assets/img/icons/arrow-up-right.svg";
|
|
97
100
|
import Ticket from "@/assets/img/icons/ticket-02.svg";
|
|
98
101
|
import DefaultPrimaryButton from "@/components/presenters/overridables/VCarouselPrimaryButton.vue";
|
|
102
|
+
import { formatUrl } from "@/components/helpers/common";
|
|
99
103
|
|
|
100
104
|
// Inject the FileUpload component or fallback to the default one
|
|
101
105
|
const VCarouselPrimaryButton = inject("VCarouselPrimaryButton", DefaultPrimaryButton);
|
|
@@ -115,11 +119,6 @@ const currentSlide = ref(0); // Start at 0
|
|
|
115
119
|
const itemsToShow = 4; // Number of items to show at a time
|
|
116
120
|
const slides = [...props.component.content?.items || []];
|
|
117
121
|
|
|
118
|
-
// Format URL
|
|
119
|
-
const formatUrl = (url) => {
|
|
120
|
-
return url.startsWith("http") ? url : `//${url}`;
|
|
121
|
-
};
|
|
122
|
-
|
|
123
122
|
// Navigate to the next slide
|
|
124
123
|
const nextSlide = () => {
|
|
125
124
|
if (currentSlide.value <= slides.length - itemsToShow) {
|
|
@@ -44,7 +44,7 @@
|
|
|
44
44
|
</div>
|
|
45
45
|
<a
|
|
46
46
|
v-if="card?.link"
|
|
47
|
-
:href="card.link"
|
|
47
|
+
:href="formatUrl(card.link)"
|
|
48
48
|
class="text-gray-900 text-lg font-semibold hover:underline block mb-2 w-full"
|
|
49
49
|
target="_blank"
|
|
50
50
|
rel="noopener noreferrer"
|
|
@@ -61,8 +61,8 @@
|
|
|
61
61
|
<div v-if="Object.keys(button).length && button?.show" class="flex justify-center">
|
|
62
62
|
<a
|
|
63
63
|
class="border-brand-300 hover:border-brand-700 border text-brand-700 h-[44px] rounded-full px-[14px] py-[10px] inline-flex gap-1.5 items-center font-semibold text-base"
|
|
64
|
-
:href="button.url"
|
|
65
|
-
:target="button.
|
|
64
|
+
:href="formatUrl(button.url)"
|
|
65
|
+
:target="button.open_in_new_tab ? '_blank' : ''"
|
|
66
66
|
>
|
|
67
67
|
{{ button.title }}
|
|
68
68
|
<ArrowUpRight class="w-5 h-5"></ArrowUpRight>
|
|
@@ -75,6 +75,7 @@
|
|
|
75
75
|
import { ref } from "vue";
|
|
76
76
|
import ArrowUpRight from "@/assets/img/icons/arrow-up-right.svg";
|
|
77
77
|
import PlayButton from "@/assets/svg/play.svg";
|
|
78
|
+
import { formatUrl } from "@/components/helpers/common";
|
|
78
79
|
|
|
79
80
|
const props = defineProps({
|
|
80
81
|
component: {
|
|
@@ -45,6 +45,7 @@ import 'vue3-carousel/carousel.css';
|
|
|
45
45
|
import { ref } from "vue";
|
|
46
46
|
import ArrowUpRight from '@/assets/img/icons/arrow-up-right.svg';
|
|
47
47
|
import {Carousel, Slide} from "vue3-carousel";
|
|
48
|
+
import { formatUrl } from "@/components/helpers/common";
|
|
48
49
|
|
|
49
50
|
const props = defineProps({
|
|
50
51
|
component: {
|
|
@@ -56,10 +57,6 @@ const props = defineProps({
|
|
|
56
57
|
const currentSlide = ref(0);
|
|
57
58
|
const componentData = ref(props.component);
|
|
58
59
|
const slides = componentData.value.data.filter((o) => o.public);
|
|
59
|
-
|
|
60
|
-
const formatUrl = (url) => {
|
|
61
|
-
return url.startsWith('http') ? url : `//${url}`;
|
|
62
|
-
};
|
|
63
60
|
</script>
|
|
64
61
|
|
|
65
62
|
<style scoped>
|
|
@@ -43,7 +43,7 @@
|
|
|
43
43
|
<a
|
|
44
44
|
v-if="selectedItem?.primary_button?.show"
|
|
45
45
|
class="text-sm md:text-md font-semibold text-brand-600 flex items-center gap-2 mt-4"
|
|
46
|
-
:target="selectedItem?.primary_button?.
|
|
46
|
+
:target="selectedItem?.primary_button?.open_in_new_tab ? '_blank' : ''"
|
|
47
47
|
:href="selectedItem?.primary_button?.url.startsWith('http') ? selectedItem.primary_button.url : `//${selectedItem.primary_button.url}`"
|
|
48
48
|
>
|
|
49
49
|
{{ selectedItem?.primary_button?.label ?? 'N/A' }}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
<template>
|
|
2
|
+
<div class="overflow-hidden">
|
|
3
|
+
<div class="max-w-[1640px] md:px-[120px] mx-auto w-full mt-[40px]" :class="{'flex gap-8': headerComponent?.featured_image}">
|
|
4
|
+
<img v-if="headerComponent?.featured_image"
|
|
5
|
+
:src="headerComponent?.featured_image"
|
|
6
|
+
class="w-[480px] object-cover rounded-[24px]"
|
|
7
|
+
alt="Feature"/>
|
|
8
|
+
<div v-if="headerComponent"
|
|
9
|
+
class="w-full rounded-[24px] flex items-center justify-center flex-col"
|
|
10
|
+
:class="{'bg-pale-100 min-h-[320px]': !headerComponent?.featured_image, 'border border-brand-400': headerComponent?.featured_image}"
|
|
11
|
+
>
|
|
12
|
+
<h3 class="text-xl text-brand-600 font-semibold max-w-[744px]">{{ headerComponent.title }}</h3>
|
|
13
|
+
<p v-if="headerComponent?.supporting_text" class="text-[30px] font-semibold mt-2 text-gray-900 leading-[38px] max-w-[744px] text-center" v-html="headerComponent.supporting_text"></p>
|
|
14
|
+
</div>
|
|
15
|
+
</div>
|
|
16
|
+
</div>
|
|
17
|
+
</template>
|
|
18
|
+
<script setup>
|
|
19
|
+
import {ref, computed} from "vue";
|
|
20
|
+
|
|
21
|
+
const props = defineProps({
|
|
22
|
+
section: {
|
|
23
|
+
required: true,
|
|
24
|
+
type: Object,
|
|
25
|
+
},
|
|
26
|
+
});
|
|
27
|
+
|
|
28
|
+
const section = ref(props.section);
|
|
29
|
+
const headerComponent = computed(() => {
|
|
30
|
+
return section.value.components.find((component) => component.type === "callout");
|
|
31
|
+
});
|
|
32
|
+
</script>
|
|
@@ -13,8 +13,8 @@
|
|
|
13
13
|
|
|
14
14
|
<script setup>
|
|
15
15
|
import { ref, markRaw } from "vue";
|
|
16
|
-
import
|
|
17
|
-
import
|
|
16
|
+
import HeaderPresenter from "@/components/presenters/components/HeaderPresenter.vue";
|
|
17
|
+
import CollectionGridPresenter from "@/components/presenters/components/CollectionGridPresenter.vue";
|
|
18
18
|
|
|
19
19
|
const props = defineProps({
|
|
20
20
|
section: {
|
|
@@ -25,9 +25,9 @@ const props = defineProps({
|
|
|
25
25
|
|
|
26
26
|
const section = ref(props.section);
|
|
27
27
|
const componentMaps = ref({
|
|
28
|
-
header: markRaw(
|
|
29
|
-
news_grid: markRaw(
|
|
30
|
-
video_grid: markRaw(
|
|
28
|
+
header: markRaw(HeaderPresenter),
|
|
29
|
+
news_grid: markRaw(CollectionGridPresenter),
|
|
30
|
+
video_grid: markRaw(CollectionGridPresenter),
|
|
31
31
|
});
|
|
32
32
|
|
|
33
33
|
const currentComponent = (component) => {
|
|
@@ -21,8 +21,8 @@
|
|
|
21
21
|
<a
|
|
22
22
|
v-if="data?.primary_button.url"
|
|
23
23
|
class="text-brand-700 inline-flex gap-1.5 items-center font-semibold text-base"
|
|
24
|
-
:href="data.primary_button.url"
|
|
25
|
-
:target="data.primary_button.
|
|
24
|
+
:href="formatUrl(data.primary_button.url)"
|
|
25
|
+
:target="data.primary_button.open_in_new_tab ? '_blank' : ''">
|
|
26
26
|
{{ data.primary_button.label }}
|
|
27
27
|
<ArrowUpRight class="w-5 h-5"></ArrowUpRight>
|
|
28
28
|
</a>
|
|
@@ -36,6 +36,7 @@
|
|
|
36
36
|
import {ref, computed} from "vue";
|
|
37
37
|
import ArrowUpRight from "@/assets/img/icons/arrow-up-right.svg";
|
|
38
38
|
import IconComponent from "@/components/common/Icon.vue";
|
|
39
|
+
import { formatUrl } from "@/components/helpers/common";
|
|
39
40
|
|
|
40
41
|
const props = defineProps({
|
|
41
42
|
section: {
|
|
@@ -12,7 +12,7 @@
|
|
|
12
12
|
<a
|
|
13
13
|
v-if="link.url"
|
|
14
14
|
class="text-gray-900 w-full inline-flex justify-between gap-1.5 items-center leading-[28px] font-semibold text-lg hover:underline"
|
|
15
|
-
:href="link.url"
|
|
15
|
+
:href="formatUrl(link.url)"
|
|
16
16
|
:target="link.open_in_new_tab ? '_blank' : ''">
|
|
17
17
|
<div class="flex gap-4 items-center max-w-[94%] w-full">
|
|
18
18
|
<LinkExternal class="w-5 h-5"></LinkExternal>
|
|
@@ -31,6 +31,7 @@
|
|
|
31
31
|
import {ref, computed} from "vue";
|
|
32
32
|
import ArrowUpRight from "@/assets/img/icons/arrow-up-right.svg";
|
|
33
33
|
import LinkExternal from "@/assets/img/icons/link-external-01.svg";
|
|
34
|
+
import { formatUrl } from "@/components/helpers/common";
|
|
34
35
|
|
|
35
36
|
const props = defineProps({
|
|
36
37
|
section: {
|
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
</p>
|
|
12
12
|
<div v-if="component?.type === 'logos'" class="flex flex-wrap justify-center" :class="{'gap-6': isHorizontal, 'gap-12': !isHorizontal}">
|
|
13
13
|
<template v-for="logo in component.data">
|
|
14
|
-
<a :href="logo?.url" title="Brand">
|
|
14
|
+
<a :href="logo?.url" title="Brand" target="_blank">
|
|
15
15
|
<img v-if="logo?.logo" :src="logo?.logo" :class="getLogoHeight(component?.height)" alt="Brand Logo"/>
|
|
16
16
|
<span v-else class="text-sm">No photo</span>
|
|
17
17
|
</a>
|
|
@@ -1,21 +1,50 @@
|
|
|
1
1
|
<template>
|
|
2
2
|
<div class="overflow-hidden">
|
|
3
3
|
<div class="max-w-[1640px] md:px-[120px] mx-auto w-full mt-4 px-4">
|
|
4
|
-
<div class="grid grid-cols-12 gap-4">
|
|
4
|
+
<div class="grid grid-cols-12 gap-4" v-if="paragraphComponent">
|
|
5
5
|
<div class="col-span-4 bg-gray-100 rounded-xl p-8" v-if="paragraphComponent">
|
|
6
6
|
<h3 class="text-[20px] text-gray-900 font-semibold">{{ paragraphComponent.title }}</h3>
|
|
7
7
|
<p class="text-md font-normal mt-2 text-gray-600 leading-6" v-html="paragraphComponent.paragraph"></p>
|
|
8
8
|
</div>
|
|
9
9
|
<div class="col-span-8" v-if="imageComponent">
|
|
10
|
-
<img :src="imageComponent.featured_image" :alt="imageComponent.caption" class="w-full h-auto"
|
|
10
|
+
<img :src="imageComponent.featured_image" :alt="imageComponent.caption" class="w-full h-auto"/>
|
|
11
11
|
<p v-html="imageComponent.caption" class="mt-2 text-[13px]"></p>
|
|
12
12
|
</div>
|
|
13
13
|
</div>
|
|
14
|
+
<div v-else class="my-[44px]">
|
|
15
|
+
<div
|
|
16
|
+
v-if="headerComponent"
|
|
17
|
+
class="w-full flex-col mb-6"
|
|
18
|
+
>
|
|
19
|
+
<h3 class="text-[36px] text-gray-900 font-semibold">{{ headerComponent.title }}</h3>
|
|
20
|
+
<p v-if="headerComponent?.supporting_text"
|
|
21
|
+
class="text-[20px] font-normal mt-4 text-gray-600 leading-[30px]"
|
|
22
|
+
v-html="headerComponent.supporting_text"></p>
|
|
23
|
+
</div>
|
|
24
|
+
<div class="flex flex-row gap-8">
|
|
25
|
+
<div class="grid grid-cols-2 gap-8 w-2/3">
|
|
26
|
+
<div v-for="item in featureItemsComponent.data" class="flex gap-3">
|
|
27
|
+
<div v-if="item?.icon" class="w-[48px] h-[48px] bg-brand-100 border-[8px] border-brand-50 rounded-full flex items-center justify-center">
|
|
28
|
+
<IconComponent :icon="item.icon" icon-classes="w-5 h-5 text-brand-600"></IconComponent>
|
|
29
|
+
</div>
|
|
30
|
+
<div class="max-w-[324px]">
|
|
31
|
+
<h3 class="font-semibold text-[20px] text-gray-900">{{ item.title }}</h3>
|
|
32
|
+
<p class="mt-2 text-md font-normal text-gray-600 leading-[24px]">{{ item.supporting_text }}</p>
|
|
33
|
+
</div>
|
|
34
|
+
</div>
|
|
35
|
+
</div>
|
|
36
|
+
<div v-if="imageComponent" class="w-[560px]">
|
|
37
|
+
<img :src="imageComponent.featured_image" :alt="imageComponent?.caption ?? 'Image'"
|
|
38
|
+
class="rounded-br-[24px] rounded-tl-[24px] w-full"/>
|
|
39
|
+
</div>
|
|
40
|
+
</div>
|
|
41
|
+
</div>
|
|
14
42
|
</div>
|
|
15
43
|
</div>
|
|
16
44
|
</template>
|
|
17
45
|
|
|
18
46
|
<script setup>
|
|
47
|
+
import IconComponent from "@/components/common/Icon.vue";
|
|
19
48
|
import {ref, computed} from "vue";
|
|
20
49
|
|
|
21
50
|
const props = defineProps({
|
|
@@ -29,8 +58,14 @@ const section = ref(props.section);
|
|
|
29
58
|
const paragraphComponent = computed(() => {
|
|
30
59
|
return section.value.components.find((component) => component.type === "paragraph");
|
|
31
60
|
});
|
|
61
|
+
const headerComponent = computed(() => {
|
|
62
|
+
return section.value.components.find((component) => component.type === "header");
|
|
63
|
+
});
|
|
32
64
|
const imageComponent = computed(() => {
|
|
33
65
|
return section.value.components.find((component) => component.type === "image_block");
|
|
34
66
|
});
|
|
67
|
+
const featureItemsComponent = computed(() => {
|
|
68
|
+
return section.value.components.find((component) => component.type === "feature_items");
|
|
69
|
+
});
|
|
35
70
|
|
|
36
71
|
</script>
|
|
@@ -14,6 +14,7 @@
|
|
|
14
14
|
<script setup>
|
|
15
15
|
import Plus from "@/assets/img/icons/plus.svg";
|
|
16
16
|
import ShoppingCart from "@/assets/img/icons/shopping-cart-01.svg";
|
|
17
|
+
import { formatUrl } from "@/components/helpers/common";
|
|
17
18
|
|
|
18
19
|
const props = defineProps({
|
|
19
20
|
button: {
|
|
@@ -21,8 +22,4 @@ const props = defineProps({
|
|
|
21
22
|
required: true,
|
|
22
23
|
},
|
|
23
24
|
});
|
|
24
|
-
|
|
25
|
-
const formatUrl = (url) => {
|
|
26
|
-
return url.startsWith("http") ? url : `//${url}`;
|
|
27
|
-
};
|
|
28
25
|
</script>
|