diff --git a/src/stable/components/Event/Event.js b/src/stable/components/Event/Event.js
new file mode 100644
index 00000000..43a6861f
--- /dev/null
+++ b/src/stable/components/Event/Event.js
@@ -0,0 +1,93 @@
+import styles from '!!raw-loader!./event.css';
+
+const template = document.createElement('template');
+template.innerHTML = `
+
+
+
+`;
+
+class Event extends HTMLElement {
+ constructor() {
+ super();
+
+ // Create a shadow root
+ const shadow = this.attachShadow({ mode: 'open' });
+ shadow.appendChild(template.content.cloneNode(true));
+ }
+ connectedCallback() {
+ this.setupDatetime();
+ }
+
+ setupDatetime() {
+ // Get args.when (Date)
+ const dateInfo = this.getAttribute('datetime');
+ const numFromString = Number(dateInfo);
+ const dateISO = new Date(numFromString).toISOString();
+ // Month & Day
+ const dateFormat = new Date(dateISO).toLocaleDateString('en-DE', {
+ month: 'short',
+ day: 'numeric',
+ });
+ const dateSpan = document.createElement('span');
+ dateSpan.innerText = dateFormat + '\n';
+ const eventDate = this.shadowRoot.querySelector('.event-date');
+ eventDate.appendChild(dateSpan);
+
+ // Year
+ const year = new Date(dateISO).toLocaleDateString('en-DE', {
+ year: 'numeric',
+ });
+ const yearSpan = document.createElement('span');
+ yearSpan.innerText = year;
+ const eventYear = this.shadowRoot.querySelector('.event-year');
+ eventYear.appendChild(yearSpan);
+
+ // Get Time
+ const locTime = new Date(dateISO).toLocaleTimeString('en-US', {
+ hour: '2-digit',
+ minute: '2-digit',
+ });
+ const timeSpan = document.createElement('span');
+ timeSpan.innerText = locTime;
+ const eventTime = this.shadowRoot.querySelector('.event-time');
+ eventTime.appendChild(timeSpan);
+ }
+}
+
+export default Event;
diff --git a/src/stable/components/Event/cod-event.js b/src/stable/components/Event/cod-event.js
new file mode 100644
index 00000000..5f7997d1
--- /dev/null
+++ b/src/stable/components/Event/cod-event.js
@@ -0,0 +1,2 @@
+import Event from './Event';
+customElements.define('cod-event', Event);
diff --git a/src/stable/components/Event/event.css b/src/stable/components/Event/event.css
new file mode 100644
index 00000000..feeb6ddd
--- /dev/null
+++ b/src/stable/components/Event/event.css
@@ -0,0 +1,54 @@
+.event-container {
+ width: fit-content;
+ min-width: 340px;
+ display: flex;
+}
+.event-container .date-info {
+ background-color: #004445;
+ height: 75px;
+ justify-content: center;
+ text-align: center;
+ flex: 0;
+ color: white;
+ font-weight: lighter;
+ padding: 3px 20px;
+ line-height: normal;
+}
+.event-container .date-info .event-date {
+ color: white;
+ flex: 0;
+ font-weight: 900;
+ display: flex;
+}
+.event-container .event-info {
+ flex: 3;
+ padding: 5px 10px;
+}
+.event-container .event-info .event-title {
+ display: flex;
+}
+.event-container .event-info .event-title ::slotted(a) {
+ text-decoration: none !important;
+ border-bottom: 3px solid #279989 !important;
+ color: #000 !important;
+}
+.event-container .event-info .event-title svg {
+ top: 5px;
+ position: relative;
+}
+.event-container .event-info .event-title:hover svg {
+ transform: translate(5px, 0px);
+}
+.event-container .event-info .info-row {
+ display: flex;
+ margin-top: 10px;
+ flex-flow: row wrap;
+}
+.event-container .event-info .info-row .info-item {
+ flex-grow: 1;
+}
+.event-container .event-info .info-row .event-time {
+ font-weight: 900;
+}
+
+/*# sourceMappingURL=event.css.map */
diff --git a/src/stable/components/Event/event.css.map b/src/stable/components/Event/event.css.map
new file mode 100644
index 00000000..7e007c33
--- /dev/null
+++ b/src/stable/components/Event/event.css.map
@@ -0,0 +1 @@
+{"version":3,"sourceRoot":"","sources":["event.scss"],"names":[],"mappings":"AAAA;EACE;EACA;EACA;;AAEA;EACE;EACA;EACA;EACA;EACA;EACA;EACA;EACA;EACA;;AAEA;EACE;EACA;EACA;EACA;;AAIJ;EACE;EACA;;AAEA;EACE;;AAEA;EACE;EACA;EACA;;AAGF;EACE;EACA;;AAIJ;EACE;;AAGF;EACE;EACA;EACA;;AAEA;EACE;;AAGF;EACE","file":"event.css"}
\ No newline at end of file
diff --git a/src/stable/components/Event/event.scss b/src/stable/components/Event/event.scss
new file mode 100644
index 00000000..67ef25e8
--- /dev/null
+++ b/src/stable/components/Event/event.scss
@@ -0,0 +1,62 @@
+.event-container {
+ width: fit-content;
+ min-width: 340px;
+ display: flex;
+
+ .date-info {
+ background-color: #004445;
+ height: 75px;
+ justify-content: center;
+ text-align: center;
+ flex: 0;
+ color: white;
+ font-weight: lighter;
+ padding: 3px 20px;
+ line-height: normal;
+
+ .event-date {
+ color: white;
+ flex: 0;
+ font-weight: 900;
+ display: flex;
+ }
+ }
+
+ .event-info {
+ flex: 3;
+ padding: 5px 10px;
+
+ .event-title {
+ display: flex;
+
+ ::slotted(a) {
+ text-decoration: none !important;
+ border-bottom: 3px solid #279989 !important;
+ color: #000 !important;
+ }
+
+ svg {
+ top: 5px;
+ position: relative;
+ }
+ }
+
+ .event-title:hover svg {
+ transform: translate(5px, 0px);
+ }
+
+ .info-row {
+ display: flex;
+ margin-top: 10px;
+ flex-flow: row wrap;
+
+ .info-item {
+ flex-grow: 1;
+ }
+
+ .event-time {
+ font-weight: 900;
+ }
+ }
+ }
+}
diff --git a/src/stable/components/Tag/Tag.css b/src/stable/components/Tag/Tag.css
index 46c95b74..b6c9667c 100644
--- a/src/stable/components/Tag/Tag.css
+++ b/src/stable/components/Tag/Tag.css
@@ -1,3 +1,8 @@
.tag-container {
display: inline;
+
+ ::slotted(a) {
+ text-decoration: none !important;
+ color: #000 !important;
+ }
}
diff --git a/src/stable/docs/Event.mdx b/src/stable/docs/Event.mdx
new file mode 100644
index 00000000..ff2cee44
--- /dev/null
+++ b/src/stable/docs/Event.mdx
@@ -0,0 +1,84 @@
+import {
+ Meta,
+ Canvas,
+ Title,
+ Subtitle,
+ Description,
+ Primary,
+ Controls,
+ Stories,
+ Story,
+ Source,
+} from '@storybook/blocks';
+import * as EventStories from '../stories/event.stories';
+
+import '../../../.storybook/docs'; // Import all documentation components
+
+
+
+# Event
+
+
+ Event element will be used within Department pages to display Event
+ information
+
+
+## Usage
+
+
+
+
+
+##
+
+
+
+## Slots
+
+
+
+
+## HTML Attributes / JS Properties
+
+ element."},
+])}>
+
+
+## Events
+
+
+
+
+## Methods
+
+
+
+
+## Custom CSS Properties
+
+
+
+
+## CSS Parts
+
+
+
+
+## Dependencies
+
+
+
+## Accessibility
+
+event components are designed to be accessible by default.
diff --git a/src/stable/stories/event.stories.js b/src/stable/stories/event.stories.js
new file mode 100644
index 00000000..11200384
--- /dev/null
+++ b/src/stable/stories/event.stories.js
@@ -0,0 +1,115 @@
+import '../components/Event/cod-event';
+import '../components/Tag/cod-tag';
+import { html } from 'lit-html';
+import { expect } from '@storybook/test';
+
+export default {
+ title: 'Components/Event',
+ argTypes: {
+ title: { control: 'text' },
+ when: { control: 'date' },
+ virutalEvent: { control: 'boolean' },
+ location: { control: 'text' },
+ tag: { control: 'text' },
+ },
+};
+
+const Template = (args) => {
+ const event = document.createElement('cod-event');
+
+ // Title
+ const title = document.createElement('a');
+ title.setAttribute('href', 'https://www.example.com');
+ title.slot = 'event-title';
+ title.textContent = args.title;
+ event.appendChild(title);
+
+ // Datetime
+ const eventDate = args.when;
+ event.setAttribute('datetime', eventDate);
+
+ // Default Datetime
+ if (!args.when) {
+ const defaultDate = Date.now();
+ event.setAttribute('datetime', defaultDate);
+ }
+
+ // Location
+ const location = document.createElement('span');
+ location.slot = 'event-location';
+
+ // Virtual Event
+ if (args.virutalEvent === true) {
+ location.textContent = 'Virtual Event';
+ } else {
+ location.textContent = args.location;
+ }
+ event.appendChild(location);
+
+ // Tag
+ const tagSpan = document.createElement('span');
+ tagSpan.innerHTML = `
+ ${args.tag}
+ `;
+ tagSpan.slot = 'event-tag';
+ event.appendChild(tagSpan);
+
+ return event;
+};
+
+export const Default = Template.bind({});
+
+Default.args = {
+ title: 'DDOT Virtual Community Input Meeting',
+ location: 'Conference Room',
+ tag: 'Meeting',
+};
+
+export const TagLink = {
+ tags: ['!dev'],
+ render: () => {
+ return html`
+
+ DDOT Virtual Community Input Meeting
+ Conference Room
+ Click Me
+
+ `;
+ },
+};
+
+export const Test = {
+ tags: ['!dev'],
+ render: () => {
+ return html`
+ DDOT Virtual Community Input MeetingConference Room
+ Meeting
+
+ `;
+ },
+ play: async ({ canvasElement }) => {
+ const event = canvasElement.querySelector('cod-event');
+ const eventShadowRoot = event.shadowRoot;
+ const titleSlot = eventShadowRoot.querySelector('slot[name="event-title"]');
+
+ // Tests if title slot is empty
+ expect(titleSlot).not.toBeNull();
+
+ // Test if title is a link
+ const titleLink = titleSlot.assignedElements()[0];
+ expect(titleLink.tagName).toBe('A');
+ },
+};