commit
60deda3f73
23 changed files with 4307 additions and 0 deletions
@ -0,0 +1,24 @@ |
|||||
|
# Logs |
||||
|
logs |
||||
|
*.log |
||||
|
npm-debug.log* |
||||
|
yarn-debug.log* |
||||
|
yarn-error.log* |
||||
|
pnpm-debug.log* |
||||
|
lerna-debug.log* |
||||
|
|
||||
|
node_modules |
||||
|
dist |
||||
|
dist-ssr |
||||
|
*.local |
||||
|
|
||||
|
# Editor directories and files |
||||
|
.vscode/* |
||||
|
!.vscode/extensions.json |
||||
|
.idea |
||||
|
.DS_Store |
||||
|
*.suo |
||||
|
*.ntvs* |
||||
|
*.njsproj |
||||
|
*.sln |
||||
|
*.sw? |
@ -0,0 +1,3 @@ |
|||||
|
{ |
||||
|
"recommendations": ["Vue.volar"] |
||||
|
} |
@ -0,0 +1,5 @@ |
|||||
|
# Vue 3 + TypeScript + Vite |
||||
|
|
||||
|
This template should help get you started developing with Vue 3 and TypeScript in Vite. The template uses Vue 3 `<script setup>` SFCs, check out the [script setup docs](https://v3.vuejs.org/api/sfc-script-setup.html#sfc-script-setup) to learn more. |
||||
|
|
||||
|
Learn more about the recommended Project Setup and IDE Support in the [Vue Docs TypeScript Guide](https://vuejs.org/guide/typescript/overview.html#project-setup). |
@ -0,0 +1,10 @@ |
|||||
|
/* eslint-disable */ |
||||
|
/* prettier-ignore */ |
||||
|
// @ts-nocheck
|
||||
|
// noinspection JSUnusedGlobalSymbols
|
||||
|
// Generated by unplugin-auto-import
|
||||
|
// biome-ignore lint: disable
|
||||
|
export {} |
||||
|
declare global { |
||||
|
|
||||
|
} |
@ -0,0 +1,15 @@ |
|||||
|
/* eslint-disable */ |
||||
|
// @ts-nocheck
|
||||
|
// Generated by unplugin-vue-components
|
||||
|
// Read more: https://github.com/vuejs/core/pull/3399
|
||||
|
// biome-ignore lint: disable
|
||||
|
export {} |
||||
|
|
||||
|
/* prettier-ignore */ |
||||
|
declare module 'vue' { |
||||
|
export interface GlobalComponents { |
||||
|
LocaleSwitcher: typeof import('./src/components/LocaleSwitcher/index.vue')['default'] |
||||
|
ThemeSwitcher: typeof import('./src/components/ThemeSwitcher/index.vue')['default'] |
||||
|
VanButton: typeof import('vant/es')['Button'] |
||||
|
} |
||||
|
} |
@ -0,0 +1,61 @@ |
|||||
|
<!DOCTYPE html> |
||||
|
<html lang="en"> |
||||
|
<head> |
||||
|
<meta charset="UTF-8" /> |
||||
|
<link rel="icon" type="image/svg+xml" href="/vite.svg" /> |
||||
|
<meta |
||||
|
name="viewport" |
||||
|
content="width=device-width, viewport-fit=cover, initial-scale=1, user-scalable=no, minimal-ui" |
||||
|
/> |
||||
|
<title>Vite + Vue + TS</title> |
||||
|
<script> |
||||
|
(function flexible(window, document) { |
||||
|
var docEl = document.documentElement; |
||||
|
var dpr = window.devicePixelRatio || 1; |
||||
|
|
||||
|
// adjust body font size |
||||
|
function setBodyFontSize() { |
||||
|
if (document.body) { |
||||
|
document.body.style.fontSize = 12 * dpr + "px"; |
||||
|
} else { |
||||
|
document.addEventListener("DOMContentLoaded", setBodyFontSize); |
||||
|
} |
||||
|
} |
||||
|
setBodyFontSize(); |
||||
|
|
||||
|
// set 1rem = viewWidth / 10 |
||||
|
function setRemUnit() { |
||||
|
var rem = docEl.clientWidth / 10; |
||||
|
docEl.style.fontSize = rem + "px"; |
||||
|
} |
||||
|
|
||||
|
setRemUnit(); |
||||
|
|
||||
|
// reset rem unit on page resize |
||||
|
window.addEventListener("resize", setRemUnit); |
||||
|
window.addEventListener("pageshow", function (e) { |
||||
|
if (e.persisted) { |
||||
|
setRemUnit(); |
||||
|
} |
||||
|
}); |
||||
|
|
||||
|
// detect 0.5px supports |
||||
|
if (dpr >= 2) { |
||||
|
var fakeBody = document.createElement("body"); |
||||
|
var testElement = document.createElement("div"); |
||||
|
testElement.style.border = ".5px solid transparent"; |
||||
|
fakeBody.appendChild(testElement); |
||||
|
docEl.appendChild(fakeBody); |
||||
|
if (testElement.offsetHeight === 1) { |
||||
|
docEl.classList.add("hairlines"); |
||||
|
} |
||||
|
docEl.removeChild(fakeBody); |
||||
|
} |
||||
|
})(window, document); |
||||
|
</script> |
||||
|
</head> |
||||
|
<body> |
||||
|
<div id="app"></div> |
||||
|
<script type="module" src="/src/main.ts"></script> |
||||
|
</body> |
||||
|
</html> |
File diff suppressed because it is too large
@ -0,0 +1,33 @@ |
|||||
|
{ |
||||
|
"name": "my-vue-app", |
||||
|
"private": true, |
||||
|
"version": "0.0.0", |
||||
|
"type": "module", |
||||
|
"scripts": { |
||||
|
"dev": "vite", |
||||
|
"build": "vue-tsc -b && vite build", |
||||
|
"preview": "vite preview" |
||||
|
}, |
||||
|
"dependencies": { |
||||
|
"@tailwindcss/postcss": "^4.1.4", |
||||
|
"@tailwindcss/vite": "^4.1.4", |
||||
|
"pinia": "^3.0.2", |
||||
|
"tailwindcss": "^4.1.4", |
||||
|
"vant": "^4.9.19", |
||||
|
"vue": "^3.5.13" |
||||
|
}, |
||||
|
"devDependencies": { |
||||
|
"@types/node": "^22.15.3", |
||||
|
"@vant/auto-import-resolver": "^1.3.0", |
||||
|
"@vitejs/plugin-vue": "^5.2.2", |
||||
|
"@vue/tsconfig": "^0.7.0", |
||||
|
"postcss": "^8.5.3", |
||||
|
"postcss-pxtorem": "^6.1.0", |
||||
|
"typescript": "~5.7.2", |
||||
|
"unplugin-auto-import": "^19.1.2", |
||||
|
"unplugin-vue-components": "^28.5.0", |
||||
|
"vite": "^6.3.1", |
||||
|
"vue-tsc": "^2.2.8" |
||||
|
}, |
||||
|
"packageManager": "[email protected]+sha512.6b865ad4b62a1d9842b61d674a393903b871d9244954f652b8842c2b553c72176b278f64c463e52d40fff8aba385c235c8c9ecf5cc7de4fd78b8bb6d49633ab6" |
||||
|
} |
File diff suppressed because it is too large
@ -0,0 +1,9 @@ |
|||||
|
export default { |
||||
|
plugins: { |
||||
|
"@tailwindcss/postcss": {}, |
||||
|
"postcss-pxtorem": { |
||||
|
rootValue: 37.5, |
||||
|
propList: ["*"], |
||||
|
}, |
||||
|
}, |
||||
|
}; |
After Width: | Height: | Size: 1.5 KiB |
@ -0,0 +1,34 @@ |
|||||
|
<script setup lang="ts"> |
||||
|
import ThemeSwitcher from "@/components/ThemeSwitcher/index.vue"; |
||||
|
import { useThemeStore } from "@/stores/theme"; |
||||
|
const themeStore = useThemeStore(); |
||||
|
themeStore.initTheme(); |
||||
|
</script> |
||||
|
|
||||
|
<template> |
||||
|
<div class="text-center text-red-300">欢迎来带我的vue3模板</div> |
||||
|
<van-button>asdasd</van-button> |
||||
|
<div> |
||||
|
<div class="pl-1 text-xs">dasd</div> |
||||
|
</div> |
||||
|
<div> |
||||
|
<ThemeSwitcher /> |
||||
|
</div> |
||||
|
</template> |
||||
|
|
||||
|
<style scoped> |
||||
|
.logo { |
||||
|
height: 6em; |
||||
|
padding: 1.5em; |
||||
|
will-change: filter; |
||||
|
transition: filter 300ms; |
||||
|
} |
||||
|
|
||||
|
.logo:hover { |
||||
|
filter: drop-shadow(0 0 2em #646cffaa); |
||||
|
} |
||||
|
|
||||
|
.logo.vue:hover { |
||||
|
filter: drop-shadow(0 0 2em #42b883aa); |
||||
|
} |
||||
|
</style> |
@ -0,0 +1,55 @@ |
|||||
|
@import "tailwindcss"; |
||||
|
|
||||
|
@theme { |
||||
|
--spacing: 4px; |
||||
|
|
||||
|
--breakpoint-sm: 40rem; |
||||
|
--breakpoint-md: 48rem; |
||||
|
--breakpoint-lg: 64rem; |
||||
|
--breakpoint-xl: 80rem; |
||||
|
--breakpoint-2xl: 96rem; |
||||
|
--container-3xs: 16rem; |
||||
|
--container-2xs: 18rem; |
||||
|
--container-xs: 20rem; |
||||
|
--container-sm: 24rem; |
||||
|
--container-md: 28rem; |
||||
|
--container-lg: 32rem; |
||||
|
--container-xl: 36rem; |
||||
|
--container-2xl: 42rem; |
||||
|
--container-3xl: 48rem; |
||||
|
--container-4xl: 56rem; |
||||
|
--container-5xl: 64rem; |
||||
|
--container-6xl: 72rem; |
||||
|
--container-7xl: 80rem; |
||||
|
|
||||
|
--text-xs: 0.32rem; |
||||
|
--text-xs--line-height: calc(1 / 0.32); |
||||
|
--text-sm: 0.373rem; |
||||
|
--text-sm--line-height: calc(1.25 / 0.373); |
||||
|
--text-base: 0.427rem; |
||||
|
--text-base--line-height: calc(1.5 / 0.427); |
||||
|
--text-lg: 0.48rem; |
||||
|
--text-lg--line-height: calc(1.75 / 0.48); |
||||
|
--text-xl: 0.533rem; |
||||
|
--text-xl--line-height: calc(1.75 / 0.533); |
||||
|
/* --text-2xl: 1.5rem; |
||||
|
--text-2xl--line-height: calc(2 / 1.5); |
||||
|
--text-3xl: 1.875rem; |
||||
|
--text-3xl--line-height: calc(2.25 / 1.875); |
||||
|
--text-4xl: 2.25rem; |
||||
|
--text-4xl--line-height: calc(2.5 / 2.25); |
||||
|
--text-5xl: 3rem; |
||||
|
--text-5xl--line-height: 1; |
||||
|
--text-6xl: 3.75rem; |
||||
|
--text-6xl--line-height: 1; |
||||
|
--text-7xl: 4.5rem; |
||||
|
--text-7xl--line-height: 1; |
||||
|
--text-8xl: 6rem; |
||||
|
--text-8xl--line-height: 1; |
||||
|
--text-9xl: 8rem; |
||||
|
--text-9xl--line-height: 1; */ |
||||
|
} |
||||
|
|
||||
|
#app { |
||||
|
font-size: 14px; |
||||
|
} |
After Width: | Height: | Size: 496 B |
@ -0,0 +1,21 @@ |
|||||
|
<template> |
||||
|
<div class="p-4 space-x-2"> |
||||
|
<button @click="toggleDark" class="px-4 py-2 rounded bg-white dark:bg-black"> |
||||
|
{{ isDark ? '亮色模式' : '暗黑模式' }} |
||||
|
</button> |
||||
|
|
||||
|
<button @click="setTheme('theme-red')" class="px-4 py-2 rounded bg-primary bg-mint-500 bg-primary"> |
||||
|
红色主题 |
||||
|
</button> |
||||
|
|
||||
|
<button @click="setTheme('theme-green')" class="px-4 py-2 rounded bg-primary"> |
||||
|
绿色主题 |
||||
|
</button> |
||||
|
</div> |
||||
|
</template> |
||||
|
|
||||
|
<script setup lang="ts"> |
||||
|
import { useThemeStore } from '@/stores/theme' |
||||
|
|
||||
|
const { isDark, toggleDark, setTheme } = useThemeStore() |
||||
|
</script> |
@ -0,0 +1,10 @@ |
|||||
|
import { createApp } from "vue"; |
||||
|
import { createPinia } from "pinia"; |
||||
|
import "@/assets/main.css"; |
||||
|
import App from "./App.vue"; |
||||
|
|
||||
|
const pinia = createPinia(); |
||||
|
const app = createApp(App); |
||||
|
|
||||
|
app.use(pinia); |
||||
|
app.mount("#app"); |
@ -0,0 +1,51 @@ |
|||||
|
import { defineStore } from "pinia"; |
||||
|
import { ref } from "vue"; |
||||
|
|
||||
|
export const useThemeStore = defineStore("theme", () => { |
||||
|
const isDark = ref(false); |
||||
|
const themeClass = ref(""); // 主题色 class,比如 'theme-red'
|
||||
|
|
||||
|
function initTheme() { |
||||
|
const systemPrefersDark = window.matchMedia( |
||||
|
"(prefers-color-scheme: dark)" |
||||
|
).matches; |
||||
|
if ( |
||||
|
localStorage.theme === "dark" || |
||||
|
(!("theme" in localStorage) && systemPrefersDark) |
||||
|
) { |
||||
|
isDark.value = true; |
||||
|
document.documentElement.classList.add("dark"); |
||||
|
} else { |
||||
|
isDark.value = false; |
||||
|
document.documentElement.classList.remove("dark"); |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
function toggleDark() { |
||||
|
isDark.value = !isDark.value; |
||||
|
localStorage.theme = isDark.value ? "dark" : "light"; |
||||
|
if (isDark.value) { |
||||
|
document.documentElement.classList.add("dark"); |
||||
|
} else { |
||||
|
document.documentElement.classList.remove("dark"); |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
function setTheme(theme: string) { |
||||
|
themeClass.value = theme; |
||||
|
const html = document.documentElement; |
||||
|
|
||||
|
// 移除以前的 theme-xxx 类
|
||||
|
html.classList.forEach((cls) => { |
||||
|
if (cls.startsWith("theme-")) { |
||||
|
html.classList.remove(cls); |
||||
|
} |
||||
|
}); |
||||
|
// 加上新的
|
||||
|
if (theme) { |
||||
|
html.classList.add(theme); |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
return { isDark, themeClass, toggleDark, setTheme, initTheme }; |
||||
|
}); |
@ -0,0 +1 @@ |
|||||
|
/// <reference types="vite/client" />
|
@ -0,0 +1,18 @@ |
|||||
|
{ |
||||
|
"extends": "@vue/tsconfig/tsconfig.dom.json", |
||||
|
"compilerOptions": { |
||||
|
"tsBuildInfoFile": "./node_modules/.tmp/tsconfig.app.tsbuildinfo", |
||||
|
|
||||
|
/* Linting */ |
||||
|
"strict": true, //开启所有严格检查模式 |
||||
|
"noUnusedLocals": true, //不能有没用到的局部变量 |
||||
|
"noUnusedParameters": true, // 不能有没用到的函数参数 |
||||
|
"noFallthroughCasesInSwitch": true, //switch 语句必须用 break 或 return |
||||
|
"noUncheckedSideEffectImports": true, //禁止直接导入有副作用的模块(除非显式标注) |
||||
|
"baseUrl": "./", |
||||
|
"paths": { |
||||
|
"@/*": ["src/*"] |
||||
|
} |
||||
|
}, |
||||
|
"include": ["src/**/*.ts", "src/**/*.tsx", "src/**/*.vue"] |
||||
|
} |
@ -0,0 +1,7 @@ |
|||||
|
{ |
||||
|
"files": [], |
||||
|
"references": [ |
||||
|
{ "path": "./tsconfig.app.json" }, |
||||
|
{ "path": "./tsconfig.node.json" } |
||||
|
] |
||||
|
} |
@ -0,0 +1,24 @@ |
|||||
|
{ |
||||
|
"compilerOptions": { |
||||
|
"tsBuildInfoFile": "./node_modules/.tmp/tsconfig.node.tsbuildinfo", |
||||
|
"target": "ES2022", |
||||
|
"lib": ["ES2023"], |
||||
|
"module": "ESNext", |
||||
|
"skipLibCheck": true, |
||||
|
|
||||
|
/* Bundler mode */ |
||||
|
"moduleResolution": "bundler", |
||||
|
"allowImportingTsExtensions": true, |
||||
|
"isolatedModules": true, |
||||
|
"moduleDetection": "force", |
||||
|
"noEmit": true, |
||||
|
|
||||
|
/* Linting */ |
||||
|
"strict": true, |
||||
|
"noUnusedLocals": true, |
||||
|
"noUnusedParameters": true, |
||||
|
"noFallthroughCasesInSwitch": true, |
||||
|
"noUncheckedSideEffectImports": true |
||||
|
}, |
||||
|
"include": ["vite.config.ts"] |
||||
|
} |
@ -0,0 +1,26 @@ |
|||||
|
import { defineConfig } from "vite"; |
||||
|
import vue from "@vitejs/plugin-vue"; |
||||
|
import tailwindcss from "@tailwindcss/vite"; |
||||
|
import path from "path"; |
||||
|
import AutoImport from "unplugin-auto-import/vite"; |
||||
|
import Components from "unplugin-vue-components/vite"; |
||||
|
import { VantResolver } from "@vant/auto-import-resolver"; |
||||
|
|
||||
|
// https://vite.dev/config/
|
||||
|
export default defineConfig({ |
||||
|
plugins: [ |
||||
|
vue(), |
||||
|
tailwindcss(), |
||||
|
AutoImport({ |
||||
|
resolvers: [VantResolver()], |
||||
|
}), |
||||
|
Components({ |
||||
|
resolvers: [VantResolver()], |
||||
|
}), |
||||
|
], |
||||
|
resolve: { |
||||
|
alias: { |
||||
|
"@": path.resolve(__dirname, "src"), |
||||
|
}, |
||||
|
}, |
||||
|
}); |
Loading…
Reference in new issue