├── .prettierignore ├── .npmrc ├── src ├── tutorial │ ├── src │ │ ├── step-12 │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── _hint │ │ │ │ └── App │ │ │ │ │ └── template.html │ │ │ ├── ChildComp │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ └── description.md │ │ ├── step-1 │ │ │ └── App │ │ │ │ └── template.html │ │ ├── step-11 │ │ │ ├── _hint │ │ │ │ └── App │ │ │ │ │ ├── template.html │ │ │ │ │ ├── options.js │ │ │ │ │ └── composition.js │ │ │ ├── ChildComp │ │ │ │ └── template.html │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── composition.js │ │ │ │ └── options.js │ │ │ └── description.md │ │ ├── step-2 │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ └── _hint │ │ │ │ └── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── step-14 │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── ChildComp │ │ │ │ └── template.html │ │ │ ├── _hint │ │ │ │ └── App │ │ │ │ │ └── template.html │ │ │ └── description.md │ │ ├── step-13 │ │ │ ├── ChildComp │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── _hint │ │ │ │ └── App │ │ │ │ │ └── template.html │ │ │ └── description.md │ │ ├── step-3 │ │ │ ├── App │ │ │ │ ├── style.css │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── _hint │ │ │ │ └── App │ │ │ │ │ └── template.html │ │ │ └── description.md │ │ ├── step-9 │ │ │ ├── App │ │ │ │ ├── options.js │ │ │ │ ├── template.html │ │ │ │ └── composition.js │ │ │ └── _hint │ │ │ │ └── App │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── step-8 │ │ │ ├── App │ │ │ │ ├── style.css │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ └── _hint │ │ │ │ └── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── step-15 │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── style.css │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── import-map.json │ │ │ └── description.md │ │ ├── step-4 │ │ │ ├── _hint │ │ │ │ └── App │ │ │ │ │ ├── template.html │ │ │ │ │ ├── options.js │ │ │ │ │ └── composition.js │ │ │ └── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── step-5 │ │ │ ├── _hint │ │ │ │ └── App │ │ │ │ │ ├── template.html │ │ │ │ │ ├── options.js │ │ │ │ │ └── composition.js │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ └── description.md │ │ ├── step-6 │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── _hint │ │ │ │ └── App │ │ │ │ │ ├── template.html │ │ │ │ │ ├── options.js │ │ │ │ │ └── composition.js │ │ │ └── description.md │ │ ├── step-10 │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── _hint │ │ │ │ └── App │ │ │ │ │ ├── options.js │ │ │ │ │ └── composition.js │ │ │ └── description.md │ │ └── step-7 │ │ │ ├── App │ │ │ ├── template.html │ │ │ ├── options.js │ │ │ └── composition.js │ │ │ ├── _hint │ │ │ └── App │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ └── description.md │ ├── index.md │ └── tutorial.data.ts ├── examples │ ├── src │ │ ├── hello-world │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ └── description.txt │ │ ├── markdown │ │ │ ├── description.txt │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ ├── composition.js │ │ │ │ └── style.css │ │ │ └── import-map.json │ │ ├── svg │ │ │ ├── description.txt │ │ │ ├── AxisLabel │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── PolyGraph │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── util.js │ │ │ └── App │ │ │ │ ├── style.css │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── attribute-bindings │ │ │ ├── App │ │ │ │ ├── style.css │ │ │ │ ├── options.js │ │ │ │ ├── composition.js │ │ │ │ └── template.html │ │ │ └── description.txt │ │ ├── crud │ │ │ ├── description.txt │ │ │ └── App │ │ │ │ ├── style.css │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── simple-component │ │ │ ├── TodoItem │ │ │ │ ├── template.html │ │ │ │ ├── composition.js │ │ │ │ └── options.js │ │ │ ├── description.txt │ │ │ └── App │ │ │ │ ├── options.js │ │ │ │ ├── template.html │ │ │ │ └── composition.js │ │ ├── cells │ │ │ ├── description.txt │ │ │ ├── Cell │ │ │ │ ├── style.css │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── App │ │ │ │ ├── options.js │ │ │ │ ├── composition.js │ │ │ │ ├── template.html │ │ │ │ └── style.css │ │ │ └── store.js │ │ ├── counter │ │ │ ├── description.txt │ │ │ └── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── timer │ │ │ ├── description.txt │ │ │ └── App │ │ │ │ ├── style.css │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── circle-drawer │ │ │ ├── description.txt │ │ │ └── App │ │ │ │ ├── style.css │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── flight-booker │ │ │ ├── description.txt │ │ │ └── App │ │ │ │ ├── style.css │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── todomvc │ │ │ ├── App │ │ │ │ └── style.css │ │ │ └── description.txt │ │ ├── temperature-converter │ │ │ ├── description.txt │ │ │ └── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── modal │ │ │ ├── description.txt │ │ │ ├── Modal │ │ │ │ ├── options.js │ │ │ │ ├── composition.js │ │ │ │ ├── template.html │ │ │ │ └── style.css │ │ │ └── App │ │ │ │ ├── options.js │ │ │ │ ├── composition.js │ │ │ │ └── template.html │ │ ├── handling-input │ │ │ ├── App │ │ │ │ ├── style.css │ │ │ │ ├── options.js │ │ │ │ ├── composition.js │ │ │ │ └── template.html │ │ │ └── description.txt │ │ ├── tree │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── style.css │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ ├── description.txt │ │ │ └── TreeItem │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── grid │ │ │ ├── description.txt │ │ │ ├── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ │ └── Grid │ │ │ │ ├── template.html │ │ │ │ ├── style.css │ │ │ │ ├── options.js │ │ │ │ └── composition.js │ │ ├── form-bindings │ │ │ ├── description.txt │ │ │ └── App │ │ │ │ ├── options.js │ │ │ │ ├── composition.js │ │ │ │ └── template.html │ │ ├── list-transition │ │ │ ├── import-map.json │ │ │ ├── description.txt │ │ │ └── App │ │ │ │ ├── template.html │ │ │ │ ├── options.js │ │ │ │ ├── style.css │ │ │ │ └── composition.js │ │ ├── conditionals-and-loops │ │ │ ├── description.txt │ │ │ └── App │ │ │ │ ├── options.js │ │ │ │ ├── composition.js │ │ │ │ └── template.html │ │ └── fetching-data │ │ │ ├── description.txt │ │ │ └── App │ │ │ ├── style.css │ │ │ ├── template.html │ │ │ ├── options.js │ │ │ └── composition.js │ └── index.md ├── public │ ├── logo-uwu.png │ ├── images │ │ ├── logo.png │ │ ├── paypal.png │ │ └── partners │ │ │ ├── curotec.png │ │ │ ├── epicmax.png │ │ │ ├── herodevs.png │ │ │ ├── monterail.png │ │ │ ├── redberry.png │ │ │ ├── curotec-hero.jpg │ │ │ ├── jump24-hero.jpg │ │ │ ├── tighten-hero.jpg │ │ │ ├── vehikl-hero.jpg │ │ │ ├── webreinvent.png │ │ │ ├── 64robots-hero.jpg │ │ │ ├── herodevs-dark.png │ │ │ ├── herodevs-hero.png │ │ │ ├── monterail-dark.png │ │ │ ├── monterail-hero.png │ │ │ ├── redberry-hero.jpg │ │ │ ├── passionatepeople.png │ │ │ ├── webreinvent-hero.jpg │ │ │ ├── passionatepeople-dark.png │ │ │ ├── passionatepeople-hero.jpg │ │ │ ├── jump24.svg │ │ │ └── jump24-dark.svg │ ├── logo.svg │ ├── service-worker.js │ └── _headers ├── about │ ├── images │ │ ├── ben-hong.jpeg │ │ └── evan-you.jpeg │ ├── team.md │ └── team │ │ ├── Member.ts │ │ └── TeamHero.vue ├── guide │ ├── components │ │ └── images │ │ │ ├── slots.png │ │ │ ├── named-slots.png │ │ │ ├── prop-drilling.png │ │ │ └── provide-inject.png │ ├── extras │ │ ├── images │ │ │ ├── options-api.png │ │ │ ├── render-pipeline.png │ │ │ └── composition-api-after.png │ │ └── demos │ │ │ ├── Colors.vue │ │ │ ├── AnimateWatcher.vue │ │ │ ├── SpreadSheet.vue │ │ │ ├── spreadSheetStore.js │ │ │ ├── DisabledButton.vue │ │ │ └── SpreadSheetCell.vue │ ├── essentials │ │ └── images │ │ │ ├── components.png │ │ │ ├── directive.png │ │ │ └── lifecycle.png │ ├── scaling-up │ │ └── images │ │ │ └── state-flow.png │ ├── typescript │ │ └── images │ │ │ └── takeover-mode.png │ ├── built-ins │ │ ├── images │ │ │ └── transition-classes.png │ │ ├── keep-alive-demos │ │ │ ├── CompB.vue │ │ │ ├── CompA.vue │ │ │ └── SwitchComponent.vue │ │ └── transition-demos │ │ │ ├── Basic.vue │ │ │ ├── BetweenComponents.vue │ │ │ ├── SlideFade.vue │ │ │ ├── CssAnimation.vue │ │ │ ├── ListBasic.vue │ │ │ ├── JsHooks.vue │ │ │ ├── ListStagger.vue │ │ │ ├── BetweenElements.vue │ │ │ ├── ListMove.vue │ │ │ └── NestedTransitions.vue │ ├── best-practices │ │ └── images │ │ │ ├── AccessiblePlaceholder.png │ │ │ ├── AccessibleARIAdescribedby.png │ │ │ ├── AccessibleARIAlabelDevTools.png │ │ │ ├── AccessibleLabelChromeDevTools.png │ │ │ ├── AccessibleARIAlabelledbyDevTools.png │ │ │ └── AccessibilityChromeDeveloperTools.png │ └── reusability │ │ └── mouse.js ├── ecosystem │ ├── themes.md │ ├── newsletters.md │ └── themes │ │ ├── ThemePage.vue │ │ ├── ThemeList.vue │ │ ├── ThemeHero.vue │ │ ├── ThemeContact.vue │ │ └── ThemeProduct.vue ├── partners │ ├── all.md │ ├── index.md │ ├── [partnerId].md │ ├── [partnerId].paths.ts │ └── components │ │ ├── type.ts │ │ ├── utils.ts │ │ ├── PartnerLocation.vue │ │ ├── PartnerAll.vue │ │ ├── PartnerHero.vue │ │ └── PartnerJoin.vue ├── index.md ├── api │ └── index.md └── error-reference │ ├── errors.data.ts │ ├── ErrorsTable.vue │ └── index.md ├── .github ├── FUNDING.yml ├── pull_request_template.md ├── contributing │ └── oxford-comma.jpg ├── dependabot.yml ├── workflows │ ├── ryu-cho.yaml │ └── automerge.yml └── scripts │ └── tag-alert-blocks.js ├── .prettierrc ├── .vitepress ├── inlined-scripts │ ├── uwu.js │ ├── perfops.js │ └── restorePreference.js ├── theme │ ├── styles │ │ ├── index.css │ │ ├── utilities.css │ │ ├── pages.css │ │ ├── badges.css │ │ ├── options-boxes.css │ │ ├── style-guide.css │ │ ├── vue-mastery.css │ │ └── inline-demo.css │ ├── components │ │ ├── preferences.ts │ │ ├── sponsors.ts │ │ ├── TextAd.vue │ │ ├── ReplLoading.vue │ │ ├── VueSchoolLink.vue │ │ ├── SiteMap.vue │ │ ├── Banner.vue │ │ └── SecurityUpdateButton.vue │ └── index.ts ├── textAdMdPlugin.ts └── headerMdPlugin.ts ├── netlify.toml ├── .editorconfig ├── env.d.ts ├── tsconfig.json ├── vercel.json ├── package.json ├── README.md └── .gitignore /.prettierignore: -------------------------------------------------------------------------------- 1 | *.vue 2 | -------------------------------------------------------------------------------- /.npmrc: -------------------------------------------------------------------------------- 1 | package-manager-strict=false 2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-12/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /src/examples/src/hello-world/App/template.html: -------------------------------------------------------------------------------- 1 |

{{ message }}

-------------------------------------------------------------------------------- /src/tutorial/src/step-1/App/template.html: -------------------------------------------------------------------------------- 1 |

Hello World!

2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-11/_hint/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-2/App/template.html: -------------------------------------------------------------------------------- 1 |

Hello World!

2 | -------------------------------------------------------------------------------- /src/examples/src/markdown/description.txt: -------------------------------------------------------------------------------- 1 | Um editor de markdown simples. -------------------------------------------------------------------------------- /src/tutorial/src/step-14/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /src/examples/src/svg/description.txt: -------------------------------------------------------------------------------- 1 | Diga "Olá Mundo ou Hello World" com a Vue! -------------------------------------------------------------------------------- /src/tutorial/src/step-13/ChildComp/template.html: -------------------------------------------------------------------------------- 1 |

Child component

2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-3/App/style.css: -------------------------------------------------------------------------------- 1 | .title { 2 | color: red; 3 | } 4 | -------------------------------------------------------------------------------- /src/tutorial/src/step-9/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | // ... 3 | } 4 | -------------------------------------------------------------------------------- /src/tutorial/src/step-9/App/template.html: -------------------------------------------------------------------------------- 1 |

hello

2 | -------------------------------------------------------------------------------- /src/examples/src/attribute-bindings/App/style.css: -------------------------------------------------------------------------------- 1 | .red { 2 | color: red; 3 | } -------------------------------------------------------------------------------- /src/examples/src/crud/description.txt: -------------------------------------------------------------------------------- 1 | https://eugenkiss.github.io/7guis/tasks/#crud -------------------------------------------------------------------------------- /src/examples/src/simple-component/TodoItem/template.html: -------------------------------------------------------------------------------- 1 |
  • {{ todo.text }}
  • -------------------------------------------------------------------------------- /src/tutorial/src/step-11/ChildComp/template.html: -------------------------------------------------------------------------------- 1 |

    A Child Component!

    2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-12/_hint/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-14/ChildComp/template.html: -------------------------------------------------------------------------------- 1 | Fallback content 2 | -------------------------------------------------------------------------------- /src/examples/src/cells/description.txt: -------------------------------------------------------------------------------- 1 | https://eugenkiss.github.io/7guis/tasks/#cells -------------------------------------------------------------------------------- /src/examples/src/counter/description.txt: -------------------------------------------------------------------------------- 1 | https://eugenkiss.github.io/7guis/tasks/#counter -------------------------------------------------------------------------------- /src/examples/src/hello-world/description.txt: -------------------------------------------------------------------------------- 1 | Diga "Hello World ou Olá Mundo" com a Vue! -------------------------------------------------------------------------------- /src/examples/src/timer/description.txt: -------------------------------------------------------------------------------- 1 | https://eugenkiss.github.io/7guis/tasks/#timer -------------------------------------------------------------------------------- /src/tutorial/src/step-11/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-13/App/template.html: -------------------------------------------------------------------------------- 1 | 2 |

    {{ childMsg }}

    3 | -------------------------------------------------------------------------------- /src/examples/src/circle-drawer/description.txt: -------------------------------------------------------------------------------- 1 | https://eugenkiss.github.io/7guis/tasks/#circle -------------------------------------------------------------------------------- /src/examples/src/flight-booker/description.txt: -------------------------------------------------------------------------------- 1 | https://eugenkiss.github.io/7guis/tasks/#flight -------------------------------------------------------------------------------- /src/tutorial/src/step-3/_hint/App/template.html: -------------------------------------------------------------------------------- 1 |

    Make me red

    2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-8/App/style.css: -------------------------------------------------------------------------------- 1 | .done { 2 | text-decoration: line-through; 3 | } 4 | -------------------------------------------------------------------------------- /src/examples/src/todomvc/App/style.css: -------------------------------------------------------------------------------- 1 | @import "https://unpkg.com/todomvc-app-css@2.4.1/index.css"; -------------------------------------------------------------------------------- /src/tutorial/src/step-12/ChildComp/template.html: -------------------------------------------------------------------------------- 1 |

    {{ msg || 'No props passed yet' }}

    2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-14/_hint/App/template.html: -------------------------------------------------------------------------------- 1 | Message: {{ msg }} 2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-15/App/template.html: -------------------------------------------------------------------------------- 1 |

    🎉 Congratulations!

    2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-2/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | // opções do componente 3 | } 4 | -------------------------------------------------------------------------------- /src/examples/src/counter/App/template.html: -------------------------------------------------------------------------------- 1 | {{ count }} 2 | 3 | -------------------------------------------------------------------------------- /src/examples/src/svg/AxisLabel/template.html: -------------------------------------------------------------------------------- 1 | {{stat.label}} 2 | -------------------------------------------------------------------------------- /src/examples/src/temperature-converter/description.txt: -------------------------------------------------------------------------------- 1 | https://eugenkiss.github.io/7guis/tasks/#temp -------------------------------------------------------------------------------- /src/tutorial/src/step-11/App/composition.js: -------------------------------------------------------------------------------- 1 | export default { 2 | // registar o componente 3 | } 4 | -------------------------------------------------------------------------------- /src/tutorial/src/step-11/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | // registar o componente filho 3 | } 4 | -------------------------------------------------------------------------------- /src/examples/src/modal/description.txt: -------------------------------------------------------------------------------- 1 | Componente de Modal com ranhuras personalizáveis e transições de CSS. -------------------------------------------------------------------------------- /src/public/logo-uwu.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/logo-uwu.png -------------------------------------------------------------------------------- /.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | # There are the supported funding model platforms 2 | 3 | open_collective: nazarepiedady 4 | -------------------------------------------------------------------------------- /src/examples/src/handling-input/App/style.css: -------------------------------------------------------------------------------- 1 | button, a { 2 | display: block; 3 | margin-bottom: 1em; 4 | } -------------------------------------------------------------------------------- /src/examples/src/modal/Modal/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | props: { 3 | show: Boolean 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /src/tutorial/src/step-4/_hint/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /src/examples/src/modal/Modal/composition.js: -------------------------------------------------------------------------------- 1 | export default { 2 | props: { 3 | show: Boolean 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /src/examples/src/tree/App/template.html: -------------------------------------------------------------------------------- 1 |
      2 | 3 |
    4 | -------------------------------------------------------------------------------- /src/public/images/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/logo.png -------------------------------------------------------------------------------- /src/public/images/paypal.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/paypal.png -------------------------------------------------------------------------------- /src/tutorial/src/step-12/ChildComp/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | props: { 3 | msg: String 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /src/tutorial/src/step-2/_hint/App/template.html: -------------------------------------------------------------------------------- 1 |

    {{ message }}

    2 |

    Count is: {{ counter.count }}

    3 | -------------------------------------------------------------------------------- /src/about/images/ben-hong.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/about/images/ben-hong.jpeg -------------------------------------------------------------------------------- /src/about/images/evan-you.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/about/images/evan-you.jpeg -------------------------------------------------------------------------------- /src/tutorial/src/step-12/ChildComp/composition.js: -------------------------------------------------------------------------------- 1 | export default { 2 | props: { 3 | msg: String 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /src/tutorial/src/step-3/App/template.html: -------------------------------------------------------------------------------- 1 | 2 |

    Make me red

    3 | -------------------------------------------------------------------------------- /src/tutorial/src/step-4/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | -------------------------------------------------------------------------------- /src/tutorial/src/step-5/_hint/App/template.html: -------------------------------------------------------------------------------- 1 | 2 |

    {{ text }}

    3 | -------------------------------------------------------------------------------- /.prettierrc: -------------------------------------------------------------------------------- 1 | { 2 | "semi": false, 3 | "singleQuote": true, 4 | "trailingComma": "none", 5 | "printWidth": 75 6 | } 7 | -------------------------------------------------------------------------------- /src/examples/src/simple-component/TodoItem/composition.js: -------------------------------------------------------------------------------- 1 | export default { 2 | props: { 3 | todo: Object 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /src/examples/src/simple-component/TodoItem/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | props: { 3 | todo: Object 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /src/tutorial/src/step-13/_hint/App/template.html: -------------------------------------------------------------------------------- 1 | 2 |

    {{ childMsg }}

    3 | -------------------------------------------------------------------------------- /src/tutorial/src/step-15/App/style.css: -------------------------------------------------------------------------------- 1 | h1 { 2 | text-align: center; 3 | cursor: pointer; 4 | margin-top: 3em; 5 | } 6 | -------------------------------------------------------------------------------- /.github/pull_request_template.md: -------------------------------------------------------------------------------- 1 | ## Description of Problem 2 | 3 | ## Proposed Solution 4 | 5 | ## Additional Information 6 | 7 | -------------------------------------------------------------------------------- /src/examples/src/counter/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | count: 0 5 | } 6 | } 7 | } -------------------------------------------------------------------------------- /src/examples/src/grid/description.txt: -------------------------------------------------------------------------------- 1 | Um exemplo de criação de um componente de grade reutilizável e utilizando-o com dado externo. -------------------------------------------------------------------------------- /src/examples/src/handling-input/description.txt: -------------------------------------------------------------------------------- 1 | Este exemplo demonstra a manipulação da entrada do utilizador com a diretiva v-on. -------------------------------------------------------------------------------- /src/tutorial/src/step-5/App/template.html: -------------------------------------------------------------------------------- 1 | 2 |

    {{ text }}

    3 | -------------------------------------------------------------------------------- /.github/contributing/oxford-comma.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/.github/contributing/oxford-comma.jpg -------------------------------------------------------------------------------- /.vitepress/inlined-scripts/uwu.js: -------------------------------------------------------------------------------- 1 | if (location.search.includes('?uwu')) { 2 | document.documentElement.classList.add('uwu') 3 | } 4 | -------------------------------------------------------------------------------- /src/examples/src/tree/App/style.css: -------------------------------------------------------------------------------- 1 | .item { 2 | cursor: pointer; 3 | line-height: 1.5; 4 | } 5 | .bold { 6 | font-weight: bold; 7 | } -------------------------------------------------------------------------------- /src/guide/components/images/slots.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/components/images/slots.png -------------------------------------------------------------------------------- /src/public/images/partners/curotec.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/curotec.png -------------------------------------------------------------------------------- /src/public/images/partners/epicmax.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/epicmax.png -------------------------------------------------------------------------------- /src/tutorial/src/step-4/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | count: 0 5 | } 6 | } 7 | } 8 | -------------------------------------------------------------------------------- /src/tutorial/src/step-6/App/template.html: -------------------------------------------------------------------------------- 1 | 2 |

    Vue is awesome!

    3 |

    Oh no 😢

    4 | -------------------------------------------------------------------------------- /src/examples/src/todomvc/description.txt: -------------------------------------------------------------------------------- 1 | Uma implementação da TodoMVC completamente em conformidade com a especificação 2 | https://todomvc.com/ -------------------------------------------------------------------------------- /src/guide/extras/images/options-api.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/extras/images/options-api.png -------------------------------------------------------------------------------- /src/public/images/partners/herodevs.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/herodevs.png -------------------------------------------------------------------------------- /src/public/images/partners/monterail.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/monterail.png -------------------------------------------------------------------------------- /src/public/images/partners/redberry.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/redberry.png -------------------------------------------------------------------------------- /src/tutorial/src/step-5/_hint/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | text: '' 5 | } 6 | } 7 | } 8 | -------------------------------------------------------------------------------- /netlify.toml: -------------------------------------------------------------------------------- 1 | [build.environment] 2 | NODE_VERSION = "20" 3 | 4 | [build] 5 | publish = ".vitepress/dist" 6 | command = "pnpm run build" 7 | -------------------------------------------------------------------------------- /src/guide/components/images/named-slots.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/components/images/named-slots.png -------------------------------------------------------------------------------- /src/guide/essentials/images/components.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/essentials/images/components.png -------------------------------------------------------------------------------- /src/guide/essentials/images/directive.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/essentials/images/directive.png -------------------------------------------------------------------------------- /src/guide/essentials/images/lifecycle.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/essentials/images/lifecycle.png -------------------------------------------------------------------------------- /src/guide/extras/images/render-pipeline.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/extras/images/render-pipeline.png -------------------------------------------------------------------------------- /src/guide/scaling-up/images/state-flow.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/scaling-up/images/state-flow.png -------------------------------------------------------------------------------- /src/public/images/partners/curotec-hero.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/curotec-hero.jpg -------------------------------------------------------------------------------- /src/public/images/partners/jump24-hero.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/jump24-hero.jpg -------------------------------------------------------------------------------- /src/public/images/partners/tighten-hero.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/tighten-hero.jpg -------------------------------------------------------------------------------- /src/public/images/partners/vehikl-hero.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/vehikl-hero.jpg -------------------------------------------------------------------------------- /src/public/images/partners/webreinvent.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/webreinvent.png -------------------------------------------------------------------------------- /src/tutorial/src/step-3/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | titleClass: 'title' 5 | } 6 | } 7 | } 8 | -------------------------------------------------------------------------------- /src/examples/src/hello-world/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | message: 'Hello World!' 5 | } 6 | } 7 | } -------------------------------------------------------------------------------- /src/guide/components/images/prop-drilling.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/components/images/prop-drilling.png -------------------------------------------------------------------------------- /src/guide/typescript/images/takeover-mode.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/typescript/images/takeover-mode.png -------------------------------------------------------------------------------- /src/public/images/partners/64robots-hero.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/64robots-hero.jpg -------------------------------------------------------------------------------- /src/public/images/partners/herodevs-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/herodevs-dark.png -------------------------------------------------------------------------------- /src/public/images/partners/herodevs-hero.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/herodevs-hero.png -------------------------------------------------------------------------------- /src/public/images/partners/monterail-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/monterail-dark.png -------------------------------------------------------------------------------- /src/public/images/partners/monterail-hero.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/monterail-hero.png -------------------------------------------------------------------------------- /src/public/images/partners/redberry-hero.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/redberry-hero.jpg -------------------------------------------------------------------------------- /src/tutorial/src/step-15/import-map.json: -------------------------------------------------------------------------------- 1 | { 2 | "imports": { 3 | "js-confetti": "https://cdn.jsdelivr.net/npm/js-confetti/+esm" 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /src/tutorial/src/step-9/_hint/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | mounted() { 3 | this.$refs.pElementRef.textContent = 'mounted!' 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /src/examples/src/form-bindings/description.txt: -------------------------------------------------------------------------------- 1 | Nós podemos criar vínculos de duas vias entre o estado e as entradas do formulário usando a diretiva v-model. -------------------------------------------------------------------------------- /src/examples/src/list-transition/import-map.json: -------------------------------------------------------------------------------- 1 | { 2 | "imports": { 3 | "lodash-es": "https://cdn.jsdelivr.net/npm/lodash-es/+esm" 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /src/guide/components/images/provide-inject.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/components/images/provide-inject.png -------------------------------------------------------------------------------- /src/public/images/partners/passionatepeople.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/passionatepeople.png -------------------------------------------------------------------------------- /src/public/images/partners/webreinvent-hero.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/webreinvent-hero.jpg -------------------------------------------------------------------------------- /src/examples/src/list-transition/description.txt: -------------------------------------------------------------------------------- 1 | (FLIP) transições de lista com o embutido. 2 | https://aerotwist.com/blog/flip-your-animations/ -------------------------------------------------------------------------------- /src/examples/src/timer/App/style.css: -------------------------------------------------------------------------------- 1 | .elapsed-container { 2 | width: 300px; 3 | } 4 | 5 | .elapsed-bar { 6 | background-color: red; 7 | height: 10px; 8 | } -------------------------------------------------------------------------------- /src/guide/built-ins/images/transition-classes.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/built-ins/images/transition-classes.png -------------------------------------------------------------------------------- /src/guide/extras/images/composition-api-after.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/extras/images/composition-api-after.png -------------------------------------------------------------------------------- /src/public/images/partners/passionatepeople-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/passionatepeople-dark.png -------------------------------------------------------------------------------- /src/public/images/partners/passionatepeople-hero.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/public/images/partners/passionatepeople-hero.jpg -------------------------------------------------------------------------------- /src/tutorial/src/step-11/_hint/App/options.js: -------------------------------------------------------------------------------- 1 | import ChildComp from './ChildComp.vue' 2 | 3 | export default { 4 | components: { 5 | ChildComp 6 | } 7 | } 8 | -------------------------------------------------------------------------------- /src/tutorial/src/step-6/_hint/App/template.html: -------------------------------------------------------------------------------- 1 | 2 |

    Vue is awesome!

    3 |

    Oh no 😢

    4 | -------------------------------------------------------------------------------- /src/examples/src/conditionals-and-loops/description.txt: -------------------------------------------------------------------------------- 1 | Nós podemos interpretar o conteúdo condicionalmente ou percorrer um objeto com as diretivas `v-if` e `v-for`. 2 | -------------------------------------------------------------------------------- /src/tutorial/src/step-11/_hint/App/composition.js: -------------------------------------------------------------------------------- 1 | import ChildComp from './ChildComp.vue' 2 | 3 | export default { 4 | components: { 5 | ChildComp 6 | } 7 | } 8 | -------------------------------------------------------------------------------- /src/ecosystem/themes.md: -------------------------------------------------------------------------------- 1 | --- 2 | page: true 3 | --- 4 | 5 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /src/examples/src/conditionals-and-loops/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | show: true, 5 | list: [1, 2, 3] 6 | } 7 | } 8 | } -------------------------------------------------------------------------------- /src/guide/best-practices/images/AccessiblePlaceholder.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/best-practices/images/AccessiblePlaceholder.png -------------------------------------------------------------------------------- /src/tutorial/src/step-13/ChildComp/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | emits: ['response'], 3 | created() { 4 | this.$emit('response', 'hello from child') 5 | } 6 | } 7 | -------------------------------------------------------------------------------- /src/examples/src/temperature-converter/App/template.html: -------------------------------------------------------------------------------- 1 | Celsius = 2 | Fahrenheit 3 | -------------------------------------------------------------------------------- /src/examples/src/tree/description.txt: -------------------------------------------------------------------------------- 1 | Um componente de árvore encaixado que interpreta a si mesmo recursivamente. 2 | Tu podes dar duplo clique sobre um item para torná-lo em uma pasta. -------------------------------------------------------------------------------- /src/guide/best-practices/images/AccessibleARIAdescribedby.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/best-practices/images/AccessibleARIAdescribedby.png -------------------------------------------------------------------------------- /src/guide/best-practices/images/AccessibleARIAlabelDevTools.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/best-practices/images/AccessibleARIAlabelDevTools.png -------------------------------------------------------------------------------- /src/guide/best-practices/images/AccessibleLabelChromeDevTools.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/best-practices/images/AccessibleLabelChromeDevTools.png -------------------------------------------------------------------------------- /src/about/team.md: -------------------------------------------------------------------------------- 1 | --- 2 | page: true 3 | title: Conheça a Equipa 4 | --- 5 | 6 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /src/examples/src/simple-component/description.txt: -------------------------------------------------------------------------------- 1 | Aqui mostramos o componente mais simples possível o qual aceita uma propriedade e interpreta-a. 2 | Aprenda mais a respeito de componentes no guia! -------------------------------------------------------------------------------- /src/guide/best-practices/images/AccessibleARIAlabelledbyDevTools.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/best-practices/images/AccessibleARIAlabelledbyDevTools.png -------------------------------------------------------------------------------- /src/partners/all.md: -------------------------------------------------------------------------------- 1 | --- 2 | page: true 3 | footer: false 4 | --- 5 | 6 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /src/examples/src/attribute-bindings/description.txt: -------------------------------------------------------------------------------- 1 | Neste exemplo estamos vinculando os atributos ou propriedades do elemento de maneira reativa. A sintaxe `:title` é abreviação para `v-bind:title`. 2 | -------------------------------------------------------------------------------- /src/examples/src/fetching-data/description.txt: -------------------------------------------------------------------------------- 1 | Este exemplo traz os dados das mais recentes aplicações da Vue.js a partir da API da GitHub e exibe-os como uma lista. 2 | Tu podes trocar entre dois ramos. -------------------------------------------------------------------------------- /src/examples/src/markdown/App/template.html: -------------------------------------------------------------------------------- 1 |
    2 | 3 |
    4 |
    5 | -------------------------------------------------------------------------------- /src/guide/best-practices/images/AccessibilityChromeDeveloperTools.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuejs-translations/docs-pt/HEAD/src/guide/best-practices/images/AccessibilityChromeDeveloperTools.png -------------------------------------------------------------------------------- /src/tutorial/src/step-13/ChildComp/composition.js: -------------------------------------------------------------------------------- 1 | export default { 2 | emits: ['response'], 3 | setup(props, { emit }) { 4 | emit('response', 'hello from child') 5 | return {} 6 | } 7 | } 8 | -------------------------------------------------------------------------------- /src/examples/src/markdown/import-map.json: -------------------------------------------------------------------------------- 1 | { 2 | "imports": { 3 | "marked": "https://cdn.jsdelivr.net/npm/marked/+esm", 4 | "lodash-es": "https://cdn.jsdelivr.net/npm/lodash-es/+esm" 5 | } 6 | } 7 | -------------------------------------------------------------------------------- /src/partners/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page: true 3 | footer: false 4 | --- 5 | 6 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /src/examples/src/counter/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const count = ref(0) 6 | 7 | return { 8 | count 9 | } 10 | } 11 | } 12 | -------------------------------------------------------------------------------- /src/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page: true 3 | title: Vue.js - A Abstração Progressiva de JavaScript 4 | --- 5 | 6 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /src/tutorial/src/step-4/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const count = ref(0) 6 | 7 | return { 8 | count 9 | } 10 | } 11 | } 12 | -------------------------------------------------------------------------------- /.vitepress/theme/styles/index.css: -------------------------------------------------------------------------------- 1 | @import "./pages.css"; 2 | @import "./badges.css"; 3 | @import "./options-boxes.css"; 4 | @import "./inline-demo.css"; 5 | @import "./utilities.css"; 6 | @import "./style-guide.css"; 7 | -------------------------------------------------------------------------------- /src/tutorial/src/step-2/_hint/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | message: 'Hello World!', 5 | counter: { 6 | count: 0 7 | } 8 | } 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /src/tutorial/src/step-5/_hint/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const text = ref('') 6 | 7 | return { 8 | text 9 | } 10 | } 11 | } 12 | -------------------------------------------------------------------------------- /src/api/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: Referência da API 3 | sidebar: false 4 | page: true 5 | footer: false 6 | --- 7 | 8 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /src/tutorial/src/step-10/App/template.html: -------------------------------------------------------------------------------- 1 |

    Todo id: {{ todoId }}

    2 | 3 |

    Loading...

    4 |
    {{ todoData }}
    5 | -------------------------------------------------------------------------------- /src/tutorial/src/step-6/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | awesome: true 5 | } 6 | }, 7 | methods: { 8 | toggle() { 9 | // ... 10 | } 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /src/examples/src/grid/App/template.html: -------------------------------------------------------------------------------- 1 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /src/tutorial/src/step-3/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const titleClass = ref('title') 6 | 7 | return { 8 | titleClass 9 | } 10 | } 11 | } 12 | -------------------------------------------------------------------------------- /src/tutorial/src/step-9/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const pElementRef = ref(null) 6 | 7 | return { 8 | pElementRef 9 | } 10 | } 11 | } 12 | -------------------------------------------------------------------------------- /src/examples/src/modal/App/options.js: -------------------------------------------------------------------------------- 1 | import Modal from './Modal.vue' 2 | 3 | export default { 4 | components: { 5 | Modal 6 | }, 7 | data() { 8 | return { 9 | showModal: false 10 | } 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /src/tutorial/src/step-4/_hint/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | count: 0 5 | } 6 | }, 7 | methods: { 8 | increment() { 9 | this.count++ 10 | } 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /.editorconfig: -------------------------------------------------------------------------------- 1 | [*] 2 | charset = utf-8 3 | indent_style = space 4 | indent_size = 2 5 | end_of_line = lf 6 | insert_final_newline = true 7 | trim_trailing_whitespace = true 8 | 9 | [*.md] 10 | trim_trailing_whitespace = false 11 | -------------------------------------------------------------------------------- /src/tutorial/src/step-5/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | text: '' 5 | } 6 | }, 7 | methods: { 8 | onInput(e) { 9 | this.text = e.target.value 10 | } 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /src/examples/src/fetching-data/App/style.css: -------------------------------------------------------------------------------- 1 | a { 2 | text-decoration: none; 3 | color: #42b883; 4 | } 5 | li { 6 | line-height: 1.5em; 7 | margin-bottom: 20px; 8 | } 9 | .author, 10 | .date { 11 | font-weight: bold; 12 | } 13 | -------------------------------------------------------------------------------- /src/examples/src/flight-booker/App/style.css: -------------------------------------------------------------------------------- 1 | select, 2 | input, 3 | button { 4 | display: block; 5 | margin: 0.5em 0; 6 | font-size: 15px; 7 | } 8 | 9 | input[disabled] { 10 | color: #999; 11 | } 12 | 13 | p { 14 | color: red; 15 | } -------------------------------------------------------------------------------- /src/tutorial/src/step-6/_hint/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | awesome: true 5 | } 6 | }, 7 | methods: { 8 | toggle() { 9 | this.awesome = !this.awesome 10 | } 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /src/tutorial/src/step-14/App/options.js: -------------------------------------------------------------------------------- 1 | import ChildComp from './ChildComp.vue' 2 | 3 | export default { 4 | components: { 5 | ChildComp 6 | }, 7 | data() { 8 | return { 9 | msg: 'from parent' 10 | } 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /src/tutorial/src/step-12/App/options.js: -------------------------------------------------------------------------------- 1 | import ChildComp from './ChildComp.vue' 2 | 3 | export default { 4 | components: { 5 | ChildComp 6 | }, 7 | data() { 8 | return { 9 | greeting: 'Hello from parent' 10 | } 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /src/tutorial/src/step-13/App/options.js: -------------------------------------------------------------------------------- 1 | import ChildComp from './ChildComp.vue' 2 | 3 | export default { 4 | components: { 5 | ChildComp 6 | }, 7 | data() { 8 | return { 9 | childMsg: 'No child msg yet' 10 | } 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /src/tutorial/src/step-2/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | // lógica do componente 6 | 7 | return { 8 | // exposto para modelo de marcação de hipertexto (template) 9 | } 10 | } 11 | } 12 | -------------------------------------------------------------------------------- /src/examples/src/cells/Cell/style.css: -------------------------------------------------------------------------------- 1 | .cell, .cell input { 2 | height: 1.5em; 3 | line-height: 1.5; 4 | font-size: 15px; 5 | } 6 | 7 | .cell span { 8 | padding: 0 6px; 9 | } 10 | 11 | .cell input { 12 | width: 100%; 13 | box-sizing: border-box; 14 | } 15 | -------------------------------------------------------------------------------- /src/examples/src/conditionals-and-loops/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const show = ref(true) 6 | const list = ref([1, 2, 3]) 7 | 8 | return { 9 | show, 10 | list 11 | } 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /.vitepress/theme/styles/utilities.css: -------------------------------------------------------------------------------- 1 | .nowrap { 2 | white-space: nowrap; 3 | } 4 | 5 | .sr-only { 6 | position: absolute; 7 | width: 1px; 8 | height: 1px; 9 | padding: 0; 10 | margin: -1px; 11 | overflow: hidden; 12 | clip: rect(0, 0, 0, 0); 13 | border: 0; 14 | } 15 | -------------------------------------------------------------------------------- /src/examples/src/form-bindings/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | text: 'Edit me', 5 | checked: true, 6 | checkedNames: ['Jack'], 7 | picked: 'One', 8 | selected: 'A', 9 | multiSelected: ['A'] 10 | } 11 | } 12 | } -------------------------------------------------------------------------------- /src/partners/[partnerId].md: -------------------------------------------------------------------------------- 1 | --- 2 | page: true 3 | footer: false 4 | --- 5 | 6 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /src/tutorial/src/step-6/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const awesome = ref(true) 6 | 7 | function toggle() { 8 | // ... 9 | } 10 | 11 | return { 12 | awesome, 13 | toggle 14 | } 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /src/examples/src/modal/App/composition.js: -------------------------------------------------------------------------------- 1 | import Modal from './Modal.vue' 2 | import { ref } from 'vue' 3 | 4 | export default { 5 | components: { 6 | Modal 7 | }, 8 | setup() { 9 | const showModal = ref(false) 10 | 11 | return { 12 | showModal 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /src/guide/built-ins/keep-alive-demos/CompB.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 12 | -------------------------------------------------------------------------------- /src/tutorial/src/step-15/App/options.js: -------------------------------------------------------------------------------- 1 | import JSConfetti from 'js-confetti' 2 | 3 | const confetti = new JSConfetti() 4 | 5 | export default { 6 | mounted() { 7 | this.showConfetti() 8 | }, 9 | methods: { 10 | showConfetti() { 11 | confetti.addConfetti() 12 | } 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /src/tutorial/src/step-2/_hint/App/composition.js: -------------------------------------------------------------------------------- 1 | import { reactive, ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const counter = reactive({ count: 0 }) 6 | const message = ref('Hello World!') 7 | 8 | return { 9 | counter, 10 | message 11 | } 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /src/tutorial/src/step-14/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | import ChildComp from './ChildComp.vue' 3 | 4 | export default { 5 | components: { 6 | ChildComp 7 | }, 8 | setup() { 9 | const msg = ref('from parent') 10 | 11 | return { 12 | msg 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /src/tutorial/src/step-4/_hint/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const count = ref(0) 6 | 7 | function increment() { 8 | count.value++ 9 | } 10 | 11 | return { 12 | count, 13 | increment 14 | } 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /src/tutorial/src/step-5/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const text = ref('') 6 | 7 | function onInput(e) { 8 | text.value = e.target.value 9 | } 10 | 11 | return { 12 | text, 13 | onInput 14 | } 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /src/examples/src/svg/PolyGraph/template.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 10 | 11 | 12 | -------------------------------------------------------------------------------- /src/guide/built-ins/keep-alive-demos/CompA.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 12 | -------------------------------------------------------------------------------- /src/partners/[partnerId].paths.ts: -------------------------------------------------------------------------------- 1 | import partners from './partners.json' 2 | import { normalizeName } from './components/utils' 3 | 4 | export default { 5 | paths: partners.map((p) => { 6 | return { 7 | params: { 8 | partnerId: normalizeName(p.name) 9 | } 10 | } 11 | }) 12 | } 13 | -------------------------------------------------------------------------------- /src/examples/src/cells/App/options.js: -------------------------------------------------------------------------------- 1 | import Cell from './Cell.vue' 2 | import { cells } from './store.js' 3 | 4 | export default { 5 | components: { 6 | Cell 7 | }, 8 | data() { 9 | return { 10 | cols: cells.map((_, i) => String.fromCharCode(65 + i)), 11 | cells 12 | } 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /src/tutorial/src/step-12/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | import ChildComp from './ChildComp.vue' 3 | 4 | export default { 5 | components: { 6 | ChildComp 7 | }, 8 | setup() { 9 | const greeting = ref('Hello from parent') 10 | 11 | return { 12 | greeting 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /src/tutorial/src/step-13/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | import ChildComp from './ChildComp.vue' 3 | 4 | export default { 5 | components: { 6 | ChildComp 7 | }, 8 | setup() { 9 | const childMsg = ref('No child msg yet') 10 | 11 | return { 12 | childMsg 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /src/tutorial/src/step-6/_hint/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const awesome = ref(true) 6 | 7 | function toggle() { 8 | awesome.value = !awesome.value 9 | } 10 | 11 | return { 12 | awesome, 13 | toggle 14 | } 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /src/tutorial/src/step-9/_hint/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref, onMounted } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const pElementRef = ref(null) 6 | 7 | onMounted(() => { 8 | pElementRef.value.textContent = 'mounted!' 9 | }) 10 | 11 | return { 12 | p 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /.vitepress/inlined-scripts/perfops.js: -------------------------------------------------------------------------------- 1 | ;((d) => { 2 | window.rum = { key: 'a9efvfeu' } 3 | var script = d.createElement(script) 4 | script.src = '/rom3.min.js' 5 | script.type = 'text/javascript' 6 | script.defer = true 7 | script.async = true 8 | d.getElementsByTagName('head')[0].appendChild(script) 9 | })(document) 10 | -------------------------------------------------------------------------------- /src/examples/src/cells/Cell/template.html: -------------------------------------------------------------------------------- 1 |
    2 | 9 | {{ evalCell(cells[c][r]) }} 10 |
    11 | -------------------------------------------------------------------------------- /src/tutorial/src/step-7/App/template.html: -------------------------------------------------------------------------------- 1 |
    2 | 3 | 4 |
    5 |
      6 |
    • 7 | {{ todo.text }} 8 | 9 |
    • 10 |
    11 | -------------------------------------------------------------------------------- /src/examples/src/cells/App/composition.js: -------------------------------------------------------------------------------- 1 | import Cell from './Cell.vue' 2 | import { cells } from './store.js' 3 | 4 | export default { 5 | components: { 6 | Cell 7 | }, 8 | setup() { 9 | const cols = cells.map((_, i) => String.fromCharCode(65 + i)) 10 | return { 11 | cols, 12 | cells 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /src/examples/src/crud/App/style.css: -------------------------------------------------------------------------------- 1 | * { 2 | font-size: inherit; 3 | } 4 | 5 | input { 6 | display: block; 7 | margin-bottom: 10px; 8 | } 9 | 10 | select { 11 | float: left; 12 | margin: 0 1em 1em 0; 13 | width: 14em; 14 | } 15 | 16 | .buttons { 17 | clear: both; 18 | } 19 | 20 | button + button { 21 | margin-left: 5px; 22 | } 23 | -------------------------------------------------------------------------------- /src/tutorial/src/step-15/App/composition.js: -------------------------------------------------------------------------------- 1 | import JSConfetti from 'js-confetti' 2 | 3 | const confetti = new JSConfetti() 4 | 5 | export default { 6 | setup() { 7 | function showConfetti() { 8 | confetti.addConfetti() 9 | } 10 | 11 | showConfetti() 12 | 13 | return { 14 | showConfetti 15 | } 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /src/examples/src/svg/AxisLabel/options.js: -------------------------------------------------------------------------------- 1 | import { valueToPoint } from './util.js' 2 | 3 | export default { 4 | props: { 5 | stat: Object, 6 | index: Number, 7 | total: Number 8 | }, 9 | computed: { 10 | point: function () { 11 | return valueToPoint(+this.stat.value + 10, this.index, this.total) 12 | } 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /src/public/logo.svg: -------------------------------------------------------------------------------- 1 | 2 | 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /src/examples/src/handling-input/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | message: 'Hello World!' 5 | } 6 | }, 7 | methods: { 8 | reverseMessage() { 9 | this.message = this.message.split('').reverse().join('') 10 | }, 11 | notify() { 12 | alert('A navegação foi impedida.') 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /src/examples/src/timer/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | 3 |
    {{ (elapsed / 1000).toFixed(1) }}s
    4 | 5 |
    6 | Duração: 7 | {{ (duration / 1000).toFixed(1) }}s 8 |
    9 | 10 | 11 | -------------------------------------------------------------------------------- /src/examples/src/modal/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | 3 | declare module '@vue/theme/config' { 4 | import { UserConfig } from 'vitepress' 5 | const config: () => Promise 6 | export default config 7 | } 8 | 9 | declare module '@vue/theme/highlight' { 10 | const createHighlighter: () => Promise<(input: string) => string> 11 | export default createHighlighter 12 | } 13 | -------------------------------------------------------------------------------- /src/examples/src/svg/util.js: -------------------------------------------------------------------------------- 1 | export function valueToPoint(value, index, total) { 2 | const x = 0 3 | const y = -value * 0.8 4 | const angle = ((Math.PI * 2) / total) * index 5 | const cos = Math.cos(angle) 6 | const sin = Math.sin(angle) 7 | const tx = x * cos - y * sin + 100 8 | const ty = x * sin + y * cos + 100 9 | return { 10 | x: tx, 11 | y: ty 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /src/examples/src/attribute-bindings/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | message: 'Hello World!', 5 | isRed: true, 6 | color: 'green' 7 | } 8 | }, 9 | methods: { 10 | toggleRed() { 11 | this.isRed = !this.isRed 12 | }, 13 | toggleColor() { 14 | this.color = this.color === 'green' ? 'blue' : 'green' 15 | } 16 | } 17 | } -------------------------------------------------------------------------------- /src/examples/src/cells/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 14 | 15 | 16 |
    {{ c }}
    {{ i - 1 }} 12 | 13 |
    17 | -------------------------------------------------------------------------------- /src/examples/src/temperature-converter/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | c: 0, 5 | f: 32 6 | } 7 | }, 8 | methods: { 9 | setC(e, c = +e.target.value) { 10 | this.c = c 11 | this.f = c * (9 / 5) + 32 12 | }, 13 | setF(e, f = +e.target.value) { 14 | this.f = f 15 | this.c = (f - 32) * (5 / 9) 16 | } 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /src/examples/src/simple-component/App/options.js: -------------------------------------------------------------------------------- 1 | import TodoItem from './TodoItem.vue' 2 | 3 | export default { 4 | components: { 5 | TodoItem 6 | }, 7 | data() { 8 | return { 9 | groceryList: [ 10 | { id: 0, text: 'Vegetables' }, 11 | { id: 1, text: 'Cheese' }, 12 | { id: 2, text: 'Whatever else humans are supposed to eat' } 13 | ] 14 | } 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /src/examples/src/svg/App/style.css: -------------------------------------------------------------------------------- 1 | polygon { 2 | fill: #42b983; 3 | opacity: 0.75; 4 | } 5 | 6 | circle { 7 | fill: transparent; 8 | stroke: #999; 9 | } 10 | 11 | text { 12 | font-size: 10px; 13 | fill: #666; 14 | } 15 | 16 | label { 17 | display: inline-block; 18 | margin-left: 10px; 19 | width: 20px; 20 | } 21 | 22 | #raw { 23 | position: absolute; 24 | top: 0; 25 | left: 300px; 26 | } 27 | -------------------------------------------------------------------------------- /src/partners/components/type.ts: -------------------------------------------------------------------------------- 1 | export interface Partner { 2 | name: string 3 | logo: string 4 | hero?: string 5 | flipLogo?: boolean 6 | intro: string 7 | description: string[] 8 | proficiencies: string[] 9 | region: string[] 10 | location: string[] 11 | website: { 12 | text: string 13 | url: string 14 | } 15 | contact: string 16 | hiring?: string 17 | platinum?: boolean 18 | } 19 | -------------------------------------------------------------------------------- /.vitepress/theme/styles/pages.css: -------------------------------------------------------------------------------- 1 | /* always show anchors on /api/ and /style-guide/ pages */ 2 | .vt-doc.api h2 .header-anchor, 3 | .vt-doc.style-guide h2 .header-anchor { 4 | opacity: 1; 5 | } 6 | 7 | .vt-doc.sponsor h3 { 8 | text-align: center; 9 | padding-bottom: 1em; 10 | border-bottom: 1px solid var(--vt-c-divider-light); 11 | } 12 | 13 | .vt-doc.sponsor h3 .header-anchor { 14 | display: none; 15 | } 16 | -------------------------------------------------------------------------------- /src/examples/src/markdown/App/options.js: -------------------------------------------------------------------------------- 1 | import { marked } from 'marked' 2 | import { debounce } from 'lodash-es' 3 | 4 | export default { 5 | data: () => ({ 6 | input: '# hello' 7 | }), 8 | computed: { 9 | output() { 10 | return marked(this.input) 11 | } 12 | }, 13 | methods: { 14 | update: debounce(function (e) { 15 | this.input = e.target.value 16 | }, 100) 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /src/examples/src/list-transition/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 |
    7 | {{ item }} 8 | 9 |
    10 |
    11 | -------------------------------------------------------------------------------- /src/examples/src/simple-component/App/template.html: -------------------------------------------------------------------------------- 1 |
      2 | 8 | 9 |
    10 | -------------------------------------------------------------------------------- /src/examples/src/cells/Cell/options.js: -------------------------------------------------------------------------------- 1 | import { cells, evalCell } from './store.js' 2 | 3 | export default { 4 | props: { 5 | c: Number, 6 | r: Number 7 | }, 8 | data() { 9 | return { 10 | editing: false, 11 | cells 12 | } 13 | }, 14 | methods: { 15 | evalCell, 16 | update(e) { 17 | this.editing = false 18 | cells[this.c][this.r] = e.target.value.trim() 19 | } 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /src/examples/src/svg/AxisLabel/composition.js: -------------------------------------------------------------------------------- 1 | import { computed } from 'vue' 2 | import { valueToPoint } from './util.js' 3 | 4 | export default { 5 | props: { 6 | stat: Object, 7 | index: Number, 8 | total: Number 9 | }, 10 | setup(props) { 11 | const point = computed(() => 12 | valueToPoint(+props.stat.value + 10, props.index, props.total) 13 | ) 14 | 15 | return { 16 | point 17 | } 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /src/guide/reusability/mouse.js: -------------------------------------------------------------------------------- 1 | import { ref, onMounted, onUnmounted } from 'vue' 2 | 3 | export function useMouse() { 4 | const x = ref(0) 5 | const y = ref(0) 6 | 7 | function update(event) { 8 | x.value = event.pageX 9 | y.value = event.pageY 10 | } 11 | 12 | onMounted(() => window.addEventListener('mousemove', update)) 13 | onUnmounted(() => window.removeEventListener('mousemove', update)) 14 | 15 | return { x, y } 16 | } 17 | -------------------------------------------------------------------------------- /src/examples/src/cells/App/style.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0; 3 | } 4 | 5 | table { 6 | border-collapse: collapse; 7 | table-layout: fixed; 8 | width: 100%; 9 | } 10 | 11 | th { 12 | background-color: #eee; 13 | } 14 | 15 | tr:first-of-type th { 16 | width: 100px; 17 | } 18 | 19 | tr:first-of-type th:first-of-type { 20 | width: 25px; 21 | } 22 | 23 | td { 24 | border: 1px solid #ccc; 25 | height: 1.5em; 26 | overflow: hidden; 27 | } 28 | -------------------------------------------------------------------------------- /src/public/service-worker.js: -------------------------------------------------------------------------------- 1 | // force clearing previous service worker 2 | self.addEventListener('install', function (e) { 3 | self.skipWaiting() 4 | }) 5 | 6 | self.addEventListener('activate', function (e) { 7 | self.registration 8 | .unregister() 9 | .then(function () { 10 | return self.clients.matchAll() 11 | }) 12 | .then(function (clients) { 13 | clients.forEach((client) => client.navigate(client.url)) 14 | }) 15 | }) 16 | -------------------------------------------------------------------------------- /src/examples/src/grid/App/options.js: -------------------------------------------------------------------------------- 1 | import DemoGrid from './Grid.vue' 2 | 3 | export default { 4 | components: { 5 | DemoGrid 6 | }, 7 | data: () => ({ 8 | searchQuery: '', 9 | gridColumns: ['name', 'power'], 10 | gridData: [ 11 | { name: 'Chuck Norris', power: Infinity }, 12 | { name: 'Bruce Lee', power: 9000 }, 13 | { name: 'Jackie Chan', power: 7000 }, 14 | { name: 'Jet Li', power: 8000 } 15 | ] 16 | }) 17 | } 18 | -------------------------------------------------------------------------------- /src/examples/src/simple-component/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | import TodoItem from './TodoItem.vue' 3 | 4 | export default { 5 | components: { 6 | TodoItem 7 | }, 8 | setup() { 9 | const groceryList = ref([ 10 | { id: 0, text: 'Vegetables' }, 11 | { id: 1, text: 'Cheese' }, 12 | { id: 2, text: 'Whatever else humans are supposed to eat' } 13 | ]) 14 | 15 | return { 16 | groceryList 17 | } 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /src/tutorial/src/step-10/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | todoId: 1, 5 | todoData: null 6 | } 7 | }, 8 | methods: { 9 | async fetchData() { 10 | this.todoData = null 11 | const res = await fetch( 12 | `https://jsonplaceholder.typicode.com/todos/${this.todoId}` 13 | ) 14 | this.todoData = await res.json() 15 | } 16 | }, 17 | mounted() { 18 | this.fetchData() 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /src/examples/src/flight-booker/App/template.html: -------------------------------------------------------------------------------- 1 | 5 | 6 | 7 | 8 | 9 | 10 | 11 |

    {{ canBook ? '' : 'A data de regresso deve ser depois da data de partida.' }}

    12 | -------------------------------------------------------------------------------- /src/examples/src/conditionals-and-loops/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 |
      7 |
    • {{ item }}
    • 8 |
    9 |

    A lista não está vazia, porém escondida.

    10 |

    A lista está vazia.

    11 | -------------------------------------------------------------------------------- /src/examples/src/markdown/App/composition.js: -------------------------------------------------------------------------------- 1 | import { marked } from 'marked' 2 | import { debounce } from 'lodash-es' 3 | import { ref, computed } from 'vue' 4 | 5 | export default { 6 | setup() { 7 | const input = ref('# hello') 8 | 9 | const output = computed(() => marked(input.value)) 10 | 11 | const update = debounce((e) => { 12 | input.value = e.target.value 13 | }, 100) 14 | 15 | return { 16 | input, 17 | output, 18 | update 19 | } 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /src/examples/src/form-bindings/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const text = ref('Edit me') 6 | const checked = ref(true) 7 | const checkedNames = ref(['Jack']) 8 | const picked = ref('One') 9 | const selected = ref('A') 10 | const multiSelected = ref(['A']) 11 | 12 | return { 13 | text, 14 | checked, 15 | checkedNames, 16 | picked, 17 | selected, 18 | multiSelected 19 | } 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /src/examples/src/hello-world/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | // A "ref" é uma fonte de dado reativa que guarda um valor. 6 | // Tecnicamente, não precisamos envolver uma sequência de caracteres 7 | // com ref() para exibe-la, mas veremos no próximo exemplo do porquê 8 | // ser preciso caso alguma vez tencionamos mudar o valor. 9 | const message = ref('Hello World!') 10 | 11 | return { 12 | message 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /src/examples/src/crud/App/template.html: -------------------------------------------------------------------------------- 1 |
    2 | 3 | 6 | 7 | 8 | 9 | 10 |
    11 | 12 | 13 | 14 |
    15 | -------------------------------------------------------------------------------- /src/examples/src/cells/Cell/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | import { cells, evalCell } from './store.js' 3 | 4 | export default { 5 | props: { 6 | c: Number, 7 | r: Number 8 | }, 9 | setup(props) { 10 | const editing = ref(false) 11 | 12 | function update(e) { 13 | editing.value = false 14 | cells[props.c][props.r] = e.target.value.trim() 15 | } 16 | 17 | return { 18 | cells, 19 | editing, 20 | evalCell, 21 | update 22 | } 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /src/public/_headers: -------------------------------------------------------------------------------- 1 | /* 2 | X-Frame-Options: ALLOW-FROM https://staging.certification.vuejs.org https://certification.vuejs.org https://certificates.dev https://staging.certificates.dev https://alemira.com https://*.alemira.com 3 | Content-Security-Policy: frame-ancestors https://staging.certification.vuejs.org https://certification.vuejs.org https://certificates.dev https://staging.certificates.dev https://alemira.com https://*.alemira.com 4 | 5 | /assets/* 6 | cache-control: max-age=31536000 7 | cache-control: immutable 8 | -------------------------------------------------------------------------------- /src/tutorial/src/step-7/App/options.js: -------------------------------------------------------------------------------- 1 | // dar um `id` único à cada `todo` 2 | let id = 0 3 | 4 | export default { 5 | data() { 6 | return { 7 | newTodo: '', 8 | todos: [ 9 | { id: id++, text: 'Learn HTML' }, 10 | { id: id++, text: 'Learn JavaScript' }, 11 | { id: id++, text: 'Learn Vue' } 12 | ] 13 | } 14 | }, 15 | methods: { 16 | addTodo() { 17 | // ... 18 | this.newTodo = '' 19 | }, 20 | removeTodo(todo) { 21 | // ... 22 | } 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /src/examples/src/temperature-converter/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const c = ref(0) 6 | const f = ref(32) 7 | 8 | function setC(e, v = +e.target.value) { 9 | c.value = v 10 | f.value = v * (9 / 5) + 32 11 | } 12 | 13 | function setF(e, v = +e.target.value) { 14 | f.value = v 15 | c.value = (v - 32) * (5 / 9) 16 | } 17 | 18 | return { 19 | c, 20 | f, 21 | setC, 22 | setF 23 | } 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /src/partners/components/utils.ts: -------------------------------------------------------------------------------- 1 | export function track() { 2 | fathom.trackGoal('TTDUIE6G', 0) 3 | } 4 | 5 | export function normalizeName(name: string) { 6 | return name.toLowerCase().replace(/\s+/g, '') 7 | } 8 | 9 | export function getHero(img: string | undefined, name: string) { 10 | return `/images/partners/${img || `${normalizeName(name)}-hero.jpg`}` 11 | } 12 | 13 | export function getLogo(img: string, flip = false) { 14 | if (flip) img = img.replace(/(\.\w+$)/, '-dark$1') 15 | return `/images/partners/${img}` 16 | } 17 | -------------------------------------------------------------------------------- /.vitepress/inlined-scripts/restorePreference.js: -------------------------------------------------------------------------------- 1 | ;(() => { 2 | const restore = (key, cls, def = false) => { 3 | const saved = localStorage.getItem(key) 4 | if (saved ? saved !== 'false' : def) { 5 | document.documentElement.classList.add(cls) 6 | } 7 | } 8 | restore('vue-docs-prefer-composition', 'prefer-composition', true) 9 | restore('vue-docs-prefer-sfc', 'prefer-sfc', true) 10 | 11 | window.__VUE_BANNER_ID__ = 'vueconfus2024' 12 | restore(`vue-docs-banner-${__VUE_BANNER_ID__}`, 'banner-dismissed') 13 | })() 14 | -------------------------------------------------------------------------------- /src/tutorial/src/step-10/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const todoId = ref(1) 6 | const todoData = ref(null) 7 | 8 | async function fetchData() { 9 | todoData.value = null 10 | const res = await fetch( 11 | `https://jsonplaceholder.typicode.com/todos/${todoId.value}` 12 | ) 13 | todoData.value = await res.json() 14 | } 15 | 16 | fetchData() 17 | 18 | return { 19 | todoId, 20 | todoData 21 | } 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "outDir": "dist", 4 | "target": "esnext", 5 | "module": "esnext", 6 | "moduleResolution": "bundler", 7 | "esModuleInterop": true, 8 | "resolveJsonModule": true, 9 | "allowJs": true, 10 | "strict": true, 11 | "noUnusedLocals": true, 12 | "skipLibCheck": true, 13 | "jsx": "preserve", 14 | "baseUrl": ".", 15 | "paths": { 16 | "@theme/*": [".vitepress/theme/*"] 17 | } 18 | }, 19 | "include": ["env.d.ts", "src/**/*", ".vitepress/**/*"] 20 | } 21 | -------------------------------------------------------------------------------- /src/examples/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page: true 3 | title: Exemplos 4 | aside: false 5 | footer: false 6 | returnToTop: false 7 | --- 8 | 9 | 22 | 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /src/tutorial/src/step-8/App/template.html: -------------------------------------------------------------------------------- 1 |
    2 | 3 | 4 |
    5 |
      6 |
    • 7 | 8 | {{ todo.text }} 9 | 10 |
    • 11 |
    12 | 15 | -------------------------------------------------------------------------------- /src/error-reference/errors.data.ts: -------------------------------------------------------------------------------- 1 | import { defineLoader } from 'vitepress' 2 | import { errorMessages } from 'vue/compiler-sfc' 3 | // @ts-expect-error internal api 4 | import { ErrorTypeStrings } from 'vue' 5 | 6 | function filterEmptyMsg(data: Record) { 7 | return Object.fromEntries(Object.entries(data).filter(([_, msg]) => msg)) 8 | } 9 | 10 | export default defineLoader({ 11 | load() { 12 | return { 13 | compiler: filterEmptyMsg(errorMessages), 14 | runtime: filterEmptyMsg(ErrorTypeStrings) 15 | } 16 | } 17 | }) 18 | -------------------------------------------------------------------------------- /src/tutorial/src/step-10/_hint/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | todoId: 1, 5 | todoData: null 6 | } 7 | }, 8 | methods: { 9 | async fetchData() { 10 | this.todoData = null 11 | const res = await fetch( 12 | `https://jsonplaceholder.typicode.com/todos/${this.todoId}` 13 | ) 14 | this.todoData = await res.json() 15 | } 16 | }, 17 | mounted() { 18 | this.fetchData() 19 | }, 20 | watch: { 21 | todoId() { 22 | this.fetchData() 23 | } 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /src/examples/src/timer/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | duration: 15 * 1000, 5 | elapsed: 0 6 | } 7 | }, 8 | created() { 9 | let lastTime = performance.now() 10 | const update = () => { 11 | const time = performance.now() 12 | this.elapsed += Math.min(time - lastTime, this.duration - this.elapsed) 13 | lastTime = time 14 | this.handle = requestAnimationFrame(update) 15 | } 16 | update() 17 | }, 18 | unmounted() { 19 | cancelAnimationFrame(this.handle) 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /src/tutorial/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page: true 3 | title: Tutorial 4 | sidebar: false 5 | aside: false 6 | footer: false 7 | returnToTop: false 8 | --- 9 | 10 | 23 | 24 | 25 | 26 | 27 | -------------------------------------------------------------------------------- /src/tutorial/src/step-8/_hint/App/template.html: -------------------------------------------------------------------------------- 1 |
    2 | 3 | 4 |
    5 |
      6 |
    • 7 | 8 | {{ todo.text }} 9 | 10 |
    • 11 |
    12 | 15 | -------------------------------------------------------------------------------- /.github/dependabot.yml: -------------------------------------------------------------------------------- 1 | version: 2 2 | updates: 3 | # Enable version updates for npm 4 | - package-ecosystem: 'npm' 5 | # Look for `package.json` and `lock` files in the `root` directory 6 | directory: '/' 7 | # Check the npm registry for updates every day (weekdays) 8 | schedule: 9 | interval: 'daily' 10 | open-pull-requests-limit: 10 11 | versioning-strategy: lockfile-only 12 | allow: 13 | - dependency-name: 'vue' 14 | - dependency-name: 'vitepress' 15 | - dependency-name: '@vue/theme' 16 | - dependency-name: '@vue/repl' 17 | -------------------------------------------------------------------------------- /src/about/team/Member.ts: -------------------------------------------------------------------------------- 1 | export interface Member { 2 | name: string 3 | avatarPic?: string 4 | title: string 5 | company?: string 6 | companyLink?: string 7 | projects: Link[] 8 | location: string | string[] 9 | languages: string[] 10 | website?: Link 11 | socials: Socials 12 | sponsor?: boolean | string 13 | reposPersonal?: string[] 14 | } 15 | 16 | export interface Link { 17 | label: string 18 | url: string 19 | } 20 | 21 | export interface Socials { 22 | github: string 23 | twitter?: string 24 | linkedin?: string 25 | codepen?: string 26 | } 27 | -------------------------------------------------------------------------------- /src/examples/src/attribute-bindings/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const message = ref('Hello World!') 6 | const isRed = ref(true) 7 | const color = ref('green') 8 | 9 | function toggleRed() { 10 | isRed.value = !isRed.value 11 | } 12 | 13 | function toggleColor() { 14 | color.value = color.value === 'green' ? 'blue' : 'green' 15 | } 16 | 17 | return { 18 | message, 19 | isRed, 20 | color, 21 | toggleRed, 22 | toggleColor 23 | } 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /src/examples/src/handling-input/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const message = ref('Hello World!') 6 | 7 | function reverseMessage() { 8 | // Acessa/altera o valor de uma `ref` através da 9 | // sua propriedade `.value` 10 | message.value = message.value.split('').reverse().join('') 11 | } 12 | 13 | function notify() { 14 | alert('A navegação foi impedida.') 15 | } 16 | 17 | return { 18 | message, 19 | reverseMessage, 20 | notify 21 | } 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /.vitepress/theme/styles/badges.css: -------------------------------------------------------------------------------- 1 | .vt-badge.wip:before { 2 | content: 'WIP'; 3 | } 4 | 5 | .vt-badge.ts { 6 | background-color: #3178c6; 7 | } 8 | .vt-badge.ts:before { 9 | content: 'TS'; 10 | } 11 | 12 | .vt-badge.dev-only, 13 | .vt-badge.experimental { 14 | color: var(--vt-c-text-light-1); 15 | background-color: var(--vt-c-yellow); 16 | } 17 | 18 | .vt-badge.dev-only:before { 19 | content: 'Dev only'; 20 | } 21 | 22 | .vt-badge.experimental:before { 23 | content: 'Experimental'; 24 | } 25 | 26 | .vt-badge[data-text]:before { 27 | content: attr(data-text); 28 | } 29 | -------------------------------------------------------------------------------- /src/examples/src/svg/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 |
    7 | 8 | 9 | {{stat.value}} 10 | 11 |
    12 | 13 |
    14 | 15 | 16 |
    17 | 18 |
    {{ stats }}
    19 | -------------------------------------------------------------------------------- /src/guide/built-ins/transition-demos/Basic.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 15 | 16 | 27 | -------------------------------------------------------------------------------- /src/examples/src/markdown/App/style.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0; 3 | } 4 | 5 | .editor { 6 | height: 100vh; 7 | display: flex; 8 | } 9 | 10 | .input, 11 | .output { 12 | overflow: auto; 13 | width: 50%; 14 | height: 100%; 15 | box-sizing: border-box; 16 | padding: 0 20px; 17 | } 18 | 19 | .input { 20 | border: none; 21 | border-right: 1px solid #ccc; 22 | resize: none; 23 | outline: none; 24 | background-color: #f6f6f6; 25 | font-size: 14px; 26 | font-family: 'Monaco', courier, monospace; 27 | padding: 20px; 28 | } 29 | 30 | code { 31 | color: #f66; 32 | } 33 | -------------------------------------------------------------------------------- /src/tutorial/src/step-10/_hint/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref, watch } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const todoId = ref(1) 6 | const todoData = ref(null) 7 | 8 | async function fetchData() { 9 | todoData.value = null 10 | const res = await fetch( 11 | `https://jsonplaceholder.typicode.com/todos/${todoId.value}` 12 | ) 13 | todoData.value = await res.json() 14 | } 15 | 16 | fetchData() 17 | 18 | watch(todoId, fetchData) 19 | 20 | return { 21 | todoId, 22 | todoData 23 | } 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /src/guide/extras/demos/Colors.vue: -------------------------------------------------------------------------------- 1 | 11 | 12 | 22 | 23 | 30 | -------------------------------------------------------------------------------- /src/examples/src/grid/Grid/template.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 9 | 10 | 11 | 12 | 13 | 16 | 17 | 18 |
    5 | {{ capitalize(key) }} 6 | 7 | 8 |
    14 | {{entry[key]}} 15 |
    19 |

    Nenhuma correspondência encontrada.

    20 | -------------------------------------------------------------------------------- /src/examples/src/svg/PolyGraph/options.js: -------------------------------------------------------------------------------- 1 | import AxisLabel from './AxisLabel.vue' 2 | import { valueToPoint } from './util.js' 3 | 4 | export default { 5 | components: { 6 | AxisLabel 7 | }, 8 | props: { 9 | stats: Array 10 | }, 11 | computed: { 12 | // uma propriedade computada para os pontos do polígono 13 | points() { 14 | const total = this.stats.length 15 | return this.stats 16 | .map((stat, i) => { 17 | const { x, y } = valueToPoint(stat.value, i, total) 18 | return `${x},${y}` 19 | }) 20 | .join(' ') 21 | } 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /src/examples/src/grid/App/composition.js: -------------------------------------------------------------------------------- 1 | import DemoGrid from './Grid.vue' 2 | import { ref } from 'vue' 3 | 4 | export default { 5 | components: { 6 | DemoGrid 7 | }, 8 | setup() { 9 | const searchQuery = ref('') 10 | const gridColumns = ['name', 'power'] 11 | const gridData = [ 12 | { name: 'Chuck Norris', power: Infinity }, 13 | { name: 'Bruce Lee', power: 9000 }, 14 | { name: 'Jackie Chan', power: 7000 }, 15 | { name: 'Jet Li', power: 8000 } 16 | ] 17 | 18 | return { 19 | searchQuery, 20 | gridColumns, 21 | gridData 22 | } 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /src/tutorial/src/step-7/_hint/App/options.js: -------------------------------------------------------------------------------- 1 | // dar um `id` único à cada `todo` 2 | let id = 0 3 | 4 | export default { 5 | data() { 6 | return { 7 | newTodo: '', 8 | todos: [ 9 | { id: id++, text: 'Learn HTML' }, 10 | { id: id++, text: 'Learn JavaScript' }, 11 | { id: id++, text: 'Learn Vue' } 12 | ] 13 | } 14 | }, 15 | methods: { 16 | addTodo() { 17 | this.todos.push({ id: id++, text: this.newTodo }) 18 | this.newTodo = '' 19 | }, 20 | removeTodo(todo) { 21 | this.todos = this.todos.filter((t) => t !== todo) 22 | } 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /src/examples/src/tree/TreeItem/template.html: -------------------------------------------------------------------------------- 1 |
  • 2 |
    3 | {{ model.name }} 4 | [{{ isOpen ? '-' : '+' }}] 5 |
    6 |
      7 | 11 | 12 | 13 |
    • +
    • 14 |
    15 |
  • 16 | -------------------------------------------------------------------------------- /src/partners/components/PartnerLocation.vue: -------------------------------------------------------------------------------- 1 | 24 | -------------------------------------------------------------------------------- /vercel.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://openapi.vercel.sh/vercel.json", 3 | "headers": [ 4 | { 5 | "source": "/assets/(.*)", 6 | "headers": [ 7 | { 8 | "key": "Cache-Control", 9 | "value": "max-age=31536000, immutable" 10 | } 11 | ] 12 | }, 13 | { 14 | "source": "/(.*).png", 15 | "headers": [ 16 | { 17 | "key": "Cache-Control", 18 | "value": "max-age=604800, immutable" 19 | } 20 | ] 21 | } 22 | ], 23 | "rewrites": [ 24 | { 25 | "source": "/:path*", 26 | "destination": "/:path*.html" 27 | } 28 | ] 29 | } 30 | -------------------------------------------------------------------------------- /.vitepress/theme/styles/options-boxes.css: -------------------------------------------------------------------------------- 1 | .next-steps { 2 | margin-top: 3rem; 3 | } 4 | 5 | .next-steps .vt-box { 6 | border: 1px solid var(--vt-c-bg-soft); 7 | } 8 | 9 | .next-steps .vt-box:hover { 10 | border-color: var(--vt-c-green-light); 11 | transition: border-color 0.3s cubic-bezier(0.25, 0.8, 0.25, 1); 12 | } 13 | 14 | .vt-doc .next-steps-link { 15 | font-size: 20px; 16 | line-height: 1.4; 17 | letter-spacing: -0.02em; 18 | margin-bottom: 0.75em; 19 | display: block; 20 | color: var(--vt-c-green); 21 | } 22 | 23 | .vt-doc .next-steps-caption { 24 | margin-bottom: 0; 25 | color: var(--vt-c-text-2); 26 | transition: color 0.5s; 27 | } 28 | -------------------------------------------------------------------------------- /src/examples/src/svg/PolyGraph/composition.js: -------------------------------------------------------------------------------- 1 | import AxisLabel from './AxisLabel.vue' 2 | import { computed } from 'vue' 3 | import { valueToPoint } from './util.js' 4 | 5 | export default { 6 | components: { 7 | AxisLabel 8 | }, 9 | props: { 10 | stats: Array 11 | }, 12 | setup(props) { 13 | const points = computed(() => { 14 | const total = props.stats.length 15 | return props.stats 16 | .map((stat, i) => { 17 | const { x, y } = valueToPoint(stat.value, i, total) 18 | return `${x},${y}` 19 | }) 20 | .join(' ') 21 | }) 22 | 23 | return { 24 | points 25 | } 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /src/guide/extras/demos/AnimateWatcher.vue: -------------------------------------------------------------------------------- 1 | 17 | 18 | 24 | 25 | 31 | -------------------------------------------------------------------------------- /src/tutorial/src/step-7/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | // dar um `id` único à cada `todo` 6 | let id = 0 7 | 8 | const newTodo = ref('') 9 | const todos = ref([ 10 | { id: id++, text: 'Learn HTML' }, 11 | { id: id++, text: 'Learn JavaScript' }, 12 | { id: id++, text: 'Learn Vue' } 13 | ]) 14 | 15 | function addTodo() { 16 | // ... 17 | newTodo.value = '' 18 | } 19 | 20 | function removeTodo(todo) { 21 | // ... 22 | } 23 | 24 | return { 25 | newTodo, 26 | todos, 27 | addTodo, 28 | removeTodo 29 | } 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /src/guide/built-ins/transition-demos/BetweenComponents.vue: -------------------------------------------------------------------------------- 1 | 9 | 10 | 23 | -------------------------------------------------------------------------------- /src/examples/src/attribute-bindings/App/template.html: -------------------------------------------------------------------------------- 1 |

    2 | 3 | Paire o ponteiro do rato sobre mim por alguns segundos para ver o título saltar dinamicamente! 4 | 5 |

    6 | 7 | 10 |

    11 | Isto deveria ser vermelho... porém clica-me para alterná-lo. 12 |

    13 | 14 | 15 |

    16 | Isto deve ser verde, e deve alternar entre verde e azul sobre clique. 17 |

    18 | -------------------------------------------------------------------------------- /src/examples/src/timer/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref, onUnmounted } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const duration = ref(15 * 1000) 6 | const elapsed = ref(0) 7 | 8 | let lastTime = performance.now() 9 | let handle 10 | const update = () => { 11 | const time = performance.now() 12 | elapsed.value += Math.min(time - lastTime, duration.value - elapsed.value) 13 | lastTime = time 14 | handle = requestAnimationFrame(update) 15 | } 16 | 17 | update() 18 | onUnmounted(() => { 19 | cancelAnimationFrame(handle) 20 | }) 21 | 22 | return { 23 | duration, 24 | elapsed 25 | } 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /src/tutorial/src/step-8/App/options.js: -------------------------------------------------------------------------------- 1 | let id = 0 2 | 3 | export default { 4 | data() { 5 | return { 6 | newTodo: '', 7 | hideCompleted: false, 8 | todos: [ 9 | { id: id++, text: 'Learn HTML', done: true }, 10 | { id: id++, text: 'Learn JavaScript', done: true }, 11 | { id: id++, text: 'Learn Vue', done: false } 12 | ] 13 | } 14 | }, 15 | computed: { 16 | // ... 17 | }, 18 | methods: { 19 | addTodo() { 20 | this.todos.push({ id: id++, text: this.newTodo, done: false }) 21 | this.newTodo = '' 22 | }, 23 | removeTodo(todo) { 24 | this.todos = this.todos.filter((t) => t !== todo) 25 | } 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /src/examples/src/modal/Modal/template.html: -------------------------------------------------------------------------------- 1 | 2 | 25 | 26 | -------------------------------------------------------------------------------- /src/guide/built-ins/transition-demos/SlideFade.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 15 | 16 | 31 | -------------------------------------------------------------------------------- /src/tutorial/tutorial.data.ts: -------------------------------------------------------------------------------- 1 | import path from 'path' 2 | import { createMarkdownRenderer } from 'vitepress' 3 | import { readExamples, ExampleData } from '../examples/examples.data' 4 | 5 | export declare const data: Record 6 | 7 | export default { 8 | watch: './src/**', 9 | async load() { 10 | const md = await createMarkdownRenderer(process.cwd(), undefined, '/') 11 | const files = readExamples(path.resolve(__dirname, './src')) 12 | for (const step in files) { 13 | const stepFiles = files[step] 14 | const desc = stepFiles['description.md'] as string 15 | if (desc) { 16 | stepFiles['description.md'] = md.render(desc) 17 | } 18 | } 19 | return files 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /src/ecosystem/newsletters.md: -------------------------------------------------------------------------------- 1 | # Boletins Informativos da Comunidade {#community-newsletters} 2 | 3 | Existem muitos boletins informativos ou blogues dedicados à Vue da comunidade que nos trazem as últimas notícias e acontecimentos no ecossistema da Vue. Eis uma lista não exaustiva dos que estão ativos que encontrámos: 4 | 5 | - [Vue.js Feed](https://vuejsfeed.com/) 6 | - [Michael Thiessen](https://michaelnthiessen.com/newsletter) 7 | - [Jakub Andrzejewski](https://dev.to/jacobandrewsky) 8 | - [Weekly Vue News](https://weekly-vue.news/) 9 | - [Vue.js Developers Newsletter](https://vuejsdevelopers.com/newsletter/) 10 | 11 | Se soubermos dum bom boletim informativo que ainda não esteja incluído, podemos enviar um pedido de atualização usando a ligação abaixo! 12 | -------------------------------------------------------------------------------- /src/tutorial/src/step-15/description.md: -------------------------------------------------------------------------------- 1 | # Nós Conseguimos! {#you-did-it} 2 | 3 | Nós concluímos o tutorial! 4 | 5 | Neste momento, deveríamos ter uma boa ideia de como é trabalhar com a Vue. No entanto, cobrimos muitas coisas demasiado rápido e omitimos os detalhes, não sem dúvidas que devemos continuar a aprender! Como próximo passo, podemos: 6 | 7 | - Configurar um projeto real de Vue na nossa máquina seguindo a [Introdução Rápida](/guide/quick-start) 8 | 9 | - Passar pelo [Guia Principal](/guide/essentials/application), o qual cobre todos os tópicos que aprendemos até aqui em maiores detalhes, e muito mais. 10 | 11 | - Consultar mais alguns [Exemplos](/examples/) práticos e interativos. 12 | 13 | Estamos ansiosos para ver o que irás construir a seguir! 14 | -------------------------------------------------------------------------------- /src/examples/src/tree/App/options.js: -------------------------------------------------------------------------------- 1 | import TreeItem from './TreeItem.vue' 2 | 3 | const treeData = { 4 | name: 'My Tree', 5 | children: [ 6 | { name: 'hello' }, 7 | { name: 'wat' }, 8 | { 9 | name: 'child folder', 10 | children: [ 11 | { 12 | name: 'child folder', 13 | children: [{ name: 'hello' }, { name: 'wat' }] 14 | }, 15 | { name: 'hello' }, 16 | { name: 'wat' }, 17 | { 18 | name: 'child folder', 19 | children: [{ name: 'hello' }, { name: 'wat' }] 20 | } 21 | ] 22 | } 23 | ] 24 | } 25 | 26 | export default { 27 | components: { 28 | TreeItem 29 | }, 30 | data() { 31 | return { 32 | treeData 33 | } 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /src/guide/built-ins/keep-alive-demos/SwitchComponent.vue: -------------------------------------------------------------------------------- 1 | 10 | 11 | 25 | -------------------------------------------------------------------------------- /src/tutorial/src/step-7/_hint/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | // dar um `id` único à cada `todo` 6 | let id = 0 7 | 8 | const newTodo = ref('') 9 | const todos = ref([ 10 | { id: id++, text: 'Learn HTML' }, 11 | { id: id++, text: 'Learn JavaScript' }, 12 | { id: id++, text: 'Learn Vue' } 13 | ]) 14 | 15 | function addTodo() { 16 | todos.value.push({ id: id++, text: newTodo.value }) 17 | newTodo.value = '' 18 | } 19 | 20 | function removeTodo(todo) { 21 | todos.value = todos.value.filter((t) => t !== todo) 22 | } 23 | 24 | return { 25 | newTodo, 26 | todos, 27 | addTodo, 28 | removeTodo 29 | } 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /src/error-reference/ErrorsTable.vue: -------------------------------------------------------------------------------- 1 | 8 | 9 | 28 | 29 | 35 | -------------------------------------------------------------------------------- /.vitepress/theme/components/preferences.ts: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | import { AugmentedHeader } from '../../headerMdPlugin' 3 | 4 | export const inBrowser = typeof window !== 'undefined' 5 | const get = (key: string, defaultValue = false): boolean => 6 | inBrowser 7 | ? JSON.parse(localStorage.getItem(key) || String(defaultValue)) 8 | : defaultValue 9 | 10 | export const preferCompositionKey = 'vue-docs-prefer-composition' 11 | export const preferComposition = ref(get(preferCompositionKey, true)) 12 | 13 | export const preferSFCKey = 'vue-docs-prefer-sfc' 14 | export const preferSFC = ref(get(preferSFCKey, true)) 15 | 16 | export function filterHeadersByPreference(h: AugmentedHeader) { 17 | return preferComposition.value ? !h.optionsOnly : !h.compositionOnly 18 | } 19 | -------------------------------------------------------------------------------- /.github/workflows/ryu-cho.yaml: -------------------------------------------------------------------------------- 1 | name: ryu-cho 2 | 3 | on: 4 | schedule: 5 | - cron: '*/5 * * * *' 6 | 7 | jobs: 8 | ryu-cho: 9 | name: Ryu Cho 10 | runs-on: ubuntu-latest 11 | steps: 12 | - uses: vuejs-translations/ryu-cho@v1 13 | with: 14 | access-token: ${{ secrets.RYU_CHO_ACCESS_TOKEN }} 15 | username: ${{ secrets.RYU_CHO_USER_NAME }} 16 | email: ${{ secrets.RYU_CHO_USER_EMAIL }} 17 | upstream-repo: https://github.com/vuejs-translations/docs-pt.git 18 | upstream-repo-branch: main 19 | head-repo: https://github.com/vuejs/docs 20 | head-repo-branch: main 21 | track-from: b27e90689cb81114317fda8d6f9099ad4d68590c 22 | # path-starts-with: src/ 23 | workflow-name: ryu-cho 24 | -------------------------------------------------------------------------------- /src/examples/src/list-transition/App/options.js: -------------------------------------------------------------------------------- 1 | import { shuffle } from 'lodash-es' 2 | 3 | const getInitialItems = () => [1, 2, 3, 4, 5] 4 | let id = getInitialItems().length + 1 5 | 6 | export default { 7 | data() { 8 | return { 9 | items: getInitialItems() 10 | } 11 | }, 12 | methods: { 13 | insert() { 14 | const i = Math.round(Math.random() * this.items.length) 15 | this.items.splice(i, 0, id++) 16 | }, 17 | reset() { 18 | this.items = getInitialItems() 19 | id = getInitialItems().length + 1 20 | }, 21 | shuffle() { 22 | this.items = shuffle(this.items) 23 | }, 24 | remove(item) { 25 | const i = this.items.indexOf(item) 26 | if (i > -1) { 27 | this.items.splice(i, 1) 28 | } 29 | } 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /src/examples/src/list-transition/App/style.css: -------------------------------------------------------------------------------- 1 | .container { 2 | position: relative; 3 | padding: 0; 4 | } 5 | 6 | .item { 7 | width: 100%; 8 | height: 30px; 9 | background-color: #f3f3f3; 10 | border: 1px solid #666; 11 | box-sizing: border-box; 12 | } 13 | 14 | /* 1. declare transition */ 15 | .fade-move, 16 | .fade-enter-active, 17 | .fade-leave-active { 18 | transition: all 0.5s cubic-bezier(0.55, 0, 0.1, 1); 19 | } 20 | 21 | /* 2. declare enter from and leave to state */ 22 | .fade-enter-from, 23 | .fade-leave-to { 24 | opacity: 0; 25 | transform: scaleY(0.01) translate(30px, 0); 26 | } 27 | 28 | /* 3. ensure leaving items are taken out of layout flow so that moving 29 | animations can be calculated correctly. */ 30 | .fade-leave-active { 31 | position: absolute; 32 | } 33 | -------------------------------------------------------------------------------- /src/examples/src/tree/TreeItem/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | name: 'TreeItem', // necessário para a auto-referência 3 | props: { 4 | model: Object 5 | }, 6 | data() { 7 | return { 8 | isOpen: false 9 | } 10 | }, 11 | computed: { 12 | isFolder() { 13 | return this.model.children && this.model.children.length 14 | } 15 | }, 16 | methods: { 17 | toggle() { 18 | if (this.isFolder) { 19 | this.isOpen = !this.isOpen 20 | } 21 | }, 22 | changeType() { 23 | if (!this.isFolder) { 24 | this.model.children = [] 25 | this.addChild() 26 | this.isOpen = true 27 | } 28 | }, 29 | addChild() { 30 | this.model.children.push({ 31 | name: 'new stuff' 32 | }) 33 | } 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /src/ecosystem/themes/ThemePage.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 24 | -------------------------------------------------------------------------------- /src/examples/src/handling-input/App/template.html: -------------------------------------------------------------------------------- 1 | 6 |

    {{ message }}

    7 | 8 | 12 | 13 | 14 | 15 | 16 | 17 | 21 | 22 | Uma ligação com "e.preventDefault()" 23 | 24 | -------------------------------------------------------------------------------- /src/guide/built-ins/transition-demos/CssAnimation.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 17 | 18 | 37 | -------------------------------------------------------------------------------- /src/examples/src/fetching-data/App/template.html: -------------------------------------------------------------------------------- 1 |

    As Mais Recentes Aplicações do Núcleo de Vue

    2 | 6 |

    vuejs/vue@{{ currentBranch }}

    7 | 17 | -------------------------------------------------------------------------------- /src/tutorial/src/step-8/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | let id = 0 6 | 7 | const newTodo = ref('') 8 | const hideCompleted = ref(false) 9 | const todos = ref([ 10 | { id: id++, text: 'Learn HTML', done: true }, 11 | { id: id++, text: 'Learn JavaScript', done: true }, 12 | { id: id++, text: 'Learn Vue', done: false } 13 | ]) 14 | 15 | function addTodo() { 16 | todos.value.push({ id: id++, text: newTodo.value, done: false }) 17 | newTodo.value = '' 18 | } 19 | 20 | function removeTodo(todo) { 21 | todos.value = todos.value.filter((t) => t !== todo) 22 | } 23 | 24 | return { 25 | newTodo, 26 | hideCompleted, 27 | todos, 28 | addTodo, 29 | removeTodo 30 | } 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /src/tutorial/src/step-8/_hint/App/options.js: -------------------------------------------------------------------------------- 1 | let id = 0 2 | 3 | export default { 4 | data() { 5 | return { 6 | newTodo: '', 7 | hideCompleted: false, 8 | todos: [ 9 | { id: id++, text: 'Learn HTML', done: true }, 10 | { id: id++, text: 'Learn JavaScript', done: true }, 11 | { id: id++, text: 'Learn Vue', done: false } 12 | ] 13 | } 14 | }, 15 | computed: { 16 | filteredTodos() { 17 | return this.hideCompleted 18 | ? this.todos.filter((t) => !t.done) 19 | : this.todos 20 | } 21 | }, 22 | methods: { 23 | addTodo() { 24 | this.todos.push({ id: id++, text: this.newTodo, done: false }) 25 | this.newTodo = '' 26 | }, 27 | removeTodo(todo) { 28 | this.todos = this.todos.filter((t) => t !== todo) 29 | } 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /.github/workflows/automerge.yml: -------------------------------------------------------------------------------- 1 | name: Dependabot auto-merge 2 | on: pull_request 3 | 4 | permissions: 5 | pull-requests: write 6 | contents: write 7 | 8 | jobs: 9 | dependabot: 10 | runs-on: ubuntu-latest 11 | if: ${{ github.actor == 'dependabot[bot]' }} 12 | steps: 13 | - name: Dependabot metadata 14 | id: metadata 15 | uses: dependabot/fetch-metadata@v1.1.1 16 | with: 17 | github-token: '${{ secrets.ACCESS_TOKEN }}' 18 | - name: Enable auto-merge for theme 19 | if: ${{contains(steps.metadata.outputs.dependency-names, '@vue/theme') && steps.metadata.outputs.update-type != 'version-update:semver-major'}} 20 | run: gh pr merge --auto --merge "$PR_URL" 21 | env: 22 | PR_URL: ${{github.event.pull_request.html_url}} 23 | GITHUB_TOKEN: ${{secrets.ACCESS_TOKEN}} 24 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "engines": { 3 | "node": ">=18.0.0" 4 | }, 5 | "type": "module", 6 | "scripts": { 7 | "dev": "vitepress", 8 | "build": "vitepress build", 9 | "preview": "vitepress preview", 10 | "preinstall": "npx only-allow pnpm" 11 | }, 12 | "dependencies": { 13 | "@vue/repl": "^4.4.2", 14 | "@vue/theme": "^2.3.0", 15 | "dynamics.js": "^1.1.5", 16 | "gsap": "^3.12.5", 17 | "vitepress": "^1.4.3", 18 | "vue": "^3.5.12" 19 | }, 20 | "devDependencies": { 21 | "@types/body-scroll-lock": "^3.1.2", 22 | "@types/markdown-it": "^14.1.2", 23 | "@types/node": "^22.7.5", 24 | "typescript": "^5.6.3", 25 | "vitepress-plugin-llms": "^0.0.8", 26 | "vue-tsc": "^2.1.6" 27 | }, 28 | "packageManager": "pnpm@10.13.1+sha256.0f9ed48d808996ae007835fb5c4641cf9a300def2eddc9e957d9bbe4768c5f28" 29 | } 30 | -------------------------------------------------------------------------------- /src/ecosystem/themes/ThemeList.vue: -------------------------------------------------------------------------------- 1 | 5 | 6 | 15 | 16 | 42 | -------------------------------------------------------------------------------- /src/examples/src/fetching-data/App/options.js: -------------------------------------------------------------------------------- 1 | const API_URL = `https://api.github.com/repos/vuejs/core/commits?per_page=3&sha=` 2 | 3 | export default { 4 | data: () => ({ 5 | branches: ['main', 'v2-compat'], 6 | currentBranch: 'main', 7 | commits: [] 8 | }), 9 | 10 | created() { 11 | // pedir na inicialização 12 | this.fetchData() 13 | }, 14 | 15 | watch: { 16 | // pedir novamente sempre `currentBranch` alterar 17 | currentBranch: 'fetchData' 18 | }, 19 | 20 | methods: { 21 | async fetchData() { 22 | const url = `${API_URL}${this.currentBranch}` 23 | this.commits = await (await fetch(url)).json() 24 | }, 25 | truncate(v) { 26 | const newline = v.indexOf('\n') 27 | return newline > 0 ? v.slice(0, newline) : v 28 | }, 29 | formatDate(v) { 30 | return v.replace(/T|Z/g, ' ') 31 | } 32 | } 33 | } 34 | -------------------------------------------------------------------------------- /src/examples/src/tree/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue' 2 | import TreeItem from './TreeItem.vue' 3 | 4 | export default { 5 | components: { 6 | TreeItem 7 | }, 8 | setup() { 9 | const treeData = ref({ 10 | name: 'My Tree', 11 | children: [ 12 | { name: 'hello' }, 13 | { name: 'world' }, 14 | { 15 | name: 'child folder', 16 | children: [ 17 | { 18 | name: 'child folder', 19 | children: [{ name: 'hello' }, { name: 'world' }] 20 | }, 21 | { name: 'hello' }, 22 | { name: 'world' }, 23 | { 24 | name: 'child folder', 25 | children: [{ name: 'hello' }, { name: 'world' }] 26 | } 27 | ] 28 | } 29 | ] 30 | }) 31 | 32 | return { 33 | treeData 34 | } 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /src/examples/src/tree/TreeItem/composition.js: -------------------------------------------------------------------------------- 1 | import { ref, computed } from 'vue' 2 | 3 | export default { 4 | name: 'TreeItem', // necessário para a auto-referência 5 | props: { 6 | model: Object 7 | }, 8 | setup(props) { 9 | const isOpen = ref(false) 10 | const isFolder = computed(() => { 11 | return props.model.children && props.model.children.length 12 | }) 13 | 14 | function toggle() { 15 | isOpen.value = !isOpen.value 16 | } 17 | 18 | function changeType() { 19 | if (!isFolder.value) { 20 | props.model.children = [] 21 | addChild() 22 | isOpen.value = true 23 | } 24 | } 25 | 26 | function addChild() { 27 | props.model.children.push({ name: 'new stuff' }) 28 | } 29 | 30 | return { 31 | isOpen, 32 | isFolder, 33 | toggle, 34 | changeType, 35 | addChild 36 | } 37 | } 38 | } 39 | -------------------------------------------------------------------------------- /src/examples/src/svg/App/options.js: -------------------------------------------------------------------------------- 1 | import PolyGraph from './PolyGraph.vue' 2 | 3 | export default { 4 | components: { 5 | PolyGraph 6 | }, 7 | data: () => ({ 8 | newLabel: '', 9 | stats: [ 10 | { label: 'A', value: 100 }, 11 | { label: 'B', value: 100 }, 12 | { label: 'C', value: 100 }, 13 | { label: 'D', value: 100 }, 14 | { label: 'E', value: 100 }, 15 | { label: 'F', value: 100 } 16 | ] 17 | }), 18 | methods: { 19 | add(e) { 20 | e.preventDefault() 21 | if (!this.newLabel) return 22 | this.stats.push({ 23 | label: this.newLabel, 24 | value: 100 25 | }) 26 | this.newLabel = '' 27 | }, 28 | remove(stat) { 29 | if (this.stats.length > 3) { 30 | this.stats.splice(this.stats.indexOf(stat), 1) 31 | } else { 32 | alert("Não pode eliminar mais!") 33 | } 34 | } 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /.vitepress/theme/components/sponsors.ts: -------------------------------------------------------------------------------- 1 | // shared data across instances so we load only once 2 | 3 | import { ref } from 'vue' 4 | 5 | declare global { 6 | const fathom: { 7 | trackGoal: (id: string, value: number) => any 8 | } 9 | } 10 | 11 | export interface Sponsor { 12 | url: string 13 | img: string 14 | name: string 15 | description?: string 16 | priority?: boolean 17 | } 18 | 19 | export interface SponsorData { 20 | special: Sponsor[] 21 | platinum: Sponsor[] 22 | platinum_china: Sponsor[] 23 | gold: Sponsor[] 24 | silver: Sponsor[] 25 | bronze: Sponsor[] 26 | } 27 | 28 | export const data = ref() 29 | export const pending = ref(false) 30 | 31 | export const base = `https://sponsors.vuejs.org` 32 | 33 | export const load = async () => { 34 | if (!pending.value) { 35 | pending.value = true 36 | data.value = await (await fetch(`${base}/data.json`)).json() 37 | } 38 | } 39 | -------------------------------------------------------------------------------- /src/examples/src/circle-drawer/App/style.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0; 3 | overflow: hidden; 4 | } 5 | 6 | svg { 7 | width: 100vw; 8 | height: 100vh; 9 | background-color: #eee; 10 | } 11 | 12 | circle { 13 | stroke: #000; 14 | } 15 | 16 | .controls { 17 | position: fixed; 18 | top: 10px; 19 | left: 0; 20 | right: 0; 21 | text-align: center; 22 | } 23 | 24 | .controls button + button { 25 | margin-left: 6px; 26 | } 27 | 28 | .dialog { 29 | position: fixed; 30 | top: calc(50% - 50px); 31 | left: calc(50% - 175px); 32 | background: #fff; 33 | width: 350px; 34 | height: 100px; 35 | padding: 5px 20px; 36 | box-sizing: border-box; 37 | border-radius: 4px; 38 | text-align: center; 39 | box-shadow: 0px 4px 10px rgba(0, 0, 0, 0.25); 40 | } 41 | 42 | .dialog input { 43 | display: block; 44 | width: 200px; 45 | margin: 0px auto; 46 | } 47 | 48 | .tip { 49 | text-align: center; 50 | padding: 0 50px; 51 | color: #bbb; 52 | } 53 | -------------------------------------------------------------------------------- /src/examples/src/list-transition/App/composition.js: -------------------------------------------------------------------------------- 1 | import { shuffle as _shuffle } from 'lodash-es' 2 | import { ref } from 'vue' 3 | 4 | export default { 5 | setup() { 6 | const getInitialItems = () => [1, 2, 3, 4, 5] 7 | const items = ref(getInitialItems()) 8 | let id = items.value.length + 1 9 | 10 | function insert() { 11 | const i = Math.round(Math.random() * items.value.length) 12 | items.value.splice(i, 0, id++) 13 | } 14 | 15 | function reset() { 16 | items.value = getInitialItems() 17 | id = items.value.length + 1 18 | } 19 | 20 | function shuffle() { 21 | items.value = _shuffle(items.value) 22 | } 23 | 24 | function remove(item) { 25 | const i = items.value.indexOf(item) 26 | if (i > -1) { 27 | items.value.splice(i, 1) 28 | } 29 | } 30 | 31 | return { 32 | items, 33 | insert, 34 | reset, 35 | shuffle, 36 | remove 37 | } 38 | } 39 | } 40 | -------------------------------------------------------------------------------- /src/examples/src/grid/Grid/style.css: -------------------------------------------------------------------------------- 1 | table { 2 | border: 2px solid #42b983; 3 | border-radius: 3px; 4 | background-color: #fff; 5 | } 6 | 7 | th { 8 | background-color: #42b983; 9 | color: rgba(255, 255, 255, 0.66); 10 | cursor: pointer; 11 | user-select: none; 12 | } 13 | 14 | td { 15 | background-color: #f9f9f9; 16 | } 17 | 18 | th, 19 | td { 20 | min-width: 120px; 21 | padding: 10px 20px; 22 | } 23 | 24 | th.active { 25 | color: #fff; 26 | } 27 | 28 | th.active .arrow { 29 | opacity: 1; 30 | } 31 | 32 | .arrow { 33 | display: inline-block; 34 | vertical-align: middle; 35 | width: 0; 36 | height: 0; 37 | margin-left: 5px; 38 | opacity: 0.66; 39 | } 40 | 41 | .arrow.asc { 42 | border-left: 4px solid transparent; 43 | border-right: 4px solid transparent; 44 | border-bottom: 4px solid #fff; 45 | } 46 | 47 | .arrow.dsc { 48 | border-left: 4px solid transparent; 49 | border-right: 4px solid transparent; 50 | border-top: 4px solid #fff; 51 | } 52 | -------------------------------------------------------------------------------- /src/examples/src/cells/store.js: -------------------------------------------------------------------------------- 1 | import { reactive } from 'vue' 2 | 3 | const COLS = 5 4 | const ROWS = 20 5 | 6 | export const cells = reactive( 7 | Array.from(Array(COLS).keys()).map((i) => 8 | Array.from(Array(ROWS).keys()).map((i) => '') 9 | ) 10 | ) 11 | 12 | // adaptado de https://codesandbox.io/s/jotai-7guis-task7-cells-mzoit?file=/src/atoms.ts 13 | // by @dai-shi 14 | export function evalCell(exp) { 15 | if (!exp.startsWith('=')) { 16 | return exp 17 | } 18 | 19 | // = A1 + B2 ---> get(0,1) + get(1,2) 20 | exp = exp 21 | .slice(1) 22 | .replace( 23 | /\b([A-Z])(\d{1,2})\b/g, 24 | (_, c, r) => `get(${c.charCodeAt(0) - 65},${r})` 25 | ) 26 | 27 | try { 28 | return new Function('get', `return ${exp}`)(getCellValue) 29 | } catch (e) { 30 | return `#ERROR ${e}` 31 | } 32 | } 33 | 34 | function getCellValue(c, r) { 35 | const val = evalCell(cells[c][r]) 36 | const num = Number(val) 37 | return Number.isFinite(num) ? num : val 38 | } 39 | -------------------------------------------------------------------------------- /src/ecosystem/themes/ThemeHero.vue: -------------------------------------------------------------------------------- 1 | 13 | 14 | 56 | -------------------------------------------------------------------------------- /src/examples/src/fetching-data/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref, watchEffect } from 'vue' 2 | 3 | const API_URL = `https://api.github.com/repos/vuejs/core/commits?per_page=3&sha=` 4 | const branches = ['main', 'v2-compat'] 5 | 6 | export default { 7 | setup() { 8 | const currentBranch = ref(branches[0]) 9 | const commits = ref([]) 10 | 11 | watchEffect(async () => { 12 | // este efeito executar-se-á imediatamente e depois 13 | // re-executar-se-á sempre que `currentBranch.value` atualizar-se 14 | const url = `${API_URL}${currentBranch.value}` 15 | commits.value = await (await fetch(url)).json() 16 | }) 17 | 18 | function truncate(v) { 19 | const newline = v.indexOf('\n') 20 | return newline > 0 ? v.slice(0, newline) : v 21 | } 22 | 23 | function formatDate(v) { 24 | return v.replace(/T|Z/g, ' ') 25 | } 26 | 27 | return { 28 | branches, 29 | currentBranch, 30 | commits, 31 | truncate, 32 | formatDate 33 | } 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /src/guide/extras/demos/SpreadSheet.vue: -------------------------------------------------------------------------------- 1 | 7 | 8 | 26 | 27 | 47 | -------------------------------------------------------------------------------- /src/tutorial/src/step-8/_hint/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref, computed } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | let id = 0 6 | 7 | const newTodo = ref('') 8 | const hideCompleted = ref(false) 9 | const todos = ref([ 10 | { id: id++, text: 'Learn HTML', done: true }, 11 | { id: id++, text: 'Learn JavaScript', done: true }, 12 | { id: id++, text: 'Learn Vue', done: false } 13 | ]) 14 | 15 | const filteredTodos = computed(() => { 16 | return hideCompleted.value 17 | ? todos.value.filter((t) => !t.done) 18 | : todos.value 19 | }) 20 | 21 | function addTodo() { 22 | todos.value.push({ id: id++, text: newTodo.value, done: false }) 23 | newTodo.value = '' 24 | } 25 | 26 | function removeTodo(todo) { 27 | todos.value = todos.value.filter((t) => t !== todo) 28 | } 29 | 30 | return { 31 | newTodo, 32 | hideCompleted, 33 | todos, 34 | filteredTodos, 35 | addTodo, 36 | removeTodo 37 | } 38 | } 39 | } 40 | -------------------------------------------------------------------------------- /src/ecosystem/themes/ThemeContact.vue: -------------------------------------------------------------------------------- 1 | 8 | 9 | 50 | -------------------------------------------------------------------------------- /src/guide/built-ins/transition-demos/ListBasic.vue: -------------------------------------------------------------------------------- 1 | 19 | 20 | 31 | 32 | 43 | -------------------------------------------------------------------------------- /src/examples/src/circle-drawer/App/template.html: -------------------------------------------------------------------------------- 1 | 2 | 3 |

    4 | Clique sobre a tela para desenhar um circulo. Clique sobre um circulo para selecioná-lo. Clique com o botão direito do rato sobre a tela para ajustar o raio do circulo selecionado. 5 |

    6 |
    7 | 15 | 16 |
    17 | 18 |
    19 | 20 | 21 |
    22 | 23 |
    24 |

    Ajustar o raio do circulo em ({{ selected.cx }}, {{ selected.cy }})

    25 | 26 |
    27 | -------------------------------------------------------------------------------- /src/examples/src/svg/App/composition.js: -------------------------------------------------------------------------------- 1 | import PolyGraph from './PolyGraph.vue' 2 | import { ref, reactive } from 'vue' 3 | 4 | export default { 5 | components: { 6 | PolyGraph 7 | }, 8 | setup() { 9 | const newLabel = ref('') 10 | const stats = reactive([ 11 | { label: 'A', value: 100 }, 12 | { label: 'B', value: 100 }, 13 | { label: 'C', value: 100 }, 14 | { label: 'D', value: 100 }, 15 | { label: 'E', value: 100 }, 16 | { label: 'F', value: 100 } 17 | ]) 18 | 19 | function add(e) { 20 | e.preventDefault() 21 | if (!newLabel.value) return 22 | stats.push({ 23 | label: newLabel.value, 24 | value: 100 25 | }) 26 | newLabel.value = '' 27 | } 28 | 29 | function remove(stat) { 30 | if (stats.length > 3) { 31 | stats.splice(stats.indexOf(stat), 1) 32 | } else { 33 | alert("Não pode eliminar mais!") 34 | } 35 | } 36 | 37 | return { 38 | newLabel, 39 | stats, 40 | add, 41 | remove 42 | } 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /src/tutorial/src/step-6/description.md: -------------------------------------------------------------------------------- 1 | # Interpretação Condicional {#conditional-rendering} 2 | 3 | Nós podemos usar a diretiva `v-if` para interpretar um elemento condicionalmente: 4 | 5 | ```vue-html 6 |

    Vue is awesome!

    7 | ``` 8 | 9 | Este `

    ` será interpretado apenas se o valor de `awesome` for [verdadeiro](https://developer.mozilla.org/en-US/docs/Glossary/Truthy). Se `awesome` mudar para um valor [falso](https://developer.mozilla.org/en-US/docs/Glossary/Falsy), será removido do DOM. 10 | 11 | Nós também podemos usar `v-else` e `v-else-if` para indicar outros ramos da condição: 12 | 13 | ```vue-html 14 |

    Vue is awesome!

    15 |

    Oh no 😢

    16 | ``` 17 | 18 | Atualmente, a demonstração está exibindo ambos `

    ` ao mesmo tempo, e o botão não faz nada. Tente adicionar as diretivas `v-if` e `v-else` à eles, e implementar o método `toggle()` para que então possamos usar o botão para alternar entre eles. 19 | 20 | Mais detalhes sobre a `v-if`: Guia - Interpretação Condicional 21 | -------------------------------------------------------------------------------- /src/guide/extras/demos/spreadSheetStore.js: -------------------------------------------------------------------------------- 1 | import { reactive } from 'vue' 2 | 3 | const COLS = 3 4 | const ROWS = 3 5 | 6 | export const cells = reactive( 7 | Array.from(Array(COLS).keys()).map((i) => 8 | Array.from(Array(ROWS).keys()).map((i) => '') 9 | ) 10 | ) 11 | 12 | // initial state for demo 13 | cells[0][0] = '1' 14 | cells[0][1] = '2' 15 | cells[0][2] = '= A0 + A1' 16 | 17 | // adapted from https://codesandbox.io/s/jotai-7guis-task7-cells-mzoit?file=/src/atoms.ts 18 | // by @dai-shi 19 | export function evalCell(exp) { 20 | if (!exp.startsWith('=')) { 21 | return exp 22 | } 23 | 24 | // = A1 + B2 ---> get(0,1) + get(1,2) 25 | exp = exp 26 | .slice(1) 27 | .replace( 28 | /\b([A-Z])(\d{1,2})\b/g, 29 | (_, c, r) => `get(${c.charCodeAt(0) - 65},${r})` 30 | ) 31 | 32 | try { 33 | return new Function('get', `return ${exp}`)(getCellValue) 34 | } catch (e) { 35 | return `#ERROR ${e}` 36 | } 37 | } 38 | 39 | function getCellValue(c, r) { 40 | const val = evalCell(cells[c][r]) 41 | const num = Number(val) 42 | return Number.isFinite(num) ? num : val 43 | } 44 | -------------------------------------------------------------------------------- /.github/scripts/tag-alert-blocks.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | const { exec } = require('child_process') 4 | 5 | /** 6 | * Execute a command and return stdout as string. 7 | * @param {string} command 8 | * @returns {Promise} 9 | */ 10 | function run(command) { 11 | return new Promise((resolve, reject) => { 12 | exec(command, { encoding: 'utf-8' }, (error, stdout) => 13 | error ? reject(error) : resolve(stdout) 14 | ) 15 | }) 16 | } 17 | 18 | const ALERT_BLOCK = /^\+\s*:::\s?(\w+)/m 19 | 20 | async function isUsingAlertBlock(base = 'origin/master') { 21 | const result = await run(`git diff --name-only ${base}`) 22 | const files = ( 23 | await Promise.all( 24 | result 25 | .trim() 26 | .split(/\r?\n/) 27 | .map(file => 28 | run(`git diff ${base} -- ${file}`) 29 | .then(diff => ALERT_BLOCK.test(diff)) 30 | .then(usesAlertBlock => (usesAlertBlock ? file : '')) 31 | ) 32 | ) 33 | ).filter(Boolean) 34 | 35 | if (files.length) { 36 | return true 37 | } 38 | 39 | return false 40 | } 41 | 42 | module.exports = { isUsingAlertBlock } 43 | -------------------------------------------------------------------------------- /src/guide/extras/demos/DisabledButton.vue: -------------------------------------------------------------------------------- 1 | 13 | 14 | 24 | 25 | 54 | -------------------------------------------------------------------------------- /.vitepress/theme/index.ts: -------------------------------------------------------------------------------- 1 | import './styles/index.css' 2 | import { h, App } from 'vue' 3 | import { VPTheme } from '@vue/theme' 4 | import PreferenceSwitch from './components/PreferenceSwitch.vue' 5 | import { 6 | preferComposition, 7 | preferSFC, 8 | filterHeadersByPreference 9 | } from './components/preferences' 10 | import SponsorsAside from './components/SponsorsAside.vue' 11 | import VueSchoolLink from './components/VueSchoolLink.vue' 12 | // import Banner from './components/Banner.vue' 13 | // import TextAd from './components/TextAd.vue' 14 | 15 | export default Object.assign({}, VPTheme, { 16 | Layout: () => { 17 | // @ts-ignore 18 | return h(VPTheme.Layout, null, { 19 | // banner: () => h(Banner), 20 | 'sidebar-top': () => h(PreferenceSwitch), 21 | 'aside-mid': () => h(SponsorsAside) 22 | }) 23 | }, 24 | enhanceApp({ app }: { app: App }) { 25 | app.provide('prefer-composition', preferComposition) 26 | app.provide('prefer-sfc', preferSFC) 27 | app.provide('filter-headers', filterHeadersByPreference) 28 | app.component('VueSchoolLink', VueSchoolLink) 29 | // app.component('TextAd', TextAd) 30 | } 31 | }) 32 | -------------------------------------------------------------------------------- /.vitepress/textAdMdPlugin.ts: -------------------------------------------------------------------------------- 1 | import MarkdownIt from 'markdown-it' 2 | 3 | const excludedPages = [ 4 | 'guide/introduction.md', 5 | // 'guide/quick-start.md', 6 | // 'guide/essentials/computed.md', 7 | // 'guide/essentials/conditional.md', 8 | // 'guide/essentials/list.md', 9 | // 'guide/essentials/event-handling.md', 10 | // 'guide/essentials/forms.md', 11 | // 'guide/components/registration.md', 12 | // 'guide/components/props.md', 13 | // 'guide/components/events.md', 14 | // 'guide/components/slots.md', 15 | // 'guide/built-ins/teleport.md', 16 | 'about/faq.md', 17 | 'about/team.md', 18 | 'about/releases.md', 19 | 'about/community-guide.md', 20 | 'about/coc.md', 21 | 'sponsor/index.md', 22 | 'translations/index.md' 23 | ] 24 | 25 | export const textAdPlugin = (md: MarkdownIt) => { 26 | md.renderer.rules.heading_close = (tokens, i, options, env, self) => { 27 | const relativePath = env.relativePath 28 | const renderedContent = self.renderToken(tokens, i, options) 29 | 30 | return excludedPages.includes(relativePath) 31 | ? renderedContent 32 | : renderedContent.replace(/<\/h1>/, '

    ') 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /src/guide/extras/demos/SpreadSheetCell.vue: -------------------------------------------------------------------------------- 1 | 17 | 18 | 30 | 31 | 54 | -------------------------------------------------------------------------------- /src/examples/src/modal/Modal/style.css: -------------------------------------------------------------------------------- 1 | .modal-mask { 2 | position: fixed; 3 | z-index: 9998; 4 | top: 0; 5 | left: 0; 6 | width: 100%; 7 | height: 100%; 8 | background-color: rgba(0, 0, 0, 0.5); 9 | display: flex; 10 | transition: opacity 0.3s ease; 11 | } 12 | 13 | .modal-container { 14 | width: 300px; 15 | margin: auto; 16 | padding: 20px 30px; 17 | background-color: #fff; 18 | border-radius: 2px; 19 | box-shadow: 0 2px 8px rgba(0, 0, 0, 0.33); 20 | transition: all 0.3s ease; 21 | } 22 | 23 | .modal-header h3 { 24 | margin-top: 0; 25 | color: #42b983; 26 | } 27 | 28 | .modal-body { 29 | margin: 20px 0; 30 | } 31 | 32 | .modal-default-button { 33 | float: right; 34 | } 35 | 36 | /* 37 | * The following styles are auto-applied to elements with 38 | * transition="modal" when their visibility is toggled 39 | * by Vue.js. 40 | * 41 | * You can easily play with the modal transition by editing 42 | * these styles. 43 | */ 44 | 45 | .modal-enter-from { 46 | opacity: 0; 47 | } 48 | 49 | .modal-leave-to { 50 | opacity: 0; 51 | } 52 | 53 | .modal-enter-from .modal-container, 54 | .modal-leave-to .modal-container { 55 | -webkit-transform: scale(1.1); 56 | transform: scale(1.1); 57 | } 58 | -------------------------------------------------------------------------------- /.vitepress/theme/components/TextAd.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 19 | 20 | 54 | -------------------------------------------------------------------------------- /src/examples/src/flight-booker/App/options.js: -------------------------------------------------------------------------------- 1 | function stringToDate(str) { 2 | const [y, m, d] = str.split('-') 3 | return new Date(+y, m - 1, +d) 4 | } 5 | 6 | function dateToString(date) { 7 | return ( 8 | date.getFullYear() + 9 | '-' + 10 | pad(date.getMonth() + 1) + 11 | '-' + 12 | pad(date.getDate()) 13 | ) 14 | } 15 | 16 | function pad(n, s = String(n)) { 17 | return s.length < 2 ? `0${s}` : s 18 | } 19 | 20 | export default { 21 | data() { 22 | return { 23 | flightType: 'one-way flight', 24 | departureDate: dateToString(new Date()), 25 | returnDate: dateToString(new Date()) 26 | } 27 | }, 28 | computed: { 29 | isReturn() { 30 | return this.flightType === 'return flight' 31 | }, 32 | canBook() { 33 | return ( 34 | !this.isReturn || 35 | stringToDate(this.returnDate) > stringToDate(this.departureDate) 36 | ) 37 | } 38 | }, 39 | methods: { 40 | book() { 41 | alert( 42 | this.isReturn 43 | ? `Tu marcaste um voo com regresso partindo na ${this.departureDate} e regressando na ${this.returnDate}.` 44 | : `Tu marcaste um voo só de ida partindo na ${this.departureDate}.` 45 | ) 46 | } 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /src/error-reference/index.md: -------------------------------------------------------------------------------- 1 | 11 | 12 | # Referência do Código de Erro de Produção {#error-reference} 13 | 14 | ## Erros de Execução {#runtime-errors} 15 | 16 | Nas construções de produção, o terceiro argumento passado às seguintes APIs do manipulador de erro serão um código curto ao invés da sequência de caracteres da informação completa: 17 | 18 | - [`app.config.errorHandler`](/api/application#app-config-errorhandler) 19 | - [`onErrorCaptured`](/api/composition-api-lifecycle#onerrorcaptured) (API de Composição) 20 | - [`errorCaptured`](/api/options-lifecycle#errorcaptured) (API de Opções) 21 | 22 | A seguinte tabela mapeia os códigos às suas sequências de caracteres da informação completa. 23 | 24 | 25 | 26 | ## Erros do Compilador {#compiler-errors} 27 | 28 | A seguinte tabela fornece um mapeamento dos códigos de erro do compilador de produção às suas mensagens originais. 29 | 30 | 31 | -------------------------------------------------------------------------------- /src/examples/src/grid/Grid/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | props: { 3 | data: Array, 4 | columns: Array, 5 | filterKey: String 6 | }, 7 | data() { 8 | return { 9 | sortKey: '', 10 | sortOrders: this.columns.reduce((o, key) => ((o[key] = 1), o), {}) 11 | } 12 | }, 13 | computed: { 14 | filteredData() { 15 | const sortKey = this.sortKey 16 | const filterKey = this.filterKey && this.filterKey.toLowerCase() 17 | const order = this.sortOrders[sortKey] || 1 18 | let data = this.data 19 | if (filterKey) { 20 | data = data.filter((row) => { 21 | return Object.keys(row).some((key) => { 22 | return String(row[key]).toLowerCase().indexOf(filterKey) > -1 23 | }) 24 | }) 25 | } 26 | if (sortKey) { 27 | data = data.slice().sort((a, b) => { 28 | a = a[sortKey] 29 | b = b[sortKey] 30 | return (a === b ? 0 : a > b ? 1 : -1) * order 31 | }) 32 | } 33 | return data 34 | } 35 | }, 36 | methods: { 37 | sortBy(key) { 38 | this.sortKey = key 39 | this.sortOrders[key] = this.sortOrders[key] * -1 40 | }, 41 | capitalize(str) { 42 | return str.charAt(0).toUpperCase() + str.slice(1) 43 | } 44 | } 45 | } 46 | -------------------------------------------------------------------------------- /src/guide/built-ins/transition-demos/JsHooks.vue: -------------------------------------------------------------------------------- 1 | 41 | 42 | 56 | 57 | 66 | -------------------------------------------------------------------------------- /src/tutorial/src/step-3/description.md: -------------------------------------------------------------------------------- 1 | # Vínculos de Atributo {#attribute-bindings} 2 | 3 | Na Vue, os bigodes são apenas usado para interpolação de texto. Para vincular um atributo à um valor dinâmico, usamos a diretiva `v-bind`: 4 | 5 | ```vue-html 6 |
    7 | ``` 8 | 9 | Uma **diretiva** é um atributo especial que começa com o prefixo `v-`. Eles fazem parte da sintaxe do modelo de marcação da Vue. Semelhante às interpolações de texto, os valores da diretiva são expressão de JavaScript que têm acesso ao estado do componente. Os detalhes completos da `v-bind` e sintaxe de diretiva são discutidos no Guia - Sintaxe do Modelo de Marcação. 10 | 11 | A parte depois do sinal de dois pontos (`:id`) é o "argumento" da diretiva. Aqui, o atributo `id` do elemento será sincronizado com a propriedade `dynamicId` a partir do estado do componente. 12 | 13 | Uma vez que a `v-bind` é usada com muita frequência, esta tem uma sintaxe de abreviatura dedicada: 14 | 15 | ```vue-html 16 |
    17 | ``` 18 | 19 | Agora, tente adicionar um vínculo de `class` dinâmico ao `

    `, usando a propriedade de dadosreferência como seu valor. Se for vinculado corretamente, o texto deve tonar-se vermelho. 20 | -------------------------------------------------------------------------------- /.vitepress/theme/components/ReplLoading.vue: -------------------------------------------------------------------------------- 1 | 12 | 13 | 60 | -------------------------------------------------------------------------------- /src/examples/src/circle-drawer/App/options.js: -------------------------------------------------------------------------------- 1 | function clone(circles) { 2 | return circles.map((c) => ({ ...c })) 3 | } 4 | 5 | export default { 6 | data() { 7 | return { 8 | history: [[]], 9 | index: 0, 10 | circles: [], 11 | selected: null, 12 | adjusting: false 13 | } 14 | }, 15 | methods: { 16 | onClick({ clientX: x, clientY: y }) { 17 | if (this.adjusting) { 18 | this.adjusting = false 19 | this.selected = null 20 | this.push() 21 | return 22 | } 23 | 24 | this.selected = [...this.circles].reverse().find(({ cx, cy, r }) => { 25 | const dx = cx - x 26 | const dy = cy - y 27 | return Math.sqrt(dx * dx + dy * dy) <= r 28 | }) 29 | 30 | if (!this.selected) { 31 | this.circles.push({ 32 | cx: x, 33 | cy: y, 34 | r: 50 35 | }) 36 | this.push() 37 | } 38 | }, 39 | 40 | adjust(circle) { 41 | this.selected = circle 42 | this.adjusting = true 43 | }, 44 | 45 | push() { 46 | this.history.length = ++this.index 47 | this.history.push(clone(this.circles)) 48 | }, 49 | 50 | undo() { 51 | this.circles = clone(this.history[--this.index]) 52 | }, 53 | 54 | redo() { 55 | this.circles = clone(this.history[++this.index]) 56 | } 57 | } 58 | } 59 | -------------------------------------------------------------------------------- /src/tutorial/src/step-14/description.md: -------------------------------------------------------------------------------- 1 | # Ranhuras {#slots} 2 | 3 | Além de passar dados através das propriedades, o componente pai também pode passar fragmentos de modelo de marcação ao componente filho através das **ranhuras**: 4 | 5 |
    6 | 7 | ```vue-html 8 | 9 | This is some slot content! 10 | 11 | ``` 12 | 13 |
    14 |
    15 | 16 | ```vue-html 17 | 18 | This is some slot content! 19 | 20 | ``` 21 | 22 |
    23 | 24 | No componente filho, este pode interpretar o conteúdo da ranhura a partir do componente pai usando o elemento `` como escoadouro (ou escape): 25 | 26 |
    27 | 28 | ```vue-html 29 | 30 | 31 | ``` 32 | 33 |
    34 |
    35 | 36 | ```vue-html 37 | 38 | 39 | ``` 40 | 41 |
    42 | 43 | O conteúdo dentro do escoadouro `` tratado como conteúdo de "retrocesso (ou retorno)": este será exibido se o pai não passou nenhum conteúdo de ranhura: 44 | 45 | ```vue-html 46 | Fallback content 47 | ``` 48 | 49 | Atualmente não estamos passando nenhum conteúdo de ranhura ao ``, então devemos ver o conteúdo de retrocesso (ou retorno). Vamos fornecer algum conteúdo de ranhura ao filho enquanto fazemos uso do estado da `msg` do pai. 50 | -------------------------------------------------------------------------------- /src/examples/src/crud/App/options.js: -------------------------------------------------------------------------------- 1 | export default { 2 | data() { 3 | return { 4 | names: ['Emil, Hans', 'Mustermann, Max', 'Tisch, Roman'], 5 | selected: '', 6 | prefix: '', 7 | first: '', 8 | last: '' 9 | } 10 | }, 11 | computed: { 12 | filteredNames() { 13 | return this.names.filter((n) => 14 | n.toLowerCase().startsWith(this.prefix.toLowerCase()) 15 | ) 16 | } 17 | }, 18 | watch: { 19 | selected(name) { 20 | ;[this.last, this.first] = name.split(', ') 21 | } 22 | }, 23 | methods: { 24 | create() { 25 | if (this.hasValidInput()) { 26 | const fullName = `${this.last}, ${this.first}` 27 | if (!this.names.includes(fullName)) { 28 | this.names.push(fullName) 29 | this.first = this.last = '' 30 | } 31 | } 32 | }, 33 | update() { 34 | if (this.hasValidInput() && this.selected) { 35 | const i = this.names.indexOf(this.selected) 36 | this.names[i] = this.selected = `${this.last}, ${this.first}` 37 | } 38 | }, 39 | del() { 40 | if (this.selected) { 41 | const i = this.names.indexOf(this.selected) 42 | this.names.splice(i, 1) 43 | this.selected = this.first = this.last = '' 44 | } 45 | }, 46 | hasValidInput() { 47 | return this.first.trim() && this.last.trim() 48 | } 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/about/team/TeamHero.vue: -------------------------------------------------------------------------------- 1 | 16 | 17 | 76 | -------------------------------------------------------------------------------- /.vitepress/theme/components/VueSchoolLink.vue: -------------------------------------------------------------------------------- 1 | 12 | 20 | 59 | -------------------------------------------------------------------------------- /src/examples/src/grid/Grid/composition.js: -------------------------------------------------------------------------------- 1 | import { ref, computed } from 'vue' 2 | 3 | export default { 4 | props: { 5 | data: Array, 6 | columns: Array, 7 | filterKey: String 8 | }, 9 | setup(props) { 10 | const sortKey = ref('') 11 | const sortOrders = ref( 12 | props.columns.reduce((o, key) => ((o[key] = 1), o), {}) 13 | ) 14 | 15 | const filteredData = computed(() => { 16 | let { data, filterKey } = props 17 | if (filterKey) { 18 | filterKey = filterKey.toLowerCase() 19 | data = data.filter((row) => { 20 | return Object.keys(row).some((key) => { 21 | return String(row[key]).toLowerCase().indexOf(filterKey) > -1 22 | }) 23 | }) 24 | } 25 | const key = sortKey.value 26 | if (key) { 27 | const order = sortOrders.value[key] 28 | data = data.slice().sort((a, b) => { 29 | a = a[key] 30 | b = b[key] 31 | return (a === b ? 0 : a > b ? 1 : -1) * order 32 | }) 33 | } 34 | return data 35 | }) 36 | 37 | function sortBy(key) { 38 | sortKey.value = key 39 | sortOrders.value[key] *= -1 40 | } 41 | 42 | function capitalize(str) { 43 | return str.charAt(0).toUpperCase() + str.slice(1) 44 | } 45 | 46 | return { 47 | sortKey, 48 | sortOrders, 49 | filteredData, 50 | sortBy, 51 | capitalize 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /src/partners/components/PartnerAll.vue: -------------------------------------------------------------------------------- 1 | 22 | 23 | 35 | 36 | 58 | -------------------------------------------------------------------------------- /src/examples/src/flight-booker/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref, computed } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const flightType = ref('one-way flight') 6 | const departureDate = ref(dateToString(new Date())) 7 | const returnDate = ref(departureDate.value) 8 | 9 | const isReturn = computed(() => flightType.value === 'return flight') 10 | 11 | const canBook = computed( 12 | () => 13 | !isReturn.value || 14 | stringToDate(returnDate.value) > stringToDate(departureDate.value) 15 | ) 16 | 17 | function book() { 18 | alert( 19 | isReturn.value 20 | ? `Tu marcaste um voo com regresso partindo na ${departureDate.value} e regressando na ${returnDate.value}.` 21 | : `Tu marcaste um voo só de ida partindo na ${departureDate.value}.` 22 | ) 23 | } 24 | 25 | function stringToDate(str) { 26 | const [y, m, d] = str.split('-') 27 | return new Date(+y, m - 1, +d) 28 | } 29 | 30 | function dateToString(date) { 31 | return ( 32 | date.getFullYear() + 33 | '-' + 34 | pad(date.getMonth() + 1) + 35 | '-' + 36 | pad(date.getDate()) 37 | ) 38 | } 39 | 40 | function pad(n, s = String(n)) { 41 | return s.length < 2 ? `0${s}` : s 42 | } 43 | 44 | return { 45 | flightType, 46 | departureDate, 47 | returnDate, 48 | isReturn, 49 | canBook, 50 | book 51 | } 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /.vitepress/theme/styles/style-guide.css: -------------------------------------------------------------------------------- 1 | .style-example { 2 | border-radius: 8px 8px 12px 12px; 3 | margin: 1.6em 0; 4 | padding: 1.6em 1.6em 0.1px; 5 | position: relative; 6 | border: 1px solid transparent; 7 | transition: background-color 0.25s ease, border-color 0.25s ease; 8 | } 9 | 10 | .vt-doc .style-example h3 { 11 | margin: 0; 12 | font-size: 1.1em; 13 | } 14 | 15 | .style-example-bad { 16 | background: #f7e8e8; 17 | } 18 | .dark .style-example-bad { 19 | background: transparent; 20 | border-color: var(--vt-c-red); 21 | } 22 | 23 | .style-example-bad h3 { 24 | color: var(--vt-c-red); 25 | } 26 | 27 | .style-example-good { 28 | background: #ecfaf7; 29 | } 30 | .dark .style-example-good { 31 | background: transparent; 32 | border-color: var(--vt-c-green); 33 | } 34 | 35 | .style-example-good h3 { 36 | color: var(--vt-c-green); 37 | } 38 | 39 | .details summary { 40 | font-weight: bold !important; 41 | } 42 | 43 | .style-verb { 44 | font-size: 0.6em; 45 | display: inline-block; 46 | border-radius: 6px; 47 | font-size: 0.65em; 48 | line-height: 1; 49 | font-weight: 600; 50 | padding: 0.35em 0.4em 0.3em; 51 | position: relative; 52 | top: -0.15em; 53 | margin-right: 0.5em; 54 | color: var(--vt-c-bg); 55 | transition: color 0.5s; 56 | background-color: var(--vt-c-brand); 57 | } 58 | 59 | .style-verb.avoid { 60 | background-color: var(--vt-c-red); 61 | } 62 | .vt-doc summary { 63 | width: fit-content; 64 | cursor: pointer; 65 | } 66 | -------------------------------------------------------------------------------- /src/public/images/partners/jump24.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /src/public/images/partners/jump24-dark.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /.vitepress/theme/styles/vue-mastery.css: -------------------------------------------------------------------------------- 1 | .vue-mastery-link { 2 | background-color: var(--vt-c-bg-soft); 3 | border-radius: 8px; 4 | padding: 8px 16px 8px 8px; 5 | transition: color 0.5s, background-color 0.5s; 6 | } 7 | 8 | .vue-mastery-link a { 9 | display: flex; 10 | align-items: center; 11 | } 12 | 13 | .vue-mastery-link .banner { 14 | background-color: var(--vt-c-white-soft); 15 | border-radius: 4px; 16 | width: 96px; 17 | height: 56px; 18 | object-fit: cover; 19 | } 20 | 21 | .vue-mastery-link .description { 22 | flex: 1; 23 | font-weight: 500; 24 | font-size: 14px; 25 | line-height: 20px; 26 | color: var(--vt-c-text-1); 27 | margin: 0 0 0 16px; 28 | transition: color 0.5s; 29 | } 30 | 31 | .vue-mastery-link .description span { 32 | color: var(--vt-c-brand); 33 | } 34 | 35 | .vue-mastery-link .logo-wrapper { 36 | position: relative; 37 | width: 48px; 38 | height: 48px; 39 | border-radius: 50%; 40 | background-color: var(--vt-c-white); 41 | display: flex; 42 | justify-content: center; 43 | align-items: center; 44 | } 45 | 46 | .vue-mastery-link .logo-wrapper img { 47 | width: 25px; 48 | object-fit: contain; 49 | } 50 | 51 | @media (max-width: 576px) { 52 | .vue-mastery-link .banner { 53 | width: 56px; 54 | } 55 | 56 | .vue-mastery-link .description { 57 | font-size: 12px; 58 | line-height: 18px; 59 | } 60 | .vue-mastery-link .logo-wrapper { 61 | position: relative; 62 | width: 32px; 63 | height: 32px; 64 | } 65 | } 66 | -------------------------------------------------------------------------------- /src/guide/built-ins/transition-demos/ListStagger.vue: -------------------------------------------------------------------------------- 1 | 42 | 43 | 63 | -------------------------------------------------------------------------------- /.vitepress/theme/components/SiteMap.vue: -------------------------------------------------------------------------------- 1 | 12 | 13 | 27 | 28 | 68 | -------------------------------------------------------------------------------- /src/guide/built-ins/transition-demos/BetweenElements.vue: -------------------------------------------------------------------------------- 1 | 8 | 9 | 27 | 28 | 63 | -------------------------------------------------------------------------------- /src/examples/src/form-bindings/App/template.html: -------------------------------------------------------------------------------- 1 |

    Entrada de Texto

    2 | {{ text }} 3 | 4 |

    Caixa de Verificação

    5 | 6 | 7 | 8 | 12 |

    Múltipla Caixa de Verificação

    13 | 14 | 15 | 16 | 17 | 18 | 19 |

    Nomes verificados: 20 |

    {{ checkedNames }}
    21 |

    22 | 23 |

    Rádio

    24 | 25 | 26 |
    27 | 28 | 29 |
    30 | Escolhido: {{ picked }} 31 | 32 |

    Seleção

    33 | 39 | Selecionado: {{ selected }} 40 | 41 |

    Múltipla Seleção

    42 | 47 | Selecionado: {{ multiSelected }} 48 | -------------------------------------------------------------------------------- /src/partners/components/PartnerHero.vue: -------------------------------------------------------------------------------- 1 | 4 | 5 | 17 | 18 | 71 | -------------------------------------------------------------------------------- /src/partners/components/PartnerJoin.vue: -------------------------------------------------------------------------------- 1 | 16 | 17 | 69 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # [pt.vuejs.org](https://pt.vuejs.org) 2 | 3 | ## Colaboração 4 | 5 | Este sítio foi construído com a [VitePress](https://vitepress.dev/) e depende da [`@vue/theme`](https://github.com/vuejs/vue-theme). O seu conteúdo foi escrito no formato Markdown (`.md`) localizado no diretório `src/`. Se quisermos aplicar edições simples, podemos editar diretamente o ficheiro na GitHub e gerar um pedido de atualização do ramo principal do repositório. 6 | 7 | Se quisermos desenvolver localmente, a [`pnpm`](https://pnpm.io/) é a ferramenta de preferência para gestão de pacotes de código de JavaScript ou TypeScript: 8 | 9 | ```bash 10 | pnpm i 11 | pnpm run dev 12 | ``` 13 | 14 | Para executarmos a aplicação deste sítio, precisamos da versão 18 ou superior da Node.js. É recomendado a ativação da ferramenta [`corepack`](https://nodejs.org/api/corepack.html): 15 | 16 | ```bash 17 | corepack enable 18 | ``` 19 | 20 | 21 | ## Conteúdo 22 | 23 | - Podemos consultar a documentação da VitePress sobre as [extensões da Markdown](https://vitepress.dev/guide/markdown) suportadas e a capacidade de [usar a sintaxe da Vue dentro de um ficheiro de Markdown](https://vitepress.dev/guide/using-vue). 24 | 25 | - O [Guia de Redação](https://github.com/vuejs/docs/blob/main/.github/contributing/writing-guide.md) está disponível para os interessados em conhecer as regras e recomendações que dizem respeito a redação e manutenção do conteúdo da documentação. 26 | 27 | ## Tema 28 | 29 | Se quisermos realizar alterações sobre o tema do sítio, podemos consultar as [instruções que ajudar-nos-ão a desenvolver o tema ao lado da documentação](https://github.com/vuejs/vue-theme#developing-with-real-content). 30 | -------------------------------------------------------------------------------- /src/examples/src/crud/App/composition.js: -------------------------------------------------------------------------------- 1 | import { ref, reactive, computed, watch } from 'vue' 2 | 3 | export default { 4 | setup() { 5 | const names = reactive(['Emil, Hans', 'Mustermann, Max', 'Tisch, Roman']) 6 | const selected = ref('') 7 | const prefix = ref('') 8 | const first = ref('') 9 | const last = ref('') 10 | 11 | const filteredNames = computed(() => 12 | names.filter((n) => 13 | n.toLowerCase().startsWith(prefix.value.toLowerCase()) 14 | ) 15 | ) 16 | 17 | watch(selected, (name) => { 18 | ;[last.value, first.value] = name.split(', ') 19 | }) 20 | 21 | function create() { 22 | if (hasValidInput()) { 23 | const fullName = `${last.value}, ${first.value}` 24 | if (!names.includes(fullName)) { 25 | names.push(fullName) 26 | first.value = last.value = '' 27 | } 28 | } 29 | } 30 | 31 | function update() { 32 | if (hasValidInput() && selected.value) { 33 | const i = names.indexOf(selected.value) 34 | names[i] = selected.value = `${last.value}, ${first.value}` 35 | } 36 | } 37 | 38 | function del() { 39 | if (selected.value) { 40 | const i = names.indexOf(selected.value) 41 | names.splice(i, 1) 42 | selected.value = first.value = last.value = '' 43 | } 44 | } 45 | 46 | function hasValidInput() { 47 | return first.value.trim() && last.value.trim() 48 | } 49 | 50 | return { 51 | filteredNames, 52 | selected, 53 | prefix, 54 | first, 55 | last, 56 | create, 57 | update, 58 | del 59 | } 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /src/tutorial/src/step-5/description.md: -------------------------------------------------------------------------------- 1 | # Vínculos de Formulário {#form-bindings} 2 | 3 | Usando a `v-bind` e `v-on` ao mesmo tempo, podemos criar vínculos bidirecionais sobre os elementos de entrada de formulário: 4 | 5 | ```vue-html 6 | 7 | ``` 8 | 9 |
    10 | 11 | ```js 12 | methods: { 13 | onInput(e) { 14 | // um manipulador de `v-on` recebe o 15 | // evento nativo do DOM como argumento. 16 | this.text = e.target.value 17 | } 18 | } 19 | ``` 20 | 21 |
    22 | 23 |
    24 | 25 | ```js 26 | function onInput(e) { 27 | // um manipulador de `v-on` recebe o 28 | // evento nativo do DOM como argumento. 29 | text.value = e.target.value 30 | } 31 | ``` 32 | 33 |
    34 | 35 | Tente digitar na caixa de entrada - deve ser possível ver o texto no `

    ` atualizando-se ao digitar. 36 | 37 | Para simplificar os vínculos bidirecionais, a Vue fornece uma diretiva, `v-model`, a qual é essencialmente uma açúcar sintática para o que vimos acima: 38 | 39 | ```vue-html 40 | 41 | ``` 42 | 43 | A `v-model` sincroniza automaticamente o valor do `` com o estado vinculado, assim já não precisamos usar um manipulador de evento para isto. 44 | 45 | A `v-model` não funciona apenas sobre as entradas de texto (``), mas também sobre outros tipos de entrada tais como, caixas de confirmação (``), botões de rádio (``), e listas pendentes de seleção (`