├── .editorconfig ├── .github └── workflows │ └── deploy.yml ├── .gitignore ├── .vscode ├── extensions.json └── settings.json ├── content ├── .vitepress │ ├── config.mts │ └── theme │ │ ├── components │ │ ├── ActionButtons.vue │ │ ├── DocFooter.vue │ │ ├── Footer.vue │ │ ├── GithubCounterBtn.vue │ │ ├── SocialLinks.vue │ │ ├── SubscribeAlert.vue │ │ ├── SubscribeForm.vue │ │ └── VueThemesCallOut.vue │ │ ├── custom.scss │ │ ├── index.ts │ │ └── tailwind.css ├── changelog.md ├── contributing.md ├── index.md ├── pinia │ └── basic.md ├── public │ ├── brand-logo-small-dark.png │ ├── brand-logo-small-light.png │ ├── google6f658ffc1e5996cb.html │ ├── hero-image.png │ ├── hero.png │ ├── logos │ │ ├── android-icon-192x192.png │ │ ├── apple-icon-114x114.png │ │ ├── apple-icon-120x120.png │ │ ├── apple-icon-144x144.png │ │ ├── apple-icon-152x152.png │ │ ├── apple-icon-180x180.png │ │ ├── apple-icon-57x57.png │ │ ├── apple-icon-60x60.png │ │ ├── apple-icon-72x72.png │ │ ├── apple-icon-76x76.png │ │ ├── favicon-16x16.png │ │ ├── favicon-32x32.png │ │ ├── favicon-96x96.png │ │ ├── favicon.ico │ │ └── manifest.json │ ├── pinia-logo.png │ ├── robots.txt │ ├── vue-cheatsheet-logo.png │ ├── vue-logo.png │ └── vue-router-logo.png ├── vue-router │ ├── advanced.md │ └── basic.md └── vue │ ├── basic.md │ ├── built-in-components.md │ ├── component.md │ ├── composable.md │ ├── forms.md │ └── reactivity.md ├── package.json ├── pnpm-lock.yaml ├── postcss.config.js ├── readme.md ├── shims.d.ts ├── tailwind.config.js └── tsconfig.json /.editorconfig: -------------------------------------------------------------------------------- 1 | # EditorConfig is awesome: https://EditorConfig.org 2 | 3 | # top-most EditorConfig file 4 | root = true 5 | 6 | # Unix-style newlines with a newline ending every file 7 | [*] 8 | end_of_line = lf 9 | insert_final_newline = true 10 | 11 | # Matches multiple files with brace expansion notation 12 | # Set default charset 13 | [*.{js,py}] 14 | charset = utf-8 15 | 16 | # 4 space indentation 17 | [*.py] 18 | indent_style = space 19 | indent_size = 4 20 | 21 | # Tab indentation (no size specified) 22 | [Makefile] 23 | indent_style = tab 24 | 25 | # Indentation override for all JS under lib directory 26 | [lib/**.js] 27 | indent_style = space 28 | indent_size = 2 29 | 30 | # Matches the exact files either package.json or .travis.yml 31 | [{package.json,.travis.yml}] 32 | indent_style = space 33 | indent_size = 2 -------------------------------------------------------------------------------- /.github/workflows/deploy.yml: -------------------------------------------------------------------------------- 1 | name: Deploy - Documentation 2 | run-name: 🚀 Deploy 3 | 4 | on: 5 | workflow_dispatch: 6 | push: 7 | branches: 8 | - main 9 | 10 | jobs: 11 | deployment: 12 | runs-on: ubuntu-latest 13 | steps: 14 | - name: ⚙️ Setup pnpm 15 | uses: pnpm/action-setup@v2 16 | with: 17 | version: 8 18 | 19 | - name: ⬇️ Checkout repo 20 | uses: actions/checkout@v3 21 | 22 | - name: 📦 Build 23 | run: | 24 | pnpm i 25 | pnpm build 26 | mv content/.vitepress/dist content/.vitepress/html 27 | 28 | - name: 🚀 Upload 29 | uses: appleboy/scp-action@master 30 | with: 31 | HOST: ${{ secrets.HOST }} 32 | USERNAME: ${{ secrets.USERNAME }} 33 | PORT: ${{ secrets.PORT }} 34 | KEY: ${{ secrets.SSHKEY }} 35 | source: content/.vitepress/html 36 | target: ${{ secrets.TARGET_DIR }} 37 | strip_components: 3 38 | rm: true 39 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | lerna-debug.log* 8 | .pnpm-debug.log* 9 | 10 | # Diagnostic reports (https://nodejs.org/api/report.html) 11 | report.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json 12 | 13 | # Runtime data 14 | pids 15 | *.pid 16 | *.seed 17 | *.pid.lock 18 | 19 | # Directory for instrumented libs generated by jscoverage/JSCover 20 | lib-cov 21 | 22 | # Coverage directory used by tools like istanbul 23 | coverage 24 | *.lcov 25 | 26 | # nyc test coverage 27 | .nyc_output 28 | 29 | # Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files) 30 | .grunt 31 | 32 | # Bower dependency directory (https://bower.io/) 33 | bower_components 34 | 35 | # node-waf configuration 36 | .lock-wscript 37 | 38 | # Compiled binary addons (https://nodejs.org/api/addons.html) 39 | build/Release 40 | 41 | # Dependency directories 42 | node_modules/ 43 | jspm_packages/ 44 | 45 | # Snowpack dependency directory (https://snowpack.dev/) 46 | web_modules/ 47 | 48 | # TypeScript cache 49 | *.tsbuildinfo 50 | 51 | # Optional npm cache directory 52 | .npm 53 | 54 | # Optional eslint cache 55 | .eslintcache 56 | 57 | # Optional stylelint cache 58 | .stylelintcache 59 | 60 | # Microbundle cache 61 | .rpt2_cache/ 62 | .rts2_cache_cjs/ 63 | .rts2_cache_es/ 64 | .rts2_cache_umd/ 65 | 66 | # Optional REPL history 67 | .node_repl_history 68 | 69 | # Output of 'npm pack' 70 | *.tgz 71 | 72 | # Yarn Integrity file 73 | .yarn-integrity 74 | 75 | # dotenv environment variable files 76 | .env 77 | .env.development.local 78 | .env.test.local 79 | .env.production.local 80 | .env.local 81 | 82 | # parcel-bundler cache (https://parceljs.org/) 83 | .cache 84 | .parcel-cache 85 | 86 | # Next.js build output 87 | .next 88 | out 89 | 90 | # Nuxt.js build / generate output 91 | .nuxt 92 | dist 93 | 94 | # Gatsby files 95 | .cache/ 96 | # Comment in the public line in if your project uses Gatsby and not Next.js 97 | # https://nextjs.org/blog/next-9-1#public-directory-support 98 | # public 99 | 100 | # vuepress build output 101 | .vuepress/dist 102 | 103 | # vuepress v2.x temp and cache directory 104 | .temp 105 | .cache 106 | 107 | # Docusaurus cache and generated files 108 | .docusaurus 109 | 110 | # Serverless directories 111 | .serverless/ 112 | 113 | # FuseBox cache 114 | .fusebox/ 115 | 116 | # DynamoDB Local files 117 | .dynamodb/ 118 | 119 | # TernJS port file 120 | .tern-port 121 | 122 | # Stores VSCode versions used for testing VSCode extensions 123 | .vscode-test 124 | 125 | # yarn v2 126 | .yarn/cache 127 | .yarn/unplugged 128 | .yarn/build-state.yml 129 | .yarn/install-state.gz 130 | .pnp.* 131 | 132 | # 👉 Custom 133 | 134 | **/.vitepress/cache -------------------------------------------------------------------------------- /.vscode/extensions.json: -------------------------------------------------------------------------------- 1 | { 2 | "recommendations": [ 3 | "davidanson.vscode-markdownlint", 4 | "editorconfig.editorconfig", 5 | "streetsidesoftware.code-spell-checker", 6 | "xabikos.javascriptsnippets", 7 | "dbaeumer.vscode-eslint", 8 | "matijao.vue-nuxt-snippets", 9 | "vue.volar" 10 | ] 11 | } -------------------------------------------------------------------------------- /.vscode/settings.json: -------------------------------------------------------------------------------- 1 | { 2 | // JSON 3 | "[json]": { 4 | "editor.defaultFormatter": "vscode.json-language-features" 5 | }, 6 | "[jsonc]": { 7 | "editor.defaultFormatter": "vscode.json-language-features" 8 | }, 9 | // Markdown 10 | "[markdown]": { 11 | "editor.defaultFormatter": "DavidAnson.vscode-markdownlint", 12 | "markdown.validate.enabled": true, 13 | "markdown.occurrencesHighlight.enabled": true, 14 | }, 15 | "markdown.styles": [ 16 | "https://cdn.jsdelivr.net/gh/sindresorhus/github-markdown-css/github-markdown-dark.css", 17 | "https://cdn.jsdelivr.net/gh/elegantech/github-markdown-css@transparent/github-markdown-with-transparent-background.min.css" 18 | ], 19 | "markdown.editor.pasteUrlAsFormattedLink.enabled": "smart", 20 | "emmet.includeLanguages": { 21 | "markdown": "html", 22 | }, 23 | "commentAnchors.tagHighlights.enabled": false, 24 | } -------------------------------------------------------------------------------- /content/.vitepress/config.mts: -------------------------------------------------------------------------------- 1 | import { fileURLToPath, URL } from 'node:url' 2 | import { defineConfig } from 'vitepress' 3 | 4 | const isDev = process.env.NODE_ENV !== 'production' 5 | 6 | const gtmConfig = { 7 | headScript: ` 8 | 13 | `, 14 | bodyNoScript: ` 15 | 17 | `, 18 | } 19 | 20 | // https://vitepress.dev/reference/site-config 21 | export default defineConfig({ 22 | lang: 'en-US', 23 | title: 'Vue Cheatsheet By ThemeSelection', 24 | lastUpdated: true, 25 | description: "The one and only Vue cheatsheet you need for VueJS by ThemeSelection", 26 | head: [ 27 | ['link', { rel: 'icon', href: '/logos/favicon.ico' }], 28 | ['link', { rel: 'apple-touch-icon', href: '/logos/apple-icon-57x57.png' }], 29 | ['link', { rel: 'apple-touch-icon', href: '/logos/apple-icon-60x60.png' }], 30 | ['link', { rel: 'apple-touch-icon', href: '/logos/apple-icon-72x72.png' }], 31 | ['link', { rel: 'apple-touch-icon', href: '/logos/apple-icon-76x76.png' }], 32 | ['link', { rel: 'apple-touch-icon', href: '/logos/apple-icon-114x114.png' }], 33 | ['link', { rel: 'apple-touch-icon', href: '/logos/apple-icon-120x120.png' }], 34 | ['link', { rel: 'apple-touch-icon', href: '/logos/apple-icon-144x144.png' }], 35 | ['link', { rel: 'apple-touch-icon', href: '/logos/apple-icon-152x152.png' }], 36 | ['link', { rel: 'apple-touch-icon', href: '/logos/apple-icon-180x180.png' }], 37 | ['link', { rel: 'icon', href: '/logos/android-icon-192x192.png' }], 38 | ['link', { rel: 'icon', href: '/logos/favicon-32x32.png' }], 39 | ['link', { rel: 'icon', href: '/logos/favicon-96x96.png' }], 40 | ['link', { rel: 'icon', href: '/logos/favicon-16x16.png' }], 41 | ['link', { rel: 'manifest', href: '/logos/manifest.json' }], 42 | ['meta', { property: 'og:title', content: 'Vue Cheatsheet' }], 43 | ['meta', { property: 'og:description', content: 'The only VueJS cheatsheet you will ever need' }], 44 | ['meta', { property: 'og:image', content: 'https://ts-assets.b-cdn.net/ts-assets/vue-cheatsheet/github-banner-smm.png' }], 45 | ['meta', { property: 'twitter:image', content: 'https://ts-assets.b-cdn.net/ts-assets/vue-cheatsheet/github-banner-smm.png' }], 46 | ['meta', { property: 'twitter:title', content: 'Vue.js CheatSheet By ThemeSelection' }], 47 | ['meta', { property: 'twitter:description', content: 'Accelerate your vue learning & improve your skills with our comprehensive Vue 3 cheatsheet.' }], 48 | ['meta', { property: 'twitter:card', content: 'summary_large_image' }], 49 | ['meta', { property: 'twitter:site', content: '@Theme_Selection' }], 50 | ['meta', { property: 'twitter:creator', content: '@Theme_Selection' }], 51 | ['meta', { property: 'keywords', content: 'Vue 3 Cheatsheet, VueJS Cheatsheet, Vue JS Cheatsheet' }], 52 | ['meta', { property: 'google-site-verification', content: 'Eb4Y887SF6gMOy33YpMZEZLJuVfQHW9E3b8QjoSTDhw' }], 53 | ['script', { src: 'https://buttons.github.io/buttons.js' }] 54 | ], 55 | themeConfig: { 56 | logo: { src: '/vue-cheatsheet-logo.png', alt: 'Vue Cheatsheet' }, 57 | 58 | siteTitle: 'Vue Cheatsheet', 59 | search: { 60 | provider: 'local', 61 | options: { 62 | detailedView: true, 63 | }, 64 | }, 65 | // https://vitepress.dev/reference/default-theme-config 66 | nav: [ 67 | { text: 'Home', link: '/' }, 68 | { text: 'Freebies', link: 'https://themeselection.com/item/category/freebies/' }, 69 | { text: 'Templates', link: 'https://themeselection.com/item/category/admin-templates/' }, 70 | { text: 'UI Kits', link: 'https://themeselection.com/item/category/ui-kits/' }, 71 | ], 72 | 73 | sidebar: [ 74 | { 75 | text: 'Introduction', 76 | items: [ 77 | { text: 'Contributing', link: '/contributing' }, 78 | { text: 'Changelog', link: '/changelog' }, 79 | ], 80 | }, 81 | { 82 | text: 'Vue', 83 | items: [ 84 | { text: 'Basic', link: '/vue/basic.md' }, 85 | { text: 'Reactivity', link: '/vue/reactivity' }, 86 | { text: 'Forms', link: '/vue/forms' }, 87 | { text: 'Component', link: '/vue/component' }, 88 | { text: 'Composable', link: '/vue/composable' }, 89 | { text: 'Built-in Components', link: '/vue/built-in-components' }, 90 | ] 91 | }, 92 | { 93 | text: 'Vue Router', 94 | items: [ 95 | { text: 'Basic', link: '/vue-router/basic.md' }, 96 | { text: 'Advanced', link: '/vue-router/advanced.md' }, 97 | ] 98 | }, 99 | { 100 | text: 'Pinia', 101 | items: [ 102 | { text: 'Basic', link: '/pinia/basic.md' }, 103 | ] 104 | } 105 | ], 106 | 107 | socialLinks: [ 108 | { icon: 'twitter', link: 'https://twitter.com/Theme_Selection' } 109 | ], 110 | 111 | editLink: { 112 | pattern: 'https://github.com/themeselection/vue-cheatsheet/edit/main/content/:path' 113 | } 114 | }, 115 | vite: { 116 | resolve: { 117 | alias: [ 118 | { 119 | find: /^.*\/VPFooter\.vue$/, 120 | replacement: fileURLToPath( 121 | new URL('./theme/components/Footer.vue', import.meta.url) 122 | ) 123 | } 124 | ] 125 | } 126 | }, 127 | markdown: { 128 | // ℹ️ We only enabled this in development so that we can highlight code lines by seeing line number without calculating it in our editor. 129 | lineNumbers: false, 130 | toc: { level: [1, 2,] }, 131 | 132 | theme: { 133 | light: 'github-light', 134 | dark: 'dracula' 135 | }, 136 | math: true, 137 | }, 138 | transformHtml: async (code, id, ctx) => { 139 | return code 140 | .replace('
', `\n${gtmConfig.headScript}`) 141 | .replace('', `\n${gtmConfig.bodyNoScript}`) 142 | } 143 | }) 144 | -------------------------------------------------------------------------------- /content/.vitepress/theme/components/ActionButtons.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 |You have successfully subscribed to our newsletter 12 |
13 |Subscribe to our newsletter 6 |
7 |A weekly latest Articles, UI Kits, Free & Premium Resources.
8 | 21 | 22 | -------------------------------------------------------------------------------- /content/.vitepress/theme/components/VueThemesCallOut.vue: -------------------------------------------------------------------------------- 1 | 4 | 5 | 6 |✨ Supercharge your development process with our free & premium Vue js admin templates
10 |Double count is {{ store.doubleCount }}
161 | 162 | ``` 163 | 164 | ### Accessing Other Getters 165 | 166 | ```js 167 | export const useCounterStore = defineStore('counter', () => { 168 | 169 | const count = ref(0) 170 | const doubleCount = computed(() => count.value * 2) 171 | 172 | const doubleCountPlusOne = computed(() => doubleCount.value + 1) // [!code hl] 173 | 174 | return { count, doubleCount, doubleCountPlusOne} 175 | }) 176 | ``` 177 | 178 | ### Accessing Other Store Getters 179 | 180 | ```js 181 | import { useOtherStore } from './other-store' 182 | 183 | export const useStore = defineStore('main', { 184 | 185 | const otherGetter = computed(() => { 186 | const otherStore = useOtherStore() 187 | return state.localData + otherStore.data 188 | }) 189 | }) 190 | ``` 191 | 192 | ## Store methods aka Actions 193 | 194 | Actions are the equivalent of methods in components. 195 | 196 | ### Defining an action 197 | 198 | ```js 199 | export const useCounterStore = defineStore('counter', () => { 200 | 201 | const count = ref(0) 202 | 203 | function increment() { // [!code hl] 204 | count.value++ // [!code hl] 205 | } // [!code hl] 206 | 207 | return { count, increment } 208 | }) 209 | ``` 210 | 211 | ### Accessing Actions 212 | 213 | ```vue 214 | 219 | 220 | 221 | 222 | 223 | ``` 224 | 225 | ### Accessing other store actions 226 | 227 | ```js 228 | import { useAuthStore } from './auth-store' 229 | 230 | export const useSettingsStore = defineStore('settings', { 231 | 232 | const preferences = ref([]) 233 | 234 | const fetchPreferences = () => { 235 | const auth = useAuthStore() 236 | 237 | if(auth.isAuthenticated) 238 | preferences = await fetchPreferences() 239 | else 240 | throw new Error('User must be authenticated') 241 | } 242 | 243 | }) 244 | ``` 245 | 246 | ## Plugin 247 | 248 | A Pinia plugin is a function that optionally returns properties to be added to a store. It takes one optional argument, a context: 249 | 250 | ```js 251 | export function myPiniaPlugin(context) { 252 | context.pinia // the pinia created with `createPinia()` 253 | context.app // the current app created with `createApp()` (Vue 3 only) 254 | context.store // the store the plugin is augmenting 255 | context.options // the options object defining the store passed to `defineStore()` 256 | // ... 257 | } 258 | 259 | pinia.use(myPiniaPlugin) 260 | ``` 261 | 262 | ```js 263 | import { markRaw } from 'vue' 264 | // adapt this based on where your router is 265 | import { router } from './router' 266 | 267 | pinia.use(() => ({ hello: 'world' })) 268 | 269 | pinia.use(({ store }) => { 270 | store.router = markRaw(router) 271 | }) 272 | 273 | pinia.use(({ store }) => { 274 | store.$subscribe(() => { 275 | // react to store changes 276 | }) 277 | store.$onAction(() => { 278 | // react to store actions 279 | }) 280 | }) 281 | ``` 282 | -------------------------------------------------------------------------------- /content/public/brand-logo-small-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/brand-logo-small-dark.png -------------------------------------------------------------------------------- /content/public/brand-logo-small-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/brand-logo-small-light.png -------------------------------------------------------------------------------- /content/public/google6f658ffc1e5996cb.html: -------------------------------------------------------------------------------- 1 | google-site-verification: google6f658ffc1e5996cb.html -------------------------------------------------------------------------------- /content/public/hero-image.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/hero-image.png -------------------------------------------------------------------------------- /content/public/hero.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/hero.png -------------------------------------------------------------------------------- /content/public/logos/android-icon-192x192.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/android-icon-192x192.png -------------------------------------------------------------------------------- /content/public/logos/apple-icon-114x114.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/apple-icon-114x114.png -------------------------------------------------------------------------------- /content/public/logos/apple-icon-120x120.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/apple-icon-120x120.png -------------------------------------------------------------------------------- /content/public/logos/apple-icon-144x144.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/apple-icon-144x144.png -------------------------------------------------------------------------------- /content/public/logos/apple-icon-152x152.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/apple-icon-152x152.png -------------------------------------------------------------------------------- /content/public/logos/apple-icon-180x180.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/apple-icon-180x180.png -------------------------------------------------------------------------------- /content/public/logos/apple-icon-57x57.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/apple-icon-57x57.png -------------------------------------------------------------------------------- /content/public/logos/apple-icon-60x60.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/apple-icon-60x60.png -------------------------------------------------------------------------------- /content/public/logos/apple-icon-72x72.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/apple-icon-72x72.png -------------------------------------------------------------------------------- /content/public/logos/apple-icon-76x76.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/apple-icon-76x76.png -------------------------------------------------------------------------------- /content/public/logos/favicon-16x16.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/favicon-16x16.png -------------------------------------------------------------------------------- /content/public/logos/favicon-32x32.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/favicon-32x32.png -------------------------------------------------------------------------------- /content/public/logos/favicon-96x96.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/favicon-96x96.png -------------------------------------------------------------------------------- /content/public/logos/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/logos/favicon.ico -------------------------------------------------------------------------------- /content/public/logos/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "App", 3 | "icons": [ 4 | { 5 | "src": "\/android-icon-36x36.png", 6 | "sizes": "36x36", 7 | "type": "image\/png", 8 | "density": "0.75" 9 | }, 10 | { 11 | "src": "\/android-icon-48x48.png", 12 | "sizes": "48x48", 13 | "type": "image\/png", 14 | "density": "1.0" 15 | }, 16 | { 17 | "src": "\/android-icon-72x72.png", 18 | "sizes": "72x72", 19 | "type": "image\/png", 20 | "density": "1.5" 21 | }, 22 | { 23 | "src": "\/android-icon-96x96.png", 24 | "sizes": "96x96", 25 | "type": "image\/png", 26 | "density": "2.0" 27 | }, 28 | { 29 | "src": "\/android-icon-144x144.png", 30 | "sizes": "144x144", 31 | "type": "image\/png", 32 | "density": "3.0" 33 | }, 34 | { 35 | "src": "\/android-icon-192x192.png", 36 | "sizes": "192x192", 37 | "type": "image\/png", 38 | "density": "4.0" 39 | } 40 | ] 41 | } -------------------------------------------------------------------------------- /content/public/pinia-logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/pinia-logo.png -------------------------------------------------------------------------------- /content/public/robots.txt: -------------------------------------------------------------------------------- 1 | User-agent: * 2 | Disallow: 3 | -------------------------------------------------------------------------------- /content/public/vue-cheatsheet-logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/vue-cheatsheet-logo.png -------------------------------------------------------------------------------- /content/public/vue-logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/vue-logo.png -------------------------------------------------------------------------------- /content/public/vue-router-logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/themeselection/vue-cheatsheet/d36c2dc747aeabfe7cd9e462a9e2ef20f53d61c9/content/public/vue-router-logo.png -------------------------------------------------------------------------------- /content/vue-router/advanced.md: -------------------------------------------------------------------------------- 1 | # Advanced 2 | 3 | ## Scroll Behavior 4 | 5 | With client-side routing, we might want to scroll to the top on a new route, or keep the scroll position like a real page reload. 6 | 7 | ```ts 8 | const router = createRouter({ 9 | history: createWebHashHistory(), 10 | routes: [...], 11 | scrollBehavior (to, from, savedPosition) { 12 | // return desired position 13 | return { top : 0 } 14 | 15 | // always scroll 10px above the element #main 16 | return { el: '#main', top: 10 } 17 | 18 | // Returning the savedPosition 19 | return (savePosition ? savedPosition : { top : 0 }) 20 | 21 | // "scroll to anchor" behavior & "scroll behavior to smooth" 22 | if (to.hash) 23 | return { el: to.hash, behavior: 'smooth' } 24 | 25 | // Delaying the scroll 26 | return new Promise((resolve, reject) => { 27 | setTimeout(() => { 28 | resolve({ left: 0, top: 0 }) 29 | }, 500) 30 | }) 31 | } 32 | }) 33 | ``` 34 | 35 | ## Navigation Guards & Navigation Flow 36 | 37 | They are primarily used to guard navigations either by redirecting it or canceling it. 38 | 39 | 1. Navigation triggered. 40 | 2. Call `beforeRouteLeave` guards in deactivated components. 41 | 3. Call global `beforeEach` guards. 42 | 4. Call `beforeRouteUpdate` guards in reused components. 43 | 5. Call `beforeEnter` in route configs. 44 | 6. Resolve async route components. 45 | 7. Call `beforeRouteEnter` in activated components. 46 | 8. Call global `beforeResolve` guards. 47 | 9. Navigation is confirmed. 48 | 10. Call global `afterEach` hooks. 49 | 11. DOM updates triggered. 50 | 12. Call callbacks passed to `next` in `beforeRouteEnter` guards with instantiated instances. 51 | 52 | Every guard function receives two arguments: 53 | 54 | `to`: the target route location in a normalized format being navigated to. 55 | 56 | `from`: the current route location in a normalized format being navigated away from. 57 | 58 | ## RouterView slot 59 | 60 | The RouterView component exposes a slot that can be used to render the route component 61 | 62 | ```vue 63 | 64 |{{ msg }}
// [!code hl] 16 | 17 | 18 | // [!code hl] 19 | 20 | ``` 21 | 22 | ## Attribute Bindings 23 | 24 | ```vue 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | ``` 37 | 38 | ### Event Bindings 39 | 40 | ```vue 41 | 42 | 43 | 44 | 45 | 46 | ``` 47 | 48 | ::: info 49 | Furthermore, we'll exclusively use shorthand notation 50 | ::: 51 | 52 | ### Boolean Attributes 53 | 54 | ```vue 55 | 60 | 61 | 62 | // [!code hl] 63 | 64 | ``` 65 | 66 | ### Dynamically Binding Multiple Attributes 67 | 68 | ```vue 69 | 75 | 76 | 77 | 78 | // [!code hl] 79 | 80 | ``` 81 | 82 | ## Using JavaScript Expressions 83 | 84 | ```vue 85 | 94 | 95 | 96 | 97 | {{ number + 1 }} 98 | 99 | {{ ok ? 'YES' : 'NO' }} 100 | 101 | {{ message.split('').reverse().join('') }} 102 | 103 |hello
// Applied fade transition 20 |Current component: A
121 | count: {{ count }} 122 | 123 | 124 | ``` 125 | 126 | ```vue [CompB.vue] 127 | 132 | 133 | 134 |Current component: B
135 | Message is: 136 | 137 | 138 | ``` 139 | 140 | ::: 141 | 142 | [Try it in the Playground](https://play.vuejs.org/#eNqtU01vnDAQ/SuWL5sq6VIpN0RQlyiHtOqH0h65EJglToxt+YNuhfjvHdssYbf5kKLc8Jvn8XvzhoFulFr3DmhKM1NrpiwxYJ3KS0EI65TUlgzE3FWcyz83sCUj2WrZkRXeWS04l7JTm6m0TsLJtz2mFAeUYqJ4Ui2FsaR2WoOw5GLx5EmgfihFlkSFqA0PFjrFKwtBadawntS8MuaipA10sqQBxwqvboHnGRPKWWL/KkCGrhqGFNJ/7GQDHJHpYcTSvuLOk4IJBJKcbLIktnmPnkXsWRz1/AqgNpz10VCAamRL4eeRMm9sbphnyVzb308OG2QJjgS/smQxKHoWXb2euP4v6kVI0oWIkHPy6ZVcVH45RToLTv0443OZUZXIQ7+UDMPUeRxRfagEzq2zVgryueasfvBT8KTTU5zCtag1VAZwtRDKksh8xnRYtreb7kw7WV6t3uIZ4156/gbGVC0QZtIDs3GlHncInw2rfOzIGpS1Ze363kiBrgZ/28+mU4yD/qEsQ9klxbHG/Shp+J++BMxqB2d7vL6D+uEJ/N7sPFbSnxoM6B5KOtdspVvARfTlq1/fYYffcxG1O47sF4o3YCR3XmOkFU40KHvBC2qvQzJMtL/N1c6CMHtTXqhnjoFfUkzLZ/yc9Ue55+vzcK8UIx3/AY/eq8Q=) 143 | 144 | ## Teleport 145 | 146 | The `Hello from the modal!
152 | 153 |446 | Message to grand child: {{ message }} 447 |
448 | 449 | ``` 450 | 451 | ::: 452 | -------------------------------------------------------------------------------- /content/vue/composable.md: -------------------------------------------------------------------------------- 1 | # Composable 2 | 3 | A composable is a function that leverages Vue's Composition API to encapsulate and reuse stateful logic. 4 | 5 | ```ts 6 | // mouse.ts 7 | import { ref, onMounted, onUnmounted } from 'vue' 8 | 9 | // by convention, composable function names start with "use" 10 | export function useMouse() { 11 | // state encapsulated and managed by the composable 12 | const x = ref(0) 13 | const y = ref(0) 14 | 15 | // a composable can update its managed state over time. 16 | function update(event) { 17 | x.value = event.pageX 18 | y.value = event.pageY 19 | } 20 | 21 | // a composable can also hook into its owner component's 22 | // lifecycle to setup and teardown side effects. 23 | onMounted(() => window.addEventListener('mousemove', update)) 24 | onUnmounted(() => window.removeEventListener('mousemove', update)) 25 | 26 | // expose managed state as return value 27 | return { x, y } 28 | } 29 | ``` 30 | 31 | ## Convention & Best Practices 32 | 33 | ### Naming 34 | 35 | It is a convention to name composable functions with camelCase names that start with `use`. 36 | 37 | Example: `useMouse()` 38 | 39 | ### Input Arguments 40 | 41 | ```ts 42 | import { toValue } from 'vue' 43 | 44 | function useFeature(maybeRefOrGetter) { 45 | // If maybeRefOrGetter is a ref or a getter, 46 | // its normalized value will be returned. 47 | // Otherwise, it is returned as-is. 48 | const value = toValue(maybeRefOrGetter) 49 | } 50 | ``` 51 | 52 | ### Return values 53 | 54 | ```ts 55 | // x and y are refs 56 | const { x, y } = useMouse() 57 | ``` 58 | -------------------------------------------------------------------------------- /content/vue/forms.md: -------------------------------------------------------------------------------- 1 | # Form Input Bindings 2 | 3 | ## Basic form input 4 | 5 | ```vue 6 | 7 | 8 | {{ text }} 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 |Checked names:
{{ checkedNames }}22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | Picked: {{ picked }} 31 | 32 | 33 | 39 | Selected: {{ selected }} 40 | 41 | 42 | 47 | Selected: {{ multiSelected }} 48 | 49 | ``` 50 | 51 | [Try it in the Playground](https://play.vuejs.org/#eNq9VUtP4zAQ/iveXLorUcoutypEAsQBJB4CbmQPaTKlBse2bKeAqvz3nbHzRAW6Fy5tZuabxzf2jDfRsdb76wqieRTb3HDtmAVX6SSVvNTKOLZhBpasZkujSjZB6CSVqcyVtI45eHXsiAA/J2cFd6yEya/WmK8gf4aisTtTwXvTVVaCbewPk4ssf5787TCaD7wn13IQ2YKA3PXG495UVsLxu7H9AQEUN54FhsgNBQelFpkDlBiLV3+SeyJzLnXl4hmKXs1JZOtpqQoQR2lEhNMoYZtN4F7XFCv4nxKphXp97+3eNKCr54zmNGK8GMt9/KYxmMIHENkCBFsqM8KHTFDMqYy2y3Udzzzcs0PfH9Mp/bPQEi0gQDEC9jzPJFtwWTCnmFsBs3gSAZ0Zk721FbF1JipvmE67Pl1SPPafbJ/wcIkpxUORznobcX8jtrEP/gn59Ty/TKpWcpi0EXdP6h0S8ts9acmfYZD0shF3Thr8E/IbJdXtsTNJrnPUGEj6GxCGia4B6fG3vQh4PrdZwdUHJ2XI1hav5LB2HLpR6WEktxXt/RLEj0pemK/yuRf6bPPdB2mHfN4vQfzWfFZnMrnxzn5GmlVCvfGmvjFhU/SdCZtlUEK7apoiEKK040qygttsITBqWzwibgRkFocpBMGexLOAHvsmxx/oTz7Qn470SMInGHBtF55n223HLXzD7H7JerRF8Ui6FWLdmyCyL7xwq/nvgwNN++g72Y0X/IBiPOs2erQXOYvvwZI/7j9ZJfFx21A4HD5Vai7AXPuEOH8YM1STRpkQ6uXC6+ix2mv1fr626J8scp/jx40BC2aNE9DZXGYeAV8KMp/dXflXozNilyuB6E+Mt2CVqKjGADupZIFlD3C+2nP/RHP5eG/PXh1I25KiQglZe3wa4bN9+gn1vtzD/UPvl8o6qv8BvGa6DQ==) 52 | -------------------------------------------------------------------------------- /content/vue/reactivity.md: -------------------------------------------------------------------------------- 1 | # Reactivity 2 | 3 | ## `ref()` 4 | 5 | A ref will make its value deeply reactive. This means you can expect changes to be detected even when you mutate nested objects or arrays. 6 | 7 | ```ts 8 | const count = ref(0); 9 | 10 | console.log(count.value); // 0 11 | 12 | count.value = 10; // Will update the DOM as well 13 | 14 | console.log(count.value); // 10 15 | ``` 16 | 17 | ## `reactive()` 18 | 19 | Unlike a ref which wraps the inner value in a special object, reactive() makes an object itself reactive. 20 | 21 | ```ts 22 | const state = reactive({ count: 1 }); 23 | 24 | console.log(state); // {count: 1} 25 | console.log(state.count); // 1 26 | ``` 27 | 28 | ## `shallowRef()` 29 | 30 | The inner value of a `shallowRef` is stored and exposed as-is, and will not be made deeply reactive 31 | 32 | ```ts 33 | const state = shallowRef({ count: 1 }) 34 | 35 | // does NOT trigger change 36 | state.value.count = 2 37 | 38 | // does trigger change 39 | state.value = { count: 2 } 40 | ``` 41 | 42 | ## Computed Property 43 | 44 | ```vue 45 | 50 | 51 | 52 |
Original value: {{ value }}
54 |Computed value: {{ doubleValue }}
55 |