@dcrackel/meyersquaredui 1.0.36 → 1.0.38

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 (34) hide show
  1. package/dist/meyersquaredui.es.js +343 -219
  2. package/dist/meyersquaredui.umd.js +1 -0
  3. package/dist/style.css +1 -1
  4. package/package.json +8 -2
  5. package/src/assets/fonts/Raleway-Thin.ttf +0 -0
  6. package/src/assets/images/portrait1.png +0 -0
  7. package/src/mocks/getArticles.js +19 -0
  8. package/src/mocks/getTopFencers.js +157 -0
  9. package/src/mocks/getTournamentsMock.js +185 -0
  10. package/src/stories/Atoms/BaseButton/BaseButton.stories.js +35 -32
  11. package/src/stories/Atoms/BaseButton/BaseButton.vue +66 -4
  12. package/src/stories/Atoms/BaseText/BaseText.vue +25 -8
  13. package/src/stories/Atoms/Icon/Icon.vue +6 -1
  14. package/src/stories/Organisms/Cards/ArticleCard/ArticleCard.stories.js +25 -0
  15. package/src/stories/Organisms/Cards/ArticleCard/ArticleCard.vue +48 -0
  16. package/src/stories/Organisms/Cards/FencerCard/FencerCard.stories.js +48 -0
  17. package/src/stories/Organisms/Cards/FencerCard/FencerCard.vue +69 -0
  18. package/src/stories/Organisms/Cards/TournamentCard/TournamentCard.stories.js +24 -0
  19. package/src/stories/Organisms/Cards/TournamentCard/TournamentCard.vue +121 -0
  20. package/src/stories/Organisms/Footer/Foot.stories.js +11 -0
  21. package/src/stories/Organisms/Footer/Footer.vue +94 -0
  22. package/src/stories/Organisms/GridLayout/GridLayout.stories.js +148 -0
  23. package/src/stories/Organisms/GridLayout/GridLayout.vue +98 -0
  24. package/src/stories/Organisms/Headers/Header.stories.js +1 -1
  25. package/src/stories/Organisms/Headers/Header.vue +5 -6
  26. package/src/stories/Organisms/HeroBanners/HomePage/HeroBanner.vue +52 -25
  27. package/src/stories/Organisms/SectionBanners/DoubleButtonBanner/DoubleButtonBanner.stories.js +28 -0
  28. package/src/stories/Organisms/SectionBanners/DoubleButtonBanner/DoubleButtonBanner.vue +118 -0
  29. package/src/stories/Organisms/SectionBanners/SingleButtonBanner/SingleButtonBanner.stories.js +35 -0
  30. package/src/stories/Organisms/SectionBanners/SingleButtonBanner/SingleButtonBanner.vue +48 -0
  31. package/src/stories/Templates/HomePage/TestPage.stories.js +7 -2
  32. package/src/stories/Templates/HomePage/TestPage.vue +73 -1
  33. package/dist/meyersquaredui.cjs.js +0 -1
  34. package/src/components/HelloWorld.vue +0 -43
@@ -1,7 +1,8 @@
1
1
  <template>
2
2
  <button
3
3
  :class="[
4
- 'px-4 py-2 rounded-md transition duration-300 ease-in-out',
4
+ 'rounded-md transition duration-300 ease-in-out',
5
+ paddingClass,
5
6
  textColorClass,
6
7
  backgroundClass,
7
8
  borderClass,
@@ -10,13 +11,23 @@
10
11
  :aria-label="altText || label"
11
12
  @click="$emit('click')"
12
13
  >
13
- {{ label }}
14
+ <div :class="['flex items-center', alignmentClass, 'space-x-2']">
15
+ <BaseText :color="color" :hoverColor="hoverColor" :size="size" :weight="weight">{{ label }}</BaseText>
16
+ <Icon :icon="iconName" :color="iconColor" :size="iconSize" :type="iconType"/>
17
+ </div>
14
18
  </button>
15
19
  </template>
16
20
 
17
21
  <script>
22
+ import BaseText from "../BaseText/BaseText.vue";
23
+ import Icon from '../../Atoms/Icon/Icon.vue';
24
+
18
25
  export default {
19
26
  name: 'BaseButton',
27
+ components: {
28
+ BaseText,
29
+ Icon
30
+ },
20
31
  props: {
21
32
  label: {
22
33
  type: String,
@@ -26,11 +37,24 @@ export default {
26
37
  type: String,
27
38
  default: null,
28
39
  },
40
+ size: {
41
+ type: String,
42
+ default: 'md',
43
+ },
44
+ weight: {
45
+ type: String,
46
+ default: 'normal',
47
+ },
29
48
  color: {
30
49
  type: String,
31
50
  default: 'primary',
32
51
  validator: (value) => ['primary', 'secondary', 'accent'].includes(value),
33
52
  },
53
+ hoverColor: {
54
+ type: String,
55
+ default: '',
56
+ validator: (value) => ['primary', 'secondary', 'accent'].includes(value),
57
+ },
34
58
  backgroundColor: {
35
59
  type: String,
36
60
  default: 'primary',
@@ -42,8 +66,38 @@ export default {
42
66
  validator: (value) =>
43
67
  ['none', 'primary', 'secondary', 'accent', 'gradient1', 'gradient2'].includes(value),
44
68
  },
69
+ padding: {
70
+ type: String,
71
+ default: 'px-4 py-2',
72
+ },
73
+ iconName: {
74
+ type: String,
75
+ default: ''
76
+ },
77
+ iconColor: {
78
+ type: String,
79
+ default: 'primary',
80
+ validator: (value) => ['primary', 'secondary', 'accent'].includes(value),
81
+ },
82
+ iconSize: {
83
+ control: { type: 'select', options: ['xs', 'sm', 'md', 'lg', 'xl', '2xl', '3xl'] },
84
+ description: 'Icon size',
85
+ },
86
+ iconType: {
87
+ type: String,
88
+ default: 'fa-solid',
89
+ validator: (value) => ['fa-thin', 'fa-sharp'].includes(value),
90
+ },
91
+ align: {
92
+ type: String,
93
+ default: 'center',
94
+ validator: (value) => ['left', 'center', 'right', 'between'].includes(value),
95
+ },
45
96
  },
46
97
  computed: {
98
+ paddingClass() {
99
+ return this.padding;
100
+ },
47
101
  textColorClass() {
48
102
  const textColor = {
49
103
  primary: 'text-primary',
@@ -55,7 +109,7 @@ export default {
55
109
  backgroundClass() {
56
110
  const colorMap = {
57
111
  primary: 'bg-primary hover:bg-accent',
58
- secondary: 'bg-secondary hover:bg-accent',
112
+ secondary: 'bg-secondary hover:bg-primary',
59
113
  accent: 'bg-accent hover:bg-accent',
60
114
  };
61
115
  return colorMap[this.backgroundColor] || 'bg-primary';
@@ -71,6 +125,15 @@ export default {
71
125
  };
72
126
  return borderMap[this.border] || '';
73
127
  },
128
+ alignmentClass() {
129
+ const alignmentMap = {
130
+ left: 'justify-start',
131
+ center: 'justify-center',
132
+ right: 'justify-end',
133
+ between: 'justify-between', // New "between" option added
134
+ };
135
+ return alignmentMap[this.align] || 'justify-center';
136
+ },
74
137
  },
75
138
  };
76
139
  </script>
@@ -106,5 +169,4 @@ export default {
106
169
  background: linear-gradient(to right, #009DFF, #25E07C);
107
170
  color: white; /* Optional: You can change the text color on hover as well */
108
171
  }
109
-
110
172
  </style>
@@ -16,20 +16,24 @@ export default {
16
16
  size: {
17
17
  type: String,
18
18
  default: 'md',
19
- validator: (value) => ['xs', 'sm', 'md', 'lg', 'xl', '2xl', '3xl', '4xl', '5xl'].includes(value),
20
19
  },
21
20
  color: {
22
21
  type: String,
23
22
  default: 'primary',
24
23
  },
24
+ hoverColor: {
25
+ type: String,
26
+ default: '',
27
+ },
25
28
  weight: {
26
29
  type: String,
27
30
  default: 'normal',
28
- validator: (value) => ['light', 'normal', 'semibold', 'bold'].includes(value),
31
+ validator: (value) => ['thin','light', 'normal','semibold','bold'].includes(value),
29
32
  },
30
33
  },
31
34
  computed: {
32
35
  textClasses() {
36
+ // Map for size classes
33
37
  const sizeClasses = {
34
38
  xs: 'text-xs',
35
39
  sm: 'text-sm',
@@ -39,17 +43,30 @@ export default {
39
43
  '2xl': 'text-2xl',
40
44
  '3xl': 'text-3xl',
41
45
  '4xl': 'text-4xl',
42
- '5xl': 'text-5xl'
46
+ '5xl': 'text-5xl',
43
47
  };
44
48
 
45
49
  const weightClasses = {
46
- light: 'font-light',
47
- normal: 'font-normal',
48
- semibold: 'font-semibold',
49
- bold: 'font-bold',
50
+ thin: 'font-thin font-[100]',
51
+ light: 'font-light font-[300]',
52
+ normal: 'font-normal font-[400]',
53
+ semibold: 'font-semibold font-[600]',
54
+ bold: 'font-bold font-[700]',
50
55
  };
51
56
 
52
- return `${sizeClasses[this.size]} ${weightClasses[this.weight]} text-${this.color}`;
57
+ const hoverClass = this.hoverColor ? `hover:text-${this.hoverColor}` : '';
58
+
59
+ // Parse the size prop to allow responsive classes
60
+ const sizeClassList = this.size
61
+ .split(' ')
62
+ .map((size) => {
63
+ const [prefix, value] = size.includes(':') ? size.split(':') : [null, size];
64
+ return prefix ? `${prefix}:${sizeClasses[value]}` : sizeClasses[value];
65
+ })
66
+ .filter(Boolean)
67
+ .join(' ');
68
+
69
+ return `${sizeClassList} ${weightClasses[this.weight]} text-${this.color} ${hoverClass} font-raleway`;
53
70
  },
54
71
  },
55
72
  };
@@ -1,5 +1,5 @@
1
1
  <template>
2
- <i :class="[ 'fas', icon, colorClasses, sizeClasses ]" @click="$emit('click')" />
2
+ <i :class="[ type, icon, colorClasses, sizeClasses ]" @click="$emit('click')" />
3
3
  </template>
4
4
 
5
5
  <script>
@@ -20,6 +20,11 @@ export default {
20
20
  default: 'md',
21
21
  validator: (value) => ['xs', 'sm', 'md', 'lg', 'xl', '2xl', '3xl'].includes(value),
22
22
  },
23
+ type: {
24
+ type: String,
25
+ default: 'fa-solid',
26
+ validator: (value) => ['fa-thin', 'fa-sharp'].includes(value),
27
+ }
23
28
  },
24
29
  computed: {
25
30
  colorClasses() {
@@ -0,0 +1,25 @@
1
+ import ArticleCard from './ArticleCard.vue';
2
+ import mockArticles from "../../../../mocks/getArticles.js";
3
+
4
+ export default {
5
+ title: 'Organisms/Cards/ArticleCard',
6
+ component: ArticleCard,
7
+ argTypes: {
8
+ onReadMore: { action: 'read-more' }
9
+ }
10
+ };
11
+
12
+ const Template = (args) => ({
13
+ components: { ArticleCard },
14
+ setup() {
15
+ return { args };
16
+ },
17
+ template: '<ArticleCard v-bind="args" @read-more="args.onReadMore" />',
18
+ });
19
+
20
+ export const Default = Template.bind({});
21
+ Default.args = {
22
+ image: 'https://via.placeholder.com/300x200',
23
+ articleTitle: 'Exciting News in HEMA',
24
+ description: 'Learn about the latest developments and events happening in the HEMA community. Stay informed and get the latest updates.',
25
+ };
@@ -0,0 +1,48 @@
1
+ <template>
2
+ <div class="w-72 p-4 bg-secondary rounded-lg flex flex-col items-start">
3
+ <img :src="image" alt="Article Image" class="w-full h-40 object-cover rounded-t-md mb-4" />
4
+
5
+ <BaseText tag="h3" size="xl" weight="semibold" class="mb-2">{{ articleTitle }}</BaseText>
6
+ <BaseText tag="p" size="sm" weight="normal" class="mb-4 h-20">{{ truncatedDescription }}</BaseText>
7
+
8
+ <a href="#" @click.prevent="onReadMore" class="w-full flex justify-end pr-2">
9
+ <BaseText tag="p" size="sm" weight="simibold" class="mb-4 border-b border-secondary hover:border-accent">Read More &rarr;</BaseText>
10
+ </a>
11
+ </div>
12
+ </template>
13
+
14
+ <script>
15
+ import BaseText from "../../../Atoms/BaseText/BaseText.vue";
16
+
17
+ export default {
18
+ name: 'ArticleCard',
19
+ components: {
20
+ BaseText
21
+ },
22
+ props: {
23
+ data: {
24
+ type: Object,
25
+ required: true,
26
+ },
27
+ },
28
+ computed: {
29
+ image() {
30
+ return this.data.image;
31
+ },
32
+ articleTitle() {
33
+ return this.data.articleTitle;
34
+ },
35
+ truncatedDescription() {
36
+ if (this.data.description.length > 120) {
37
+ return this.data.description.substring(0, 120) + ' ...';
38
+ }
39
+ return this.data.description;
40
+ }
41
+ },
42
+ methods: {
43
+ onReadMore() {
44
+ this.$emit('read-more');
45
+ }
46
+ }
47
+ };
48
+ </script>
@@ -0,0 +1,48 @@
1
+ import FencerCard from './FencerCard.vue';
2
+
3
+ export default {
4
+ title: 'Organisms/Cards/FencerCard',
5
+ component: FencerCard,
6
+ argTypes: {
7
+ portrait: { control: 'text' },
8
+ displayName: { control: 'text' },
9
+ clubName: { control: 'text' },
10
+ m2Rating: { control: 'number' },
11
+ hrRating: { control: 'number' },
12
+ },
13
+ };
14
+
15
+ const Template = (args) => ({
16
+ components: { FencerCard },
17
+ setup() {
18
+ return { args };
19
+ },
20
+ template: '<FencerCard v-bind="args" />',
21
+ });
22
+
23
+ export const Default = Template.bind({});
24
+ Default.args = {
25
+ portrait: 'https://randomuser.me/api/portraits/women/26.jpg',
26
+ displayName: 'John Doe',
27
+ clubName: 'Awesome Fencing Club',
28
+ m2Rating: 'A24',
29
+ hrRating: 1567,
30
+ };
31
+
32
+ export const HighRating = Template.bind({});
33
+ HighRating.args = {
34
+ portrait: '',
35
+ displayName: 'Jane Smith',
36
+ clubName: 'Elite Fencing Academy',
37
+ m2Rating: 1500,
38
+ hrRating: 1300,
39
+ };
40
+
41
+ export const NoRating = Template.bind({});
42
+ NoRating.args = {
43
+ portrait: '',
44
+ displayName: 'Unknown Fencer',
45
+ clubName: 'No Club',
46
+ m2Rating: null,
47
+ hrRating: null,
48
+ };
@@ -0,0 +1,69 @@
1
+ <template>
2
+ <section class="mr-4 md:mr-2 items-center">
3
+ <div class="flex flex-col m-auto justify-center mb-4 items-center w-[160px]">
4
+ <img :src="portrait" alt="Fencer Portrait" class="w-[120px] h-[120px] md:w-40 md:h-40 rounded-full object-cover z-1 flex-shrink-0" />
5
+ </div>
6
+ <!-- Ratings -->
7
+ <div class="flex flex-col md:flex-row justify-center md:justify-around -mt-2 border-b border-borderGray z-10 pb-2 mb-2">
8
+ <div class="flex items-center justify-center">
9
+ <BaseText tag="p" size="xs md:sm" weight="semibold" class="primary mr-1 block z-50">M2: </BaseText>
10
+ <BaseText tag="p" size="sm md:md" weight="bold" class="text-accent">{{ m2Rating }}</BaseText>
11
+ </div>
12
+ <div class="hidden md:flex items-center justify-center">
13
+ <BaseText tag="p" size="md" weight="bold" class="text-accent">{{ hrRating }}</BaseText>
14
+ <BaseText tag="p" size="sm" weight="semibold" class="primary mr-1">:HR</BaseText>
15
+ </div>
16
+ </div>
17
+ <BaseText tag="h3" size="sm md:xl" weight="semibold" class="text-center">{{ displayName }}</BaseText>
18
+ <BaseText tag="p" size="xs md:sm" weight="normal" class="text-center h-10">{{ clubName }}</BaseText>
19
+ </section>
20
+ </template>
21
+
22
+ <script>
23
+ import BaseText from "../../../Atoms/BaseText/BaseText.vue";
24
+ import defaultPortrait from '../../../../assets/images/portrait1.png'
25
+
26
+ // :style="{ flexShrink: '0', minWidth: '160px', minHeight: '160px' }"
27
+ export default {
28
+ name: 'FencerCard',
29
+ components: {
30
+ BaseText,
31
+ defaultPortrait
32
+ },
33
+ props: {
34
+ data: {
35
+ type: Object,
36
+ required: true,
37
+ },
38
+ index: {
39
+ type: Number,
40
+ required: true,
41
+ },
42
+ },
43
+ data() {
44
+ return {
45
+ };
46
+ },
47
+ computed: {
48
+ portrait() {
49
+ return this.data.ProfileImage && this.data.ProfileImage.URL
50
+ ? this.data.ProfileImage.URL
51
+ : defaultPortrait;
52
+ },
53
+ displayName() {
54
+ return this.data.DisplayName;
55
+ },
56
+ clubName() {
57
+ return this.data.Club.Name;
58
+ },
59
+ m2Rating() {
60
+ const m2RatingForWeapon = this.data.M2Ratings.find(rating => rating.WeaponId === 1);
61
+ return m2RatingForWeapon ? m2RatingForWeapon.FormattedRating : 'U';
62
+ },
63
+ hrRating() {
64
+ return this.data.HEMARatings && this.data.HEMARatings[0] ? this.data.HEMARatings[0].Rating : 0;
65
+ },
66
+ }
67
+ };
68
+ </script>
69
+
@@ -0,0 +1,24 @@
1
+ import TournamentCard from './TournamentCard.vue';
2
+
3
+ export default {
4
+ title: 'Organisms/Cards/TournamentCard',
5
+ component: TournamentCard,
6
+ };
7
+
8
+ const Template = (args) => ({
9
+ components: { TournamentCard },
10
+ setup() {
11
+ return { args };
12
+ },
13
+ template: '<TournamentCard v-bind="args" />',
14
+ });
15
+
16
+ export const Default = Template.bind({});
17
+ Default.args = {
18
+ image: 'https://assets.simpleviewinc.com/simpleview/image/upload/c_fill,f_avif,h_800,q_65,w_1920/v1/clients/wausauwi/download_5__d27db8e0-a64a-4db5-8126-17033dab6712.jpg',
19
+ title: 'National Fencing Tournament',
20
+ location: 'New York City, NY',
21
+ startDate: 'Jan 1, 2024',
22
+ endDate: 'Jan 3, 2024',
23
+ numberOfFencers: 120,
24
+ };
@@ -0,0 +1,121 @@
1
+ <template>
2
+ <div class="md:w-full mb-8">
3
+ <!-- Desktop Version -->
4
+ <section class="hidden md:block">
5
+ <img
6
+ :src="image"
7
+ alt="Tournament Image"
8
+ class="w-full h-52 object-cover mb-2 rounded-md"
9
+ @error="imageError"
10
+ :style="fallbackStyle"
11
+ />
12
+ <BaseText tag="h3" size="xl" weight="semibold" class="mb-1">{{ title }}</BaseText>
13
+ <BaseText tag="p" size="sm" weight="semibold" class="mb-2">{{ location }}</BaseText>
14
+ <div class="flex items-center mb-1">
15
+ <span class="flex w-6 justify-center">
16
+ <Icon icon="fa-calendar" color="accent" size="sm" class="mr-3 w-4"/>
17
+ </span>
18
+ <BaseText tag="p" size="sm" class="">{{ startDate }} to {{ endDate }}</BaseText>
19
+ </div>
20
+ <div class="flex items-center">
21
+ <span class="flex w-6 justify-center">
22
+ <Icon icon="fa-user-friends" color="accent" size="sm" class="mr-3"/>
23
+ </span>
24
+ <BaseText tag="p" size="sm" class="">{{ numberOfFencers }} Registered Fencers</BaseText>
25
+ </div>
26
+ </section>
27
+
28
+ <!-- Mobile Version -->
29
+ <section class="md:hidden flex-col items-start gap-2 border-b border-borderGray">
30
+
31
+ <div class="flex flex-row">
32
+ <img :src="image"
33
+ alt="Tournament Image"
34
+ class="w-28 h-16 object-cover rounded-md"
35
+ @error="imageError"
36
+ :style="fallbackStyle"
37
+ />
38
+ <div class="flex flex-col h-16 justify-center pl-2">
39
+ <BaseText tag="h3" size="lg" weight="semibold" class="mb-1">{{ title }}</BaseText>
40
+ <BaseText tag="p" size="xs" weight="semibold" class="mb-1">{{ location }}</BaseText>
41
+ </div>
42
+ </div>
43
+ <div class="flex justify-between pt-4 pb-2">
44
+ <div class="flex justify-start w-5/12">
45
+ <Icon icon="fa-user-friends" color="accent" size="xs" class="mr-1" />
46
+ <BaseText tag="p" size="xs" class="">{{ numberOfFencers }} Registered</BaseText>
47
+ </div>
48
+ <div class="flex justify-start mb-1 w-7/12">
49
+ <Icon icon="fa-calendar" color="accent" size="xs" class="mr-1 w-4" />
50
+ <BaseText tag="p" size="xs" class="">{{ startDate }} to {{ endDate }}</BaseText>
51
+ </div>
52
+ </div>
53
+ </section>
54
+ </div>
55
+ </template>
56
+
57
+ <script>
58
+ import BaseText from "../../../Atoms/BaseText/BaseText.vue";
59
+ import Icon from "../../../Atoms/Icon/Icon.vue";
60
+
61
+ export default {
62
+ name: 'TournamentCard',
63
+ components: {
64
+ BaseText,
65
+ Icon
66
+ },
67
+ props: {
68
+ data: {
69
+ type: Object,
70
+ required: true,
71
+ }
72
+ },
73
+ data() {
74
+ return {
75
+ isImageError: false
76
+ };
77
+ },
78
+ mounted() {
79
+ console.log(this.data);
80
+ },
81
+ computed: {
82
+ image() {
83
+ return !this.isImageError && this.data.Images && this.data.Images.length > 0
84
+ ? this.data.Images[0].URL
85
+ : 'https://via.placeholder.com/300x200';
86
+ },
87
+ fallbackStyle() {
88
+ return this.isImageError
89
+ ? {backgroundColor: '#f5f5f5', display: 'flex', alignItems: 'center', justifyContent: 'center'}
90
+ : {};
91
+ },
92
+ title() {
93
+ return this.data && this.data.Name || '';
94
+ },
95
+ location() {
96
+ return this.data && this.data.Address ? `${this.data.Address.Name} • ${this.data.Address.City}, ${this.data.Address.State}` : 'Location Unavailable';
97
+ },
98
+ startDate() {
99
+ return this.data && this.formatDate(this.data.StartDate);
100
+ },
101
+ endDate() {
102
+ return this.data && this.formatDate(this.data.EndDate);
103
+ },
104
+ numberOfFencers() {
105
+ return this.data && this.data.NumberOfFencers ? this.data.NumberOfFencers : 0;
106
+ }
107
+ },
108
+ methods: {
109
+ formatDate(date) {
110
+ return new Date(date).toLocaleDateString('en-US', {
111
+ year: 'numeric',
112
+ month: 'short',
113
+ day: 'numeric',
114
+ });
115
+ },
116
+ imageError() {
117
+ this.isImageError = true;
118
+ }
119
+ }
120
+ };
121
+ </script>
@@ -0,0 +1,11 @@
1
+ import Footer from './Footer.vue';
2
+
3
+ export default {
4
+ title: 'Organisms/Footers/Footer',
5
+ component: Footer,
6
+ };
7
+
8
+ export const Default = () => ({
9
+ components: { Footer },
10
+ template: '<Footer />',
11
+ });
@@ -0,0 +1,94 @@
1
+ <template>
2
+ <section class="flex flex-col bg-primary">
3
+ <div class="h-20"></div>
4
+
5
+ <section class="w-full hidden md:flex">
6
+ <!-- logo -->
7
+ <div class="w-1/3">
8
+ <div class="items-center w-full flex justify-center">
9
+ <img :src="logo" alt="Logo" class="w-[71px] h-[56px]"/>
10
+ </div>
11
+ </div>
12
+ <!-- middle -->
13
+ <div class="w-1/3 flex flex-col">
14
+ <div class="w-full flex justify-around">
15
+ <div class="flex w-1/3">
16
+ <BaseText color="secondary" size="md" tag="p" weight="normal" class="pb-2">Tournaments</BaseText>
17
+ </div>
18
+ <div class="flex w-1/3">
19
+ <BaseText color="secondary" size="md" tag="p" weight="normal" class="pb-2">Clubs</BaseText>
20
+ </div>
21
+ <div class="flex items-center w-1/3">
22
+ <BaseText color="secondary" size="md" tag="p" weight="normal" class="pb-2">Leaderboard</BaseText>
23
+ </div>
24
+ </div>
25
+ <div class="w-full flex justify-around">
26
+ <div class="flex items-center w-1/3">
27
+ <BaseText color="secondary" size="sm" tag="p" weight="thin" class="pb-2">Upcoming</BaseText>
28
+ </div>
29
+ <div class="flex items-center w-1/3">
30
+ <BaseText color="secondary" size="sm" tag="p" weight="thin" class="pb-2">Club List</BaseText>
31
+ </div>
32
+ <div class="flex items-center w-1/3">
33
+ <BaseText color="secondary" size="sm" tag="p" weight="thin" class="pb-2">Top Fencers</BaseText>
34
+ </div>
35
+ </div>
36
+ <div class="w-full flex justify-around">
37
+ <div class="flex items-center w-1/3">
38
+ <BaseText color="secondary" size="sm" tag="p" weight="thin" class="pb-2">Past</BaseText>
39
+ </div>
40
+ <div class="flex items-center w-1/3">
41
+ <BaseText color="secondary" size="sm" tag="p" weight=thin class="pb-2">Local Clubs</BaseText>
42
+ </div>
43
+ <div class="flex w-1/3">
44
+ <BaseText color="secondary" size="sm" tag="p" weight="thin" class="pb-2">By Weapon</BaseText>
45
+ </div>
46
+ </div>
47
+ </div>
48
+ <!-- subscribe -->
49
+ <div class="w-1/3 flex flex-col">
50
+ <div class="w-full flex justify-end">
51
+ <div class="w-30 mr-16">
52
+ <BaseText color="secondary" size="md" tag="p" weight="thin" class="pb-4 ">Subscribe</BaseText>
53
+ <InputField placeholder="Email" type="email" class="w-52"/>
54
+ </div>
55
+ </div>
56
+ <div class="w-full flex justify-end mt-12">
57
+ <div class="w-48 mr-16">
58
+ <BaseText color="secondary" size="md" tag="p" weight="thin" class="pb-2 ">Follow Us</BaseText>
59
+ <div>
60
+ <Icon type="fa-brands" icon="fa-facebook" color="secondary" size="lg" class="mr-4"/>
61
+ <Icon type="fa-brands" icon="fa-discord" color="secondary" size="lg" class="mr-4"/>
62
+ <Icon type="fa-brands" icon="fa-instagram" color="secondary" size="lg" class="mr-4"/>
63
+ <Icon type="fa-brands" icon="fa-youtube" color="secondary" size="lg" class="mr-4"/>
64
+ </div>
65
+ </div>
66
+ </div>
67
+ </div>
68
+
69
+ </section>
70
+
71
+ <div class="h-32 border border-t mt-10 pb-10 border-lineGrey flex flex-col justify-center items-center">
72
+ <BaseText color="secondary" size="sm" tag="p" weight="normal" class="text-center pt-4">© Copyright Meyer Squared 2024. All rights reserved.</BaseText>
73
+ </div>
74
+ </section>
75
+ </template>
76
+
77
+ <script>
78
+ import BaseText from "../../Atoms/BaseText/BaseText.vue";
79
+ import BaseButton from "../../Atoms/BaseButton/BaseButton.vue";
80
+ import logo from "../../../assets/images/m2.png";
81
+ import InputField from "../../Atoms/InputField/InputField.vue";
82
+ import Icon from "../../Atoms/Icon/Icon.vue";
83
+
84
+ export default {
85
+ name: 'Footer',
86
+ components: {Icon, InputField, BaseButton, BaseText},
87
+ data() {
88
+ return {
89
+ logo: logo,
90
+ };
91
+ },
92
+ };
93
+ </script>
94
+