@avora-labs/meta-forge 1.0.5 → 1.0.6
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/README.md +112 -63
- package/fesm2022/{avora-labs-meta-forge-amf-auth-shell.component-BWSdjBUS.mjs → avora-labs-meta-forge-amf-auth-shell.component-FCubZyZ1.mjs} +57 -57
- package/fesm2022/avora-labs-meta-forge-amf-auth-shell.component-FCubZyZ1.mjs.map +1 -0
- package/fesm2022/{avora-labs-meta-forge-contact-support.page-BAUiKm3P.mjs → avora-labs-meta-forge-contact-support.page-CgcSAr0x.mjs} +146 -146
- package/fesm2022/avora-labs-meta-forge-contact-support.page-CgcSAr0x.mjs.map +1 -0
- package/fesm2022/{avora-labs-meta-forge-forgot-password.page-0XLiBrV1.mjs → avora-labs-meta-forge-forgot-password.page-CWdWX-mj.mjs} +238 -238
- package/fesm2022/avora-labs-meta-forge-forgot-password.page-CWdWX-mj.mjs.map +1 -0
- package/fesm2022/{avora-labs-meta-forge-login.page-etTr5NqJ.mjs → avora-labs-meta-forge-login.page-LCW-ofz1.mjs} +74 -74
- package/fesm2022/avora-labs-meta-forge-login.page-LCW-ofz1.mjs.map +1 -0
- package/fesm2022/avora-labs-meta-forge.mjs +1995 -1995
- package/fesm2022/avora-labs-meta-forge.mjs.map +1 -1
- package/package.json +3 -1
- package/styles/_palettes.scss +84 -84
- package/styles/_themes.scss +96 -96
- package/styles/_variables.scss +56 -56
- package/styles/styles.scss +295 -295
- package/fesm2022/avora-labs-meta-forge-amf-auth-shell.component-BWSdjBUS.mjs.map +0 -1
- package/fesm2022/avora-labs-meta-forge-contact-support.page-BAUiKm3P.mjs.map +0 -1
- package/fesm2022/avora-labs-meta-forge-forgot-password.page-0XLiBrV1.mjs.map +0 -1
- package/fesm2022/avora-labs-meta-forge-login.page-etTr5NqJ.mjs.map +0 -1
package/README.md
CHANGED
|
@@ -1,63 +1,112 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
```bash
|
|
48
|
-
|
|
49
|
-
```
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
1
|
+
<div align="center">
|
|
2
|
+
<img src="https://raw.githubusercontent.com/AvoraLabs/avora-cli/main/assets/logo.png" alt="AvoraMetaForge Logo" width="150" height="150" />
|
|
3
|
+
<h1>@avora-labs/meta-forge</h1>
|
|
4
|
+
<p><strong>The Ultimate Meta-Driven Framework for Modern Angular Applications.</strong></p>
|
|
5
|
+
|
|
6
|
+
<p>
|
|
7
|
+
<a href="https://www.npmjs.com/package/@avora-labs/meta-forge"><img src="https://img.shields.io/npm/v/@avora-labs/meta-forge?color=blue&style=flat-square" alt="NPM Version"></a>
|
|
8
|
+
<img src="https://img.shields.io/badge/License-Proprietary-red.svg?style=flat-square" alt="License: Proprietary">
|
|
9
|
+
<img src="https://img.shields.io/badge/Angular-v17+-dd0031.svg?style=flat-square&logo=angular" alt="Angular">
|
|
10
|
+
<img src="https://img.shields.io/badge/TypeScript-Ready-3178c6.svg?style=flat-square&logo=typescript" alt="TypeScript">
|
|
11
|
+
</p>
|
|
12
|
+
</div>
|
|
13
|
+
|
|
14
|
+
<hr/>
|
|
15
|
+
|
|
16
|
+
## ✨ What is AvoraMetaForge?
|
|
17
|
+
|
|
18
|
+
**AvoraMetaForge** flips the traditional Angular development model upside down. Instead of writing endless HTML templates and boilerplate component classes, you define your **entire application**—from data tables and dynamic forms to dashboards and interactive dialogs—using strictly typed TypeScript JSON objects (metadata).
|
|
19
|
+
|
|
20
|
+
The core engine reads this metadata and natively renders beautiful, fully responsive, and highly interactive UI components on the fly. It drastically reduces boilerplate and allows developers to focus on pure business logic.
|
|
21
|
+
|
|
22
|
+
---
|
|
23
|
+
|
|
24
|
+
## 🚀 Features
|
|
25
|
+
|
|
26
|
+
* **Zero-Boilerplate UI:** Build complex dashboards without writing a single line of HTML.
|
|
27
|
+
* **Intelligent Renderers:** Out-of-the-box support for Forms, Tables, Cards, Accordions, Stats Grids, Dialogs, and Page Headers.
|
|
28
|
+
* **Built-in State Management:** The Action Dispatcher handles everything from API calls to dialog triggers seamlessly.
|
|
29
|
+
* **Layout Engine:** Native vertical and horizontal shell layouts designed for SaaS applications.
|
|
30
|
+
* **Highly Extensible:** Inject your own custom renderers directly into the core engine.
|
|
31
|
+
|
|
32
|
+
---
|
|
33
|
+
|
|
34
|
+
## 📦 Installation
|
|
35
|
+
|
|
36
|
+
To get the most out of AvoraMetaForge, we highly recommend using our companion CLI, which handles automatic installation, wiring, and scaffolding!
|
|
37
|
+
|
|
38
|
+
### The Easy Way (Using the CLI)
|
|
39
|
+
|
|
40
|
+
```bash
|
|
41
|
+
npm install -g @avora-labs/cli
|
|
42
|
+
avora init
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
### The Manual Way
|
|
46
|
+
|
|
47
|
+
```bash
|
|
48
|
+
npm install @avora-labs/meta-forge
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
Then, inject the providers into your `app.config.ts`:
|
|
52
|
+
|
|
53
|
+
```typescript
|
|
54
|
+
import { ApplicationConfig } from '@angular/core';
|
|
55
|
+
import { provideAvoraMetaForge } from '@avora-labs/meta-forge';
|
|
56
|
+
|
|
57
|
+
export const appConfig: ApplicationConfig = {
|
|
58
|
+
providers: [
|
|
59
|
+
provideAvoraMetaForge()
|
|
60
|
+
]
|
|
61
|
+
};
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
---
|
|
65
|
+
|
|
66
|
+
## 💻 Quick Start: Building a Form
|
|
67
|
+
|
|
68
|
+
Once configured, building a production-ready form with validation takes seconds:
|
|
69
|
+
|
|
70
|
+
```typescript
|
|
71
|
+
import { FormMeta } from '@avora-labs/meta-forge';
|
|
72
|
+
|
|
73
|
+
export const loginForm: FormMeta = {
|
|
74
|
+
id: 'login',
|
|
75
|
+
submitLabel: 'Sign In',
|
|
76
|
+
onSubmit: { type: 'api', config: { action: 'auth.login' } },
|
|
77
|
+
fields: [
|
|
78
|
+
{
|
|
79
|
+
key: 'email',
|
|
80
|
+
type: 'email',
|
|
81
|
+
label: 'Email Address',
|
|
82
|
+
validators: [{ type: 'required' }, { type: 'email' }]
|
|
83
|
+
},
|
|
84
|
+
{
|
|
85
|
+
key: 'password',
|
|
86
|
+
type: 'password',
|
|
87
|
+
label: 'Password',
|
|
88
|
+
validators: [{ type: 'required' }]
|
|
89
|
+
}
|
|
90
|
+
]
|
|
91
|
+
};
|
|
92
|
+
```
|
|
93
|
+
|
|
94
|
+
Pass this config to the form renderer and you're done!
|
|
95
|
+
|
|
96
|
+
---
|
|
97
|
+
|
|
98
|
+
## 🤝 Maintainer & Author
|
|
99
|
+
|
|
100
|
+
AvoraMetaForge is built and maintained by:
|
|
101
|
+
|
|
102
|
+
**Dileesha Ekanayake**
|
|
103
|
+
📧 [dileesha.r.ekanayake@gmail.com](mailto:dileesha.r.ekanayake@gmail.com)
|
|
104
|
+
|
|
105
|
+
Feel free to reach out for support, enterprise inquiries, or just to say hi!
|
|
106
|
+
|
|
107
|
+
---
|
|
108
|
+
|
|
109
|
+
## 📄 License
|
|
110
|
+
|
|
111
|
+
This software is **UNLICENSED** and proprietary.
|
|
112
|
+
While anyone is free to download and use the compiled bundle from NPM for building applications, the source code remains private and may not be copied, modified, or redistributed.
|
|
@@ -30,66 +30,66 @@ class AmfAuthShellComponent {
|
|
|
30
30
|
/** Override the card's max-width (default 560px) */
|
|
31
31
|
maxWidth = '560px';
|
|
32
32
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.14", ngImport: i0, type: AmfAuthShellComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
33
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "21.2.14", type: AmfAuthShellComponent, isStandalone: true, selector: "amf-auth-shell", inputs: { brandName: "brandName", brandTagline: "brandTagline", maxWidth: "maxWidth" }, ngImport: i0, template: `
|
|
34
|
-
<div class="auth-page">
|
|
35
|
-
<!-- Animated Background Orbs -->
|
|
36
|
-
<div class="bg-mesh" aria-hidden="true">
|
|
37
|
-
<div class="orb orb-1"></div>
|
|
38
|
-
<div class="orb orb-2"></div>
|
|
39
|
-
<div class="orb orb-3"></div>
|
|
40
|
-
<div class="orb orb-4"></div>
|
|
41
|
-
</div>
|
|
42
|
-
|
|
43
|
-
<div class="auth-scroll-wrapper">
|
|
44
|
-
<div class="auth-card" [style.max-width]="maxWidth">
|
|
45
|
-
<!-- Brand Header -->
|
|
46
|
-
<div class="brand">
|
|
47
|
-
<div class="brand-logo">
|
|
48
|
-
<svg viewBox="0 0 24 24">
|
|
49
|
-
<path d="M12 2L2 7l10 5 10-5-10-5zM2 17l10 5 10-5M2 12l10 5 10-5"></path>
|
|
50
|
-
</svg>
|
|
51
|
-
</div>
|
|
52
|
-
<h1>{{ brandName || 'AvoraMetaForge' }}</h1>
|
|
53
|
-
<p>{{ brandTagline || 'The universal enterprise shell' }}</p>
|
|
54
|
-
</div>
|
|
55
|
-
|
|
56
|
-
<!-- Projected content slot -->
|
|
57
|
-
<ng-content></ng-content>
|
|
58
|
-
</div>
|
|
59
|
-
</div>
|
|
60
|
-
</div>
|
|
33
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "21.2.14", type: AmfAuthShellComponent, isStandalone: true, selector: "amf-auth-shell", inputs: { brandName: "brandName", brandTagline: "brandTagline", maxWidth: "maxWidth" }, ngImport: i0, template: `
|
|
34
|
+
<div class="auth-page">
|
|
35
|
+
<!-- Animated Background Orbs -->
|
|
36
|
+
<div class="bg-mesh" aria-hidden="true">
|
|
37
|
+
<div class="orb orb-1"></div>
|
|
38
|
+
<div class="orb orb-2"></div>
|
|
39
|
+
<div class="orb orb-3"></div>
|
|
40
|
+
<div class="orb orb-4"></div>
|
|
41
|
+
</div>
|
|
42
|
+
|
|
43
|
+
<div class="auth-scroll-wrapper">
|
|
44
|
+
<div class="auth-card" [style.max-width]="maxWidth">
|
|
45
|
+
<!-- Brand Header -->
|
|
46
|
+
<div class="brand">
|
|
47
|
+
<div class="brand-logo">
|
|
48
|
+
<svg viewBox="0 0 24 24">
|
|
49
|
+
<path d="M12 2L2 7l10 5 10-5-10-5zM2 17l10 5 10-5M2 12l10 5 10-5"></path>
|
|
50
|
+
</svg>
|
|
51
|
+
</div>
|
|
52
|
+
<h1>{{ brandName || 'AvoraMetaForge' }}</h1>
|
|
53
|
+
<p>{{ brandTagline || 'The universal enterprise shell' }}</p>
|
|
54
|
+
</div>
|
|
55
|
+
|
|
56
|
+
<!-- Projected content slot -->
|
|
57
|
+
<ng-content></ng-content>
|
|
58
|
+
</div>
|
|
59
|
+
</div>
|
|
60
|
+
</div>
|
|
61
61
|
`, isInline: true, styles: [":host{display:flex;flex-direction:column;height:100%}.auth-page{height:100%;background:#0a0f1e;position:relative;display:flex;flex-direction:column}.bg-mesh{position:fixed;inset:0;z-index:0;overflow:hidden;pointer-events:none}.orb{position:absolute;border-radius:50%;filter:blur(100px);opacity:.4;will-change:transform}.orb-1{width:clamp(200px,50vw,600px);height:clamp(200px,50vw,600px);background:var(--app-gradient-1, radial-gradient(circle, #6366f1, transparent));top:-20%;right:-10%;animation:blobMove1 18s ease-in-out infinite}.orb-2{width:clamp(160px,40vw,500px);height:clamp(160px,40vw,500px);background:var(--app-gradient-2, radial-gradient(circle, #c084fc, transparent));bottom:-15%;left:-10%;animation:blobMove2 22s ease-in-out infinite}.orb-3{width:clamp(100px,25vw,300px);height:clamp(100px,25vw,300px);background:var(--app-gradient-3, radial-gradient(circle, #38bdf8, transparent));top:50%;left:50%;animation:blobMove3 20s ease-in-out infinite}.orb-4{width:clamp(80px,16vw,200px);height:clamp(80px,16vw,200px);background:var(--app-primary, #6366f1);top:20%;left:20%;opacity:.2;animation:blobMove1 25s ease-in-out infinite reverse}.auth-scroll-wrapper{flex:1;display:flex;align-items:flex-start;justify-content:center;overflow-y:auto;overflow-x:hidden;padding:clamp(32px,5vw,56px) clamp(12px,4vw,24px);padding-top:max(env(safe-area-inset-top,0px),clamp(32px,5vw,56px));padding-bottom:max(env(safe-area-inset-bottom,0px),clamp(32px,5vw,56px));position:relative;z-index:1}.auth-card{background:#ffffff0d;backdrop-filter:blur(40px);-webkit-backdrop-filter:blur(40px);width:100%;max-width:600px;margin:auto;padding:clamp(16px,3vw,24px) clamp(24px,5vw,52px);border-radius:clamp(14px,2.5vw,20px);border:1px solid rgba(255,255,255,.1);box-shadow:0 25px 50px -12px #00000080,0 0 40px #0003,inset 0 1px #ffffff1a;animation:fadeInUp .5s ease-out both}.auth-card:before{content:\"\";position:absolute;inset:-1px;border-radius:inherit;background:linear-gradient(135deg,rgba(255,255,255,.1) 0%,transparent 50%,rgba(255,255,255,.05) 100%);z-index:-1;pointer-events:none}.brand{text-align:center;margin-bottom:clamp(10px,2vw,18px)}.brand-logo{width:clamp(40px,8vw,52px);height:clamp(40px,8vw,52px);background:linear-gradient(135deg,var(--app-primary, #6366f1),var(--app-accent, #c084fc));color:#fff;border-radius:14px;display:flex;align-items:center;justify-content:center;margin:0 auto clamp(8px,1.5vw,12px);box-shadow:0 0 24px var(--app-glow, rgba(99,102,241,.4));animation:float 4s ease-in-out infinite}.brand-logo svg{width:clamp(20px,4vw,26px);height:clamp(20px,4vw,26px);fill:none;stroke:currentColor;stroke-width:2;stroke-linecap:round;stroke-linejoin:round}.brand h1{font-size:clamp(1.2rem,3vw,1.65rem);font-weight:800;margin-bottom:3px;color:#f1f5f9;letter-spacing:-.02em}.brand p{color:#94a3b8;font-size:clamp(.75rem,1.8vw,.82rem)}@media(max-width:359px){.auth-card{border-radius:12px;backdrop-filter:none;-webkit-backdrop-filter:none;background:#0f1428f7}}@keyframes fadeInUp{0%{opacity:0;transform:translateY(24px)}to{opacity:1;transform:translateY(0)}}@keyframes float{0%,to{transform:translateY(0)}50%{transform:translateY(-6px)}}@keyframes blobMove1{0%,to{transform:translate(0) scale(1)}33%{transform:translate(30px,-40px) scale(1.05)}66%{transform:translate(-20px,20px) scale(.95)}}@keyframes blobMove2{0%,to{transform:translate(0) scale(1)}33%{transform:translate(-30px,30px) scale(1.05)}66%{transform:translate(20px,-20px) scale(.95)}}@keyframes blobMove3{0%,to{transform:translate(-50%,-50%) scale(1)}50%{transform:translate(-50%,-50%) scale(1.2)}}@media(prefers-reduced-motion:reduce){.orb,.brand-logo,.auth-card{animation:none!important}}\n"] });
|
|
62
62
|
}
|
|
63
63
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.14", ngImport: i0, type: AmfAuthShellComponent, decorators: [{
|
|
64
64
|
type: Component,
|
|
65
|
-
args: [{ selector: 'amf-auth-shell', standalone: true, imports: [], template: `
|
|
66
|
-
<div class="auth-page">
|
|
67
|
-
<!-- Animated Background Orbs -->
|
|
68
|
-
<div class="bg-mesh" aria-hidden="true">
|
|
69
|
-
<div class="orb orb-1"></div>
|
|
70
|
-
<div class="orb orb-2"></div>
|
|
71
|
-
<div class="orb orb-3"></div>
|
|
72
|
-
<div class="orb orb-4"></div>
|
|
73
|
-
</div>
|
|
74
|
-
|
|
75
|
-
<div class="auth-scroll-wrapper">
|
|
76
|
-
<div class="auth-card" [style.max-width]="maxWidth">
|
|
77
|
-
<!-- Brand Header -->
|
|
78
|
-
<div class="brand">
|
|
79
|
-
<div class="brand-logo">
|
|
80
|
-
<svg viewBox="0 0 24 24">
|
|
81
|
-
<path d="M12 2L2 7l10 5 10-5-10-5zM2 17l10 5 10-5M2 12l10 5 10-5"></path>
|
|
82
|
-
</svg>
|
|
83
|
-
</div>
|
|
84
|
-
<h1>{{ brandName || 'AvoraMetaForge' }}</h1>
|
|
85
|
-
<p>{{ brandTagline || 'The universal enterprise shell' }}</p>
|
|
86
|
-
</div>
|
|
87
|
-
|
|
88
|
-
<!-- Projected content slot -->
|
|
89
|
-
<ng-content></ng-content>
|
|
90
|
-
</div>
|
|
91
|
-
</div>
|
|
92
|
-
</div>
|
|
65
|
+
args: [{ selector: 'amf-auth-shell', standalone: true, imports: [], template: `
|
|
66
|
+
<div class="auth-page">
|
|
67
|
+
<!-- Animated Background Orbs -->
|
|
68
|
+
<div class="bg-mesh" aria-hidden="true">
|
|
69
|
+
<div class="orb orb-1"></div>
|
|
70
|
+
<div class="orb orb-2"></div>
|
|
71
|
+
<div class="orb orb-3"></div>
|
|
72
|
+
<div class="orb orb-4"></div>
|
|
73
|
+
</div>
|
|
74
|
+
|
|
75
|
+
<div class="auth-scroll-wrapper">
|
|
76
|
+
<div class="auth-card" [style.max-width]="maxWidth">
|
|
77
|
+
<!-- Brand Header -->
|
|
78
|
+
<div class="brand">
|
|
79
|
+
<div class="brand-logo">
|
|
80
|
+
<svg viewBox="0 0 24 24">
|
|
81
|
+
<path d="M12 2L2 7l10 5 10-5-10-5zM2 17l10 5 10-5M2 12l10 5 10-5"></path>
|
|
82
|
+
</svg>
|
|
83
|
+
</div>
|
|
84
|
+
<h1>{{ brandName || 'AvoraMetaForge' }}</h1>
|
|
85
|
+
<p>{{ brandTagline || 'The universal enterprise shell' }}</p>
|
|
86
|
+
</div>
|
|
87
|
+
|
|
88
|
+
<!-- Projected content slot -->
|
|
89
|
+
<ng-content></ng-content>
|
|
90
|
+
</div>
|
|
91
|
+
</div>
|
|
92
|
+
</div>
|
|
93
93
|
`, styles: [":host{display:flex;flex-direction:column;height:100%}.auth-page{height:100%;background:#0a0f1e;position:relative;display:flex;flex-direction:column}.bg-mesh{position:fixed;inset:0;z-index:0;overflow:hidden;pointer-events:none}.orb{position:absolute;border-radius:50%;filter:blur(100px);opacity:.4;will-change:transform}.orb-1{width:clamp(200px,50vw,600px);height:clamp(200px,50vw,600px);background:var(--app-gradient-1, radial-gradient(circle, #6366f1, transparent));top:-20%;right:-10%;animation:blobMove1 18s ease-in-out infinite}.orb-2{width:clamp(160px,40vw,500px);height:clamp(160px,40vw,500px);background:var(--app-gradient-2, radial-gradient(circle, #c084fc, transparent));bottom:-15%;left:-10%;animation:blobMove2 22s ease-in-out infinite}.orb-3{width:clamp(100px,25vw,300px);height:clamp(100px,25vw,300px);background:var(--app-gradient-3, radial-gradient(circle, #38bdf8, transparent));top:50%;left:50%;animation:blobMove3 20s ease-in-out infinite}.orb-4{width:clamp(80px,16vw,200px);height:clamp(80px,16vw,200px);background:var(--app-primary, #6366f1);top:20%;left:20%;opacity:.2;animation:blobMove1 25s ease-in-out infinite reverse}.auth-scroll-wrapper{flex:1;display:flex;align-items:flex-start;justify-content:center;overflow-y:auto;overflow-x:hidden;padding:clamp(32px,5vw,56px) clamp(12px,4vw,24px);padding-top:max(env(safe-area-inset-top,0px),clamp(32px,5vw,56px));padding-bottom:max(env(safe-area-inset-bottom,0px),clamp(32px,5vw,56px));position:relative;z-index:1}.auth-card{background:#ffffff0d;backdrop-filter:blur(40px);-webkit-backdrop-filter:blur(40px);width:100%;max-width:600px;margin:auto;padding:clamp(16px,3vw,24px) clamp(24px,5vw,52px);border-radius:clamp(14px,2.5vw,20px);border:1px solid rgba(255,255,255,.1);box-shadow:0 25px 50px -12px #00000080,0 0 40px #0003,inset 0 1px #ffffff1a;animation:fadeInUp .5s ease-out both}.auth-card:before{content:\"\";position:absolute;inset:-1px;border-radius:inherit;background:linear-gradient(135deg,rgba(255,255,255,.1) 0%,transparent 50%,rgba(255,255,255,.05) 100%);z-index:-1;pointer-events:none}.brand{text-align:center;margin-bottom:clamp(10px,2vw,18px)}.brand-logo{width:clamp(40px,8vw,52px);height:clamp(40px,8vw,52px);background:linear-gradient(135deg,var(--app-primary, #6366f1),var(--app-accent, #c084fc));color:#fff;border-radius:14px;display:flex;align-items:center;justify-content:center;margin:0 auto clamp(8px,1.5vw,12px);box-shadow:0 0 24px var(--app-glow, rgba(99,102,241,.4));animation:float 4s ease-in-out infinite}.brand-logo svg{width:clamp(20px,4vw,26px);height:clamp(20px,4vw,26px);fill:none;stroke:currentColor;stroke-width:2;stroke-linecap:round;stroke-linejoin:round}.brand h1{font-size:clamp(1.2rem,3vw,1.65rem);font-weight:800;margin-bottom:3px;color:#f1f5f9;letter-spacing:-.02em}.brand p{color:#94a3b8;font-size:clamp(.75rem,1.8vw,.82rem)}@media(max-width:359px){.auth-card{border-radius:12px;backdrop-filter:none;-webkit-backdrop-filter:none;background:#0f1428f7}}@keyframes fadeInUp{0%{opacity:0;transform:translateY(24px)}to{opacity:1;transform:translateY(0)}}@keyframes float{0%,to{transform:translateY(0)}50%{transform:translateY(-6px)}}@keyframes blobMove1{0%,to{transform:translate(0) scale(1)}33%{transform:translate(30px,-40px) scale(1.05)}66%{transform:translate(-20px,20px) scale(.95)}}@keyframes blobMove2{0%,to{transform:translate(0) scale(1)}33%{transform:translate(-30px,30px) scale(1.05)}66%{transform:translate(20px,-20px) scale(.95)}}@keyframes blobMove3{0%,to{transform:translate(-50%,-50%) scale(1)}50%{transform:translate(-50%,-50%) scale(1.2)}}@media(prefers-reduced-motion:reduce){.orb,.brand-logo,.auth-card{animation:none!important}}\n"] }]
|
|
94
94
|
}], propDecorators: { brandName: [{
|
|
95
95
|
type: Input
|
|
@@ -100,4 +100,4 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.14", ngImpo
|
|
|
100
100
|
}] } });
|
|
101
101
|
|
|
102
102
|
export { AmfAuthShellComponent as A };
|
|
103
|
-
//# sourceMappingURL=avora-labs-meta-forge-amf-auth-shell.component-
|
|
103
|
+
//# sourceMappingURL=avora-labs-meta-forge-amf-auth-shell.component-FCubZyZ1.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"avora-labs-meta-forge-amf-auth-shell.component-FCubZyZ1.mjs","sources":["../../../projects/avora-meta-forge/src/lib/avora-meta-forge/renderers/auth/amf-auth-shell.component.ts"],"sourcesContent":["/**\n * AvoraMetaForge — Auth Shell Component\n *\n * A reusable full-page auth card renderer providing the glassmorphism\n * background and card layout shared by Login, Forgot Password, Contact\n * Support, and any other auth screen built with AvoraMetaForge.\n *\n * ## Responsiveness\n * This shell is fully mobile-first. On small screens (< 480 px) the card\n * fills the viewport and scrolls naturally; on larger screens it is a\n * centered floating card capped at `maxWidth`.\n *\n * ## Usage\n * <amf-auth-shell [brandName]=\"'MyApp'\" [brandTagline]=\"'Enterprise platform'\">\n * <!-- your form, steps, or custom HTML here -->\n * </amf-auth-shell>\n *\n * ## Icon system\n * Use <span class=\"ms\">lock</span> (Material Symbols Rounded) anywhere inside\n * the shell. The .ms class is globally defined in index.html.\n */\nimport { Component, Input } from '@angular/core';\n\n\n@Component({\n selector: 'amf-auth-shell',\n standalone: true,\n imports: [],\n template: `\n <div class=\"auth-page\">\n <!-- Animated Background Orbs -->\n <div class=\"bg-mesh\" aria-hidden=\"true\">\n <div class=\"orb orb-1\"></div>\n <div class=\"orb orb-2\"></div>\n <div class=\"orb orb-3\"></div>\n <div class=\"orb orb-4\"></div>\n </div>\n\n <div class=\"auth-scroll-wrapper\">\n <div class=\"auth-card\" [style.max-width]=\"maxWidth\">\n <!-- Brand Header -->\n <div class=\"brand\">\n <div class=\"brand-logo\">\n <svg viewBox=\"0 0 24 24\">\n <path d=\"M12 2L2 7l10 5 10-5-10-5zM2 17l10 5 10-5M2 12l10 5 10-5\"></path>\n </svg>\n </div>\n <h1>{{ brandName || 'AvoraMetaForge' }}</h1>\n <p>{{ brandTagline || 'The universal enterprise shell' }}</p>\n </div>\n\n <!-- Projected content slot -->\n <ng-content></ng-content>\n </div>\n </div>\n </div>\n `,\n styles: [`\n /* ─── Host fills the full slot given by router-outlet ─── */\n :host {\n display: flex;\n flex-direction: column;\n height: 100%;\n }\n\n /* ─────────────────────────────────────────\n PAGE ROOT — fills parent, no overflow clip\n so the inner scroll wrapper can breathe\n ───────────────────────────────────────── */\n .auth-page {\n height: 100%;\n background: #0a0f1e;\n position: relative;\n display: flex;\n flex-direction: column;\n }\n\n /* ── Animated Background ── */\n .bg-mesh {\n position: fixed;\n inset: 0;\n z-index: 0;\n overflow: hidden;\n pointer-events: none;\n }\n .orb {\n position: absolute;\n border-radius: 50%;\n filter: blur(100px);\n opacity: 0.4;\n will-change: transform;\n }\n .orb-1 {\n width: clamp(200px, 50vw, 600px);\n height: clamp(200px, 50vw, 600px);\n background: var(--app-gradient-1, radial-gradient(circle, #6366f1, transparent));\n top: -20%; right: -10%;\n animation: blobMove1 18s ease-in-out infinite;\n }\n .orb-2 {\n width: clamp(160px, 40vw, 500px);\n height: clamp(160px, 40vw, 500px);\n background: var(--app-gradient-2, radial-gradient(circle, #c084fc, transparent));\n bottom: -15%; left: -10%;\n animation: blobMove2 22s ease-in-out infinite;\n }\n .orb-3 {\n width: clamp(100px, 25vw, 300px);\n height: clamp(100px, 25vw, 300px);\n background: var(--app-gradient-3, radial-gradient(circle, #38bdf8, transparent));\n top: 50%; left: 50%;\n animation: blobMove3 20s ease-in-out infinite;\n }\n .orb-4 {\n width: clamp(80px, 16vw, 200px);\n height: clamp(80px, 16vw, 200px);\n background: var(--app-primary, #6366f1);\n top: 20%; left: 20%;\n opacity: 0.2;\n animation: blobMove1 25s ease-in-out infinite reverse;\n }\n\n /* ─────────────────────────────────────────\n SCROLL WRAPPER\n On mobile the card can exceed the screen\n height — this wrapper makes it scrollable.\n ───────────────────────────────────────── */\n .auth-scroll-wrapper {\n flex: 1;\n display: flex;\n align-items: flex-start; /* always flex-start; card uses margin:auto to self-center */\n justify-content: center;\n overflow-y: auto;\n overflow-x: hidden;\n padding: clamp(32px, 5vw, 56px) clamp(12px, 4vw, 24px);\n padding-top: max(env(safe-area-inset-top, 0px), clamp(32px, 5vw, 56px));\n padding-bottom: max(env(safe-area-inset-bottom, 0px), clamp(32px, 5vw, 56px));\n position: relative;\n z-index: 1;\n }\n\n /* ── Auth Card ── */\n .auth-card {\n background: rgba(255, 255, 255, 0.05);\n backdrop-filter: blur(40px);\n -webkit-backdrop-filter: blur(40px);\n width: 100%;\n max-width: 600px;\n /* margin:auto centers the card when there is spare space in the scroll wrapper,\n but unlike align-items:center it does NOT clip the top when the card overflows —\n the wrapper's padding-top stays visible as the user scrolls up. */\n margin: auto;\n /* Vertical padding kept tight to reduce card height; horizontal generous for width */\n padding: clamp(16px, 3vw, 24px) clamp(24px, 5vw, 52px);\n border-radius: clamp(14px, 2.5vw, 20px);\n border: 1px solid rgba(255, 255, 255, 0.1);\n box-shadow:\n 0 25px 50px -12px rgba(0, 0, 0, 0.5),\n 0 0 40px rgba(0, 0, 0, 0.2),\n inset 0 1px 0 rgba(255, 255, 255, 0.1);\n animation: fadeInUp 0.5s ease-out both;\n }\n .auth-card::before {\n content: '';\n position: absolute;\n top: -1px; left: -1px; right: -1px; bottom: -1px;\n border-radius: inherit;\n background: linear-gradient(135deg, rgba(255,255,255,0.1) 0%, transparent 50%, rgba(255,255,255,0.05) 100%);\n z-index: -1;\n pointer-events: none;\n }\n\n /* ── Brand — compact horizontal layout on wide screens ── */\n .brand {\n text-align: center;\n margin-bottom: clamp(10px, 2vw, 18px);\n }\n .brand-logo {\n width: clamp(40px, 8vw, 52px);\n height: clamp(40px, 8vw, 52px);\n background: linear-gradient(135deg, var(--app-primary, #6366f1), var(--app-accent, #c084fc));\n color: white;\n border-radius: 14px;\n display: flex;\n align-items: center;\n justify-content: center;\n margin: 0 auto clamp(8px, 1.5vw, 12px);\n box-shadow: 0 0 24px var(--app-glow, rgba(99,102,241,0.4));\n animation: float 4s ease-in-out infinite;\n }\n .brand-logo svg {\n width: clamp(20px, 4vw, 26px);\n height: clamp(20px, 4vw, 26px);\n fill: none;\n stroke: currentColor;\n stroke-width: 2;\n stroke-linecap: round;\n stroke-linejoin: round;\n }\n .brand h1 {\n font-size: clamp(1.2rem, 3vw, 1.65rem);\n font-weight: 800;\n margin-bottom: 3px;\n color: #f1f5f9;\n letter-spacing: -0.02em;\n }\n .brand p {\n color: #94a3b8;\n font-size: clamp(0.75rem, 1.8vw, 0.82rem);\n }\n\n /* ─────────────────────────────────────────\n EXTRA-SMALL SCREENS (< 360 px)\n Reduce border-radius and disable blur for\n performance on very low-end devices.\n ───────────────────────────────────────── */\n @media (max-width: 359px) {\n .auth-card {\n border-radius: 12px;\n backdrop-filter: none;\n -webkit-backdrop-filter: none;\n background: rgba(15, 20, 40, 0.97);\n }\n }\n\n /* ─────────────────────────────────────────\n ANIMATIONS\n ───────────────────────────────────────── */\n @keyframes fadeInUp {\n from { opacity: 0; transform: translateY(24px); }\n to { opacity: 1; transform: translateY(0); }\n }\n @keyframes float {\n 0%, 100% { transform: translateY(0px); }\n 50% { transform: translateY(-6px); }\n }\n @keyframes blobMove1 {\n 0%, 100% { transform: translate(0, 0) scale(1); }\n 33% { transform: translate(30px, -40px) scale(1.05); }\n 66% { transform: translate(-20px, 20px) scale(0.95); }\n }\n @keyframes blobMove2 {\n 0%, 100% { transform: translate(0, 0) scale(1); }\n 33% { transform: translate(-30px, 30px) scale(1.05); }\n 66% { transform: translate(20px, -20px) scale(0.95); }\n }\n @keyframes blobMove3 {\n 0%, 100% { transform: translate(-50%, -50%) scale(1); }\n 50% { transform: translate(-50%, -50%) scale(1.2); }\n }\n\n /* ── Reduce motion for accessibility ── */\n @media (prefers-reduced-motion: reduce) {\n .orb, .brand-logo, .auth-card {\n animation: none !important;\n }\n }\n `]\n})\nexport class AmfAuthShellComponent {\n /** App brand name shown in the card header */\n @Input() brandName?: string;\n /** Tagline shown below the brand name */\n @Input() brandTagline?: string;\n /** Override the card's max-width (default 560px) */\n @Input() maxWidth?: string = '560px';\n}\n"],"names":[],"mappings":";;;AAAA;;;;;;;;;;;;;;;;;;;;AAoBG;MA+OU,qBAAqB,CAAA;;AAEvB,IAAA,SAAS;;AAET,IAAA,YAAY;;IAEZ,QAAQ,GAAY,OAAO;wGANzB,qBAAqB,EAAA,IAAA,EAAA,EAAA,EAAA,MAAA,EAAA,EAAA,CAAA,eAAA,CAAA,SAAA,EAAA,CAAA;AAArB,IAAA,OAAA,IAAA,GAAA,EAAA,CAAA,oBAAA,CAAA,EAAA,UAAA,EAAA,QAAA,EAAA,OAAA,EAAA,SAAA,EAAA,IAAA,EAAA,qBAAqB,EAAA,YAAA,EAAA,IAAA,EAAA,QAAA,EAAA,gBAAA,EAAA,MAAA,EAAA,EAAA,SAAA,EAAA,WAAA,EAAA,YAAA,EAAA,cAAA,EAAA,QAAA,EAAA,UAAA,EAAA,EAAA,QAAA,EAAA,EAAA,EAAA,QAAA,EAvOtB;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA4BT,EAAA,CAAA,EAAA,QAAA,EAAA,IAAA,EAAA,MAAA,EAAA,CAAA,6kHAAA,CAAA,EAAA,CAAA;;4FA2MU,qBAAqB,EAAA,UAAA,EAAA,CAAA;kBA3OjC,SAAS;AACE,YAAA,IAAA,EAAA,CAAA,EAAA,QAAA,EAAA,gBAAgB,EAAA,UAAA,EACd,IAAI,EAAA,OAAA,EACP,EAAE,EAAA,QAAA,EACD;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA4BT,EAAA,CAAA,EAAA,MAAA,EAAA,CAAA,6kHAAA,CAAA,EAAA;;sBA6MA;;sBAEA;;sBAEA;;;;;"}
|