gea-lib 1.0.0
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 +100 -0
- package/bin/index.js +214 -0
- package/package.json +38 -0
- package/templates/js/README.md +39 -0
- package/templates/js/_gitignore +42 -0
- package/templates/js/package.json +32 -0
- package/templates/js/playground/app.jsx +80 -0
- package/templates/js/playground/index.html +15 -0
- package/templates/js/playground/main.js +5 -0
- package/templates/js/playground/style.css +49 -0
- package/templates/js/src/components/Button.css +74 -0
- package/templates/js/src/components/Button.jsx +20 -0
- package/templates/js/src/components/Card.css +44 -0
- package/templates/js/src/components/Card.jsx +27 -0
- package/templates/js/src/index.js +3 -0
- package/templates/js/src/stores/counter.js +21 -0
- package/templates/js/vite.config.js +23 -0
- package/templates/ts/README.md +40 -0
- package/templates/ts/_gitignore +42 -0
- package/templates/ts/package.json +35 -0
- package/templates/ts/playground/app.tsx +80 -0
- package/templates/ts/playground/index.html +15 -0
- package/templates/ts/playground/main.ts +5 -0
- package/templates/ts/playground/style.css +49 -0
- package/templates/ts/src/components/Button.css +74 -0
- package/templates/ts/src/components/Button.tsx +26 -0
- package/templates/ts/src/components/Card.css +44 -0
- package/templates/ts/src/components/Card.tsx +32 -0
- package/templates/ts/src/index.ts +3 -0
- package/templates/ts/src/stores/counter.ts +21 -0
- package/templates/ts/tsconfig.build.json +10 -0
- package/templates/ts/tsconfig.json +21 -0
- package/templates/ts/vite.config.ts +23 -0
package/README.md
ADDED
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
# GeaJS Library Scaffolder (`gea-lib`)
|
|
2
|
+
|
|
3
|
+
⚡ A fast, flexible, and interactive scaffolding tool to easily bootstrap modern, reactive libraries for GeaJS. With this tool, you can set up a new GeaJS library in seconds with TypeScript or JavaScript, complete with automatic git initialization and dependency installation.
|
|
4
|
+
|
|
5
|
+
## Features
|
|
6
|
+
|
|
7
|
+
- 📦 **Pre-configured Templates:** Ready-to-go templates for both JavaScript (`js`) and TypeScript (`ts`).
|
|
8
|
+
- ⚙️ **Interactive CLI:** Step-by-step prompts to select your project name, language, and initial setup preferences.
|
|
9
|
+
- 🚀 **Silent Mode (Non-Interactive):** Fast creation using CLI flags to skip prompts.
|
|
10
|
+
- 🛠️ **Auto-configuration:** Automatic Git initialization and dependency installation using your active package manager (`npm`, `yarn`, `pnpm`, `bun`).
|
|
11
|
+
|
|
12
|
+
---
|
|
13
|
+
|
|
14
|
+
## Usage
|
|
15
|
+
|
|
16
|
+
You can run this tool remotely using `npx` (recommended), or run it locally during development.
|
|
17
|
+
|
|
18
|
+
### 1. Remote Execution (Recommended)
|
|
19
|
+
|
|
20
|
+
Since the package is published on npm, you can generate a new GeaJS library anywhere without installing it globally:
|
|
21
|
+
|
|
22
|
+
```bash
|
|
23
|
+
# Using npx (runs interactively by default)
|
|
24
|
+
npx gea-lib
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
---
|
|
28
|
+
|
|
29
|
+
### 2. Command Line Options
|
|
30
|
+
|
|
31
|
+
You can skip or pre-configure choices by passing arguments to the command:
|
|
32
|
+
|
|
33
|
+
```bash
|
|
34
|
+
npx gea-lib <project-name> [options]
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
#### Available Options:
|
|
38
|
+
|
|
39
|
+
| Option | Description |
|
|
40
|
+
| :--- | :--- |
|
|
41
|
+
| `<project-name>` | The name of the project/directory to create (e.g., `my-awesome-lib`). |
|
|
42
|
+
| `--ts` / `--typescript` | Use the TypeScript template. |
|
|
43
|
+
| `--js` / `--javascript` | Use the JavaScript template. |
|
|
44
|
+
| `--git` | Automatically initialize a git repository. |
|
|
45
|
+
| `--no-git` | Skip initializing a git repository. |
|
|
46
|
+
| `--install` | Automatically install dependencies. |
|
|
47
|
+
| `--no-install` | Skip installing dependencies. |
|
|
48
|
+
| `-y` / `--yes` | Use default choices for all prompts (creates `gea-library` in TypeScript with git and install). |
|
|
49
|
+
|
|
50
|
+
#### Examples:
|
|
51
|
+
|
|
52
|
+
**Create a TypeScript project with git and installed dependencies silently:**
|
|
53
|
+
```bash
|
|
54
|
+
npx gea-lib my-ts-lib -y
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
**Create a JavaScript project and skip dependency installation:**
|
|
58
|
+
```bash
|
|
59
|
+
npx gea-lib my-js-lib --js --no-install
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
---
|
|
63
|
+
|
|
64
|
+
### 3. Local Development & Installation
|
|
65
|
+
|
|
66
|
+
If you are developing this scaffolder tool locally, you can use these methods:
|
|
67
|
+
|
|
68
|
+
#### Run locally:
|
|
69
|
+
```bash
|
|
70
|
+
# In the scaffolder root directory
|
|
71
|
+
node ./bin/index.js
|
|
72
|
+
# Or:
|
|
73
|
+
npm start
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
#### Link locally for testing:
|
|
77
|
+
```bash
|
|
78
|
+
# Create a global symlink of the package
|
|
79
|
+
npm link
|
|
80
|
+
|
|
81
|
+
# Run it from anywhere on your machine:
|
|
82
|
+
gea-lib my-library
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
---
|
|
86
|
+
|
|
87
|
+
## Developing Your New Library
|
|
88
|
+
|
|
89
|
+
Once your project is created, navigate into the directory and run these commands to start developing:
|
|
90
|
+
|
|
91
|
+
```bash
|
|
92
|
+
# Go to the project directory
|
|
93
|
+
cd <project-name>
|
|
94
|
+
|
|
95
|
+
# Start the interactive sandbox demo environment
|
|
96
|
+
npm run dev
|
|
97
|
+
|
|
98
|
+
# Build the library for NPM distribution
|
|
99
|
+
npm run build
|
|
100
|
+
```
|
package/bin/index.js
ADDED
|
@@ -0,0 +1,214 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
import { promises as fs } from 'fs';
|
|
4
|
+
import path from 'path';
|
|
5
|
+
import { fileURLToPath } from 'url';
|
|
6
|
+
import { spawn } from 'child_process';
|
|
7
|
+
import prompts from 'prompts';
|
|
8
|
+
import pc from 'picocolors';
|
|
9
|
+
|
|
10
|
+
const __dirname = path.dirname(fileURLToPath(import.meta.url));
|
|
11
|
+
|
|
12
|
+
// Helper: Run a command in a child process
|
|
13
|
+
function runCommand(command, args, options = {}) {
|
|
14
|
+
return new Promise((resolve, reject) => {
|
|
15
|
+
const process = spawn(command, args, { stdio: 'inherit', shell: true, ...options });
|
|
16
|
+
process.on('close', (code) => {
|
|
17
|
+
if (code === 0) {
|
|
18
|
+
resolve();
|
|
19
|
+
} else {
|
|
20
|
+
reject(new Error(`Command failed with exit code ${code}`));
|
|
21
|
+
}
|
|
22
|
+
});
|
|
23
|
+
process.on('error', (err) => {
|
|
24
|
+
reject(err);
|
|
25
|
+
});
|
|
26
|
+
});
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
// Helper: Convert project-name to CamelCase library name
|
|
30
|
+
function toCamelCase(str) {
|
|
31
|
+
return str
|
|
32
|
+
.replace(/[^a-zA-Z0-9]+(.)/g, (m, chr) => chr.toUpperCase())
|
|
33
|
+
.replace(/[^a-zA-Z0-9]/g, '');
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
// Helper: Recursively copy directory and replace placeholders
|
|
37
|
+
async function copyDir(src, dest, replacements) {
|
|
38
|
+
const stat = await fs.lstat(src);
|
|
39
|
+
if (stat.isDirectory()) {
|
|
40
|
+
await fs.mkdir(dest, { recursive: true });
|
|
41
|
+
const entries = await fs.readdir(src);
|
|
42
|
+
for (const entry of entries) {
|
|
43
|
+
const srcPath = path.join(src, entry);
|
|
44
|
+
let destEntryName = entry;
|
|
45
|
+
// Rename _gitignore to .gitignore
|
|
46
|
+
if (entry === '_gitignore') {
|
|
47
|
+
destEntryName = '.gitignore';
|
|
48
|
+
}
|
|
49
|
+
const destPath = path.join(dest, destEntryName);
|
|
50
|
+
await copyDir(srcPath, destPath, replacements);
|
|
51
|
+
}
|
|
52
|
+
} else {
|
|
53
|
+
// Read file, replace templates, write to dest
|
|
54
|
+
let content = await fs.readFile(src, 'utf8');
|
|
55
|
+
for (const [key, value] of Object.entries(replacements)) {
|
|
56
|
+
const regex = new RegExp(`<%\\s*${key}\\s*%>`, 'g');
|
|
57
|
+
content = content.replace(regex, value);
|
|
58
|
+
}
|
|
59
|
+
await fs.writeFile(dest, content, 'utf8');
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
// Helper: Detect the active package manager
|
|
64
|
+
function detectPackageManager() {
|
|
65
|
+
const userAgent = process.env.npm_config_user_agent || '';
|
|
66
|
+
if (userAgent.includes('yarn')) return 'yarn';
|
|
67
|
+
if (userAgent.includes('pnpm')) return 'pnpm';
|
|
68
|
+
if (userAgent.includes('bun')) return 'bun';
|
|
69
|
+
return 'npm';
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
async function main() {
|
|
73
|
+
console.log('\n' + pc.cyan(pc.bold('⚡ GeaJS Library Scaffolder ⚡')) + '\n');
|
|
74
|
+
|
|
75
|
+
const args = process.argv.slice(2);
|
|
76
|
+
const cliOptions = {
|
|
77
|
+
projectName: args.find(a => !a.startsWith('-')),
|
|
78
|
+
language: args.includes('--ts') || args.includes('--typescript') ? 'ts' : (args.includes('--js') || args.includes('--javascript') ? 'js' : null),
|
|
79
|
+
gitInit: args.includes('--no-git') ? false : (args.includes('--git') ? true : null),
|
|
80
|
+
installDeps: args.includes('--no-install') ? false : (args.includes('--install') ? true : null),
|
|
81
|
+
yes: args.includes('-y') || args.includes('--yes')
|
|
82
|
+
};
|
|
83
|
+
|
|
84
|
+
let projectName = cliOptions.projectName;
|
|
85
|
+
let language = cliOptions.language;
|
|
86
|
+
let gitInit = cliOptions.gitInit;
|
|
87
|
+
let installDeps = cliOptions.installDeps;
|
|
88
|
+
|
|
89
|
+
if (cliOptions.yes) {
|
|
90
|
+
if (!projectName) projectName = 'gea-library';
|
|
91
|
+
if (!language) language = 'ts';
|
|
92
|
+
if (gitInit === null) gitInit = true;
|
|
93
|
+
if (installDeps === null) installDeps = true;
|
|
94
|
+
} else {
|
|
95
|
+
const questions = [];
|
|
96
|
+
|
|
97
|
+
if (!projectName) {
|
|
98
|
+
questions.push({
|
|
99
|
+
type: 'text',
|
|
100
|
+
name: 'projectName',
|
|
101
|
+
message: 'Project name:',
|
|
102
|
+
initial: 'gea-library',
|
|
103
|
+
validate: (value) => (value.trim().length > 0 ? true : 'Please enter a project name')
|
|
104
|
+
});
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
if (!language) {
|
|
108
|
+
questions.push({
|
|
109
|
+
type: 'select',
|
|
110
|
+
name: 'language',
|
|
111
|
+
message: 'Select programming language:',
|
|
112
|
+
choices: [
|
|
113
|
+
{ title: pc.blue('TypeScript'), value: 'ts' },
|
|
114
|
+
{ title: pc.yellow('JavaScript'), value: 'js' }
|
|
115
|
+
],
|
|
116
|
+
initial: 0
|
|
117
|
+
});
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
if (gitInit === null) {
|
|
121
|
+
questions.push({
|
|
122
|
+
type: 'confirm',
|
|
123
|
+
name: 'gitInit',
|
|
124
|
+
message: 'Initialize a git repository?',
|
|
125
|
+
initial: true
|
|
126
|
+
});
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
if (installDeps === null) {
|
|
130
|
+
questions.push({
|
|
131
|
+
type: 'confirm',
|
|
132
|
+
name: 'installDeps',
|
|
133
|
+
message: 'Install dependencies automatically?',
|
|
134
|
+
initial: true
|
|
135
|
+
});
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
if (questions.length > 0) {
|
|
139
|
+
const response = await prompts(questions, {
|
|
140
|
+
onCancel: () => {
|
|
141
|
+
console.log(pc.red('\n✖ Scaffolding cancelled.'));
|
|
142
|
+
process.exit(1);
|
|
143
|
+
}
|
|
144
|
+
});
|
|
145
|
+
|
|
146
|
+
if (!projectName) projectName = response.projectName;
|
|
147
|
+
if (!language) language = response.language;
|
|
148
|
+
if (gitInit === null) gitInit = response.gitInit;
|
|
149
|
+
if (installDeps === null) installDeps = response.installDeps;
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
const projectDir = path.resolve(process.cwd(), projectName);
|
|
154
|
+
const pkgName = path.basename(projectName).toLowerCase().replace(/[^a-z0-9-_]/g, '');
|
|
155
|
+
const libraryName = toCamelCase(pkgName);
|
|
156
|
+
|
|
157
|
+
console.log(`\nCreating GeaJS library in ${pc.green(projectDir)}...\n`);
|
|
158
|
+
|
|
159
|
+
// Source template path
|
|
160
|
+
const templatePath = path.resolve(__dirname, '../templates', language);
|
|
161
|
+
|
|
162
|
+
try {
|
|
163
|
+
// Copy template files
|
|
164
|
+
await copyDir(templatePath, projectDir, {
|
|
165
|
+
projectName: pkgName,
|
|
166
|
+
libraryName: libraryName
|
|
167
|
+
});
|
|
168
|
+
|
|
169
|
+
// Git initialization
|
|
170
|
+
if (gitInit) {
|
|
171
|
+
console.log(pc.dim('Initializing git repository...'));
|
|
172
|
+
try {
|
|
173
|
+
await runCommand('git', ['init'], { cwd: projectDir });
|
|
174
|
+
} catch (err) {
|
|
175
|
+
console.warn(pc.yellow('⚠ Could not initialize git repository: ' + err.message));
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
|
|
179
|
+
// Dependency installation
|
|
180
|
+
const pkgManager = detectPackageManager();
|
|
181
|
+
if (installDeps) {
|
|
182
|
+
console.log(pc.dim(`Installing dependencies using ${pkgManager}...`));
|
|
183
|
+
try {
|
|
184
|
+
const installArgs = pkgManager === 'yarn' ? [] : ['install'];
|
|
185
|
+
await runCommand(pkgManager, installArgs, { cwd: projectDir });
|
|
186
|
+
console.log(pc.green('\n✔ Dependencies installed successfully!'));
|
|
187
|
+
} catch (err) {
|
|
188
|
+
console.error(pc.red(`\n✖ Failed to install dependencies: ${err.message}`));
|
|
189
|
+
}
|
|
190
|
+
}
|
|
191
|
+
|
|
192
|
+
// Success Screen
|
|
193
|
+
console.log('\n' + pc.green(pc.bold('🎉 Project created successfully!')) + '\n');
|
|
194
|
+
console.log('To get started:');
|
|
195
|
+
|
|
196
|
+
if (path.resolve(process.cwd()) !== projectDir) {
|
|
197
|
+
console.log(` ${pc.cyan(`cd ${projectName}`)}`);
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
if (!installDeps) {
|
|
201
|
+
console.log(` ${pc.cyan(`${pkgManager} install`)}`);
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
console.log(` ${pc.cyan(`${pkgManager} run dev`)} ${pc.dim('# Starts interactive demo sandbox')}`);
|
|
205
|
+
console.log(` ${pc.cyan(`${pkgManager} run build`)} ${pc.dim('# Builds library for NPM distribution')}`);
|
|
206
|
+
console.log('\nHappy coding with GeaJS!\n');
|
|
207
|
+
|
|
208
|
+
} catch (error) {
|
|
209
|
+
console.error(pc.red(`\n✖ Scaffolding failed: ${error.message}`));
|
|
210
|
+
process.exit(1);
|
|
211
|
+
}
|
|
212
|
+
}
|
|
213
|
+
|
|
214
|
+
main();
|
package/package.json
ADDED
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "gea-lib",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"description": "Scaffold a modern, reactive library for GeaJS",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"bin": {
|
|
7
|
+
"gea-lib": "./bin/index.js"
|
|
8
|
+
},
|
|
9
|
+
"files": [
|
|
10
|
+
"bin",
|
|
11
|
+
"templates"
|
|
12
|
+
],
|
|
13
|
+
"scripts": {
|
|
14
|
+
"start": "node ./bin/index.js"
|
|
15
|
+
},
|
|
16
|
+
"keywords": [
|
|
17
|
+
"geajs",
|
|
18
|
+
"gea",
|
|
19
|
+
"reactive",
|
|
20
|
+
"library",
|
|
21
|
+
"scaffolder",
|
|
22
|
+
"create"
|
|
23
|
+
],
|
|
24
|
+
"author": "Mehmet Fıskındal",
|
|
25
|
+
"license": "MIT",
|
|
26
|
+
"repository": {
|
|
27
|
+
"type": "git",
|
|
28
|
+
"url": "git+https://github.com/mehmetfiskindal/gea-lib.git"
|
|
29
|
+
},
|
|
30
|
+
"bugs": {
|
|
31
|
+
"url": "https://github.com/mehmetfiskindal/gea-lib/issues"
|
|
32
|
+
},
|
|
33
|
+
"homepage": "https://github.com/mehmetfiskindal/gea-lib#readme",
|
|
34
|
+
"dependencies": {
|
|
35
|
+
"picocolors": "^1.1.1",
|
|
36
|
+
"prompts": "^2.4.2"
|
|
37
|
+
}
|
|
38
|
+
}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
# <% projectName %>
|
|
2
|
+
|
|
3
|
+
A modern, high-performance, and reactive component library for **GeaJS**.
|
|
4
|
+
|
|
5
|
+
Built with compiler-first reactivity, proxy-based state management, and modern glassmorphic designs.
|
|
6
|
+
|
|
7
|
+
## Features
|
|
8
|
+
|
|
9
|
+
- ⚡ **No Virtual DOM**: Built on GeaJS, compile-time JSX transformations for surgical DOM patching.
|
|
10
|
+
- 🎨 **Premium Styling**: Pre-configured responsive styles, micro-animations, and glassmorphic designs.
|
|
11
|
+
- 🛠️ **Playground Included**: An interactive visual sandbox to test and showcase your components in real-time.
|
|
12
|
+
|
|
13
|
+
## Development
|
|
14
|
+
|
|
15
|
+
To start the interactive playground:
|
|
16
|
+
|
|
17
|
+
```bash
|
|
18
|
+
npm install
|
|
19
|
+
npm run dev
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
## Production Build
|
|
23
|
+
|
|
24
|
+
To build your library for distribution:
|
|
25
|
+
|
|
26
|
+
```bash
|
|
27
|
+
npm run build
|
|
28
|
+
```
|
|
29
|
+
|
|
30
|
+
The build process bundles your components into `dist/index.js` (ES Modules).
|
|
31
|
+
|
|
32
|
+
## Usage
|
|
33
|
+
|
|
34
|
+
Register components in your main application:
|
|
35
|
+
|
|
36
|
+
```javascript
|
|
37
|
+
import { Button, Card, counterStore } from '<% projectName %>';
|
|
38
|
+
import '<% projectName %>/style.css';
|
|
39
|
+
```
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
# Logs
|
|
2
|
+
logs
|
|
3
|
+
*.log
|
|
4
|
+
npm-debug.log*
|
|
5
|
+
yarn-debug.log*
|
|
6
|
+
yarn-error.log*
|
|
7
|
+
pnpm-debug.log*
|
|
8
|
+
lerna-debug.log*
|
|
9
|
+
|
|
10
|
+
# Dependency directories
|
|
11
|
+
node_modules/
|
|
12
|
+
jspm_packages/
|
|
13
|
+
|
|
14
|
+
# Compiler outputs
|
|
15
|
+
dist/
|
|
16
|
+
tmp/
|
|
17
|
+
out/
|
|
18
|
+
.docusaurus/
|
|
19
|
+
|
|
20
|
+
# IDEs and editors
|
|
21
|
+
.idea/
|
|
22
|
+
.vscode/
|
|
23
|
+
*.suo
|
|
24
|
+
*.ntvs*
|
|
25
|
+
*.njsproj
|
|
26
|
+
*.sln
|
|
27
|
+
*.sw?
|
|
28
|
+
|
|
29
|
+
# OS files
|
|
30
|
+
.DS_Store
|
|
31
|
+
Thumbs.db
|
|
32
|
+
|
|
33
|
+
# Test coverage
|
|
34
|
+
coverage/
|
|
35
|
+
.nyc_output/
|
|
36
|
+
|
|
37
|
+
# Build environment
|
|
38
|
+
.env
|
|
39
|
+
.env.local
|
|
40
|
+
.env.development.local
|
|
41
|
+
.env.test.local
|
|
42
|
+
.env.production.local
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "<% projectName %>",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"type": "module",
|
|
5
|
+
"main": "./dist/index.js",
|
|
6
|
+
"module": "./dist/index.js",
|
|
7
|
+
"exports": {
|
|
8
|
+
".": {
|
|
9
|
+
"import": "./dist/index.js"
|
|
10
|
+
},
|
|
11
|
+
"./style.css": "./dist/style.css"
|
|
12
|
+
},
|
|
13
|
+
"files": [
|
|
14
|
+
"dist"
|
|
15
|
+
],
|
|
16
|
+
"scripts": {
|
|
17
|
+
"dev": "vite",
|
|
18
|
+
"build": "vite build",
|
|
19
|
+
"preview": "vite preview",
|
|
20
|
+
"test": "vitest run"
|
|
21
|
+
},
|
|
22
|
+
"peerDependencies": {
|
|
23
|
+
"@geajs/core": "^1.0.0"
|
|
24
|
+
},
|
|
25
|
+
"devDependencies": {
|
|
26
|
+
"@geajs/core": "^1.0.0",
|
|
27
|
+
"@geajs/vite-plugin": "^1.0.0",
|
|
28
|
+
"vite": "^8.0.0",
|
|
29
|
+
"vitest": "^2.0.0",
|
|
30
|
+
"jsdom": "^24.1.0"
|
|
31
|
+
}
|
|
32
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import { Component } from '@geajs/core';
|
|
2
|
+
import { Button, Card, counterStore } from '../src';
|
|
3
|
+
|
|
4
|
+
export default class App extends Component {
|
|
5
|
+
template() {
|
|
6
|
+
return (
|
|
7
|
+
<div style="max-width: 800px; width: 100%; padding: 2rem;">
|
|
8
|
+
<div style="text-align: center; margin-bottom: 3rem;">
|
|
9
|
+
<h1 style="font-size: 3rem; font-weight: 800; background: linear-gradient(135deg, #a78bfa 0%, #ec4899 100%); -webkit-background-clip: text; -webkit-text-fill-color: transparent; margin-bottom: 0.5rem; letter-spacing: -0.05em;">
|
|
10
|
+
GeaJS Library Playground
|
|
11
|
+
</h1>
|
|
12
|
+
<p style="color: var(--text-secondary); font-size: 1.1rem;">
|
|
13
|
+
Interactive sandbox demonstrating your reactive components
|
|
14
|
+
</p>
|
|
15
|
+
</div>
|
|
16
|
+
|
|
17
|
+
<div style="display: grid; grid-template-columns: 1fr; gap: 2rem;">
|
|
18
|
+
|
|
19
|
+
{/* Reactive Counter Card */}
|
|
20
|
+
<Card
|
|
21
|
+
title="Reactive State Demo"
|
|
22
|
+
footer={
|
|
23
|
+
<Button variant="glass" click={() => counterStore.reset()}>
|
|
24
|
+
Reset Counter
|
|
25
|
+
</Button>
|
|
26
|
+
}
|
|
27
|
+
>
|
|
28
|
+
<p style="margin-bottom: 1.5rem;">
|
|
29
|
+
GeaJS utilizes deep proxies to surgically update the DOM. Click the buttons below to see the reactivity in action.
|
|
30
|
+
</p>
|
|
31
|
+
|
|
32
|
+
<div style="display: flex; align-items: center; justify-content: center; gap: 2rem; margin: 2rem 0; padding: 1.5rem; background: rgba(255,255,255,0.02); border-radius: 16px; border: 1px dashed rgba(255,255,255,0.08);">
|
|
33
|
+
<Button variant="secondary" click={() => counterStore.decrement()}>-</Button>
|
|
34
|
+
<span style="font-family: var(--font-mono); font-size: 3rem; font-weight: bold; min-width: 80px; text-align: center; color: #ffffff;">
|
|
35
|
+
{counterStore.count}
|
|
36
|
+
</span>
|
|
37
|
+
<Button variant="primary" click={() => counterStore.increment()}>+</Button>
|
|
38
|
+
</div>
|
|
39
|
+
</Card>
|
|
40
|
+
|
|
41
|
+
{/* Button Variant Showcase */}
|
|
42
|
+
<Card title="Button Variants">
|
|
43
|
+
<p style="margin-bottom: 1.5rem;">
|
|
44
|
+
Beautiful styled buttons with hover glows and tap micro-animations.
|
|
45
|
+
</p>
|
|
46
|
+
|
|
47
|
+
<div style="display: flex; flex-wrap: wrap; gap: 1rem; justify-content: center;">
|
|
48
|
+
<Button variant="primary" click={() => alert('Primary clicked!')}>
|
|
49
|
+
Primary Glow
|
|
50
|
+
</Button>
|
|
51
|
+
<Button variant="secondary" click={() => alert('Secondary clicked!')}>
|
|
52
|
+
Secondary Glow
|
|
53
|
+
</Button>
|
|
54
|
+
<Button variant="glass" click={() => alert('Glass clicked!')}>
|
|
55
|
+
Glassmorphic
|
|
56
|
+
</Button>
|
|
57
|
+
<Button variant="primary" disabled={true}>
|
|
58
|
+
Disabled
|
|
59
|
+
</Button>
|
|
60
|
+
</div>
|
|
61
|
+
</Card>
|
|
62
|
+
|
|
63
|
+
{/* Integration Guide */}
|
|
64
|
+
<Card title="How to Import">
|
|
65
|
+
<p style="margin-bottom: 1rem;">Import components directly into your GeaJS project:</p>
|
|
66
|
+
<pre style="background: rgba(0,0,0,0.3); padding: 1rem; border-radius: 12px; border: 1px solid rgba(255,255,255,0.05); font-family: var(--font-mono); font-size: 0.9rem; color: #a78bfa; overflow-x: auto; white-space: pre-wrap;">
|
|
67
|
+
{`import { Button, Card } from 'your-library-name';
|
|
68
|
+
|
|
69
|
+
// In template:
|
|
70
|
+
<Card title="My Card">
|
|
71
|
+
<Button click={() => doSomething()}>Click Me</Button>
|
|
72
|
+
</Card>`}
|
|
73
|
+
</pre>
|
|
74
|
+
</Card>
|
|
75
|
+
|
|
76
|
+
</div>
|
|
77
|
+
</div>
|
|
78
|
+
);
|
|
79
|
+
}
|
|
80
|
+
}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html lang="en">
|
|
3
|
+
<head>
|
|
4
|
+
<meta charset="UTF-8" />
|
|
5
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
|
6
|
+
<title><% projectName %> - Component Library Playground</title>
|
|
7
|
+
<link rel="preconnect" href="https://fonts.googleapis.com">
|
|
8
|
+
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
|
9
|
+
<link href="https://fonts.googleapis.com/css2?family=Outfit:wght@300;400;600;800&family=JetBrains+Mono:wght@400;700&display=swap" rel="stylesheet">
|
|
10
|
+
</head>
|
|
11
|
+
<body>
|
|
12
|
+
<div id="app"></div>
|
|
13
|
+
<script type="module" src="/playground/main.js"></script>
|
|
14
|
+
</body>
|
|
15
|
+
</html>
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
:root {
|
|
2
|
+
--bg-color: #030014;
|
|
3
|
+
--panel-bg: rgba(255, 255, 255, 0.03);
|
|
4
|
+
--panel-border: rgba(255, 255, 255, 0.08);
|
|
5
|
+
--primary-color: #7c3aed;
|
|
6
|
+
--primary-glow: rgba(124, 58, 237, 0.3);
|
|
7
|
+
--secondary-color: #06b6d4;
|
|
8
|
+
--secondary-glow: rgba(6, 182, 212, 0.3);
|
|
9
|
+
--accent-color: #ec4899;
|
|
10
|
+
--text-primary: #f3f4f6;
|
|
11
|
+
--text-secondary: #9ca3af;
|
|
12
|
+
--font-sans: 'Outfit', sans-serif;
|
|
13
|
+
--font-mono: 'JetBrains Mono', monospace;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
* {
|
|
17
|
+
box-sizing: border-box;
|
|
18
|
+
margin: 0;
|
|
19
|
+
padding: 0;
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
body {
|
|
23
|
+
background-color: var(--bg-color);
|
|
24
|
+
color: var(--text-primary);
|
|
25
|
+
font-family: var(--font-sans);
|
|
26
|
+
min-height: 100vh;
|
|
27
|
+
display: flex;
|
|
28
|
+
justify-content: center;
|
|
29
|
+
align-items: center;
|
|
30
|
+
overflow-x: hidden;
|
|
31
|
+
background-image:
|
|
32
|
+
radial-gradient(circle at 10% 20%, rgba(124, 58, 237, 0.15) 0%, transparent 40%),
|
|
33
|
+
radial-gradient(circle at 90% 80%, rgba(6, 182, 212, 0.15) 0%, transparent 40%);
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
/* Scrollbar styles */
|
|
37
|
+
::-webkit-scrollbar {
|
|
38
|
+
width: 8px;
|
|
39
|
+
}
|
|
40
|
+
::-webkit-scrollbar-track {
|
|
41
|
+
background: var(--bg-color);
|
|
42
|
+
}
|
|
43
|
+
::-webkit-scrollbar-thumb {
|
|
44
|
+
background: var(--panel-border);
|
|
45
|
+
border-radius: 4px;
|
|
46
|
+
}
|
|
47
|
+
::-webkit-scrollbar-thumb:hover {
|
|
48
|
+
background: var(--primary-color);
|
|
49
|
+
}
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
.gea-btn {
|
|
2
|
+
font-family: var(--font-sans, 'Outfit', sans-serif);
|
|
3
|
+
font-weight: 600;
|
|
4
|
+
font-size: 0.95rem;
|
|
5
|
+
padding: 0.75rem 1.5rem;
|
|
6
|
+
border-radius: 12px;
|
|
7
|
+
border: 1px solid transparent;
|
|
8
|
+
cursor: pointer;
|
|
9
|
+
transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
|
|
10
|
+
display: inline-flex;
|
|
11
|
+
align-items: center;
|
|
12
|
+
justify-content: center;
|
|
13
|
+
gap: 0.5rem;
|
|
14
|
+
position: relative;
|
|
15
|
+
overflow: hidden;
|
|
16
|
+
color: #ffffff;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
.gea-btn::after {
|
|
20
|
+
content: '';
|
|
21
|
+
position: absolute;
|
|
22
|
+
inset: 0;
|
|
23
|
+
background: rgba(255, 255, 255, 0.1);
|
|
24
|
+
opacity: 0;
|
|
25
|
+
transition: opacity 0.2s ease;
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
.gea-btn:hover::after {
|
|
29
|
+
opacity: 1;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
.gea-btn:active {
|
|
33
|
+
transform: scale(0.97);
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
.gea-btn:disabled {
|
|
37
|
+
opacity: 0.5;
|
|
38
|
+
cursor: not-allowed;
|
|
39
|
+
transform: none;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
/* Variants */
|
|
43
|
+
.gea-btn-primary {
|
|
44
|
+
background: linear-gradient(135deg, var(--primary-color, #7c3aed) 0%, #6d28d9 100%);
|
|
45
|
+
box-shadow: 0 4px 15px var(--primary-glow, rgba(124, 58, 237, 0.3));
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
.gea-btn-primary:hover {
|
|
49
|
+
box-shadow: 0 6px 20px var(--primary-glow, rgba(124, 58, 237, 0.5));
|
|
50
|
+
transform: translateY(-1px);
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
.gea-btn-secondary {
|
|
54
|
+
background: linear-gradient(135deg, var(--secondary-color, #06b6d4) 0%, #0891b2 100%);
|
|
55
|
+
box-shadow: 0 4px 15px var(--secondary-glow, rgba(6, 182, 212, 0.3));
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
.gea-btn-secondary:hover {
|
|
59
|
+
box-shadow: 0 6px 20px var(--secondary-glow, rgba(6, 182, 212, 0.5));
|
|
60
|
+
transform: translateY(-1px);
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
.gea-btn-glass {
|
|
64
|
+
background: rgba(255, 255, 255, 0.05);
|
|
65
|
+
border: 1px solid rgba(255, 255, 255, 0.1);
|
|
66
|
+
backdrop-filter: blur(10px);
|
|
67
|
+
-webkit-backdrop-filter: blur(10px);
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
.gea-btn-glass:hover {
|
|
71
|
+
background: rgba(255, 255, 255, 0.1);
|
|
72
|
+
border-color: rgba(255, 255, 255, 0.2);
|
|
73
|
+
box-shadow: 0 4px 20px rgba(0, 0, 0, 0.2);
|
|
74
|
+
}
|