1
0
Fork 0
mirror of https://github.com/archtechx/airwire-demo.git synced 2025-12-12 08:34:03 +00:00

public release

This commit is contained in:
Samuel Štancl 2021-05-21 18:38:26 +02:00
commit d6d22f8355
115 changed files with 67218 additions and 0 deletions

View file

@ -0,0 +1 @@
// todo

View file

@ -0,0 +1,108 @@
@props([
// For how long should a notification be displayed before it's removed.
'duration' => 1750,
// Display stored notifications after 150ms, to give the rest of the page time to load, making things feel smoother.
'loadDelay' => 150,
])
<div
x-data='{
messages: {},
pendingRemovals: {},
add(message) {
if (typeof message === "string") {
message = {
title: message,
body: "",
link: "",
}
}
let indices = Object.keys(this.messages).sort();
let lastIndex = parseInt(indices[indices.length - 1]) || 0;
let index = lastIndex + 1;
this.messages[index] = message;
this.scheduleRemoval(index);
},
scheduleRemoval(messageIndex) {
// For loops we use integers
messageIndex = parseInt(messageIndex);
// Schedule removals for the object and all of the following ones of they dont have a removal scheduled yet.
for (let i = messageIndex; i >= 0; i--) {
// For object keys we use strings
let index = i.toString();
if (! Object.keys(this.pendingRemovals).includes(index)) {
this.pendingRemovals[index] = setTimeout(() => { this.remove(index) }, {!! $duration !!});
}
}
},
cancelRemoval(messageIndex) {
// For loops we use integers
messageIndex = parseInt(messageIndex);
// When we cancel the removal of a message, we also want to cancel the removal of all
// messages above it, to prevent the messages from changing position on the screen.
for (let i = 0; i <= messageIndex; i++) {
// For object keys we use strings
let index = i.toString();
clearTimeout(this.pendingRemovals[index]);
delete this.pendingRemovals[index];
}
},
remove(messageIndex) {
delete this.messages[messageIndex];
delete this.pendingRemovals[messageIndex];
},
}'
x-init="window.notify = (...args) => add(...args)"
class="
fixed inset-0 px-4 py-6 pointer-events-none sm:p-6
flex flex-col {{-- Stack notifications below each other --}}
items-center justify-start {{-- Mobile: top center --}}
sm:items-end sm:justify-start {{-- Desktop: top right corner --}}
space-y-3 {{-- Space between individual notifications --}}
"
>
<template x-for="[index, message] of Object.entries(messages)" :key="index" hidden>
<div
x-transition:enter="transform ease-out duration-200 transition"
x-transition:enter-start="translate-y-2 opacity-0 sm:translate-y-0 sm:translate-x-10"
x-transition:enter-end="translate-y-0 opacity-100 sm:translate-x-0"
x-transition:leave="transition ease-in duration-200"
x-transition:leave-start="opacity-100"
x-transition:leave-end="opacity-0"
class="max-w-sm w-full bg-white hover:bg-purple-50 shadow rounded-md overflow-hidden pointer-events-auto"
@mouseenter="cancelRemoval(index)"
@mouseleave="scheduleRemoval(index)"
>
<div class="rounded-lg shadow-xs overflow-hidden">
<div class="p-4">
<div class="flex items-start">
<div class="flex-shrink-0">
@svg('heroicon-o-information-circle', ['class' => 'h-6 w-6 text-purple-500'])
</div>
<template x-if="message.link">
<a :href="message.link" class="ml-3 w-0 flex-1 pt-0.5">
<p x-text="message.title" class="text-sm leading-5 font-medium text-gray-700"></p>
<p x-text="message.body" class="mt-1 text-sm text-gray-500"></p>
</a>
</template>
<template x-if="! message.link">
<div class="ml-3 w-0 flex-1 pt-0.5">
<p x-text="message.title" class="text-sm leading-5 font-medium text-gray-700"></p>
<p x-text="message.body" class="mt-1 text-sm text-gray-500"></p>
</div>
</template>
<div class="ml-4 flex-shrink-0 flex">
<button
@click="remove(index)"
class="rounded-md inline-flex text-gray-400 hover:text-gray-500 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-purple-500"
>
<span class="sr-only">Close notification</span>
@svg('heroicon-o-x', ['class' => 'h-5 w-5'])
</button>
</div>
</div>
</div>
</div>
</div>
</template>
</div>

View file

@ -0,0 +1,26 @@
<!DOCTYPE html>
<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<link href="{{ asset('css/app.css') }}" rel="stylesheet">
<title>Vue | Airwire</title>
<!-- Fonts -->
<link rel="stylesheet" href="https://rsms.me/inter/inter.css">
<style>
body {
font-family: 'Inter var', sans-serif;
}
</style>
</head>
<body class="antialiased">
<div class="relative flex items-top justify-center min-h-screen bg-gray-100 dark:bg-gray-900 py-4 sm:pt-0">
<div id="app" class="2xl:w-3/4 w-full"></div>
</div>
</body>
<script src="{{ asset('js/app.js') }}"></script>
</html>