mirror of
https://github.com/aljazceru/opencode.git
synced 2025-12-24 19:24:22 +01:00
wip: cloud stuff
This commit is contained in:
28
cloud/app/.gitignore
vendored
Normal file
28
cloud/app/.gitignore
vendored
Normal file
@@ -0,0 +1,28 @@
|
|||||||
|
dist
|
||||||
|
.wrangler
|
||||||
|
.output
|
||||||
|
.vercel
|
||||||
|
.netlify
|
||||||
|
.vinxi
|
||||||
|
app.config.timestamp_*.js
|
||||||
|
|
||||||
|
# Environment
|
||||||
|
.env
|
||||||
|
.env*.local
|
||||||
|
|
||||||
|
# dependencies
|
||||||
|
/node_modules
|
||||||
|
|
||||||
|
# IDEs and editors
|
||||||
|
/.idea
|
||||||
|
.project
|
||||||
|
.classpath
|
||||||
|
*.launch
|
||||||
|
.settings/
|
||||||
|
|
||||||
|
# Temp
|
||||||
|
gitignore
|
||||||
|
|
||||||
|
# System Files
|
||||||
|
.DS_Store
|
||||||
|
Thumbs.db
|
||||||
61
cloud/app/.opencode/agent/css.md
Normal file
61
cloud/app/.opencode/agent/css.md
Normal file
@@ -0,0 +1,61 @@
|
|||||||
|
---
|
||||||
|
description: use whenever you are styling a ui with css
|
||||||
|
---
|
||||||
|
|
||||||
|
you are very good at writing clean maintainable css using modern techniques
|
||||||
|
|
||||||
|
css is structured like this
|
||||||
|
|
||||||
|
```css
|
||||||
|
[data-page="home"] {
|
||||||
|
[data-component="header"] {
|
||||||
|
[data-slot="logo"] {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
top level pages are scoped using `data-page`
|
||||||
|
|
||||||
|
pages can break down into components using `data-component`
|
||||||
|
|
||||||
|
components can break down into slots using `data-slot`
|
||||||
|
|
||||||
|
structure things so that this hierarchy is followed - you should rarely need to
|
||||||
|
nest components inside other components. you should NEVER nest components inside
|
||||||
|
slots. you should NEVER nest slots inside other slots.
|
||||||
|
|
||||||
|
thei hierarchy in css file does NOT have to match the hierarchy in the dom - you
|
||||||
|
can put components or slots at the same level even if one goes inside another.
|
||||||
|
|
||||||
|
it is more important to follow the pages -> components -> slots structure
|
||||||
|
|
||||||
|
use data attributes to represent different states of the component
|
||||||
|
|
||||||
|
```css
|
||||||
|
[data-component="modal"] {
|
||||||
|
opacity: 0;
|
||||||
|
|
||||||
|
&[data-state="open"] {
|
||||||
|
opacity: 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
this will allow jsx to control the syling
|
||||||
|
|
||||||
|
avoid selectors that just target an element type like `> span` you should assign
|
||||||
|
it a slot name. it's ok to do this sometimes where it makes sense semantically
|
||||||
|
like targeting `li` elements in a list
|
||||||
|
|
||||||
|
in terms of file structure `./src/style/` contains all universal styling rules.
|
||||||
|
these should not contain anything specific to a page
|
||||||
|
|
||||||
|
`./src/style/token` contains all the tokens used in the project
|
||||||
|
|
||||||
|
`./src/style/component` is for reusable components like buttons or inputs
|
||||||
|
|
||||||
|
page specific styles should go next to the page they are styling so
|
||||||
|
`./src/routes/about.tsx` should have its styles in `./src/routes/about.css`
|
||||||
|
|
||||||
|
`about.css` should be scoped using `data-page="about"`
|
||||||
32
cloud/app/README.md
Normal file
32
cloud/app/README.md
Normal file
@@ -0,0 +1,32 @@
|
|||||||
|
# SolidStart
|
||||||
|
|
||||||
|
Everything you need to build a Solid project, powered by [`solid-start`](https://start.solidjs.com);
|
||||||
|
|
||||||
|
## Creating a project
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# create a new project in the current directory
|
||||||
|
npm init solid@latest
|
||||||
|
|
||||||
|
# create a new project in my-app
|
||||||
|
npm init solid@latest my-app
|
||||||
|
```
|
||||||
|
|
||||||
|
## Developing
|
||||||
|
|
||||||
|
Once you've created a project and installed dependencies with `npm install` (or `pnpm install` or `yarn`), start a development server:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
npm run dev
|
||||||
|
|
||||||
|
# or start the server and open the app in a new browser tab
|
||||||
|
npm run dev -- --open
|
||||||
|
```
|
||||||
|
|
||||||
|
## Building
|
||||||
|
|
||||||
|
Solid apps are built with _presets_, which optimise your project for deployment to different environments.
|
||||||
|
|
||||||
|
By default, `npm run build` will generate a Node app that you can run with `npm start`. To use a different preset, add it to the `devDependencies` in `package.json` and specify in your `app.config.js`.
|
||||||
|
|
||||||
|
## This project was created with the [Solid CLI](https://github.com/solidjs-community/solid-cli)
|
||||||
9
cloud/app/app.config.ts
Normal file
9
cloud/app/app.config.ts
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
import { defineConfig } from "@solidjs/start/config"
|
||||||
|
|
||||||
|
export default defineConfig({
|
||||||
|
vite: {
|
||||||
|
server: {
|
||||||
|
allowedHosts: true,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
})
|
||||||
21
cloud/app/package.json
Normal file
21
cloud/app/package.json
Normal file
@@ -0,0 +1,21 @@
|
|||||||
|
{
|
||||||
|
"name": "@opencode/cloud-app",
|
||||||
|
"type": "module",
|
||||||
|
"scripts": {
|
||||||
|
"dev": "vinxi dev --host 0.0.0.0",
|
||||||
|
"build": "vinxi build",
|
||||||
|
"start": "vinxi start",
|
||||||
|
"version": "vinxi version"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"@ibm/plex": "6.4.1",
|
||||||
|
"@solidjs/meta": "^0.29.4",
|
||||||
|
"@solidjs/router": "^0.15.0",
|
||||||
|
"@solidjs/start": "^1.1.0",
|
||||||
|
"solid-js": "^1.9.5",
|
||||||
|
"vinxi": "^0.5.7"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=22"
|
||||||
|
}
|
||||||
|
}
|
||||||
BIN
cloud/app/public/favicon.ico
Normal file
BIN
cloud/app/public/favicon.ico
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 664 B |
1
cloud/app/src/app.css
Normal file
1
cloud/app/src/app.css
Normal file
@@ -0,0 +1 @@
|
|||||||
|
@import "./style/index.css";
|
||||||
21
cloud/app/src/app.tsx
Normal file
21
cloud/app/src/app.tsx
Normal file
@@ -0,0 +1,21 @@
|
|||||||
|
import { MetaProvider, Title } from "@solidjs/meta";
|
||||||
|
import { Router } from "@solidjs/router";
|
||||||
|
import { FileRoutes } from "@solidjs/start/router";
|
||||||
|
import { Suspense } from "solid-js";
|
||||||
|
import "@ibm/plex/css/ibm-plex.css";
|
||||||
|
import "./app.css";
|
||||||
|
|
||||||
|
export default function App() {
|
||||||
|
return (
|
||||||
|
<Router
|
||||||
|
root={props => (
|
||||||
|
<MetaProvider>
|
||||||
|
<Title>SolidStart - Basic</Title>
|
||||||
|
<Suspense>{props.children}</Suspense>
|
||||||
|
</MetaProvider>
|
||||||
|
)}
|
||||||
|
>
|
||||||
|
<FileRoutes />
|
||||||
|
</Router>
|
||||||
|
);
|
||||||
|
}
|
||||||
19
cloud/app/src/asset/logo-ornate-dark.svg
Normal file
19
cloud/app/src/asset/logo-ornate-dark.svg
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
<svg width="289" height="50" viewBox="0 0 289 50" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<path d="M8.5 16.5H24.5V33H8.5V16.5Z" fill="white" fill-opacity="0.2"/>
|
||||||
|
<path d="M48.5 16.5H64.5V33H48.5V16.5Z" fill="white" fill-opacity="0.2"/>
|
||||||
|
<path d="M120.5 16.5H136.5V33H120.5V16.5Z" fill="white" fill-opacity="0.2"/>
|
||||||
|
<path d="M160.5 16.5H176.5V33H160.5V16.5Z" fill="white" fill-opacity="0.2"/>
|
||||||
|
<path d="M192.5 16.5H208.5V33H192.5V16.5Z" fill="white" fill-opacity="0.2"/>
|
||||||
|
<path d="M232.5 16.5H248.5V33H232.5V16.5Z" fill="white" fill-opacity="0.2"/>
|
||||||
|
<path d="M264.5 0H288.5V8.5H272.5V16.5H288.5V25H272.5V33H288.5V41.5H264.5V0Z" fill="white" fill-opacity="0.95"/>
|
||||||
|
<path d="M248.5 0H224.5V41.5H248.5V33H232.5V8.5H248.5V0Z" fill="white" fill-opacity="0.95"/>
|
||||||
|
<path d="M256.5 8.5H248.5V33H256.5V8.5Z" fill="white" fill-opacity="0.95"/>
|
||||||
|
<path fill-rule="evenodd" clip-rule="evenodd" d="M184.5 0H216.5V41.5H184.5V0ZM208.5 8.5H192.5V33H208.5V8.5Z" fill="white" fill-opacity="0.95"/>
|
||||||
|
<path d="M144.5 8.5H136.5V41.5H144.5V8.5Z" fill="white" fill-opacity="0.5"/>
|
||||||
|
<path d="M136.5 0H112.5V41.5H120.5V8.5H136.5V0Z" fill="white" fill-opacity="0.5"/>
|
||||||
|
<path d="M80.5 0H104.5V8.5H88.5V16.5H104.5V25H88.5V33H104.5V41.5H80.5V0Z" fill="white" fill-opacity="0.5"/>
|
||||||
|
<path fill-rule="evenodd" clip-rule="evenodd" d="M40.5 0H72.5V41.5H48.5V49.5H40.5V0ZM64.5 8.5H48.5V33H64.5V8.5Z" fill="white" fill-opacity="0.5"/>
|
||||||
|
<path fill-rule="evenodd" clip-rule="evenodd" d="M0.5 0H32.5V41.5955H0.5V0ZM24.5 8.5H8.5V33H24.5V8.5Z" fill="white" fill-opacity="0.5"/>
|
||||||
|
<path d="M152.5 0H176.5V8.5H160.5V33H176.5V41.5H152.5V0Z" fill="white" fill-opacity="0.95"/>
|
||||||
|
</svg>
|
||||||
|
|
||||||
|
After Width: | Height: | Size: 1.6 KiB |
BIN
cloud/app/src/asset/screenshot-github.webp
Normal file
BIN
cloud/app/src/asset/screenshot-github.webp
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 902 KiB |
BIN
cloud/app/src/asset/screenshot-splash.webp
Normal file
BIN
cloud/app/src/asset/screenshot-splash.webp
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 456 KiB |
BIN
cloud/app/src/asset/screenshot-vscode.webp
Normal file
BIN
cloud/app/src/asset/screenshot-vscode.webp
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 998 KiB |
24
cloud/app/src/component/icon.tsx
Normal file
24
cloud/app/src/component/icon.tsx
Normal file
@@ -0,0 +1,24 @@
|
|||||||
|
|
||||||
|
import { JSX } from "solid-js"
|
||||||
|
|
||||||
|
|
||||||
|
export function IconCopy(props: JSX.SvgSVGAttributes<SVGSVGElement>) {
|
||||||
|
return (
|
||||||
|
<svg
|
||||||
|
{...props}
|
||||||
|
viewBox="0 0 512 512" >
|
||||||
|
<rect width="336" height="336" x="128" y="128" fill="none" stroke="currentColor" stroke-linejoin="round" stroke-width="32" rx="57" ry="57"></rect>
|
||||||
|
<path fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="32" d="m383.5 128l.5-24a56.16 56.16 0 0 0-56-56H112a64.19 64.19 0 0 0-64 64v216a56.16 56.16 0 0 0 56 56h24"></path>
|
||||||
|
</svg>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export function IconCheck(props: JSX.SvgSVGAttributes<SVGSVGElement>) {
|
||||||
|
return (
|
||||||
|
<svg
|
||||||
|
{...props}
|
||||||
|
viewBox="0 0 24 24" >
|
||||||
|
<path fill="currentColor" d="M9 16.17L5.53 12.7a.996.996 0 1 0-1.41 1.41l4.18 4.18c.39.39 1.02.39 1.41 0L20.29 7.71a.996.996 0 1 0-1.41-1.41z"></path>
|
||||||
|
</svg>
|
||||||
|
)
|
||||||
|
}
|
||||||
4
cloud/app/src/entry-client.tsx
Normal file
4
cloud/app/src/entry-client.tsx
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
// @refresh reload
|
||||||
|
import { mount, StartClient } from "@solidjs/start/client";
|
||||||
|
|
||||||
|
mount(() => <StartClient />, document.getElementById("app")!);
|
||||||
21
cloud/app/src/entry-server.tsx
Normal file
21
cloud/app/src/entry-server.tsx
Normal file
@@ -0,0 +1,21 @@
|
|||||||
|
// @refresh reload
|
||||||
|
import { createHandler, StartServer } from "@solidjs/start/server";
|
||||||
|
|
||||||
|
export default createHandler(() => (
|
||||||
|
<StartServer
|
||||||
|
document={({ assets, children, scripts }) => (
|
||||||
|
<html lang="en">
|
||||||
|
<head>
|
||||||
|
<meta charset="utf-8" />
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||||
|
<link rel="icon" href="/favicon.ico" />
|
||||||
|
{assets}
|
||||||
|
</head>
|
||||||
|
<body data-color-mode="dark">
|
||||||
|
<div id="app">{children}</div>
|
||||||
|
{scripts}
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
|
)}
|
||||||
|
/>
|
||||||
|
));
|
||||||
1
cloud/app/src/global.d.ts
vendored
Normal file
1
cloud/app/src/global.d.ts
vendored
Normal file
@@ -0,0 +1 @@
|
|||||||
|
/// <reference types="@solidjs/start/env" />
|
||||||
19
cloud/app/src/routes/[...404].tsx
Normal file
19
cloud/app/src/routes/[...404].tsx
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
import { Title } from "@solidjs/meta";
|
||||||
|
import { HttpStatusCode } from "@solidjs/start";
|
||||||
|
|
||||||
|
export default function NotFound() {
|
||||||
|
return (
|
||||||
|
<main>
|
||||||
|
<Title>Not Found</Title>
|
||||||
|
<HttpStatusCode code={404} />
|
||||||
|
<h1>Page Not Found</h1>
|
||||||
|
<p>
|
||||||
|
Visit{" "}
|
||||||
|
<a href="https://start.solidjs.com" target="_blank">
|
||||||
|
start.solidjs.com
|
||||||
|
</a>{" "}
|
||||||
|
to learn how to build SolidStart apps.
|
||||||
|
</p>
|
||||||
|
</main>
|
||||||
|
);
|
||||||
|
}
|
||||||
264
cloud/app/src/routes/index.css
Normal file
264
cloud/app/src/routes/index.css
Normal file
@@ -0,0 +1,264 @@
|
|||||||
|
[data-page="home"] {
|
||||||
|
--color-bg: oklch(0.2097 0.008 274.53);
|
||||||
|
--color-border: oklch(0.46 0.02 269.88);
|
||||||
|
--color-text: #ffffff;
|
||||||
|
--color-text-secondary: oklch(0.72 0.01 270.15);
|
||||||
|
--color-text-dimmed: hsl(224, 7%, 46%);
|
||||||
|
padding: var(--space-6);
|
||||||
|
font-family: var(--font-mono);
|
||||||
|
color: var(--color-text);
|
||||||
|
|
||||||
|
a {
|
||||||
|
color: var(--color-text);
|
||||||
|
text-decoration: underline;
|
||||||
|
text-underline-offset: 0.1875rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
background: var(--color-bg);
|
||||||
|
position: fixed;
|
||||||
|
overflow-y: scroll;
|
||||||
|
inset: 0;
|
||||||
|
|
||||||
|
[data-component="content"] {
|
||||||
|
max-width: 67.5rem;
|
||||||
|
margin: 0 auto;
|
||||||
|
border: 2px solid var(--color-border);
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-component="top"] {
|
||||||
|
padding: var(--space-12);
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: start;
|
||||||
|
gap: var(--space-4);
|
||||||
|
|
||||||
|
[data-slot="logo"] {
|
||||||
|
height: 70px;
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-slot="title"] {
|
||||||
|
font-size: var(--font-size-2xl);
|
||||||
|
text-transform: uppercase;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-component="cta"] {
|
||||||
|
height: var(--space-19);
|
||||||
|
border-top: 2px solid var(--color-border);
|
||||||
|
display: flex;
|
||||||
|
|
||||||
|
[data-slot="left"] {
|
||||||
|
display: flex;
|
||||||
|
padding: 0 var(--space-12);
|
||||||
|
text-transform: uppercase;
|
||||||
|
text-decoration: underline;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
text-underline-offset: 0.1875rem;
|
||||||
|
border-right: 2px solid var(--color-border);
|
||||||
|
|
||||||
|
a {
|
||||||
|
color: var(--color-text);
|
||||||
|
text-decoration: underline;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-slot="right"] {
|
||||||
|
flex: 1;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
gap: 0.625rem;
|
||||||
|
padding: 0 var(--space-6);
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-slot="command"] {
|
||||||
|
all: unset;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
cursor: pointer;
|
||||||
|
color: var(--color-text-secondary);
|
||||||
|
font-size: 1.125rem;
|
||||||
|
font-family: var(--font-mono);
|
||||||
|
gap: var(--space-2);
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-slot="highlight"] {
|
||||||
|
color: var(--color-text);
|
||||||
|
font-weight: 500;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-component="features"] {
|
||||||
|
border-top: 2px solid var(--color-border);
|
||||||
|
padding: var(--space-12);
|
||||||
|
|
||||||
|
[data-slot="list"] {
|
||||||
|
padding-left: var(--space-4);
|
||||||
|
margin: 0;
|
||||||
|
list-style: disc;
|
||||||
|
|
||||||
|
li {
|
||||||
|
margin-bottom: var(--space-4);
|
||||||
|
|
||||||
|
strong {
|
||||||
|
text-transform: uppercase;
|
||||||
|
font-weight: 600;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
li:last-child {
|
||||||
|
margin-bottom: 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-component="install"] {
|
||||||
|
border-top: 2px solid var(--color-border);
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1fr 1fr;
|
||||||
|
grid-template-rows: 1fr 1fr;
|
||||||
|
|
||||||
|
@media (max-width: 40rem) {
|
||||||
|
grid-template-columns: 1fr;
|
||||||
|
grid-template-rows: auto;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-component="title"] {
|
||||||
|
letter-spacing: -0.03125rem;
|
||||||
|
text-transform: uppercase;
|
||||||
|
font-weight: 400;
|
||||||
|
font-size: var(--font-size-md);
|
||||||
|
flex-shrink: 0;
|
||||||
|
color: oklch(0.55 0.02 269.87);
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-component="method"] {
|
||||||
|
padding: var(--space-4) var(--space-6);
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: start;
|
||||||
|
gap: var(--space-3);
|
||||||
|
|
||||||
|
&:nth-child(1) {}
|
||||||
|
|
||||||
|
&:nth-child(2) {
|
||||||
|
border-left: 2px solid var(--color-border);
|
||||||
|
}
|
||||||
|
|
||||||
|
&:nth-child(3) {
|
||||||
|
border-top: 2px solid var(--color-border);
|
||||||
|
}
|
||||||
|
|
||||||
|
&:nth-child(4) {
|
||||||
|
border-top: 2px solid var(--color-border);
|
||||||
|
border-left: 2px solid var(--color-border);
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-slot="button"] {
|
||||||
|
all: unset;
|
||||||
|
cursor: pointer;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
color: var(--color-text-secondary);
|
||||||
|
gap: var(--space-2);
|
||||||
|
|
||||||
|
strong {
|
||||||
|
color: var(--color-text);
|
||||||
|
font-weight: 500;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-component="screenshots"] {
|
||||||
|
border-top: 2px solid var(--color-border);
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1fr 1fr;
|
||||||
|
gap: 0;
|
||||||
|
|
||||||
|
[data-slot="left"] {
|
||||||
|
padding: var(--space-8) var(--space-6);
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
|
||||||
|
img {
|
||||||
|
width: 100%;
|
||||||
|
height: "auto";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-slot="right"] {
|
||||||
|
display: grid;
|
||||||
|
grid-template-rows: 1fr 1fr;
|
||||||
|
border-left: 2px solid var(--color-border);
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-slot="filler"] {
|
||||||
|
display: flex;
|
||||||
|
flex-grow: 1;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-slot="cell"] {
|
||||||
|
padding: var(--space-8) var(--space-6);
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
gap: var(--space-4);
|
||||||
|
|
||||||
|
&:nth-child(2) {
|
||||||
|
border-top: 2px solid var(--color-border);
|
||||||
|
}
|
||||||
|
|
||||||
|
img {
|
||||||
|
width: 80%;
|
||||||
|
height: "auto";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-component="copy-status"] {
|
||||||
|
[data-slot="copy"] {
|
||||||
|
display: block;
|
||||||
|
width: 16px;
|
||||||
|
height: 16px;
|
||||||
|
color: var(--color-text-dimmed);
|
||||||
|
|
||||||
|
[data-copied] & {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-slot="check"] {
|
||||||
|
display: none;
|
||||||
|
width: 16px;
|
||||||
|
height: 16px;
|
||||||
|
color: white;
|
||||||
|
|
||||||
|
[data-copied] & {
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-component="footer"] {
|
||||||
|
border-top: 2px solid var(--color-border);
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1fr 1fr 1fr;
|
||||||
|
font-size: var(--font-size-lg);
|
||||||
|
height: var(--space-20);
|
||||||
|
|
||||||
|
[data-slot="cell"] {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
border-right: 2px solid var(--color-border);
|
||||||
|
text-transform: uppercase;
|
||||||
|
|
||||||
|
&:last-child {
|
||||||
|
border-right: none;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
169
cloud/app/src/routes/index.tsx
Normal file
169
cloud/app/src/routes/index.tsx
Normal file
@@ -0,0 +1,169 @@
|
|||||||
|
import { Title } from "@solidjs/meta"
|
||||||
|
import { onCleanup, onMount } from "solid-js"
|
||||||
|
import "./index.css"
|
||||||
|
import logo from "../asset/logo-ornate-dark.svg"
|
||||||
|
import IMG_SPLASH from "../asset/screenshot-splash.webp"
|
||||||
|
import IMG_VSCODE from "../asset/screenshot-vscode.webp"
|
||||||
|
import IMG_GITHUB from "../asset/screenshot-github.webp"
|
||||||
|
import { IconCopy, IconCheck } from "../component/icon"
|
||||||
|
|
||||||
|
function CopyStatus() {
|
||||||
|
return (
|
||||||
|
<div data-component="copy-status">
|
||||||
|
<IconCopy data-slot="copy" />
|
||||||
|
<IconCheck data-slot="check" />
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function Home() {
|
||||||
|
onMount(() => {
|
||||||
|
const commands = document.querySelectorAll("[data-copy]")
|
||||||
|
for (const button of commands) {
|
||||||
|
const callback = () => {
|
||||||
|
const text = button.textContent
|
||||||
|
alert(text)
|
||||||
|
if (text) {
|
||||||
|
navigator.clipboard.writeText(text)
|
||||||
|
button.setAttribute("data-copied", "")
|
||||||
|
setTimeout(() => {
|
||||||
|
button.removeAttribute("data-copied")
|
||||||
|
}, 1500)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
button.addEventListener("click", callback)
|
||||||
|
onCleanup(() => {
|
||||||
|
button.removeEventListener("click", callback)
|
||||||
|
})
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
return (
|
||||||
|
<main data-page="home">
|
||||||
|
<Title>opencode | AI coding agent built for the terminal</Title>
|
||||||
|
<div data-component="content">
|
||||||
|
<section data-component="top">
|
||||||
|
<img data-slot="logo" src={logo} alt="logo" />
|
||||||
|
<h1 data-slot="title">The AI coding agent built for the terminal.</h1>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section data-component="cta">
|
||||||
|
<div data-slot="left">
|
||||||
|
<a href="/docs">Get Started</a>
|
||||||
|
</div>
|
||||||
|
<div data-slot="right">
|
||||||
|
<button data-copy data-slot="command" data-command="curl -fsSL https://opencode.ai/install | bash">
|
||||||
|
<span>
|
||||||
|
<span>curl -fsSL </span>
|
||||||
|
<span data-slot="protocol">https://</span>
|
||||||
|
<span data-slot="highlight">opencode.ai/install</span>
|
||||||
|
| bash
|
||||||
|
</span>
|
||||||
|
<CopyStatus />
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section data-component="features">
|
||||||
|
<ul data-slot="list">
|
||||||
|
<li>
|
||||||
|
<strong>Native TUI</strong>: A responsive, native, themeable terminal UI.
|
||||||
|
</li>
|
||||||
|
<li>
|
||||||
|
<strong>LSP enabled</strong>: Automatically loads the right LSPs for the LLM.
|
||||||
|
</li>
|
||||||
|
<li>
|
||||||
|
<strong>Multi-session</strong>: Start multiple agents in parallel on the same project.
|
||||||
|
</li>
|
||||||
|
<li>
|
||||||
|
<strong>Shareable links</strong>: Share a link to any sessions for reference or to debug.
|
||||||
|
</li>
|
||||||
|
<li>
|
||||||
|
<strong>Claude Pro</strong>: Log in with Anthropic to use your Claude Pro or Max account.
|
||||||
|
</li>
|
||||||
|
<li>
|
||||||
|
<strong>Use any model</strong>: Supports 75+ LLM providers through{" "}
|
||||||
|
<a href="https://models.dev">Models.dev</a>, including local models.
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section data-component="install">
|
||||||
|
<div data-component="method">
|
||||||
|
<h3 data-component="title">npm</h3>
|
||||||
|
<button data-copy data-slot="button">
|
||||||
|
<span>
|
||||||
|
npm install -g <strong>opencode-ai</strong>
|
||||||
|
</span>
|
||||||
|
<CopyStatus />
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
<div data-component="method">
|
||||||
|
<h3 data-component="title">bun</h3>
|
||||||
|
<button data-copy data-slot="button">
|
||||||
|
<span>
|
||||||
|
bun install -g <strong>opencode-ai</strong>
|
||||||
|
</span>
|
||||||
|
<CopyStatus />
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
<div data-component="method">
|
||||||
|
<h3 data-component="title">homebrew</h3>
|
||||||
|
<button data-copy data-slot="button">
|
||||||
|
<span>
|
||||||
|
brew install <strong>sst/tap/opencode</strong>
|
||||||
|
</span>
|
||||||
|
<CopyStatus />
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
<div data-component="method">
|
||||||
|
<h3 data-component="title">paru</h3>
|
||||||
|
<button data-copy data-slot="button">
|
||||||
|
<span>
|
||||||
|
paru -S <strong>opencode-bin</strong>
|
||||||
|
</span>
|
||||||
|
<CopyStatus />
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section data-component="screenshots">
|
||||||
|
<div data-slot="left">
|
||||||
|
<div data-component="title">opencode TUI with tokyonight theme</div>
|
||||||
|
<div data-slot="filler">
|
||||||
|
<img src={IMG_SPLASH} alt="opencode TUI with tokyonight theme" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div data-slot="right">
|
||||||
|
<div data-slot="cell">
|
||||||
|
<div data-component="title">opencode in VS Code</div>
|
||||||
|
<div data-slot="filler">
|
||||||
|
<img src={IMG_VSCODE} alt="opencode in VS Code" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div data-slot="cell">
|
||||||
|
<div data-component="title">opencode in GitHub</div>
|
||||||
|
<div data-slot="filler">
|
||||||
|
<img src={IMG_GITHUB} alt="opencode in GitHub" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<footer data-component="footer">
|
||||||
|
<div data-slot="cell">
|
||||||
|
<a href="https://github.com/sst/opencode">GitHub</a>
|
||||||
|
</div>
|
||||||
|
<div data-slot="cell">
|
||||||
|
<a href="https://opencode.ai/discord">Discord</a>
|
||||||
|
</div>
|
||||||
|
<div data-slot="cell">
|
||||||
|
<span>
|
||||||
|
©2025 <a href="https://anoma.ly">Anomaly Innovations</a>
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
</footer>
|
||||||
|
</div>
|
||||||
|
</main>
|
||||||
|
)
|
||||||
|
}
|
||||||
8
cloud/app/src/style/base.css
Normal file
8
cloud/app/src/style/base.css
Normal file
@@ -0,0 +1,8 @@
|
|||||||
|
html {
|
||||||
|
color-scheme: dark;
|
||||||
|
line-height: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
body {
|
||||||
|
font-family: var(--font-sans);
|
||||||
|
}
|
||||||
102
cloud/app/src/style/component/button.css
Normal file
102
cloud/app/src/style/component/button.css
Normal file
@@ -0,0 +1,102 @@
|
|||||||
|
[data-component="button"] {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
gap: var(--space-2);
|
||||||
|
padding: var(--space-3) var(--space-4);
|
||||||
|
border: 1px solid transparent;
|
||||||
|
border-radius: var(--space-2);
|
||||||
|
font-family: var(--font-sans);
|
||||||
|
font-size: var(--font-size-md);
|
||||||
|
font-weight: 500;
|
||||||
|
line-height: 1.25;
|
||||||
|
cursor: pointer;
|
||||||
|
transition: all 0.2s ease-in-out;
|
||||||
|
text-decoration: none;
|
||||||
|
user-select: none;
|
||||||
|
|
||||||
|
&:disabled {
|
||||||
|
opacity: 0.5;
|
||||||
|
cursor: not-allowed;
|
||||||
|
}
|
||||||
|
|
||||||
|
&:focus {
|
||||||
|
outline: none;
|
||||||
|
box-shadow: 0 0 0 2px var(--color-primary);
|
||||||
|
}
|
||||||
|
|
||||||
|
&[data-color="primary"] {
|
||||||
|
background-color: var(--color-primary);
|
||||||
|
color: var(--color-primary-text);
|
||||||
|
border-color: var(--color-primary);
|
||||||
|
|
||||||
|
&:hover:not(:disabled) {
|
||||||
|
background-color: var(--color-primary-hover);
|
||||||
|
border-color: var(--color-primary-hover);
|
||||||
|
}
|
||||||
|
|
||||||
|
&:active:not(:disabled) {
|
||||||
|
background-color: var(--color-primary-active);
|
||||||
|
border-color: var(--color-primary-active);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&[data-color="danger"] {
|
||||||
|
background-color: var(--color-danger);
|
||||||
|
color: var(--color-danger-text);
|
||||||
|
border-color: var(--color-danger);
|
||||||
|
|
||||||
|
&:hover:not(:disabled) {
|
||||||
|
background-color: var(--color-danger-hover);
|
||||||
|
border-color: var(--color-danger-hover);
|
||||||
|
}
|
||||||
|
|
||||||
|
&:active:not(:disabled) {
|
||||||
|
background-color: var(--color-danger-active);
|
||||||
|
border-color: var(--color-danger-active);
|
||||||
|
}
|
||||||
|
|
||||||
|
&:focus {
|
||||||
|
box-shadow: 0 0 0 2px var(--color-danger);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&[data-color="warning"] {
|
||||||
|
background-color: var(--color-warning);
|
||||||
|
color: var(--color-warning-text);
|
||||||
|
border-color: var(--color-warning);
|
||||||
|
|
||||||
|
&:hover:not(:disabled) {
|
||||||
|
background-color: var(--color-warning-hover);
|
||||||
|
border-color: var(--color-warning-hover);
|
||||||
|
}
|
||||||
|
|
||||||
|
&:active:not(:disabled) {
|
||||||
|
background-color: var(--color-warning-active);
|
||||||
|
border-color: var(--color-warning-active);
|
||||||
|
}
|
||||||
|
|
||||||
|
&:focus {
|
||||||
|
box-shadow: 0 0 0 2px var(--color-warning);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&[data-size="small"] {
|
||||||
|
padding: var(--space-2) var(--space-3);
|
||||||
|
font-size: var(--font-size-sm);
|
||||||
|
gap: var(--space-1-5);
|
||||||
|
}
|
||||||
|
|
||||||
|
&[data-size="large"] {
|
||||||
|
padding: var(--space-4) var(--space-6);
|
||||||
|
font-size: var(--font-size-lg);
|
||||||
|
gap: var(--space-3);
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-slot="icon"] {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
width: 1em;
|
||||||
|
height: 1em;
|
||||||
|
}
|
||||||
|
}
|
||||||
8
cloud/app/src/style/index.css
Normal file
8
cloud/app/src/style/index.css
Normal file
@@ -0,0 +1,8 @@
|
|||||||
|
@import "./token/color.css";
|
||||||
|
@import "./token/font.css";
|
||||||
|
@import "./token/space.css";
|
||||||
|
|
||||||
|
@import "./component/button.css";
|
||||||
|
|
||||||
|
@import "./reset.css";
|
||||||
|
@import "./base.css";
|
||||||
76
cloud/app/src/style/reset.css
Normal file
76
cloud/app/src/style/reset.css
Normal file
@@ -0,0 +1,76 @@
|
|||||||
|
/* 1. Use a more-intuitive box-sizing model */
|
||||||
|
*,
|
||||||
|
*::before,
|
||||||
|
*::after {
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 2. Remove default margin */
|
||||||
|
* {
|
||||||
|
margin: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 3. Enable keyword animations */
|
||||||
|
@media (prefers-reduced-motion: no-preference) {
|
||||||
|
html {
|
||||||
|
interpolate-size: allow-keywords;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
body {
|
||||||
|
/* 4. Add accessible line-height */
|
||||||
|
line-height: 1.5;
|
||||||
|
/* 5. Improve text rendering */
|
||||||
|
-webkit-font-smoothing: antialiased;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 6. Improve media defaults */
|
||||||
|
img,
|
||||||
|
picture,
|
||||||
|
video,
|
||||||
|
canvas,
|
||||||
|
svg {
|
||||||
|
display: block;
|
||||||
|
max-width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 7. Inherit fonts for form controls */
|
||||||
|
input,
|
||||||
|
button,
|
||||||
|
textarea,
|
||||||
|
select {
|
||||||
|
font: inherit;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 8. Avoid text overflows */
|
||||||
|
p,
|
||||||
|
h1,
|
||||||
|
h2,
|
||||||
|
h3,
|
||||||
|
h4,
|
||||||
|
h5,
|
||||||
|
h6 {
|
||||||
|
overflow-wrap: break-word;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 9. Improve line wrapping */
|
||||||
|
p {
|
||||||
|
text-wrap: pretty;
|
||||||
|
}
|
||||||
|
|
||||||
|
h1,
|
||||||
|
h2,
|
||||||
|
h3,
|
||||||
|
h4,
|
||||||
|
h5,
|
||||||
|
h6 {
|
||||||
|
text-wrap: balance;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
10. Create a root stacking context
|
||||||
|
*/
|
||||||
|
#root,
|
||||||
|
#__next {
|
||||||
|
isolation: isolate;
|
||||||
|
}
|
||||||
90
cloud/app/src/style/token/color.css
Normal file
90
cloud/app/src/style/token/color.css
Normal file
@@ -0,0 +1,90 @@
|
|||||||
|
body {
|
||||||
|
--color-white: #ffffff;
|
||||||
|
--color-black: #000000;
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-color-mode="dark"] {
|
||||||
|
/* OpenCode theme colors */
|
||||||
|
--color-bg: #0c0c0e;
|
||||||
|
--color-bg-surface: #161618;
|
||||||
|
--color-bg-elevated: #1c1c1f;
|
||||||
|
|
||||||
|
--color-text: #ffffff;
|
||||||
|
--color-text-muted: #a1a1a6;
|
||||||
|
--color-text-disabled: #68686f;
|
||||||
|
|
||||||
|
--color-accent: #007aff;
|
||||||
|
--color-accent-hover: #0056b3;
|
||||||
|
--color-accent-active: #004085;
|
||||||
|
|
||||||
|
--color-success: #30d158;
|
||||||
|
--color-warning: #ff9f0a;
|
||||||
|
--color-danger: #ff453a;
|
||||||
|
|
||||||
|
--color-border: #38383a;
|
||||||
|
--color-border-muted: #2c2c2e;
|
||||||
|
|
||||||
|
/* Button colors */
|
||||||
|
--color-primary: var(--color-accent);
|
||||||
|
--color-primary-hover: var(--color-accent-hover);
|
||||||
|
--color-primary-active: var(--color-accent-active);
|
||||||
|
--color-primary-text: #ffffff;
|
||||||
|
|
||||||
|
--color-danger: #ff453a;
|
||||||
|
--color-danger-hover: #d70015;
|
||||||
|
--color-danger-active: #a50011;
|
||||||
|
--color-danger-text: #ffffff;
|
||||||
|
|
||||||
|
--color-warning: #ff9f0a;
|
||||||
|
--color-warning-hover: #cc7f08;
|
||||||
|
--color-warning-active: #995f06;
|
||||||
|
--color-warning-text: #000000;
|
||||||
|
|
||||||
|
/* Surface colors */
|
||||||
|
--color-surface: var(--color-bg-surface);
|
||||||
|
--color-surface-hover: var(--color-bg-elevated);
|
||||||
|
--color-border: var(--color-border);
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-color-mode="light"] {
|
||||||
|
/* OpenCode light theme colors */
|
||||||
|
--color-bg: #ffffff;
|
||||||
|
--color-bg-surface: #f5f5f7;
|
||||||
|
--color-bg-elevated: #ffffff;
|
||||||
|
|
||||||
|
--color-text: #1d1d1f;
|
||||||
|
--color-text-muted: #6e6e73;
|
||||||
|
--color-text-disabled: #86868b;
|
||||||
|
|
||||||
|
--color-accent: #007aff;
|
||||||
|
--color-accent-hover: #0056b3;
|
||||||
|
--color-accent-active: #004085;
|
||||||
|
|
||||||
|
--color-success: #30d158;
|
||||||
|
--color-warning: #ff9f0a;
|
||||||
|
--color-danger: #ff3b30;
|
||||||
|
|
||||||
|
--color-border: #d2d2d7;
|
||||||
|
--color-border-muted: #e5e5ea;
|
||||||
|
|
||||||
|
/* Button colors */
|
||||||
|
--color-primary: var(--color-accent);
|
||||||
|
--color-primary-hover: var(--color-accent-hover);
|
||||||
|
--color-primary-active: var(--color-accent-active);
|
||||||
|
--color-primary-text: #ffffff;
|
||||||
|
|
||||||
|
--color-danger: #ff3b30;
|
||||||
|
--color-danger-hover: #d70015;
|
||||||
|
--color-danger-active: #a50011;
|
||||||
|
--color-danger-text: #ffffff;
|
||||||
|
|
||||||
|
--color-warning: #ff9f0a;
|
||||||
|
--color-warning-hover: #cc7f08;
|
||||||
|
--color-warning-active: #995f06;
|
||||||
|
--color-warning-text: #000000;
|
||||||
|
|
||||||
|
/* Surface colors */
|
||||||
|
--color-surface: var(--color-bg-surface);
|
||||||
|
--color-surface-hover: var(--color-bg-elevated);
|
||||||
|
--color-border: var(--color-border);
|
||||||
|
}
|
||||||
18
cloud/app/src/style/token/font.css
Normal file
18
cloud/app/src/style/token/font.css
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
body {
|
||||||
|
--font-size-2xs: 0.6875rem;
|
||||||
|
--font-size-xs: 0.75rem;
|
||||||
|
--font-size-sm: 0.8125rem;
|
||||||
|
--font-size-md: 0.9375rem;
|
||||||
|
--font-size-lg: 1.125rem;
|
||||||
|
--font-size-xl: 1.25rem;
|
||||||
|
--font-size-2xl: 1.5rem;
|
||||||
|
--font-size-3xl: 1.875rem;
|
||||||
|
--font-size-4xl: 2.25rem;
|
||||||
|
--font-size-5xl: 3rem;
|
||||||
|
--font-size-6xl: 3.75rem;
|
||||||
|
--font-size-7xl: 4.5rem;
|
||||||
|
--font-size-8xl: 6rem;
|
||||||
|
--font-size-9xl: 8rem;
|
||||||
|
--font-mono: IBM Plex Mono;
|
||||||
|
--font-sans: Inter;
|
||||||
|
}
|
||||||
41
cloud/app/src/style/token/space.css
Normal file
41
cloud/app/src/style/token/space.css
Normal file
@@ -0,0 +1,41 @@
|
|||||||
|
body {
|
||||||
|
--space-0: 0;
|
||||||
|
--space-px: 1px;
|
||||||
|
--space-0-5: 0.125rem;
|
||||||
|
--space-1: 0.25rem;
|
||||||
|
--space-1-5: 0.375rem;
|
||||||
|
--space-2: 0.5rem;
|
||||||
|
--space-2-5: 0.625rem;
|
||||||
|
--space-3: 0.75rem;
|
||||||
|
--space-3-5: 0.875rem;
|
||||||
|
--space-4: 1rem;
|
||||||
|
--space-4-5: 1.125rem;
|
||||||
|
--space-5: 1.25rem;
|
||||||
|
--space-6: 1.5rem;
|
||||||
|
--space-7: 1.75rem;
|
||||||
|
--space-8: 2rem;
|
||||||
|
--space-9: 2.25rem;
|
||||||
|
--space-10: 2.5rem;
|
||||||
|
--space-11: 2.75rem;
|
||||||
|
--space-12: 3rem;
|
||||||
|
--space-14: 3.5rem;
|
||||||
|
--space-16: 4rem;
|
||||||
|
--space-17: 4.25rem;
|
||||||
|
--space-18: 4.5rem;
|
||||||
|
--space-19: 4.75rem;
|
||||||
|
--space-20: 5rem;
|
||||||
|
--space-24: 6rem;
|
||||||
|
--space-28: 7rem;
|
||||||
|
--space-32: 8rem;
|
||||||
|
--space-36: 9rem;
|
||||||
|
--space-40: 10rem;
|
||||||
|
--space-44: 11rem;
|
||||||
|
--space-48: 12rem;
|
||||||
|
--space-52: 13rem;
|
||||||
|
--space-56: 14rem;
|
||||||
|
--space-60: 15rem;
|
||||||
|
--space-64: 16rem;
|
||||||
|
--space-72: 18rem;
|
||||||
|
--space-80: 20rem;
|
||||||
|
--space-96: 24rem;
|
||||||
|
}
|
||||||
19
cloud/app/tsconfig.json
Normal file
19
cloud/app/tsconfig.json
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
{
|
||||||
|
"compilerOptions": {
|
||||||
|
"target": "ESNext",
|
||||||
|
"module": "ESNext",
|
||||||
|
"moduleResolution": "bundler",
|
||||||
|
"allowSyntheticDefaultImports": true,
|
||||||
|
"esModuleInterop": true,
|
||||||
|
"jsx": "preserve",
|
||||||
|
"jsxImportSource": "solid-js",
|
||||||
|
"allowJs": true,
|
||||||
|
"strict": true,
|
||||||
|
"noEmit": true,
|
||||||
|
"types": ["vinxi/types/client"],
|
||||||
|
"isolatedModules": true,
|
||||||
|
"paths": {
|
||||||
|
"~/*": ["./src/*"]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -20,6 +20,7 @@
|
|||||||
--space-12: 3rem;
|
--space-12: 3rem;
|
||||||
--space-14: 3.5rem;
|
--space-14: 3.5rem;
|
||||||
--space-16: 4rem;
|
--space-16: 4rem;
|
||||||
|
--space-18: 4.5rem;
|
||||||
--space-20: 5rem;
|
--space-20: 5rem;
|
||||||
--space-24: 6rem;
|
--space-24: 6rem;
|
||||||
--space-28: 7rem;
|
--space-28: 7rem;
|
||||||
|
|||||||
Reference in New Issue
Block a user