-
Notifications
You must be signed in to change notification settings - Fork 0
/
2681a891.html
1 lines (1 loc) · 326 KB
/
2681a891.html
1
<!DOCTYPE html><html lang="zh-CN" data-theme="light"><head><meta charset="UTF-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><meta name="viewport" content="width=device-width,initial-scale=1,viewport-fit=cover"><title>vue3.0的学习 | 梦洁小站-属于你我的小天地</title><meta name="author" content="梦洁"><meta name="copyright" content="梦洁"><meta name="format-detection" content="telephone=no"><meta name="theme-color" content="#ffffff"><meta name="description" content="一.创建vue3.0工程1.使用vue-cli创建123456789## 查看@vue/cli版本,确保@vue/cli版本在4.5.0以上vue --version## 安装或者升级你的@vue/clinpm install -g @vue/cli## 创建vue create vue_test## 启动cd vue_testnpm run serve 2.使用 vite 创建官方文档:htt"><meta property="og:type" content="article"><meta property="og:title" content="vue3.0的学习"><meta property="og:url" content="https://www.dreamlove.top/2681a891.html"><meta property="og:site_name" content="梦洁小站-属于你我的小天地"><meta property="og:description" content="一.创建vue3.0工程1.使用vue-cli创建123456789## 查看@vue/cli版本,确保@vue/cli版本在4.5.0以上vue --version## 安装或者升级你的@vue/clinpm install -g @vue/cli## 创建vue create vue_test## 启动cd vue_testnpm run serve 2.使用 vite 创建官方文档:htt"><meta property="og:locale" content="zh_CN"><meta property="og:image" content="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251524226.jpg"><meta property="article:published_time" content="2022-06-23T08:18:00.000Z"><meta property="article:modified_time" content="2022-06-25T10:45:16.000Z"><meta property="article:author" content="梦洁"><meta property="article:tag" content="vue"><meta property="article:tag" content="HTML"><meta property="article:tag" content="javscript"><meta name="twitter:card" content="summary"><meta name="twitter:image" content="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251524226.jpg"><link rel="shortcut icon" href="https://oss.dreamlove.top/i/2024/02/02/nw24wu.png"><link rel="canonical" href="https://www.dreamlove.top/2681a891.html"><link rel="preconnect" href="https://lib.baomitu.com"><link rel="preconnect" href="//busuanzi.ibruce.info"><link rel="stylesheet" href="/css/index.css?v=4.13.0"><link rel="stylesheet" href="https://lib.baomitu.com/font-awesome/6.5.1/css/all.min.css"><link rel="stylesheet" href="https://lib.baomitu.com/fancyapps-ui/5.0.33/fancybox/fancybox.min.css" media="print" onload='this.media="all"'><script>const GLOBAL_CONFIG={root:"/",algolia:{appId:"G7A2D1SYPY",apiKey:"49056313a9be02852c7dbedfcb772831",indexName:"blog",hits:{per_page:20},languages:{input_placeholder:"搜索文章",hits_empty:"找不到您查询的内容:${query}",hits_stats:"找到 ${hits} 条结果,用时 ${time} 毫秒"}},localSearch:void 0,translate:void 0,noticeOutdate:void 0,highlight:{plugin:"highlight.js",highlightCopy:!0,highlightLang:!0,highlightHeightLimit:!1},copy:{success:"复制成功",error:"复制错误",noSupport:"浏览器不支持"},relativeDate:{homepage:!1,post:!1},runtime:"天",dateSuffix:{just:"刚刚",min:"分钟前",hour:"小时前",day:"天前",month:"个月前"},copyright:void 0,lightbox:"fancybox",Snackbar:void 0,infinitegrid:{js:"https://lib.baomitu.com/egjs-infinitegrid/4.11.1/infinitegrid.min.js",buttonText:"加载更多"},isPhotoFigcaption:!1,islazyload:!1,isAnchor:!1,percent:{toc:!0,rightside:!1},autoDarkmode:!1}</script><script id="config-diff">var GLOBAL_CONFIG_SITE={title:"vue3.0的学习",isPost:!0,isHome:!1,isHighlightShrink:!1,isToc:!0,postUpdate:"2022-06-25 10:45:16"}</script><script>(e=>{e.saveToLocal={set:(e,t,o)=>{if(0===o)return;const a={value:t,expiry:Date.now()+864e5*o};localStorage.setItem(e,JSON.stringify(a))},get:e=>{const t=localStorage.getItem(e);if(!t)return;const o=JSON.parse(t);if(!(Date.now()>o.expiry))return o.value;localStorage.removeItem(e)}},e.getScript=(e,t={})=>new Promise((o,a)=>{const n=document.createElement("script");n.src=e,n.async=!0,n.onerror=a,n.onload=n.onreadystatechange=function(){const e=this.readyState;e&&"loaded"!==e&&"complete"!==e||(n.onload=n.onreadystatechange=null,o())},Object.keys(t).forEach(e=>{n.setAttribute(e,t[e])}),document.head.appendChild(n)}),e.getCSS=(e,t=!1)=>new Promise((o,a)=>{const n=document.createElement("link");n.rel="stylesheet",n.href=e,t&&(n.id=t),n.onerror=a,n.onload=n.onreadystatechange=function(){const e=this.readyState;e&&"loaded"!==e&&"complete"!==e||(n.onload=n.onreadystatechange=null,o())},document.head.appendChild(n)}),e.activateDarkMode=()=>{document.documentElement.setAttribute("data-theme","dark"),null!==document.querySelector('meta[name="theme-color"]')&&document.querySelector('meta[name="theme-color"]').setAttribute("content","#0d0d0d")},e.activateLightMode=()=>{document.documentElement.setAttribute("data-theme","light"),null!==document.querySelector('meta[name="theme-color"]')&&document.querySelector('meta[name="theme-color"]').setAttribute("content","#ffffff")};const t=saveToLocal.get("theme");"dark"===t?activateDarkMode():"light"===t&&activateLightMode();const o=saveToLocal.get("aside-status");void 0!==o&&("hide"===o?document.documentElement.classList.add("hide-aside"):document.documentElement.classList.remove("hide-aside"));/iPad|iPhone|iPod|Macintosh/.test(navigator.userAgent)&&document.documentElement.classList.add("apple")})(window)</script><meta name="generator" content="Hexo 7.1.1"></head><body><div id="sidebar"><div id="menu-mask"></div><div id="sidebar-menus"><div class="avatar-img is-center"><img src="https://oss.dreamlove.top/i/2024/02/02/nw24wu.png" onerror='onerror=null,src="/img/404.png"' alt="avatar"></div><div class="sidebar-site-data site-data is-center"><a href="/archives/"><div class="headline">文章</div><div class="length-num">168</div></a><a href="/tags/"><div class="headline">标签</div><div class="length-num">90</div></a><a href="/categories/"><div class="headline">分类</div><div class="length-num">68</div></a></div><hr class="custom-hr"><div class="menus_items"><div class="menus_item"><a class="site-page" href="/"><i class="fa-fw fas fa-home"></i><span> 首页</span></a></div><div class="menus_item"><a class="site-page" href="/link/"><i class="fa-fw fas fa-link"></i><span> 友情和链接</span></a></div><div class="menus_item"><a class="site-page" href="/navigation/"><i class="fa-fw fas fa-link"></i><span> 链接导航</span></a></div><div class="menus_item"><a class="site-page group" href="javascript:void(0);"><i class="fa-fw fas fa-list"></i><span> 私有化导航</span><i class="fas fa-chevron-down"></i></a><ul class="menus_item_child"><li><a class="site-page child" target="_blank" rel="noopener" href="https://mark.123916.xyz/"><i class="fa-fw fas fa-database"></i><span> 导航</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://cloud.reassurehome.com/"><i class="fa-fw fas fa-hippo"></i><span> Alist(私有)</span></a></li></ul></div><div class="menus_item"><a class="site-page group" href="javascript:void(0);"><i class="fa-fw fas fa-list"></i><span> 工具</span><i class="fas fa-chevron-down"></i></a><ul class="menus_item_child"><li><a class="site-page child" target="_blank" rel="noopener" href="https://short.123916.xyz/027a2"><i class="fa-fw fas fa-paperclip"></i><span> clash免费订阅地址</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://short.123916.xyz/admin/"><i class="fa-fw fas fa-paperclip"></i><span> 短链接生成</span></a></li></ul></div><div class="menus_item"><a class="site-page group" href="javascript:void(0);"><i class="fa-fw fas fa-list"></i><span> 好玩的</span><i class="fas fa-chevron-down"></i></a><ul class="menus_item_child"><li><a class="site-page child" target="_blank" rel="noopener" href="https://make.girls.moe/#/"><i class="fa-fw fas fa-database"></i><span> 动漫头像制作</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="http://dfqshy.ysepan.com/"><i class="fa-fw fas fa-database"></i><span> FC游戏大全网盘</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://www.yikm.net/"><i class="fa-fw fas fa-database"></i><span> 小霸王</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://www.return8090.com/"><i class="fa-fw fas fa-database"></i><span> 小霸王(广告多)</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="http://farm.dreamlove.top"><i class="fa-fw fas fa-database"></i><span> QQ农场经典版</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://codepip.com/"><i class="fa-fw fas fa-database"></i><span> CssGame</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://photo.123916.xyz/"><i class="fa-fw fas fa-database"></i><span> 有趣的照片</span></a></li></ul></div><div class="menus_item"><a class="site-page group" href="javascript:void(0);"><i class="fa-fw fas fa-list"></i><span> 其他</span><i class="fas fa-chevron-down"></i></a><ul class="menus_item_child"><li><a class="site-page child" href="/archives/"><i class="fa-fw fas fa-archive"></i><span> 归档</span></a></li><li><a class="site-page child" href="/about/"><i class="fa-fw fas fa-heart"></i><span> 关于</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://buy.dreamlove.top/"><i class="fa-fw fas fa-heart"></i><span> 购物</span></a></li></ul></div></div></div></div><div class="post" id="body-wrap"><header class="post-bg" id="page-header" style="background-image:url(https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251524226.jpg)"><nav id="nav"><span id="blog-info"><a href="/" title="梦洁小站-属于你我的小天地"><span class="site-name">梦洁小站-属于你我的小天地</span></a></span><div id="menus"><div id="search-button"><a class="site-page social-icon search" href="javascript:void(0);"><i class="fas fa-search fa-fw"></i><span> 搜索</span></a></div><div class="menus_items"><div class="menus_item"><a class="site-page" href="/"><i class="fa-fw fas fa-home"></i><span> 首页</span></a></div><div class="menus_item"><a class="site-page" href="/link/"><i class="fa-fw fas fa-link"></i><span> 友情和链接</span></a></div><div class="menus_item"><a class="site-page" href="/navigation/"><i class="fa-fw fas fa-link"></i><span> 链接导航</span></a></div><div class="menus_item"><a class="site-page group" href="javascript:void(0);"><i class="fa-fw fas fa-list"></i><span> 私有化导航</span><i class="fas fa-chevron-down"></i></a><ul class="menus_item_child"><li><a class="site-page child" target="_blank" rel="noopener" href="https://mark.123916.xyz/"><i class="fa-fw fas fa-database"></i><span> 导航</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://cloud.reassurehome.com/"><i class="fa-fw fas fa-hippo"></i><span> Alist(私有)</span></a></li></ul></div><div class="menus_item"><a class="site-page group" href="javascript:void(0);"><i class="fa-fw fas fa-list"></i><span> 工具</span><i class="fas fa-chevron-down"></i></a><ul class="menus_item_child"><li><a class="site-page child" target="_blank" rel="noopener" href="https://short.123916.xyz/027a2"><i class="fa-fw fas fa-paperclip"></i><span> clash免费订阅地址</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://short.123916.xyz/admin/"><i class="fa-fw fas fa-paperclip"></i><span> 短链接生成</span></a></li></ul></div><div class="menus_item"><a class="site-page group" href="javascript:void(0);"><i class="fa-fw fas fa-list"></i><span> 好玩的</span><i class="fas fa-chevron-down"></i></a><ul class="menus_item_child"><li><a class="site-page child" target="_blank" rel="noopener" href="https://make.girls.moe/#/"><i class="fa-fw fas fa-database"></i><span> 动漫头像制作</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="http://dfqshy.ysepan.com/"><i class="fa-fw fas fa-database"></i><span> FC游戏大全网盘</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://www.yikm.net/"><i class="fa-fw fas fa-database"></i><span> 小霸王</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://www.return8090.com/"><i class="fa-fw fas fa-database"></i><span> 小霸王(广告多)</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="http://farm.dreamlove.top"><i class="fa-fw fas fa-database"></i><span> QQ农场经典版</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://codepip.com/"><i class="fa-fw fas fa-database"></i><span> CssGame</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://photo.123916.xyz/"><i class="fa-fw fas fa-database"></i><span> 有趣的照片</span></a></li></ul></div><div class="menus_item"><a class="site-page group" href="javascript:void(0);"><i class="fa-fw fas fa-list"></i><span> 其他</span><i class="fas fa-chevron-down"></i></a><ul class="menus_item_child"><li><a class="site-page child" href="/archives/"><i class="fa-fw fas fa-archive"></i><span> 归档</span></a></li><li><a class="site-page child" href="/about/"><i class="fa-fw fas fa-heart"></i><span> 关于</span></a></li><li><a class="site-page child" target="_blank" rel="noopener" href="https://buy.dreamlove.top/"><i class="fa-fw fas fa-heart"></i><span> 购物</span></a></li></ul></div></div><div id="toggle-menu"><a class="site-page" href="javascript:void(0);"><i class="fas fa-bars fa-fw"></i></a></div></div></nav><div id="post-info"><h1 class="post-title">vue3.0的学习</h1><div id="post-meta"><div class="meta-firstline"><span class="post-meta-date"><i class="far fa-calendar-alt fa-fw post-meta-icon"></i><span class="post-meta-label">发表于</span><time class="post-meta-date-created" datetime="2022-06-23T08:18:00.000Z" title="发表于 2022-06-23 08:18:00">2022-06-23</time><span class="post-meta-separator">|</span><i class="fas fa-history fa-fw post-meta-icon"></i><span class="post-meta-label">更新于</span><time class="post-meta-date-updated" datetime="2022-06-25T10:45:16.000Z" title="更新于 2022-06-25 10:45:16">2022-06-25</time></span><span class="post-meta-categories"><span class="post-meta-separator">|</span><i class="fas fa-inbox fa-fw post-meta-icon"></i><a class="post-meta-categories" href="/categories/HTML/">HTML</a><i class="fas fa-angle-right post-meta-separator"></i><i class="fas fa-inbox fa-fw post-meta-icon"></i><a class="post-meta-categories" href="/categories/HTML/javscript/">javscript</a><i class="fas fa-angle-right post-meta-separator"></i><i class="fas fa-inbox fa-fw post-meta-icon"></i><a class="post-meta-categories" href="/categories/HTML/javscript/vue/">vue</a></span></div><div class="meta-secondline"><span class="post-meta-separator">|</span><span class="post-meta-wordcount"><i class="far fa-file-word fa-fw post-meta-icon"></i><span class="post-meta-label">字数总计:</span><span class="word-count">12.9k</span><span class="post-meta-separator">|</span><i class="far fa-clock fa-fw post-meta-icon"></i><span class="post-meta-label">阅读时长:</span><span>54分钟</span></span><span class="post-meta-separator">|</span><span class="post-meta-pv-cv" data-flag-title="vue3.0的学习"><i class="far fa-eye fa-fw post-meta-icon"></i><span class="post-meta-label">阅读量:</span><span id="busuanzi_value_page_pv"><i class="fa-solid fa-spinner fa-spin"></i></span></span></div></div></div></header><main class="layout" id="content-inner"><div id="post"><article class="post-content" id="article-container"><h2 id="一-创建vue3-0工程"><a href="#一-创建vue3-0工程" class="headerlink" title="一.创建vue3.0工程"></a>一.创建vue3.0工程</h2><h3 id="1-使用vue-cli创建"><a href="#1-使用vue-cli创建" class="headerlink" title="1.使用vue-cli创建"></a>1.使用vue-cli创建</h3><figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">## 查看@vue/cli版本,确保@vue/cli版本在4.5.0以上</span></span><br><span class="line">vue --version</span><br><span class="line"><span class="comment">## 安装或者升级你的@vue/cli</span></span><br><span class="line">npm install -g @vue/cli</span><br><span class="line"><span class="comment">## 创建</span></span><br><span class="line">vue create vue_test</span><br><span class="line"><span class="comment">## 启动</span></span><br><span class="line"><span class="built_in">cd</span> vue_test</span><br><span class="line">npm run serve</span><br></pre></td></tr></table></figure><h3 id="2-使用-vite-创建"><a href="#2-使用-vite-创建" class="headerlink" title="2.使用 vite 创建"></a>2.使用 vite 创建</h3><p>官方文档:<a target="_blank" rel="noopener" href="https://v3.cn.vuejs.org/guide/installation.html#vite">https://v3.cn.vuejs.org/guide/installation.html#vite</a></p><p>vite官网:<a target="_blank" rel="noopener" href="https://vitejs.cn/">https://vitejs.cn</a></p><ul><li>什么是vite?—— 新一代前端构建工具。</li><li>优势如下:<ul><li>开发环境中,无需打包操作,可快速的冷启动。</li><li>轻量快速的热重载(HMR)。</li><li>真正的按需编译,不再等待整个应用编译完成。</li></ul></li><li>创建</li></ul><figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">## 创建工程</span></span><br><span class="line">npm init vite-app <project-name></span><br><span class="line"><span class="comment">## 进入工程目录</span></span><br><span class="line"><span class="built_in">cd</span> <project-name></span><br><span class="line"><span class="comment">## 安装依赖</span></span><br><span class="line">npm install</span><br><span class="line"><span class="comment">## 运行</span></span><br><span class="line">npm run dev</span><br></pre></td></tr></table></figure><ul><li>传统构建 与 vite构建对比图</li></ul><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206241639183.png" alt="传统的构建"></p><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206241639804.png" alt="vite的构建"></p><h2 id="一-extra-分析vue2-x和vue3-x结构"><a href="#一-extra-分析vue2-x和vue3-x结构" class="headerlink" title="一(extra).分析vue2.x和vue3.x结构"></a>一(extra).分析vue2.x和vue3.x结构</h2><ul><li><p><strong>主要区别</strong></p><ul><li><p>1.引入的不在是vue2.x时候的<strong>vue构造函数</strong>了,而是引入的是一个名字叫<code>createApp</code>的工厂函数,并且比原来的构造函数更轻(我理解的是大小更小,加载更快)</p></li><li><p>2.在vue3.x结构当中,<code>template</code>部分的内容可以不被一个统一的容器所包裹了</p><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206241649042.png" alt="左vue2.x 右vue3.x"></p></li></ul></li></ul><h3 id="vue2-x的-main-js-初始时的代码"><a href="#vue2-x的-main-js-初始时的代码" class="headerlink" title="vue2.x的 main.js 初始时的代码"></a>vue2.x的 main.js 初始时的代码</h3><figure class="highlight javascript"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> <span class="title class_">Vue</span> <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">import</span> <span class="title class_">App</span> <span class="keyword">from</span> <span class="string">"./App.vue"</span>;</span><br><span class="line"></span><br><span class="line"><span class="keyword">new</span> <span class="title class_">Vue</span>({</span><br><span class="line"> <span class="attr">render</span>:<span class="function"><span class="params">h</span>=></span><span class="title function_">h</span>(<span class="title class_">App</span>),</span><br><span class="line">}).$mount(<span class="string">"#app"</span>);</span><br></pre></td></tr></table></figure><h3 id="vue3-x的-main-js-初始化时的代码"><a href="#vue3-x的-main-js-初始化时的代码" class="headerlink" title="vue3.x的 main.js 初始化时的代码"></a>vue3.x的 main.js 初始化时的代码</h3><figure class="highlight javascript"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {createApp} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">import</span> <span class="title class_">App</span> <span class="keyword">from</span> <span class="string">"./App.vue"</span>;</span><br><span class="line"><span class="title function_">createApp</span>(<span class="title class_">App</span>).<span class="title function_">mount</span>(<span class="string">"#app"</span>);</span><br></pre></td></tr></table></figure><h2 id="二-常用的Composition-API-组合API"><a href="#二-常用的Composition-API-组合API" class="headerlink" title="二.常用的Composition API(组合API)"></a>二.常用的Composition API(组合API)</h2><h3 id="1-setup"><a href="#1-setup" class="headerlink" title="1.setup"></a>1.setup</h3><h4 id="setup是vue3-0新增加的一个配置项-为一个函数-里面可以写函数代码-注意区分下methods当中的写法"><a href="#setup是vue3-0新增加的一个配置项-为一个函数-里面可以写函数代码-注意区分下methods当中的写法" class="headerlink" title="setup是vue3.0新增加的一个配置项,为一个函数,里面可以写函数代码,注意区分下methods当中的写法"></a><code>setup</code>是vue3.0新增加的一个配置项,为一个函数,里面可以写函数代码,<strong>注意区分下methods当中的写法</strong></h4><ul><li><code>methods</code>当中书写一个函数的写法<ul><li>这里是通过简写的形式书写的,实际上的完整的写法应该是<code>sayWelcom: ()=>{ ... }</code></li></ul></li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="attr">methods</span>:{</span><br><span class="line"> ...</span><br><span class="line"> <span class="title function_">sayWelcom</span>(<span class="params"></span>){</span><br><span class="line"> <span class="title function_">alert</span>(<span class="string">"欢迎大家来到唐朝"</span>)</span><br><span class="line"> },</span><br><span class="line"> ...</span><br><span class="line">},</span><br></pre></td></tr></table></figure><ul><li><code>setup</code>当中书写一个函数的写法<ul><li>可以看到,是直接书写一个函数</li></ul></li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line"><span class="title function_">setup</span>(<span class="params"></span>) {</span><br><span class="line"> ...</span><br><span class="line"> <span class="keyword">let</span> name = <span class="string">'李白'</span>;</span><br><span class="line"> <span class="keyword">function</span> <span class="title function_">sayHello</span>(<span class="params"></span>){</span><br><span class="line"> <span class="comment">//注意作用域的问题</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(name);</span><br><span class="line"> <span class="title function_">alert</span>(<span class="string">"大家好,我叫李白"</span>);</span><br><span class="line"> }</span><br><span class="line"> ...</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> sayHello,</span><br><span class="line"> }</span><br><span class="line">},</span><br></pre></td></tr></table></figure><h4 id="组件所用到的数据-方法-都可以写在setup当中-当然-你也可以写在vue2当中的data-methods等当中"><a href="#组件所用到的数据-方法-都可以写在setup当中-当然-你也可以写在vue2当中的data-methods等当中" class="headerlink" title="组件所用到的数据,方法,都可以写在setup当中,当然,你也可以写在vue2当中的data,methods等当中"></a>组件所用到的数据,方法,都可以写在setup当中,当然,你也可以写在vue2当中的data,methods等当中</h4><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br></pre></td><td class="code"><pre><span class="line"><span class="title function_">data</span>(<span class="params"></span>){</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> <span class="attr">money</span>:<span class="string">"20K"</span></span><br><span class="line"> }</span><br><span class="line"> },</span><br><span class="line"> <span class="attr">methods</span>:{</span><br><span class="line"> <span class="comment">//vue2当中的可以混合使用vue3的setup</span></span><br><span class="line"> <span class="title function_">sayOther</span>(<span class="params"></span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`你的名字叫<span class="subst">${<span class="variable language_">this</span>.name}</span>,工资是<span class="subst">${<span class="variable language_">this</span>.money}</span>`</span>);</span><br><span class="line"> }</span><br><span class="line"> },</span><br><span class="line"> <span class="comment">// setup是新增的一个配置项,为一个函数,数据,方法,什么的都可以写在这里面</span></span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="comment">//下面二行代码是不考虑数据响应式的写法</span></span><br><span class="line"> <span class="keyword">let</span> name = <span class="string">"李白"</span>;</span><br><span class="line"> <span class="keyword">let</span> age = <span class="number">1000</span>;</span><br><span class="line"> </span><br><span class="line"> </span><br><span class="line"> <span class="comment">//需要返回一个对象,对象当中的属性和方法,均可以在模板当中直接使用</span></span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> name,</span><br><span class="line"> age,</span><br><span class="line"> }</span><br><span class="line"> },</span><br></pre></td></tr></table></figure><h4 id="setup的返回值"><a href="#setup的返回值" class="headerlink" title="setup的返回值"></a>setup的返回值</h4><ul><li>若返回一个对象,则对象中的<strong>属性</strong>、<strong>方法</strong>等 在模板中均可以直接使用。(重点关注!)</li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="comment">//与此同时,vue2当中的也可以使用</span></span><br><span class="line"> <span class="title function_">data</span>(<span class="params"></span>){</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> <span class="attr">money</span>:<span class="string">"20K"</span></span><br><span class="line"> }</span><br><span class="line"> },</span><br><span class="line"> <span class="attr">methods</span>:{</span><br><span class="line"> <span class="title function_">sayWelcom</span>(<span class="params"></span>){</span><br><span class="line"> <span class="title function_">alert</span>(<span class="string">"欢迎大家来到唐朝"</span>)</span><br><span class="line"> },</span><br><span class="line"> <span class="comment">//vue2当中的可以混合使用vue3的setup</span></span><br><span class="line"> <span class="title function_">sayOther</span>(<span class="params"></span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`你的名字叫<span class="subst">${<span class="variable language_">this</span>.name}</span>,工资是<span class="subst">${<span class="variable language_">this</span>.money}</span>`</span>);</span><br><span class="line"> }</span><br><span class="line"> },</span><br><span class="line"> <span class="comment">// setup是新增的一个配置项,为一个函数,数据,方法,什么的都可以写在这里面</span></span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="comment">//下面二行代码是不考虑数据响应式的写法</span></span><br><span class="line"> <span class="keyword">let</span> name = <span class="string">"李白"</span>;</span><br><span class="line"> <span class="keyword">let</span> age = <span class="number">1000</span>;</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">function</span> <span class="title function_">sayHello</span>(<span class="params"></span>){</span><br><span class="line"> <span class="comment">//注意作用域的问题</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(name);</span><br><span class="line"> <span class="title function_">alert</span>(<span class="string">"大家好,我叫李白"</span>);</span><br><span class="line"> }</span><br><span class="line"> <span class="keyword">function</span> <span class="title function_">sayOtherSetup</span>(<span class="params"></span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`你的名字叫<span class="subst">${name}</span>,工资是<span class="subst">${<span class="variable language_">this</span>.money}</span>`</span>);<span class="comment">//你的名字叫李白,工资是undefined</span></span><br><span class="line"> }</span><br><span class="line"> <span class="comment">//需要返回一个对象,对象当中的属性和方法,均可以在模板当中直接使用</span></span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> name,</span><br><span class="line"> age,</span><br><span class="line"> sayHello,</span><br><span class="line"> sayOtherSetup</span><br><span class="line"> }</span><br><span class="line"> },</span><br><span class="line">};</span><br></pre></td></tr></table></figure><ul><li>若返回一个渲染函数:则可以自定义渲染内容。(了解)</li></ul><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206241905608.png" alt="h就是渲染函数,在组件使用记得要引入 import {h} from "vue""></p><h4 id="注意点"><a href="#注意点" class="headerlink" title="注意点"></a>注意点</h4><ul><li><p>vue2.x的配置,比如<code>data</code>,<code>methods</code>,<code>computed</code>可以访问到<code>setup</code>中的<strong>属性</strong>,<strong>方法</strong>,但是,setup不能访问到vue2.x的<code>data</code>,<code>methods</code>,<code>computed</code>等,<strong>因为setup当中的this为undefined</strong></p><ul><li>因为我们通过<code>data</code>,<code>methods</code>,<code>computed</code>访问都是<code>this.xxx</code>来进行范围数据或者方法的,但是在vue3当中,<code>setup</code>里是没有this的,所以就不能访问了</li></ul></li><li><p>setup不能是一个async函数,因为返回值不再是return的对象, 而是promise, 模板看不到return对象中的属性。(<strong>后期也可以返回一个Promise实例,但需要Suspense的配合</strong>)</p></li></ul><h3 id="2-ref函数-处理基本数据类型"><a href="#2-ref函数-处理基本数据类型" class="headerlink" title="2.ref函数-处理基本数据类型"></a>2.ref函数-处理基本数据类型</h3><ul><li><p>首先肯定是引入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {ref} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li></ul><h4 id="ref函数作用"><a href="#ref函数作用" class="headerlink" title="ref函数作用:"></a>ref函数作用:</h4><ul><li>创建一个包含响应式数据的引用对象</li><li>js当中操作数据:<code>xxx.value</code></li><li>模板当中读取,不需要添加<code>.value</code>,直接<code><div>{{xxx}}</div></code></li></ul><h4 id="ref函数语法"><a href="#ref函数语法" class="headerlink" title="ref函数语法:"></a>ref函数语法:</h4><ul><li><p><code>const xxx = ref(initValue)</code></p></li><li><p>查看<code>ref</code>函数创建完成后的数据对象</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {ref} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="comment">//ref作用:定义一个响应式函数,返回响应数据</span></span><br><span class="line"> <span class="keyword">let</span> name = <span class="title function_">ref</span>(<span class="string">"李白"</span>);</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(name);</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> name,</span><br><span class="line"> };</span><br><span class="line"> },</span><br><span class="line">};</span><br></pre></td></tr></table></figure><p>输出的内容</p><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206241915707.png" alt="输出查看ref函数生成的变量-传入基本数据类型"></p></li><li><p>对ref传入的基本数据类型进行响应式修改</p><ul><li><strong>别漏掉了一层value!</strong></li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {ref} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="comment">//ref作用:定义一个响应式函数</span></span><br><span class="line"> <span class="keyword">let</span> name = <span class="title function_">ref</span>(<span class="string">"李白"</span>);</span><br><span class="line"> <span class="comment">//响应式修改</span></span><br><span class="line"> name.<span class="property">value</span> = <span class="string">"李黑"</span>;</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> name,</span><br><span class="line"> };</span><br><span class="line"> },</span><br><span class="line">};</span><br></pre></td></tr></table></figure></li></ul><blockquote><p>ref函数创建的对象,全称为 Reference implement 引用实行对象 ,这里简称为引用对象</p></blockquote><h3 id="3-ref函数-处理对象数据类型"><a href="#3-ref函数-处理对象数据类型" class="headerlink" title="3.ref函数-处理对象数据类型"></a>3.ref函数-处理对象数据类型</h3><ul><li><p>首先肯定也是引入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {ref} <span class="keyword">from</span> <span class="string">"vue"</span></span><br></pre></td></tr></table></figure></li><li><p>ref函数参数传入一个对象</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {ref} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="comment">//ref作用:定义一个响应式函数</span></span><br><span class="line"> <span class="keyword">let</span> job = <span class="title function_">ref</span>({</span><br><span class="line"> <span class="attr">salary</span>:<span class="string">"30K"</span>,</span><br><span class="line"> <span class="attr">type</span>:<span class="string">"前端工程师"</span></span><br><span class="line"> })</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(job);</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> job,</span><br><span class="line"> };</span><br><span class="line"> },</span><br><span class="line">};</span><br></pre></td></tr></table></figure><p>输出查看变量<code>job</code></p><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206241919131.png" alt="输出查看ref函数生成的变量-传入对象"></p></li><li><p>对ref传入的对象进行响应式修改</p><ul><li>注意不要少了一层<code>value</code>,使得指向真正保存数据的结构</li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {ref} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="comment">//ref作用:定义一个响应式函数</span></span><br><span class="line"> <span class="keyword">let</span> job = <span class="title function_">ref</span>({</span><br><span class="line"> <span class="attr">salary</span>:<span class="string">"30K"</span>,</span><br><span class="line"> <span class="attr">type</span>:<span class="string">"前端工程师"</span></span><br><span class="line"> })</span><br><span class="line"> <span class="comment">//改变ref当中的对象-响应式修改</span></span><br><span class="line"> job.<span class="property">value</span>.<span class="property">salary</span> = <span class="string">"100k"</span>;</span><br><span class="line"> job.<span class="property">value</span>.<span class="property">type</span> = <span class="string">"高级前端工程师"</span>;</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> job,</span><br><span class="line"> };</span><br><span class="line"> },</span><br><span class="line">};</span><br></pre></td></tr></table></figure></li></ul><h3 id="4-ref函数总结"><a href="#4-ref函数总结" class="headerlink" title="4.ref函数总结"></a>4.ref函数总结</h3><ul><li>ref当中,可以接收的数据类型可以是:基本数据类型,也可以是对象类型</li><li>基本数据类型的数据vue实现响应式的原理:依靠<code>Object.defineProperty()</code>的 <strong>get</strong> 和 <strong>set完成</strong></li><li>对象/引用数据类型的数据vue实现响应式的原理: 求助了Vue3.0中的一个新函数—— <code>reactive</code>函数。</li></ul><h3 id="5-reactive函数"><a href="#5-reactive函数" class="headerlink" title="5.reactive函数"></a>5.reactive函数</h3><ul><li><p>首先是引入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {reactive} <span class="keyword">from</span> <span class="string">"vue"</span></span><br></pre></td></tr></table></figure></li></ul><h4 id="reactive作用"><a href="#reactive作用" class="headerlink" title="reactive作用:"></a>reactive作用:</h4><ul><li>定义一个对象数据类型的响应式数据,基本类型不要使用(<strong>基本类型的使用请使用ref函数</strong>)<ul><li>如果对基本数据类型使用了,会提示<strong>value cannot be made reactive: 我是基本数据类型,</strong><code>let test = reactive("我是基本数据类型");</code>使用这代码就会提示这个</li></ul></li></ul><h4 id="reactive语法"><a href="#reactive语法" class="headerlink" title="reactive语法:"></a>reactive语法:</h4><ul><li><code>const 代理对象 = reactive(源对象)</code><strong>源对象接收一个对象或者数组</strong></li></ul><h4 id="注意点-1"><a href="#注意点-1" class="headerlink" title="注意点:"></a>注意点:</h4><ul><li><p>通过<code>reactive</code>函数处理的源对象,<strong>不管是何种方式的添加,删除,数据都是响应式的</strong>(这一点和vue2不同)</p><ul><li><strong>reactive定义的数组或者对象,不能直接对整体进行赋值修改,否则定义的数据将失去响应性!!!!!</strong><ul><li>因为通过<code>reactive</code>所创建的响应书数据返回的是<code>Proxy</code>对象,如果(保存这个地址的变量)对其整体赋值,那么就不是一个<code>Proxy</code>对象了,而是一个普通的对象了,所以就会失去响应式</li></ul></li></ul></li><li><p>比方说vue2.x给<strong>对象添加</strong>一个数据要是响应式,必须要通过<code>this.$set</code>或者<code>Vue.set</code>来实现),vue3.0却不用</p></li><li><p>比方说vue2.x对<strong>数组</strong>进行修改,添加,只能使用vue重写的那几个方法,但是vue3.x当中,通过<code>reactive</code>操作的,可以通过下标来操作数组,vue3.0操作过后数组依旧是响应式数据</p></li><li><p>reactive定义的响应式数据是“<strong>深层次的</strong>”,不管有多少层,都是默认全部处理为响应式</p></li><li><p>内部基于 ES6 的 <code>Proxy</code> 实现,通过代理对象操作源对象内部数据进行操作。</p></li></ul><h4 id="示例"><a href="#示例" class="headerlink" title="示例:"></a>示例:</h4><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> { reactive, ref } <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="attr">name</span>: <span class="string">"App"</span>,</span><br><span class="line"> <span class="attr">components</span>: {},</span><br><span class="line"> <span class="comment">// setup是新增的一个配置项,为一个函数,数据,方法,什么的都可以写在这里面</span></span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="comment">//ref对基本数据类型的处理</span></span><br><span class="line"> <span class="keyword">let</span> name = <span class="title function_">ref</span>(<span class="string">"李白"</span>);</span><br><span class="line"> <span class="keyword">let</span> age = <span class="title function_">ref</span>(<span class="number">1000</span>);</span><br><span class="line"> <span class="comment">// let test = reactive("我是基本数据类型");</span></span><br><span class="line"> <span class="comment">//通过reactive函数实现对象的响应式数据</span></span><br><span class="line"> <span class="keyword">let</span> job = <span class="title function_">reactive</span>({</span><br><span class="line"> <span class="attr">type</span>:<span class="string">"前端工程师"</span>,</span><br><span class="line"> <span class="attr">salary</span>:<span class="string">"10K"</span>,</span><br><span class="line"> <span class="attr">address</span>:<span class="string">"尚硅谷"</span>,</span><br><span class="line"> <span class="attr">hobby</span>:[<span class="string">"吃饭"</span>,<span class="string">"睡觉"</span>,<span class="string">"打豆豆"</span>]</span><br><span class="line"> })</span><br><span class="line"></span><br><span class="line"> <span class="keyword">function</span> <span class="title function_">changeValue</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="comment">//改变ref当中的基本数据类型</span></span><br><span class="line"> name.<span class="property">value</span> = <span class="string">"李黑"</span>;</span><br><span class="line"> age.<span class="property">value</span> = <span class="number">2000</span>;</span><br><span class="line"></span><br><span class="line"> <span class="comment">//改变reactive的值</span></span><br><span class="line"> job.<span class="property">type</span> = <span class="string">"高级工程师"</span></span><br><span class="line"> job.<span class="property">salary</span> = <span class="string">"30K"</span></span><br><span class="line"> job.<span class="property">address</span> = <span class="string">"苹果"</span></span><br><span class="line"> job.<span class="property">hobby</span>[<span class="number">0</span>] = <span class="string">"吃零食"</span>;<span class="comment">//vue3是可以这样子做的</span></span><br><span class="line"> } </span><br><span class="line"></span><br><span class="line"> <span class="comment">//需要返回一个对象,对象当中的属性和方法,均可以在模板当中直接使用</span></span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> name,</span><br><span class="line"> age,</span><br><span class="line"> changeValue,</span><br><span class="line"> job,</span><br><span class="line"> };</span><br><span class="line"> },</span><br><span class="line">};</span><br></pre></td></tr></table></figure><h4 id="失去响应式示例"><a href="#失去响应式示例" class="headerlink" title="失去响应式示例"></a>失去响应式示例</h4><ul><li><p><strong>reactive定义的数组或者对象,不能直接对整体进行赋值修改,否则定义的数据将失去响应性!!!!!</strong></p><ul><li>因为通过<code>reactive</code>所创建的响应书数据返回的是<code>Proxy</code>对象,如果(保存这个地址的变量)对其整体赋值,那么就不是一个<code>Proxy</code>对象了,而是一个普通的对象了,所以就会失去响应式</li></ul></li><li><p>如下示例,当经过一秒后,页面显示的内容并没有被改变!</p></li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span></span></span><br><span class="line"><span class="language-xml"> {{ banner }}</span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> { ref } <span class="keyword">from</span> <span class="string">"vue"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> { reactive } <span class="keyword">from</span> <span class="string">"vue"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> { onMounted } <span class="keyword">from</span> <span class="string">"vue"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"App"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> banner = <span class="title function_">reactive</span>({ <span class="attr">age</span>: <span class="number">0</span> });</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//banner执行的是`Proxy`对象</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"修改之前的banner"</span>, banner);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">onMounted</span>(<span class="function">() =></span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="built_in">setTimeout</span>(<span class="function">() =></span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> banner = { <span class="attr">age</span>: <span class="number">1000</span> };</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"修改完成"</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//banner指向了一个普通的对象</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"修改之后的banner"</span>, banner);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }, <span class="number">2000</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> });</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> banner,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> };</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">style</span> <span class="attr">lang</span>=<span class="string">"less"</span>></span><span class="tag"></<span class="name">style</span>></span></span></span><br></pre></td></tr></table></figure><h3 id="6-reactive对比ref"><a href="#6-reactive对比ref" class="headerlink" title="6.reactive对比ref"></a>6.reactive对比ref</h3><ul><li>从定义数据角度对比:<ul><li>ref用来定义:<strong style="color:#dd5145">基本类型数据</strong>。</li><li>reactive用来定义:<strong style="color:#dd5145">对象(或数组)类型数据</strong>。</li><li>备注:ref也可以用来定义<strong style="color:#dd5145">对象(或数组)类型数据</strong>, 它内部会自动通过<code>reactive</code>转为<strong style="color:#dd5145">代理对象</strong>。</li></ul></li><li>从原理角度对比:<ul><li>ref通过<code>Object.defineProperty()</code>的<code>get</code>与<code>set</code>来实现响应式(数据劫持)。</li><li>reactive通过使用<strong style="color:#dd5145">Proxy</strong>来实现响应式(数据劫持), 并通过<strong style="color:#dd5145">Reflect</strong>操作<strong style="color:orange">源对象</strong>内部的数据。</li></ul></li><li>从使用角度对比:<ul><li>ref定义的数据:操作数据<strong style="color:#dd5145">需要</strong><code>.value</code>,读取数据时模板中直接读取<strong style="color:#dd5145">不需要</strong><code>.value</code>。</li><li>reactive定义的数据:操作数据与读取数据:<strong style="color:#dd5145">均不需要</strong><code>.value</code>。</li></ul></li></ul><h3 id="7-vue2响应式原理-演示简版"><a href="#7-vue2响应式原理-演示简版" class="headerlink" title="7.vue2响应式原理-演示简版"></a>7.vue2响应式原理-演示简版</h3><h4 id="实现原理:"><a href="#实现原理:" class="headerlink" title="实现原理:"></a>实现原理:</h4><ul><li><p>对象类型:通过<code>Object.defineProperty()</code>对属性的读取、修改进行拦截(数据劫持)。</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="title class_">Object</span>.<span class="title function_">defineProperty</span>(data, <span class="string">'count'</span>, {</span><br><span class="line"> get () {}, </span><br><span class="line"> set () {}</span><br><span class="line">})</span><br></pre></td></tr></table></figure></li><li><p>数组类型:通过重写更新数组的一系列方法来实现拦截。(对数组的变更方法进行了包裹)。</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="title function_">push</span>()</span><br><span class="line"><span class="title function_">pop</span>()</span><br><span class="line"><span class="title function_">shift</span>()</span><br><span class="line"><span class="title function_">unshift</span>()</span><br><span class="line"><span class="title function_">splice</span>()</span><br><span class="line"><span class="title function_">sort</span>()</span><br><span class="line"><span class="title function_">reverse</span>()</span><br></pre></td></tr></table></figure></li><li><p>vue2.x当中直接添加,<strong>非响应式</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="title function_">data</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> <span class="title class_">Person</span>: {</span><br><span class="line"> <span class="attr">name</span>: <span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">age</span>: <span class="number">1000</span>,</span><br><span class="line"> <span class="attr">hobby</span>: [<span class="string">"吃饭"</span>, <span class="string">"睡觉"</span>, <span class="string">"打豆豆"</span>],</span><br><span class="line"> },</span><br><span class="line"> };</span><br><span class="line"> },</span><br><span class="line"> <span class="attr">methods</span>: {</span><br><span class="line"> <span class="title function_">addSex</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="comment">// 直接添加,添加后的数据非响应式</span></span><br><span class="line"> <span class="variable language_">this</span>.<span class="property">Person</span>.<span class="property">sex</span> = <span class="string">"男"</span>;</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="variable language_">this</span>.<span class="property">Person</span>);</span><br><span class="line"> },</span><br><span class="line"> },</span><br><span class="line">};</span><br></pre></td></tr></table></figure></li><li><p>通过<code>this.$set(添加的对象,新增加的属性名称/要修改的索引下标,新添加值/新值)</code>,<strong>为响应式</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br></pre></td><td class="code"><pre><span class="line"><script></span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="attr">name</span>: <span class="string">"App"</span>,</span><br><span class="line"> <span class="attr">components</span>: {},</span><br><span class="line"> <span class="title function_">data</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> <span class="title class_">Person</span>: {</span><br><span class="line"> <span class="attr">name</span>: <span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">age</span>: <span class="number">1000</span>,</span><br><span class="line"> <span class="attr">hobby</span>: [<span class="string">"吃饭"</span>, <span class="string">"睡觉"</span>, <span class="string">"打豆豆"</span>],</span><br><span class="line"> },</span><br><span class="line"> };</span><br><span class="line"> },</span><br><span class="line"> <span class="attr">methods</span>: {</span><br><span class="line"> <span class="title function_">addSex</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="comment">// 直接添加,添加后的数据非响应式</span></span><br><span class="line"> <span class="comment">// this.Person.sex = "男";</span></span><br><span class="line"> <span class="comment">// console.log(this.Person);</span></span><br><span class="line"> <span class="comment">//通过this.$set添加 响应式</span></span><br><span class="line"> <span class="variable language_">this</span>.$set(<span class="variable language_">this</span>.<span class="property">Person</span>, <span class="string">"sex"</span>, <span class="string">"男"</span>);</span><br><span class="line"> },</span><br><span class="line"> <span class="title function_">changeHobby</span>(<span class="params"></span>){</span><br><span class="line"> <span class="comment">//通过this.$set添加/修改 响应式</span></span><br><span class="line"> <span class="variable language_">this</span>.$set(<span class="variable language_">this</span>.<span class="property">Person</span>.<span class="property">hobby</span>,<span class="number">2</span>,<span class="string">"打游戏"</span>);</span><br><span class="line"> <span class="variable language_">this</span>.$set(<span class="variable language_">this</span>.<span class="property">Person</span>.<span class="property">hobby</span>,<span class="number">3</span>,<span class="string">"吃饭饭"</span>);</span><br><span class="line"> }</span><br><span class="line"> },</span><br><span class="line">};</span><br><span class="line"></script></span><br></pre></td></tr></table></figure></li></ul><h4 id="vue2对响应式数据存在的问题"><a href="#vue2对响应式数据存在的问题" class="headerlink" title="vue2对响应式数据存在的问题"></a>vue2对响应式数据存在的问题</h4><ul><li>新增属性,删除属性,界面不会更新(vue3.x已经解决)</li><li>直接通过下标修改数组,界面不会自动更新(vue3.x已经解决)</li><li>以上vue2.x的解决都是通过重写方法或者this.$set\vue.set</li></ul><h3 id="8-vue3响应式原理和vue2响应式原理-分析简版"><a href="#8-vue3响应式原理和vue2响应式原理-分析简版" class="headerlink" title="8.vue3响应式原理和vue2响应式原理-分析简版"></a>8.vue3响应式原理和vue2响应式原理-分析简版</h3><h4 id="vue2响应式代码示例演示"><a href="#vue2响应式代码示例演示" class="headerlink" title="vue2响应式代码示例演示"></a>vue2响应式代码示例演示</h4><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br></pre></td><td class="code"><pre><span class="line"><script></span><br><span class="line"><span class="comment">// vue2的响应式原理 - 当我们在增加/删除/修改/读取的时候可以捕捉到</span></span><br><span class="line"><span class="comment">// 缺点,添加无法变成响应式,修改可以,读取也可以</span></span><br><span class="line"><span class="keyword">var</span> <span class="title class_">Person1</span> = {</span><br><span class="line"> <span class="attr">name</span>: <span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">age</span>: <span class="number">1000</span>,</span><br><span class="line">}</span><br><span class="line"><span class="keyword">var</span> p1 = {};</span><br><span class="line"><span class="title class_">Object</span>.<span class="title function_">defineProperty</span>(p1, <span class="string">"name"</span>, {</span><br><span class="line"> <span class="comment">//如果不设置这个,delete 删除属性是删除不掉的</span></span><br><span class="line"> <span class="attr">configurable</span>: <span class="literal">true</span>,</span><br><span class="line"> <span class="title function_">get</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"你读取了name"</span>);</span><br><span class="line"> <span class="keyword">return</span> <span class="title class_">Person1</span>.<span class="property">name</span>;</span><br><span class="line"> },</span><br><span class="line"> <span class="title function_">set</span>(<span class="params">newValue</span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"你设置了name,并将值设置为"</span>, newValue);</span><br><span class="line"> <span class="title class_">Person1</span>.<span class="property">name</span> = newValue;</span><br><span class="line"> }</span><br><span class="line">});</span><br><span class="line"><span class="title class_">Object</span>.<span class="title function_">defineProperty</span>(p1, <span class="string">"age"</span>, {</span><br><span class="line"> <span class="comment">//如果不设置这个,delete 删除属性是删除不掉的</span></span><br><span class="line"> <span class="attr">configurable</span>: <span class="literal">true</span>,</span><br><span class="line"> <span class="title function_">get</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"你读取了age"</span>);</span><br><span class="line"> <span class="keyword">return</span> <span class="title class_">Person1</span>.<span class="property">age</span>;</span><br><span class="line"> },</span><br><span class="line"> <span class="title function_">set</span>(<span class="params">newValue</span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"你设置了age,并将值设置为"</span>, newValue);</span><br><span class="line"> <span class="title class_">Person1</span>.<span class="property">age</span> = newValue;</span><br><span class="line"> }</span><br><span class="line">});</span><br><span class="line"></script></span><br></pre></td></tr></table></figure><h4 id="vue3响应式原理代码示例演示"><a href="#vue3响应式原理代码示例演示" class="headerlink" title="vue3响应式原理代码示例演示"></a>vue3响应式原理代码示例演示</h4><blockquote><p>vue3响应式原理主要是通过<strong>调用window上面的方法 - Proxy</strong></p></blockquote><ul><li><strong>Proxy语法格式</strong><ul><li>new Proxy(要监视的数据,配置项目)</li><li>配置项目当中,异步传入一个对象,里面可以配置<ul><li><code>get(targetObj,propName){ ... }</code></li><li><code>set(targetObj,propName){ ... }</code></li><li><code>deleteProxy(targetObj,propName){ ... }</code></li></ul></li><li>参数<strong>targetObj</strong>为被修改的对象</li><li>参数<strong>propName</strong>为被修改的属性名称</li></ul></li><li>最基本的实现-无检测,<strong>但是可以实现基本的p2删除,修改,添加,删除反馈到Person2</strong>,但是无法捕捉到变化</li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//vue3响应式原理 - 调用window上面的方法Proxy</span></span><br><span class="line"><span class="keyword">var</span> <span class="title class_">Person2</span> = {</span><br><span class="line"> <span class="attr">name</span>:<span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">age</span>:<span class="number">1000</span>,</span><br><span class="line">}</span><br><span class="line"><span class="comment">//这样子实现了p2修改,Person2也会被修改</span></span><br><span class="line"><span class="keyword">var</span> p2 = <span class="keyword">new</span> <span class="title class_">Proxy</span>(<span class="title class_">Person2</span>,{</span><br><span class="line"></span><br><span class="line">});</span><br></pre></td></tr></table></figure><ul><li>响应式的实现-添加检测操作,这样子捕捉到对谁修改了,可以进行一些操作(也就是我们经常需要的数据变了,视图也变化的操作)</li></ul><p>注意这里除了set get 还有<strong>一个新的 deleteProperty</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//vue3响应式原理 - 调用window上面的方法Proxy</span></span><br><span class="line"><span class="keyword">var</span> <span class="title class_">Person2</span> = {</span><br><span class="line"> <span class="attr">name</span>:<span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">age</span>:<span class="number">1000</span>,</span><br><span class="line">}</span><br><span class="line"><span class="comment">//这样子实现了p2修改,Person2也会被修改</span></span><br><span class="line"><span class="keyword">var</span> p2 = <span class="keyword">new</span> <span class="title class_">Proxy</span>(<span class="title class_">Person2</span>,{</span><br><span class="line"> <span class="comment">/* 参数1为被操作的对象 参数2为被操作的属性 */</span></span><br><span class="line"> <span class="title function_">get</span>(<span class="params">targetObj,propName</span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`检测到<span class="subst">${propName}</span>属性被读取了`</span>); </span><br><span class="line"> <span class="keyword">return</span> targetObj[propName]</span><br><span class="line"> },</span><br><span class="line"> <span class="title function_">set</span>(<span class="params">targetObj,propName,newValue</span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`检测到<span class="subst">${propName}</span>属性将要被修改为<span class="subst">${newValue}</span>`</span>);</span><br><span class="line"> targetObj[propName] = newValue;</span><br><span class="line"> },</span><br><span class="line"> <span class="comment">//删除检测</span></span><br><span class="line"> <span class="title function_">deleteProperty</span>(<span class="params">targetObj,propName</span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`属性<span class="subst">${propName}</span>将要被删除`</span>);</span><br><span class="line"> <span class="keyword">return</span> <span class="keyword">delete</span> targetObj[propName];</span><br><span class="line"> }</span><br><span class="line">});</span><br><span class="line"></span><br><span class="line"><span class="keyword">var</span> <span class="title class_">Person</span> = {</span><br><span class="line"> <span class="attr">name</span>:<span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">age</span>:<span class="number">1000</span>,</span><br><span class="line">};</span><br><span class="line"><span class="keyword">var</span> p = <span class="keyword">new</span> <span class="title class_">Proxy</span>(<span class="title class_">Person</span>,{</span><br><span class="line"> <span class="title function_">get</span>(<span class="params">targetObj,propName</span>){</span><br><span class="line"> <span class="comment">//输出 {name: '李白', age: 1000} 'name'</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(targetObj,propName);</span><br><span class="line"> },</span><br><span class="line">})</span><br><span class="line"><span class="comment">//触发get</span></span><br><span class="line"><span class="variable language_">console</span>.<span class="title function_">log</span>(p.<span class="property">name</span>);</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="comment">//试试看数组</span></span><br><span class="line"><span class="keyword">var</span> hobby = [<span class="string">'吃饭'</span>, <span class="string">'睡觉'</span>, <span class="string">'打豆豆'</span>];</span><br><span class="line"><span class="keyword">var</span> p3 = <span class="keyword">new</span> <span class="title class_">Proxy</span>(hobby, {</span><br><span class="line"> <span class="title function_">get</span>(<span class="params">targetObj, propName</span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`检测到<span class="subst">${propName}</span>属性被读取了`</span>);</span><br><span class="line"> <span class="keyword">return</span> targetObj[propName]</span><br><span class="line"> },</span><br><span class="line"> <span class="title function_">set</span>(<span class="params">targetObj, propName, newValue</span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`检测到<span class="subst">${propName}</span>属性将要被修改为<span class="subst">${newValue}</span>`</span>);</span><br><span class="line"> targetObj[propName] = newValue;</span><br><span class="line"> },</span><br><span class="line"> <span class="comment">//删除检测</span></span><br><span class="line"> <span class="title function_">deleteProperty</span>(<span class="params">targetObj, propName</span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`属性<span class="subst">${propName}</span>将要被删除`</span>);</span><br><span class="line"> <span class="keyword">return</span> <span class="keyword">delete</span> targetObj[propName];</span><br><span class="line"> }</span><br><span class="line">})</span><br></pre></td></tr></table></figure><ul><li>vue3官方真正实现是通过proxy(代理) Reflect(反射) 来实现的</li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//vue3响应式原理 - 调用window上面的方法Proxy</span></span><br><span class="line"><span class="keyword">var</span> <span class="title class_">Person2</span> = {</span><br><span class="line"> <span class="attr">name</span>: <span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">age</span>: <span class="number">1000</span>,</span><br><span class="line">}</span><br><span class="line"><span class="comment">//这样子实现了p2修改,Person2也会被修改</span></span><br><span class="line"><span class="keyword">var</span> p2 = <span class="keyword">new</span> <span class="title class_">Proxy</span>(<span class="title class_">Person2</span>, {</span><br><span class="line"> <span class="comment">/* 参数1为操作的对象 参数2为操作的属性 */</span></span><br><span class="line"> <span class="title function_">get</span>(<span class="params">targetObj, propName</span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`检测到<span class="subst">${propName}</span>属性被读取了`</span>);</span><br><span class="line"> <span class="comment">// return targetObj[propName];</span></span><br><span class="line"> <span class="comment">//实际上vue是通过window上面的Reflect方法进行返回属性的</span></span><br><span class="line"> <span class="comment">//因为Reflect可以会返回获取成功还是失败</span></span><br><span class="line"> <span class="keyword">return</span> <span class="title class_">Reflect</span>.<span class="title function_">get</span>(targetObj,propName);</span><br><span class="line"> },</span><br><span class="line"> <span class="title function_">set</span>(<span class="params">targetObj, propName, newValue</span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`检测到<span class="subst">${propName}</span>属性将要被修改为<span class="subst">${newValue}</span>`</span>);</span><br><span class="line"> <span class="comment">// targetObj[propName] = newValue;</span></span><br><span class="line"> <span class="keyword">return</span> <span class="title class_">Reflect</span>.<span class="title function_">set</span>(targetObj,propName,newValue);</span><br><span class="line"> },</span><br><span class="line"> <span class="comment">//删除检测</span></span><br><span class="line"> <span class="title function_">deleteProperty</span>(<span class="params">targetObj, propName</span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`属性<span class="subst">${propName}</span>将要被删除`</span>);</span><br><span class="line"> <span class="comment">// return delete targetObj[propName];</span></span><br><span class="line"> <span class="comment">//为什么不用delete,delete被占用了,所以用deleteProperty</span></span><br><span class="line"> <span class="keyword">return</span> <span class="title class_">Reflect</span>.<span class="title function_">deleteProperty</span>(targetObj,propName);</span><br><span class="line"> }</span><br><span class="line">});</span><br><span class="line"><span class="comment">//试试看数组</span></span><br><span class="line"><span class="keyword">var</span> hobby = [<span class="string">'吃饭'</span>, <span class="string">'睡觉'</span>, <span class="string">'打豆豆'</span>];</span><br><span class="line"><span class="keyword">var</span> p3 = <span class="keyword">new</span> <span class="title class_">Proxy</span>(hobby, {</span><br><span class="line"> <span class="title function_">get</span>(<span class="params">targetObj, propName</span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`检测到<span class="subst">${propName}</span>属性被读取了`</span>);</span><br><span class="line"> <span class="keyword">return</span> targetObj[propName]</span><br><span class="line"> },</span><br><span class="line"> <span class="title function_">set</span>(<span class="params">targetObj, propName, newValue</span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`检测到<span class="subst">${propName}</span>属性将要被修改为<span class="subst">${newValue}</span>`</span>);</span><br><span class="line"> targetObj[propName] = newValue;</span><br><span class="line"> },</span><br><span class="line"> <span class="comment">//删除检测</span></span><br><span class="line"> <span class="title function_">deleteProperty</span>(<span class="params">targetObj, propName</span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">`属性<span class="subst">${propName}</span>将要被删除`</span>);</span><br><span class="line"> <span class="keyword">return</span> <span class="keyword">delete</span> targetObj[propName];</span><br><span class="line"> }</span><br><span class="line">})</span><br></pre></td></tr></table></figure><ul><li>有人<strong>读取</strong>的时候调用 get</li><li>有人<strong>修改/添加</strong>的时候调用set</li><li>有人<strong>删除</strong>的时候调用deleteProperty</li></ul><h3 id="9-setup注意的二个点"><a href="#9-setup注意的二个点" class="headerlink" title="9.setup注意的二个点"></a>9.setup注意的二个点</h3><h4 id="注意点1-setup优于所有的生命周期先执行"><a href="#注意点1-setup优于所有的生命周期先执行" class="headerlink" title="注意点1-setup优于所有的生命周期先执行"></a>注意点1-setup优于所有的生命周期先执行</h4><ul><li>在<code>beforeCreate</code>之前,<code>setup</code>就会被执行,但是<strong>此时的setup当中的this是undefined</strong>(所以这就是为什么vue3.x的<code>setup</code>当中不可以使用vue2.x配置对象当中<code>data</code>,<code>computed</code>,<code>methods</code>等,因为执行setup函数的时候,data,computed,methods等都还没有被执行,怎么可以获取到里面的数据)</li></ul><h4 id="注意点2-setup的参数"><a href="#注意点2-setup的参数" class="headerlink" title="注意点2-setup的参数"></a>注意点2-setup的参数</h4><ul><li>参数1—<strong>props</strong>:值为<strong>对象</strong>—-包含,组件外部传递过来的属性,并且组件内部使用props配置对象进行接收了的值,就会出现在setup的props参数当中</li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//父组件</span></span><br><span class="line"><<span class="title class_">Demo</span> weight=<span class="string">"100kg"</span> height=<span class="string">"180"</span>></<span class="title class_">Demo</span>></span><br></pre></td></tr></table></figure><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//子组件</span></span><br><span class="line"><span class="keyword">import</span> { reactive } <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="comment">//声明接收了父组件传递过来的值</span></span><br><span class="line"> <span class="attr">props</span>:[<span class="string">'weight'</span>],</span><br><span class="line"> <span class="title function_">setup</span>(<span class="params">props, context</span>) {</span><br><span class="line"> <span class="comment">//输出 {weight: '100kg'}</span></span><br><span class="line"> <span class="comment">//由于height没有被props配置对象声明接收</span></span><br><span class="line"> <span class="comment">//所以输出setup参数当中的props没有出现height</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(props);</span><br><span class="line"> <span class="keyword">let</span> data = <span class="title function_">reactive</span>({</span><br><span class="line"> <span class="title class_">Person</span>: {</span><br><span class="line"> <span class="attr">name</span>: <span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">sex</span>: <span class="string">"男"</span>,</span><br><span class="line"> },</span><br><span class="line"> });</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> data,</span><br><span class="line"> };</span><br><span class="line"> },</span><br><span class="line">};</span><br></pre></td></tr></table></figure><ul><li><p>参数2—<strong>context</strong>:上下文对象</p><ul><li><p><strong>attrts</strong>: 值为对象,包含着从外部组件传递过来的属性,但是组件内部并没有在使用<code>props</code>配置对象接收的属性(<code>attrs</code>作用相当于捡下配置对象<code>props</code>的漏网之鱼)</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//父组件</span></span><br><span class="line"><<span class="title class_">Demo</span> weight=<span class="string">"100kg"</span> height=<span class="string">"180"</span>></<span class="title class_">Demo</span>></span><br><span class="line"></span><br><span class="line"><span class="comment">//子组件</span></span><br><span class="line"><span class="keyword">import</span> { reactive } <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="comment">//声明接收了父组件传递过来的值</span></span><br><span class="line"> <span class="attr">props</span>:[<span class="string">'weight'</span>],</span><br><span class="line"> <span class="title function_">setup</span>(<span class="params">props, context</span>) {</span><br><span class="line"> <span class="comment">//输出Proxy {height: '180', __vInternal: 1}</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(context.<span class="property">attrs</span>);</span><br><span class="line"> <span class="keyword">let</span> data = <span class="title function_">reactive</span>({</span><br><span class="line"> <span class="title class_">Person</span>: {</span><br><span class="line"> <span class="attr">name</span>: <span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">sex</span>: <span class="string">"男"</span>,</span><br><span class="line"> },</span><br><span class="line"> });</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> data,</span><br><span class="line"> };</span><br><span class="line"> },</span><br><span class="line">};</span><br></pre></td></tr></table></figure></li><li><p><strong>slots</strong>: 收到的插槽内容 相当于<code>this.$slots</code></p></li><li><p><strong>emit</strong>: 分发自定义事件的函数(存储着组件接收到的自定义事件),类似于<code>this.$emit</code> ,使用方法和<code>this.$emit</code>一样</p><ul><li><p>当然了,vue3多出来的一个配置项目叫<strong>emits</strong> ,负责接收传递过来的自定义事件,和<code>props</code>配置对象一样.(老师演示的时候必须要加这个<code>emits</code>配置对象去接收自定义事件,不然会有警告提示,我使用的时候是不用加也可以的)</p></li><li><p><code>context.emit</code> 的使用</p><p><strong>父组件</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">Demo</span> @<span class="attr">sayHello</span>=<span class="string">"hello"</span> <span class="attr">weight</span>=<span class="string">"100kg"</span> <span class="attr">height</span>=<span class="string">"180"</span>></span><span class="tag"></<span class="name">Demo</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> <span class="title class_">Demo</span> <span class="keyword">from</span> <span class="string">"@/components/Demo"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"App"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">components</span>: { <span class="title class_">Demo</span> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">function</span> <span class="title function_">hello</span>(<span class="params">value</span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">alert</span>(<span class="string">"我会说"</span> + value);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> hello,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> };</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br></pre></td></tr></table></figure><p><strong>子组件</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是Demo<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> {{ data.Person.name }}</span></span><br><span class="line"><span class="language-xml"> {{ data.Person.age }}</span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">slot</span> <span class="attr">name</span>=<span class="string">"one"</span>></span><span class="tag"></<span class="name">slot</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"chufa"</span>></span>按钮触发自定义事件<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> { reactive } <span class="keyword">from</span> <span class="string">"vue"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">""</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">props</span>:[<span class="string">'weight'</span>],</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">emits</span>:[<span class="string">"sayHello"</span>],<span class="comment">//可加可不加</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params">props, context</span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> data = <span class="title function_">reactive</span>({</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title class_">Person</span>: {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"李白"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">sex</span>: <span class="string">"男"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> });</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">function</span> <span class="title function_">chufa</span>(<span class="params"></span>){</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> context.<span class="title function_">emit</span>(<span class="string">"sayHello"</span>,<span class="string">"叫我将军大人"</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> data,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> chufa</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> };</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">style</span>></span></span></span><br><span class="line"><span class="language-xml"><span class="tag"></<span class="name">style</span>></span></span></span><br><span class="line"></span><br></pre></td></tr></table></figure></li></ul></li></ul></li></ul><h4 id="为什么自定义事件需要通过emit来去使用呢"><a href="#为什么自定义事件需要通过emit来去使用呢" class="headerlink" title="为什么自定义事件需要通过emit来去使用呢?"></a>为什么自定义事件需要通过emit来去使用呢?</h4><ul><li>之前已经说过了,<code>setup</code>当中是没有<code>this</code>的,所以我们不可以像vue2时候通过<code>this.$emit</code>来触发自定义事件,我们就必须要通过<code>setup</code>当中的第二个参数<code>context</code>来去代替<code>this</code></li></ul><h3 id="10-vue3的computed"><a href="#10-vue3的computed" class="headerlink" title="10.vue3的computed"></a>10.vue3的computed</h3><h4 id="回顾vue2时候的computed"><a href="#回顾vue2时候的computed" class="headerlink" title="回顾vue2时候的computed"></a>回顾vue2时候的computed</h4><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是Demo<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> 姓:<span class="tag"><<span class="name">input</span> <span class="attr">v-model</span>=<span class="string">"name"</span> /></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">br</span> /></span></span></span><br><span class="line"><span class="language-xml"> 名:<span class="tag"><<span class="name">input</span> <span class="attr">v-model</span>=<span class="string">"last_name"</span> /></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>全称展示:<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> 全称修改:<span class="tag"><<span class="name">input</span> <span class="attr">v-model</span>=<span class="string">"fullName"</span> /></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">""</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">data</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"李"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">last_name</span>: <span class="string">"白"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> };</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">computed</span>: {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//简写</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">// fullName() {</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">// return this.name + "-" + this.last_name;</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">// },</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> </span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//全写</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">fullName</span>:{</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">get</span>(<span class="params"></span>){</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> <span class="variable language_">this</span>.<span class="property">name</span> + <span class="string">"-"</span> + <span class="variable language_">this</span>.<span class="property">last_name</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">set</span>(<span class="params">newValue</span>){</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> [<span class="variable language_">this</span>.<span class="property">name</span>,<span class="variable language_">this</span>.<span class="property">last_name</span>] = newValue.<span class="title function_">split</span>(<span class="string">"-"</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br></pre></td></tr></table></figure><h4 id="vue3时候的computed计算属性"><a href="#vue3时候的computed计算属性" class="headerlink" title="vue3时候的computed计算属性"></a>vue3时候的computed计算属性</h4><ul><li><p>可以传入一个回调函数,返回值作为计算后的值,也可以传入一个配置对象,设置getter 和 setter</p></li><li><p>首先引入包</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {computed} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li><li><p>添加只读,不可修改 - <strong>简写方式</strong></p></li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> { computed, reactive } <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="keyword">let</span> person = <span class="title function_">reactive</span>({</span><br><span class="line"> <span class="attr">name</span>:<span class="string">"李"</span>,</span><br><span class="line"> <span class="attr">last_name</span>:<span class="string">"白"</span>,</span><br><span class="line"> });</span><br><span class="line"> <span class="comment">//只读,不可修改</span></span><br><span class="line"> person.<span class="property">fullName</span> = <span class="title function_">computed</span>(<span class="function">()=></span>{</span><br><span class="line"> <span class="keyword">return</span> person.<span class="property">name</span> + <span class="string">"-"</span> + person.<span class="property">last_name</span>;</span><br><span class="line"> });</span><br><span class="line"></span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> person</span><br><span class="line"> }</span><br><span class="line"> },</span><br><span class="line">};</span><br></pre></td></tr></table></figure><ul><li><p>可读可修改,和computed一个,添加配置对象,设置<code>get</code> 和 <code>set</code>即可实现可读可修改 -完整写法</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> { computed, reactive } <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="keyword">let</span> person = <span class="title function_">reactive</span>({</span><br><span class="line"> <span class="attr">name</span>:<span class="string">"李"</span>,</span><br><span class="line"> <span class="attr">last_name</span>:<span class="string">"白"</span>,</span><br><span class="line"> });</span><br><span class="line"> <span class="comment">//可读可修改</span></span><br><span class="line"> person.<span class="property">fullName</span> = <span class="title function_">computed</span>({</span><br><span class="line"> <span class="title function_">get</span>(<span class="params"></span>){</span><br><span class="line"> <span class="keyword">return</span> person.<span class="property">name</span> + <span class="string">"-"</span> + person.<span class="property">last_name</span>;</span><br><span class="line"> },</span><br><span class="line"> <span class="title function_">set</span>(<span class="params">newValue</span>){</span><br><span class="line"> <span class="comment">//解构赋值</span></span><br><span class="line"> [person.<span class="property">name</span>,person.<span class="property">last_name</span>] = newValue.<span class="title function_">split</span>(<span class="string">"-"</span>);</span><br><span class="line"> }</span><br><span class="line"> })</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> person</span><br><span class="line"> }</span><br><span class="line"> },</span><br><span class="line">};</span><br></pre></td></tr></table></figure></li></ul><h3 id="11-vue3的watch"><a href="#11-vue3的watch" class="headerlink" title="11.vue3的watch"></a>11.vue3的watch</h3><ul><li><p>首先导入包</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {watch} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li><li><p>语法格式:</p><ul><li>watch(监视的数据,回调函数)<ul><li>回调函数有二个参数,一个为newValue,一个为oldValue</li></ul></li></ul></li><li><p>两个小“坑”:</p><ul><li>监视reactive定义的响应式数据时:oldValue无法正确获取、强制开启了深度监视(deep配置失效)</li><li>监视reactive定义的响应式数据中某个属性时:deep配置有效</li></ul></li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//情况一:监视ref定义的响应式数据</span></span><br><span class="line"><span class="title function_">watch</span>(sum,<span class="function">(<span class="params">newValue,oldValue</span>)=></span>{</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">'sum变化了'</span>,newValue,oldValue)</span><br><span class="line">},{<span class="attr">immediate</span>:<span class="literal">true</span>})</span><br><span class="line"></span><br><span class="line"><span class="comment">//情况二:监视多个ref定义的响应式数据 使用数组形式</span></span><br><span class="line"><span class="title function_">watch</span>([sum,msg],<span class="function">(<span class="params">newValue,oldValue</span>)=></span>{</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">'sum或msg变化了'</span>,newValue,oldValue)</span><br><span class="line">}) </span><br><span class="line"></span><br><span class="line"><span class="comment">/* 情况三:监视reactive定义的响应式数据</span></span><br><span class="line"><span class="comment"> 若watch监视的是reactive定义的响应式数据,则无法正确获得oldValue!!</span></span><br><span class="line"><span class="comment"> 若watch监视的是reactive定义的响应式数据,则强制开启了深度监视 </span></span><br><span class="line"><span class="comment">*/</span></span><br><span class="line"><span class="title function_">watch</span>(person,<span class="function">(<span class="params">newValue,oldValue</span>)=></span>{</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">'person变化了'</span>,newValue,oldValue)</span><br><span class="line">},{<span class="attr">immediate</span>:<span class="literal">true</span>,<span class="attr">deep</span>:<span class="literal">false</span>}) <span class="comment">//此处的deep配置不再奏效</span></span><br><span class="line"></span><br><span class="line"><span class="comment">//情况四:监视reactive定义的响应式数据中的[某个属性] 注意形式</span></span><br><span class="line"><span class="title function_">watch</span>(<span class="function">()=></span>person.<span class="property">job</span>,<span class="function">(<span class="params">newValue,oldValue</span>)=></span>{</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">'person的job变化了'</span>,newValue,oldValue)</span><br><span class="line">},{<span class="attr">immediate</span>:<span class="literal">true</span>,<span class="attr">deep</span>:<span class="literal">true</span>}) </span><br><span class="line"></span><br><span class="line"><span class="comment">//情况五:监视reactive定义的响应式数据中的[某些属性] 注意形式</span></span><br><span class="line"><span class="title function_">watch</span>([<span class="function">()=></span>person.<span class="property">job</span>,<span class="function">()=></span>person.<span class="property">name</span>],<span class="function">(<span class="params">newValue,oldValue</span>)=></span>{</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">'person的job变化了'</span>,newValue,oldValue)</span><br><span class="line">},{<span class="attr">immediate</span>:<span class="literal">true</span>,<span class="attr">deep</span>:<span class="literal">true</span>})</span><br><span class="line"></span><br><span class="line"><span class="comment">//特殊情况</span></span><br><span class="line"><span class="title function_">watch</span>(<span class="function">()=></span>person.<span class="property">job</span>,<span class="function">(<span class="params">newValue,oldValue</span>)=></span>{</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">'person的job变化了'</span>,newValue,oldValue)</span><br><span class="line">},{<span class="attr">deep</span>:<span class="literal">true</span>}) <span class="comment">//此处由于监视的是reactive素定义的对象中的某个属性,所以deep配置有效</span></span><br></pre></td></tr></table></figure><ul><li><p>针对监视是否有value的值的分析 ref对象讨论(reactive对象不需要讨论)</p><ul><li><p>结论:要监视数据的变化,<strong>必须要是真正保存数据的结构</strong>才可以监视成功</p><ul><li><p>所以ref创建的对象/引用数据类型需要添加一层<code>value</code>才可以监视到变化,或者添加一下深度监视</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">let</span> person = <span class="title function_">ref</span>({</span><br><span class="line"> <span class="attr">name</span>: <span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">age</span>: <span class="number">18</span>,</span><br><span class="line"> <span class="attr">jobList</span>: {</span><br><span class="line"> <span class="attr">j1</span>: {</span><br><span class="line"> <span class="attr">salary</span>: <span class="number">13</span>,</span><br><span class="line"> },</span><br><span class="line"> },</span><br><span class="line">}); </span><br><span class="line"><span class="title function_">watch</span>(person.<span class="property">value</span>,<span class="function">(<span class="params">newValue,oldValue</span>)=></span>{</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"person被改变了"</span>);</span><br><span class="line">}) </span><br><span class="line"><span class="comment">// 或者</span></span><br><span class="line"><span class="title function_">watch</span>(person,<span class="function">(<span class="params">newValue,oldValue</span>)=></span>{</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"person被改变了"</span>);</span><br><span class="line">},{<span class="attr">deep</span>:<span class="literal">true</span>})</span><br><span class="line"></span><br></pre></td></tr></table></figure></li></ul></li><li><p>对于ref所创建的<strong>基本数据类型</strong>,<strong>第一个参数直接写入就可以</strong> 比如<code>let number = ref(0);</code></p><ul><li><p>因为真正监视的是ref所创建的<code>refImpl对象</code>,监视里面的<code>RefImpl对象</code>当中<code>value</code>的值的变化</p></li><li><p>如图 当我们修改值的时候,实际上修改的是<code>value</code>的值,所以监视的时候发现<code>value</code>变化了,就有反应</p><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206242101799.png"></p></li></ul></li><li><p>对于ref当中的<strong>引用数据类型</strong>,需要添加value获取真正保存数据的结构proxy 或者添加一下深度监视</p><ul><li><p>因为对于引用数据类型,ref是交给<code>proxy</code>来创建的,</p></li><li><p>所以书写代码的时候,第一个参数要么为 <code>person.value</code> 或者第三个参数配置对象添加<code>deep:true</code></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">let</span> person = <span class="title function_">ref</span>({</span><br><span class="line"> <span class="attr">name</span>: <span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">age</span>: <span class="number">18</span>,</span><br><span class="line"> <span class="attr">jobList</span>: {</span><br><span class="line"> <span class="attr">j1</span>: {</span><br><span class="line"> <span class="attr">salary</span>: <span class="number">13</span>,</span><br><span class="line"> },</span><br><span class="line"> },</span><br><span class="line">}); </span><br><span class="line"><span class="title function_">watch</span>(person.<span class="property">value</span>,<span class="function">(<span class="params">newValue,oldValue</span>)=></span>{</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"person被改变了"</span>);</span><br><span class="line">}) </span><br><span class="line"><span class="comment">// 或者</span></span><br><span class="line"><span class="title function_">watch</span>(person,<span class="function">(<span class="params">newValue,oldValue</span>)=></span>{</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"person被改变了"</span>);</span><br><span class="line">},{<span class="attr">deep</span>:<span class="literal">true</span>})</span><br><span class="line"></span><br></pre></td></tr></table></figure><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206242104063.png" alt="ref创建后的person"></p></li></ul></li></ul></li></ul><h3 id="12-vue3的watchEffect"><a href="#12-vue3的watchEffect" class="headerlink" title="12.vue3的watchEffect"></a>12.vue3的watchEffect</h3><ul><li><p>首先是导入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {watchEffect} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li><li><p>watchEffect和watch的区别</p><ul><li><strong>watchEffect:</strong> 不用指明监视哪个属性,监视的回调中用到哪个属性,那就监视用到的属性</li></ul></li><li><p>watchEffect有点像computed:</p><ul><li>但<strong>computed注重的计算出来的值</strong>(回调函数的返回值),所以<strong>必须要写返回值</strong>。</li><li>而<strong>watchEffect更注重的是过程</strong>(回调函数的函数体),所以<strong>不用写返回值</strong>。</li></ul></li><li><p>示例</p></li></ul><p>通过<code>watchEffect</code>来监视用到的值</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>数字{{ number }}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"number += 1"</span>></span>单击我数字+1<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">hr</span>/></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>薪资:{{person.jobList.j1.salary}}K<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"person.jobList.j1.salary += 1"</span>></span>单击我薪资+1<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> { ref, watch, reactive ,watchEffect} <span class="keyword">from</span> <span class="string">"vue"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> number = <span class="title function_">ref</span>(<span class="number">0</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> person = <span class="title function_">ref</span>({</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"李白"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">age</span>: <span class="number">18</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">jobList</span>: {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">j1</span>: {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">salary</span>: <span class="number">13</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> });</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">watchEffect</span>(<span class="function">()=></span>{</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//用到了numbere和person当中的name</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//那么就会自动监视这二个值,当发生变化的时候就执行这个回调</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">const</span> numberName = number.<span class="property">value</span> + person.<span class="property">name</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"watchEffect回调执行了"</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> })</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> number,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> person,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> };</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">style</span> <span class="attr">lang</span>=<span class="string">"less"</span> <span class="attr">scoped</span>></span></span></span><br><span class="line"><span class="language-xml"><span class="tag"></<span class="name">style</span>></span></span></span><br><span class="line"></span><br></pre></td></tr></table></figure><h3 id="13-vue3的生命周期钩子"><a href="#13-vue3的生命周期钩子" class="headerlink" title="13.vue3的生命周期钩子"></a>13.vue3的生命周期钩子</h3><h4 id="vue2的生命周期-vue2生命周期介绍官网"><a href="#vue2的生命周期-vue2生命周期介绍官网" class="headerlink" title="vue2的生命周期 @vue2生命周期介绍官网"></a>vue2的生命周期 <a target="_blank" rel="noopener" href="https://cn.vuejs.org/v2/guide/instance.html#%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F%E5%9B%BE%E7%A4%BA">@vue2生命周期介绍官网</a></h4><h4 id="vue3的生命周期-vue3生命周期介绍官网"><a href="#vue3的生命周期-vue3生命周期介绍官网" class="headerlink" title="vue3的生命周期 @vue3生命周期介绍官网"></a>vue3的生命周期 <a target="_blank" rel="noopener" href="https://v3.cn.vuejs.org/guide/instance.html#%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F%E5%9B%BE%E7%A4%BA">@vue3生命周期介绍官网</a></h4><ul><li><p><strong><code>setup</code>永远在所有的生命周期之前</strong></p></li><li><p>Vue3.0中可以继续使用Vue2.x中的生命周期钩子,<strong>但有有两个被更名</strong>:</p><ul><li><code>beforeDestroy</code> =>变为了 <code>beforeUnmount</code></li><li><code>destroyed</code> =>变为了 <code>unmounted</code></li></ul></li><li><p>代码– <strong>配置对象当中的生命周期钩子</strong></p></li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br></pre></td><td class="code"><pre><span class="line"><script></span><br><span class="line"><span class="keyword">import</span> { ref } <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="comment">//vue3的生命周期钩子-配置项 在配置对象方面,不同点就在于beforeDestroy =>变为了beforeUnmounte ,desctroyed =>变为了unmounted</span></span><br><span class="line"><span class="title function_">beforeCreate</span>(<span class="params"></span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- beforecreate ---"</span>);</span><br><span class="line">},</span><br><span class="line"><span class="title function_">created</span>(<span class="params"></span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- created ---"</span>);</span><br><span class="line">},</span><br><span class="line"><span class="title function_">beforeMount</span>(<span class="params"></span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- beforeMount ---"</span>);</span><br><span class="line">},</span><br><span class="line"><span class="title function_">mounted</span>(<span class="params"></span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- mounted ---"</span>);</span><br><span class="line">},</span><br><span class="line"><span class="title function_">beforeUpdate</span>(<span class="params"></span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- beforeUpdate ---"</span>);</span><br><span class="line">}, </span><br><span class="line"><span class="title function_">updated</span>(<span class="params"></span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- updated --- "</span>);</span><br><span class="line">},</span><br><span class="line"><span class="title function_">beforeUnmount</span>(<span class="params"></span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- beforeUnmount ---"</span>);</span><br><span class="line">},</span><br><span class="line"><span class="title function_">unmounted</span>(<span class="params"></span>){</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- unmounted ---"</span>);</span><br><span class="line">},</span><br><span class="line">};</span><br><span class="line"></script></span><br></pre></td></tr></table></figure><ul><li>代码 — <strong>vue3的组合函数的生命周期</strong></li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br></pre></td><td class="code"><pre><span class="line"><script></span><br><span class="line"><span class="keyword">import</span> { ref } <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="comment">//组合函数生命周期钩子</span></span><br><span class="line"><span class="keyword">import</span> {</span><br><span class="line"> onBeforeMount,</span><br><span class="line"> onMounted,</span><br><span class="line"> onBeforeUpdate,</span><br><span class="line"> onUpdated,</span><br><span class="line"> onBeforeUnmount,</span><br><span class="line"> onUnmounted,</span><br><span class="line">} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="comment">// vue3的生命周期钩子</span></span><br><span class="line"> <span class="attr">name</span>: <span class="string">""</span>,</span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>) {</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- setup ---"</span>);</span><br><span class="line"> <span class="keyword">let</span> number = <span class="title function_">ref</span>(<span class="number">0</span>);</span><br><span class="line"> <span class="comment">// 组合函数生命周期钩子</span></span><br><span class="line"> <span class="title function_">onBeforeMount</span>(<span class="function">() =></span> {</span><br><span class="line"> <span class="comment">//生命周期回调函数</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- onBeofreMount ---"</span>);</span><br><span class="line"> });</span><br><span class="line"> <span class="title function_">onMounted</span>(<span class="function">() =></span> {</span><br><span class="line"> <span class="comment">//生命周期回调函数</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- onMounted ---"</span>);</span><br><span class="line"> });</span><br><span class="line"> <span class="title function_">onBeforeUpdate</span>(<span class="function">() =></span> {</span><br><span class="line"> <span class="comment">//生命周期回调函数</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- onBeforeUpdate ---"</span>);</span><br><span class="line"> });</span><br><span class="line"> <span class="title function_">onUpdated</span>(<span class="function">() =></span> {</span><br><span class="line"> <span class="comment">//生命周期回调函数</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- onUpdated ---"</span>);</span><br><span class="line"> });</span><br><span class="line"> <span class="title function_">onBeforeUnmount</span>(<span class="function">() =></span> {</span><br><span class="line"> <span class="comment">//生命周期回调函数</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- onBeofreUnmount ---"</span>);</span><br><span class="line"> });</span><br><span class="line"> <span class="title function_">onUnmounted</span>(<span class="function">() =></span> {</span><br><span class="line"> <span class="comment">//生命周期回调函数</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"--- onUnmounted ---"</span>);</span><br><span class="line"> });</span><br><span class="line"></span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> number,</span><br><span class="line"> };</span><br><span class="line"> }</span><br><span class="line">};</span><br><span class="line"></script></span><br></pre></td></tr></table></figure><ul><li><p>组合函数形式的生命周期钩子和vue2.x配置对象生命周期钩子的对应关系</p><ul><li><p><code>beforeCreate</code>===><code>setup()</code></p></li><li><p><code>created</code>=======><code>setup()</code></p></li><li><p><code>beforeMount</code> ===><code>onBeforeMount</code></p></li><li><p><code>mounted</code>=======><code>onMounted</code></p></li><li><p><code>beforeUpdate</code>===><code>onBeforeUpdate</code></p></li><li><p><code>updated</code> =======><code>onUpdated</code></p></li><li><p><code>beforeUnmount</code> ==><code>onBeforeUnmount</code></p></li><li><p><code>unmounted</code> =====><code>onUnmounted</code></p></li></ul></li><li><p>其他都是加了一个<code>on</code>就没有了,还有就是,如果配置对象生命周期函数和组合函数生命周期一起写了,永远是组合函数的先执行</p></li></ul><h3 id="14-自定义hooks"><a href="#14-自定义hooks" class="headerlink" title="14.自定义hooks"></a>14.自定义hooks</h3><ul><li><p>什么是hook?—— 本质是一个函数,把setup函数中使用的Composition API进行了封装。</p></li><li><p>类似于vue2.x中的mixin。</p></li><li><p>自定义hook的优势: <strong>复用代码</strong>, 让setup中的逻辑更清楚易懂。</p></li></ul><h4 id="比如说有一个需求-单击鼠标可以获取鼠标的位置的函数功能-我们用hook看看"><a href="#比如说有一个需求-单击鼠标可以获取鼠标的位置的函数功能-我们用hook看看" class="headerlink" title="比如说有一个需求,单击鼠标可以获取鼠标的位置的函数功能,我们用hook看看"></a>比如说有一个需求,单击鼠标可以获取鼠标的位置的函数功能,我们用hook看看</h4><p><strong>hooks/usePoint.js</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> { reactive, onMounted, onUnmounted } <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> <span class="keyword">function</span> (<span class="params"></span>) {</span><br><span class="line"> <span class="keyword">let</span> point = <span class="title function_">reactive</span>({</span><br><span class="line"> <span class="attr">x</span>: <span class="number">0</span>,</span><br><span class="line"> <span class="attr">y</span>: <span class="number">0</span>,</span><br><span class="line"> });</span><br><span class="line"></span><br><span class="line"> <span class="comment">//获取单击坐标</span></span><br><span class="line"> <span class="keyword">function</span> <span class="title function_">getPoint</span>(<span class="params">event</span>) {</span><br><span class="line"> point.<span class="property">x</span> = event.<span class="property">pageX</span>;</span><br><span class="line"> point.<span class="property">y</span> = event.<span class="property">pageY</span>;</span><br><span class="line"> }</span><br><span class="line"> <span class="comment">//生命周期</span></span><br><span class="line"> <span class="title function_">onMounted</span>(<span class="function">() =></span> {</span><br><span class="line"> <span class="comment">//添加鼠标单击回调</span></span><br><span class="line"> <span class="variable language_">window</span>.<span class="title function_">addEventListener</span>(<span class="string">"click"</span>, getPoint);</span><br><span class="line"></span><br><span class="line"> });</span><br><span class="line"></span><br><span class="line"> <span class="comment">//卸载后移除回调</span></span><br><span class="line"> <span class="title function_">onUnmounted</span>(<span class="function">() =></span> {</span><br><span class="line"> <span class="comment">//移除回调</span></span><br><span class="line"> <span class="variable language_">window</span>.<span class="title function_">removeEventListener</span>(<span class="string">"click"</span>, getPoint);</span><br><span class="line"> });</span><br><span class="line"> <span class="comment">//必须,相当于ref或者reactive执行后返回一个数据</span></span><br><span class="line"> <span class="keyword">return</span> point;</span><br><span class="line">}</span><br></pre></td></tr></table></figure><p><strong>App.vue</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> </span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">Demo</span> <span class="attr">v-if</span>=<span class="string">"isShow"</span>></span><span class="tag"></<span class="name">Demo</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">Test</span>/></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"isShow = !isShow"</span>></span>切换显示<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> <span class="title class_">Demo</span> <span class="keyword">from</span> <span class="string">"@/components/Demo"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> <span class="title class_">Test</span> <span class="keyword">from</span> <span class="string">"@/components/Test"</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> { ref } <span class="keyword">from</span> <span class="string">"vue"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"App"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">components</span>: { <span class="title class_">Demo</span> ,<span class="title class_">Test</span>},</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> </span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> isShow = <span class="title function_">ref</span>(<span class="literal">true</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> isShow,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> };</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br></pre></td></tr></table></figure><p><strong>componets/Demo.vue</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span>我是Demo<span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>坐标轴:x轴{{ point.x }} y轴:{{ point.y }}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> usePoint <span class="keyword">from</span> <span class="string">"../hooks/usePoint"</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">""</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//使用hooks,并接受返回的数据用于展示</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> point = <span class="title function_">usePoint</span>();</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> point,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br></pre></td></tr></table></figure><p><strong>components/Test.vue</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">hr</span>/></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是test<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>坐标轴:x轴{{ point.x }} y轴:{{ point.y }}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> usePoint <span class="keyword">from</span> <span class="string">"../hooks/usePoint"</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">''</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>){</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//使用hooks,并接受返回的数据用于展示</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> point = <span class="title function_">usePoint</span>();</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> point,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">}</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br></pre></td></tr></table></figure><h3 id="15-toRef和toRefs"><a href="#15-toRef和toRefs" class="headerlink" title="15.toRef和toRefs"></a>15.toRef和toRefs</h3><h4 id="toRef"><a href="#toRef" class="headerlink" title="toRef"></a>toRef</h4><h5 id="语法格式"><a href="#语法格式" class="headerlink" title="语法格式"></a>语法格式</h5><ul><li><strong>toRef</strong> :(要分割的对象,分割的属性)<ul><li>比如<code>toRef(person,'name');</code> 意思为分割响应式数据<code>person</code>当中的name</li></ul></li></ul><h5 id="用途点"><a href="#用途点" class="headerlink" title="用途点"></a>用途点</h5><ul><li>不想在<code>template</code>模板当中,写这么多重复的,比如下方代码,太多<code>person</code>这个单词了,我们不想这样子,就可以在<code>setup</code> return的时候做些处理</li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是Demo<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> 姓:<span class="tag"><<span class="name">input</span> <span class="attr">v-model</span>=<span class="string">"person.name"</span>/></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">br</span>/></span></span></span><br><span class="line"><span class="language-xml"> 名:<span class="tag"><<span class="name">input</span> <span class="attr">v-model</span>=<span class="string">"person.last_name"</span>/></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>全称展示:{{person.fullName}}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> 全称修改:<span class="tag"><<span class="name">input</span> <span class="attr">v-model</span>=<span class="string">"person.fullName"</span>/></span> </span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"></template></span><br></pre></td></tr></table></figure><ul><li>切记,普通的这样子处理是不可以实现响应式的,</li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br></pre></td><td class="code"><pre><span class="line"><script></span><br><span class="line"><span class="keyword">import</span> {reactive} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="attr">name</span>: <span class="string">''</span>,</span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>){</span><br><span class="line"> <span class="keyword">let</span> person = <span class="title function_">reactive</span>({</span><br><span class="line"> <span class="attr">name</span>:<span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">age</span>:<span class="number">18</span>,</span><br><span class="line"> <span class="attr">job</span>:{</span><br><span class="line"> <span class="attr">job1</span>:{</span><br><span class="line"> <span class="attr">salary</span>:<span class="number">10</span></span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line"> });</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> <span class="comment">//如果我们直接更改,是达不到响应式的</span></span><br><span class="line"> <span class="comment">//因为下方的代码等同于这样子,未经过reactive处理的了</span></span><br><span class="line"> <span class="comment">// return {</span></span><br><span class="line"> <span class="comment">// name:"李白",</span></span><br><span class="line"> <span class="comment">// age:18</span></span><br><span class="line"> <span class="comment">// }</span></span><br><span class="line"> <span class="attr">name</span>:person.<span class="property">name</span>,</span><br><span class="line"> <span class="attr">age</span>:person.<span class="property">age</span>,</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></script></span><br></pre></td></tr></table></figure><ul><li>这样子才可以实现响应式分割</li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span>我是Demo<span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>{{person}}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>姓名:{{name}}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>年龄:{{age}}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>工资:{{salary}}K<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"name+='!'"</span>></span>改变姓名<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"age++"</span>></span>改变年龄<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"salary++"</span>></span>改变工资<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> {reactive,toRef,ref,toRefs} <span class="keyword">from</span> <span class="string">"vue"</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">""</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>){</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> person = <span class="title function_">reactive</span>({</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>:<span class="string">"李白"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">age</span>:<span class="number">18</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">job</span>:{</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">job1</span>:{</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">salary</span>:<span class="number">10</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> })</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> person,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>:<span class="title function_">toRef</span>(person,<span class="string">'name'</span>),</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">age</span>:<span class="title function_">toRef</span>(person,<span class="string">'age'</span>),</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">salary</span>:<span class="title function_">toRef</span>(person.<span class="property">job</span>.<span class="property">job1</span>,<span class="string">'salary'</span>)</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">style</span> <span class="attr">lang</span>=<span class="string">"less"</span> <span class="attr">scoped</span>></span></span></span><br><span class="line"><span class="language-xml"><span class="tag"></<span class="name">style</span>></span></span></span><br><span class="line"></span><br></pre></td></tr></table></figure><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251345989.png" alt="toRef示意图-可以理解,通过toRef创建的,数据始终指向源数据"></p><h4 id="toRefs"><a href="#toRefs" class="headerlink" title="toRefs"></a>toRefs</h4><h5 id="语法格式-1"><a href="#语法格式-1" class="headerlink" title="语法格式"></a>语法格式</h5><ul><li><code>toRefs(要拆分的响应式数据)</code> ,返回分割后的响应式数据对象</li></ul><h5 id="示例-1"><a href="#示例-1" class="headerlink" title="示例"></a>示例</h5><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br></pre></td><td class="code"><pre><span class="line"><script></span><br><span class="line"><span class="keyword">import</span> {reactive,toRef,ref,toRefs} <span class="keyword">from</span> <span class="string">"vue"</span></span><br><span class="line"><span class="keyword">export</span> <span class="keyword">default</span> {</span><br><span class="line"> <span class="attr">name</span>: <span class="string">""</span>,</span><br><span class="line"> <span class="title function_">setup</span>(<span class="params"></span>){</span><br><span class="line"> <span class="keyword">let</span> person = <span class="title function_">reactive</span>({</span><br><span class="line"> <span class="attr">name</span>:<span class="string">"李白"</span>,</span><br><span class="line"> <span class="attr">age</span>:<span class="number">18</span>,</span><br><span class="line"> <span class="attr">job</span>:{</span><br><span class="line"> <span class="attr">job1</span>:{</span><br><span class="line"> <span class="attr">salary</span>:<span class="number">10</span></span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line"> })</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="title function_">toRefs</span>(person));</span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> person,</span><br><span class="line"> <span class="attr">name</span>:<span class="title function_">toRef</span>(person,<span class="string">'name'</span>),</span><br><span class="line"> <span class="attr">age</span>:<span class="title function_">toRef</span>(person,<span class="string">'age'</span>),</span><br><span class="line"> <span class="attr">salary</span>:<span class="title function_">toRef</span>(person.<span class="property">job</span>.<span class="property">job1</span>,<span class="string">'salary'</span>)</span><br><span class="line"> }</span><br><span class="line"> <span class="comment">//用的比较多的是下方这种</span></span><br><span class="line"> <span class="comment">//就将person对象拆分为了name,age,job这三个响应式数据</span></span><br><span class="line"> <span class="keyword">return</span> {</span><br><span class="line"> ...<span class="title function_">toRefs</span>(person),</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line">};</span><br><span class="line"></script></span><br></pre></td></tr></table></figure><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251346405.png" alt="toRefs(person)的结果"></p><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251348513.png" alt="toRefs示意图 将这个person对象拆分为多部分,每一部分都是指向源数据的部分"></p><h2 id="三-其他composition-API"><a href="#三-其他composition-API" class="headerlink" title="三.其他composition API"></a>三.其他composition API</h2><ul><li><p>这二者什么时候使用?</p><ul><li><p>如果有一个对象数据,结构比较深, 但变化时只是外层属性变化 ===> <code>shallowReactive</code></p></li><li><p>如果有一个对象数据,后续功能不会修改该对象中的属性,而是生新的对象来替换 ===> <code>shallowRef</code></p></li></ul></li></ul><h3 id="1-shallowRef和shallowReactive"><a href="#1-shallowRef和shallowReactive" class="headerlink" title="1.shallowRef和shallowReactive"></a>1.shallowRef和shallowReactive</h3><h4 id="shallowRef"><a href="#shallowRef" class="headerlink" title="shallowRef"></a>shallowRef</h4><ul><li><p>只处理基本数据类型的响应式,不对对象的响应式进行处理(在普通的<code>ref</code>当中,如果遇到的是对象,那么会将对象交给<code>reactive</code>进行处理,但是使用了<code>shallowRef</code>后就不会)</p></li><li><p>使用依旧需要导入包</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {shallowRef} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li><li><p>怎么使用和ref一样的用法</p></li><li><p><strong>如图,shallRef传入一个对象后输出,会发现原来怎么样,就是怎么样的</strong></p></li></ul><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251352569.png" alt="图,shallRef传入一个对象后输出,会发现原来怎么样,就是怎么样的"></p><ul><li><strong>而原来的ref函数如果遇到对象会交给reactive进行处理</strong></li></ul><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251354203.png" alt="而原来的ref函数如果遇到对象会交给reactive进行处理"></p><h4 id="shallowReactive"><a href="#shallowReactive" class="headerlink" title="shallowReactive"></a>shallowReactive</h4><ul><li><p>只使得对象<strong>第一层为响应式数据</strong>,更深层次不会变为响应式数据</p></li><li><p>使用,依旧先导入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {shallowReactive} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li><li><p>然后使用方法和<code>reactive</code>是一样的</p></li></ul><p><strong>示例代码</strong></p><p><code>person为shallowReactive创建的</code>,button想操作里面的salary,结果是不行的</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span>我是Demo<span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>{{person}}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>姓名:{{person.name}}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>年龄:{{person.age}}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>工资:{{person.job.job1.salary}}K<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"person.name+='!'"</span>></span>改变姓名<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"person.age++"</span>></span>改变年龄<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"person.job.job1.salary++"</span>></span>改变工资<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> {shallowReactive} <span class="keyword">from</span> <span class="string">"vue"</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">""</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>){</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> person = <span class="title function_">shallowReactive</span>({</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>:<span class="string">"李白"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">age</span>:<span class="number">18</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">job</span>:{</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">job1</span>:{</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">salary</span>:<span class="number">10</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> })</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//不管是ref reactive shallowReactive shallowRef</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">// 返回的都是响应式数据</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">// 只不过深层次的是否是响应式就看使用哪一个方法了</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> person,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br><span class="line"></span><br></pre></td></tr></table></figure><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251403250.png"></p><ul><li>不管是ref reactive shallowReactive shallowRef 返回的都是响应式数据,只不过深层次的是否是响应式就看使用哪一个方法了<ul><li>所以你会发现,直接替换person,x这二个数据,也会引发视图变化</li></ul></li></ul><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251403807.png"></p><h3 id="2-readonly和shallowReadonly"><a href="#2-readonly和shallowReadonly" class="headerlink" title="2.readonly和shallowReadonly"></a>2.readonly和shallowReadonly</h3><ul><li>readonly: 让一个响应式数据变为只读的(<strong>深</strong>只读),通俗点就是全部都是只读数据</li><li>shallowReadonly:让一个响应式数据变为只读的(<strong>浅</strong>只读),通俗点就是只有第一层数据为只读的</li><li>应用场景: 不希望数据被修改时。</li><li>都是传递给一个响应数据,将这个响应式数据变为只读的,注意,<strong>非响应式数据是数据被修改了,视图没有发生变化,这个时候数据还是可以被修改的</strong></li></ul><h4 id="readonly"><a href="#readonly" class="headerlink" title="readonly"></a>readonly</h4><ul><li><p>先导入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {readonly} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li><li><p>传入一个响应式数据,返回一个全部为只读的数据</p></li></ul><h4 id="shallowReadonly"><a href="#shallowReadonly" class="headerlink" title="shallowReadonly"></a>shallowReadonly</h4><ul><li><p>先导入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {shallowReadonly} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li><li><p>传入一个响应式数据,返回一个<strong>第一层为只读的数据</strong></p></li></ul><h4 id="二者的示例代码"><a href="#二者的示例代码" class="headerlink" title="二者的示例代码"></a>二者的示例代码</h4><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span>我是Demo<span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>姓名:{{name}}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>年龄:{{age}}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>工资:{{job.job1.salary}}K<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>{{a}}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"name+='!'"</span>></span>改变姓名<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"age++"</span>></span>改变年龄<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"job.job1.salary++"</span>></span>改变工资<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"a++"</span>></span>改变a<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> {ref,reactive,toRefs,readonly, shallowReadonly} <span class="keyword">from</span> <span class="string">"vue"</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">""</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>){</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> person = <span class="title function_">reactive</span>({</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>:<span class="string">"李白"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">age</span>:<span class="number">18</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">job</span>:{</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">job1</span>:{</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">salary</span>:<span class="number">10</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> });</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> a = <span class="title function_">ref</span>(<span class="number">100</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> a = <span class="title function_">readonly</span>(a);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//person = readonly(person);//全部变为了只读</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> person = <span class="title function_">shallowReadonly</span>(person);<span class="comment">//第一层变为了只读,其他没有变</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> ...<span class="title function_">toRefs</span>(person),</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> a</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br></pre></td></tr></table></figure><p>代码效果:除了<code>改变工资</code>外,其他的都不可以修改</p><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251408950.png"></p><h3 id="3-toRaw和markRaw"><a href="#3-toRaw和markRaw" class="headerlink" title="3.toRaw和markRaw"></a>3.toRaw和markRaw</h3><h4 id="toRaw"><a href="#toRaw" class="headerlink" title="toRaw"></a>toRaw</h4><ul><li>作用:将一个由<code>reactive</code>生成的<strong style="color:orange">响应式对象</strong>转为<strong style="color:orange">普通对象</strong>。</li><li>使用场景:用于读取响应式对象对应的普通对象,对这个普通对象的所有操作,不会引起页面更新。</li></ul><ul><li><p>语法: <code>var 转换成的普通对象 = toRaw(响应式对象)</code></p></li><li><p>引入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {toRaw} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li></ul><h4 id="markRaw"><a href="#markRaw" class="headerlink" title="markRaw"></a>markRaw</h4><ul><li><p>作用:标记一个对象,使其永远不会再成为响应式对象。</p></li><li><p><strong>要知道,在vue3的时候,对一个响应式数据添加新值,那么这个新值也会变为响应式数据的,并且是可以通过数组索引来操作响应式数据的(但是在vue2是不可以的)</strong></p></li><li><p>应用场景:</p><ol><li>有些值不应被设置为响应式的,例如复杂的第三方类库等。</li><li>当渲染具有不可变数据源的大列表时,跳过响应式转换可以提高性能。</li></ol></li><li><p>引入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {markRaw} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li></ul><h4 id="二者的示例代码-1"><a href="#二者的示例代码-1" class="headerlink" title="二者的示例代码"></a>二者的示例代码</h4><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br><span class="line">56</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span>我是Demo<span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>姓名:{{ name }}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>年龄:{{ age }}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>工资:{{ job.job1.salary }}K<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"name += '!'"</span>></span>改变姓名<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"age++"</span>></span>改变年龄<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"job.job1.salary++"</span>></span>改变工资<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"showRawPerson"</span>></span>显示原始的数据<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>车位信息:{{ person.car }}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"addCar"</span>></span>添加车位<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"person.car.name+='!'"</span>></span>车子名称改变<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"person.car.price++"</span>></span>车子价格改变<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> { reactive, toRefs, toRaw, markRaw } <span class="keyword">from</span> <span class="string">"vue"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">""</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> person = <span class="title function_">reactive</span>({</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"李白"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">age</span>: <span class="number">18</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">job</span>: {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">job1</span>: {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">salary</span>: <span class="number">10</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> });</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">function</span> <span class="title function_">showRawPerson</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//调用toRaw将响应式数据转化为普通数据</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> rawPerson = <span class="title function_">toRaw</span>(person);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//看看是否会影响person--测试是不会的</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> rawPerson.<span class="property">age</span>++;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="variable language_">console</span>.<span class="title function_">log</span>(rawPerson);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">function</span> <span class="title function_">addCar</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//将要新添加数据</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//但是我不想新添加的数据为想响应式的,就可以使用markRaw</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//进行标记,标记为非响应式数据</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> person.<span class="property">car</span> = <span class="title function_">markRaw</span>({</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"宝马"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">price</span>: <span class="number">40</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> });</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> person,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> ...<span class="title function_">toRefs</span>(person),</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> showRawPerson,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> addCar,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> };</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br></pre></td></tr></table></figure><h3 id="4-customRef"><a href="#4-customRef" class="headerlink" title="4.customRef"></a>4.customRef</h3><ul><li><p>功能:<strong>自定义ref,并对其依赖项跟踪和更新触发</strong>(可以显示控制)</p></li><li><p>要自定义ref,需要记住下面二个</p><ul><li>需要返回<code>customRef</code>函数创建的东东</li><li><code>customRef</code>函数自动传入的回调函数参数分别为<code>tracker</code>(追踪器),<code>trigger</code>(触发器),并且这个函数需要返回一个配置对象(配置对象包含<code>set</code>和<code>get</code>)</li></ul></li><li><p>引入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {customRef} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li><li><p>案例: 实现防抖,输入内容0.5秒后才更新</p></li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span>></span>我是Demo<span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">input</span> <span class="attr">type</span>=<span class="string">"text"</span> <span class="attr">v-model</span>=<span class="string">"searchKey"</span> /></span></span></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">h1</span>></span>{{ searchKey }}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> { customRef } <span class="keyword">from</span> <span class="string">"vue"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">""</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//创建一个自定义的 ref,并对其依赖项跟踪和更新触发进行显式控制。</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//这里就产生了闭包</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> searchKey = <span class="title function_">myRef</span>(<span class="number">0</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//自定义的ref -- 防抖</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">function</span> <span class="title function_">myRef</span>(<span class="params">value</span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">// 通过customRef去实现自定义 -- 毛坯房来自己处理</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">// ref --- 精装房来自己处理</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> timer; <span class="comment">//定时器</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//所以自定义ref ,都需要返回毛坯房</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> <span class="title function_">customRef</span>(<span class="function">(<span class="params">tracker, trigger</span>) =></span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//毛坯房里面,需要返回一个对象</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">get</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"你调用了get"</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//告诉vue这个值是需要更新的</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">tracker</span>();</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> value; <span class="comment">//返回值</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">set</span>(<span class="params">newValue</span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"调用了set"</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//告诉Vue去更新界面</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="built_in">clearTimeout</span>(timer);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">//0.5秒后更新视图</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> timer = <span class="built_in">setTimeout</span>(<span class="function">() =></span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">trigger</span>();</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> value = newValue;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }, <span class="number">500</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> };</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> });</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> searchKey,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> };</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br></pre></td></tr></table></figure><h3 id="5-provide和inject"><a href="#5-provide和inject" class="headerlink" title="5.provide和inject"></a>5.provide和inject</h3><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251422348.png"></p><ul><li><p>作用:实现<strong style="color:#dd5145">祖与后代组件间</strong>通信</p></li><li><p>套路:父组件有一个 <code>provide</code> 选项来提供数据,后代组件有一个 <code>inject</code> 选项来开始使用这些数据</p></li></ul><ul><li><p>引入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {provide,inject} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br></pre></td></tr></table></figure></li><li><p>语法格式</p><ul><li><strong>provide(‘提供的名称’,数据)</strong></li><li><strong>let 接收到的数据 = inject(‘provide提供的名称’)</strong></li></ul></li><li><p>具体写法</p><ul><li><p>祖组件当中</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {provide} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="title function_">setup</span>(<span class="params"></span>){</span><br><span class="line"> ......</span><br><span class="line"> <span class="comment">//发送数据</span></span><br><span class="line"> <span class="keyword">let</span> car = <span class="title function_">reactive</span>({<span class="attr">name</span>:<span class="string">'奔驰'</span>,<span class="attr">price</span>:<span class="string">'40万'</span>})</span><br><span class="line"> <span class="title function_">provide</span>(<span class="string">'car'</span>,car)</span><br><span class="line"> ......</span><br><span class="line">}</span><br></pre></td></tr></table></figure></li><li><p>后代组件当中</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {inject} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="title function_">setup</span>(<span class="params">props,context</span>){</span><br><span class="line"> ......</span><br><span class="line"> <span class="comment">//接收数据</span></span><br><span class="line"> <span class="keyword">const</span> car = <span class="title function_">inject</span>(<span class="string">'car'</span>)</span><br><span class="line"> <span class="keyword">return</span> {car}</span><br><span class="line"> ......</span><br><span class="line">}</span><br></pre></td></tr></table></figure></li></ul></li></ul><h3 id="6-响应式数据判断-isRef-isReactive-isProxy-isReadonly"><a href="#6-响应式数据判断-isRef-isReactive-isProxy-isReadonly" class="headerlink" title="6.响应式数据判断-isRef,isReactive,isProxy,isReadonly"></a>6.响应式数据判断-isRef,isReactive,isProxy,isReadonly</h3><ul><li>isRef:检查一个值是否是<code>ref对象</code></li><li>isReactive:检查一个对象是否由 <code>reactive</code>所创建的响应式代理</li><li>isProxy:检查一个对象是否是由<code>readonly</code>或者<code>reactive</code>函数所创建的<strong>响应式/只读数据代理</strong><ul><li><strong>readonly函数对reactive响应式数据设置为只读是不会将其转换为对象的,而是依旧是proxy</strong></li></ul></li><li>isReadonly:检查一个对象是否是由<code>readonly</code>函数所创建的只读代理</li></ul><p><strong>示例代码</strong></p><ul><li>此示例也证明了<code>ref</code>创建引用数据类型的响应式数据的时候,是交给<code>reactive</code>来进行创建的</li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {reactive,isRef,isReactive,isReadonly,isProxy} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="title function_">setup</span>(<span class="params"></span>){</span><br><span class="line"><span class="comment">//使用reactive创建响应式数据</span></span><br><span class="line"> <span class="keyword">let</span> info = <span class="title function_">reactive</span>({</span><br><span class="line"> <span class="attr">people</span>: <span class="string">"一家四口人"</span>,</span><br><span class="line"> <span class="attr">money</span>: <span class="number">8888888</span>,</span><br><span class="line"> });</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"isRef"</span>, <span class="title function_">isRef</span>(info)); <span class="comment">//false</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"isReactive"</span>, <span class="title function_">isReactive</span>(info)); <span class="comment">//true</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"isReadonly"</span>, <span class="title function_">isReadonly</span>(info)); <span class="comment">//false</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"isProxy"</span>, <span class="title function_">isProxy</span>(info)); <span class="comment">//true</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"分割----------------------------------"</span>);</span><br><span class="line"> <span class="comment">//使用ref创建响应式数据 - 传入一个对象</span></span><br><span class="line"> <span class="keyword">let</span> info1 = <span class="title function_">ref</span>({</span><br><span class="line"> <span class="attr">people</span>: <span class="string">"一家四口人"</span>,</span><br><span class="line"> <span class="attr">money</span>: <span class="number">8888888</span>,</span><br><span class="line"> });</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="title function_">isRef</span>(info1)); <span class="comment">//true</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="title function_">isReactive</span>(info1)); <span class="comment">//false</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="title function_">isProxy</span>(info1)); <span class="comment">//false</span></span><br><span class="line"> </span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="string">"分割----------------------------------"</span>);</span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="title function_">isRef</span>(info1.<span class="property">value</span>)); <span class="comment">//false</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="title function_">isReactive</span>(info1.<span class="property">value</span>)); <span class="comment">//true</span></span><br><span class="line"> <span class="variable language_">console</span>.<span class="title function_">log</span>(<span class="title function_">isProxy</span>(info1.<span class="property">value</span>)); <span class="comment">//true</span></span><br><span class="line"> </span><br><span class="line"> }</span><br></pre></td></tr></table></figure><h2 id="四-新的组件"><a href="#四-新的组件" class="headerlink" title="四.新的组件"></a>四.新的组件</h2><h3 id="1-Fragment"><a href="#1-Fragment" class="headerlink" title="1.Fragment"></a>1.Fragment</h3><ul><li>在vue2的时候,我们知道,组件必须要有一个根标签</li><li>在vue2中,组件可以没有根标签,vue会将多个标签包含在一个<code>fragment</code>虚拟元素中</li><li>好处:<strong>减少标签层级,减少内存占用</strong></li><li>如图 在vue开发提示中,没有书写根标签就会有一个蓝色的fragment</li></ul><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251431632.png"></p><h3 id="2-Teleport"><a href="#2-Teleport" class="headerlink" title="2.Teleport"></a>2.Teleport</h3><ul><li>什么是<code>teleport组件</code>,teleport组件可以将我们的<strong>组件html结构</strong>移动到指定的<strong>dom位置的技术</strong></li><li>语法:<code><teleport to="移动的位置"></teleport></code><ul><li>移动的位置可以是html,body等,也可以是选择器</li></ul></li><li>如图,就是将此弹窗移动到html标签下</li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br><span class="line">56</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"isShow = true"</span>></span>开启弹窗<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"> <!-- to当中填写要飞跃到的dom名称,比如html,body,设置可以传入一个选择器 --></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">teleport</span> <span class="attr">to</span>=<span class="string">"html"</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="comment"><!-- 遮罩层 --></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">div</span> <span class="attr">class</span>=<span class="string">"mask"</span> <span class="attr">v-if</span>=<span class="string">"isShow"</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">div</span> <span class="attr">class</span>=<span class="string">"content"</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是内容<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是内容<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是内容<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是内容<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是内容<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">button</span> @<span class="attr">click</span>=<span class="string">"isShow = false"</span>></span>关闭弹窗<span class="tag"></<span class="name">button</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">teleport</span>></span></span></span><br><span class="line"> </span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> { ref } <span class="keyword">from</span> <span class="string">"vue"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">""</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> isShow = <span class="title function_">ref</span>(<span class="literal">false</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> isShow,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> };</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">style</span> <span class="attr">scoped</span>></span><span class="language-css"></span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"><span class="selector-class">.mask</span> {</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">background-color</span>: <span class="built_in">rgba</span>(<span class="number">0</span>, <span class="number">0</span>, <span class="number">0</span>, <span class="number">0.5</span>);</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">position</span>: absolute;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">left</span>: <span class="number">0</span>;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">right</span>: <span class="number">0</span>;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">top</span>: <span class="number">0</span>;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">bottom</span>: <span class="number">0</span>;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml">}</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"><span class="selector-class">.content</span> {</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">border</span>: <span class="number">2px</span> solid hotpink;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">width</span>: <span class="number">300px</span>;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">background-color</span>: aquamarine;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">text-align</span>: center;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">position</span>: absolute;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="comment">/* 参照于父元素移动 */</span></span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">left</span>: <span class="number">50%</span>;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">top</span>:<span class="number">50%</span>;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="comment">/* 参照于自身移动 */</span></span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">transform</span>: <span class="built_in">translate</span>(-<span class="number">50%</span>,-<span class="number">50%</span>);</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml">}</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"></span><span class="tag"></<span class="name">style</span>></span></span></span><br><span class="line"></span><br></pre></td></tr></table></figure><p>图,在没有显示对话框前,通过<code>teleport</code>进行了占位,移动到了html结构下</p><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251434546.png"></p><h3 id="3-suspense-异步加载"><a href="#3-suspense-异步加载" class="headerlink" title="3.suspense/异步加载"></a>3.suspense/异步加载</h3><h4 id="前置了解"><a href="#前置了解" class="headerlink" title="前置了解"></a>前置了解</h4><ul><li><p>在普通方式的引入下<code>(import xxx组件 from "xxxx")</code>,通过这种方式,如果这个组件有一个组件没有加载完成,那么其他组件都不会显示</p><p>如图 有多层的结构下,<strong>如果红色圈圈当中的组件没有加载完成</strong>,那么其他组件都不会显示的</p></li></ul><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251437912.png" alt="有多层的结构下,如果红色圈圈当中的组件没有加载完成,那么其他组件都不会显示的"></p><p><strong>如图</strong>,<code>我是APP</code>和<code>我是儿子</code>这二个同时被加载出来,不管哪一个组件实现加载完成,后一个组件必须要等待前一个组件加载完成才会显示</p><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251452693.gif"></p><ul><li>所以vue3.x就有了异步加载(其实vue2.x的时候vue-router就有异步加载了)</li></ul><h4 id="注意要点"><a href="#注意要点" class="headerlink" title="注意要点"></a>注意要点</h4><ul><li><strong>异步加载的组件可以用suspense,也可以不用</strong></li><li><strong>如果组件中setup的返回值是一个Promise对象,该组件必须要用suspense</strong></li><li><strong>如果组件中setup出现了async,await,该组件必须要用suspense</strong></li></ul><h4 id="单纯defineAsyncComponent函数使用-未使用suspense的异步加载"><a href="#单纯defineAsyncComponent函数使用-未使用suspense的异步加载" class="headerlink" title="单纯defineAsyncComponent函数使用(未使用suspense的异步加载)"></a>单纯defineAsyncComponent函数使用(未使用suspense的异步加载)</h4><ul><li>如果只需要异步加载组件,而不需要其他的显示效果,就defineAsyncComponent即可实现</li></ul><p>示例代码</p><p>这样子加载<code>Son</code>组件的时候,就是异步的了,就不会因为<code>Son</code>组件没有加载完成而导致整个网页都没有显示</p><p><strong>Son组件代码</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span> <span class="attr">class</span>=<span class="string">"son"</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是儿子<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"Son"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">style</span>></span><span class="language-css"></span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"><span class="selector-class">.son</span>{</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">background-color</span>: green;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">padding</span>: <span class="number">30px</span>;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml">}</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"></span><span class="tag"></<span class="name">style</span>></span></span></span><br><span class="line"></span><br></pre></td></tr></table></figure><p><strong>App组件代码</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span> <span class="attr">class</span>=<span class="string">"app"</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是APP<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">Son</span>></span><span class="tag"></<span class="name">Son</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="comment">//原来方式引入</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="comment">// import Son from "@/components/Son";</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="comment">// 异步组件引入</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> {defineAsyncComponent} <span class="keyword">from</span> <span class="string">"vue"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">const</span> <span class="title class_">Son</span> = <span class="title function_">defineAsyncComponent</span>(<span class="function">()=></span><span class="keyword">import</span>(<span class="string">"@/components/Son"</span>))</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"App"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">components</span>: {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title class_">Son</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">style</span>></span><span class="language-css"></span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"><span class="selector-class">.app</span> {</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">background-color</span>: hotpink;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">padding</span>: <span class="number">40px</span>;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml">}</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"></span><span class="tag"></<span class="name">style</span>></span></span></span><br><span class="line"></span><br></pre></td></tr></table></figure><p>动图效果,可以看到,先<code>我是APP</code>进行加载完成,然后<code>Son</code>加载完成后显示,不是一起显示的</p><p><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251451168.gif"></p><h4 id="defineAsyncComponent函数和suspense组件组合使用-异步加载"><a href="#defineAsyncComponent函数和suspense组件组合使用-异步加载" class="headerlink" title="defineAsyncComponent函数和suspense组件组合使用(异步加载)"></a>defineAsyncComponent函数和suspense组件组合使用(异步加载)</h4><p>等待异步组件时渲染一些额外内容,让应用有更好的用户体验,<strong>suspense组件和异步引入defineAsyncComponent</strong>函数组合显示</p><h5 id="目的"><a href="#目的" class="headerlink" title="目的:"></a>目的:</h5><ul><li>为了让组件加载显示完成的时候不那么突兀,<strong>我们可以使用suspense组件</strong></li><li>可以使用<code>async</code>和<code>await</code></li></ul><h5 id="使用"><a href="#使用" class="headerlink" title="使用:"></a>使用:</h5><ul><li><p>引入</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> {defineAsyncComponent} <span class="keyword">from</span> <span class="string">"vue"</span>;</span><br><span class="line"><span class="comment">//当然,suspense是组件,不需要引入</span></span><br></pre></td></tr></table></figure></li><li><p><code>suspense</code>组件提供二个插槽,一个是组件加载完成后显示的,<strong>插槽名称为default</strong>,一个是加载时候的内容,<strong>插槽名称为fallback</strong></p></li><li><p>注意:</p><ul><li><strong>如果组件中setup的返回值是一个Promise对象,该组件必须要用suspense包裹</strong></li><li><strong>如果组件中setup出现了async,await,该组件必须要用suspense包裹</strong></li></ul></li></ul><h5 id="示例代码"><a href="#示例代码" class="headerlink" title="示例代码"></a>示例代码</h5><p><strong>Son组件</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span> <span class="attr">class</span>=<span class="string">"son"</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是儿子 {{name}}<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> </span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"Son"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="comment">// 这种写法效果和下面的一样</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="comment">/* async setup() {</span></span></span></span><br><span class="line"><span class="comment"><span class="language-javascript"><span class="language-xml"> let name = "李白";</span></span></span></span><br><span class="line"><span class="comment"><span class="language-javascript"><span class="language-xml"> let p = new Promise((resolve, reject) => {</span></span></span></span><br><span class="line"><span class="comment"><span class="language-javascript"><span class="language-xml"> setTimeout(() => {</span></span></span></span><br><span class="line"><span class="comment"><span class="language-javascript"><span class="language-xml"> resolve({ name });</span></span></span></span><br><span class="line"><span class="comment"><span class="language-javascript"><span class="language-xml"> }, 3000);</span></span></span></span><br><span class="line"><span class="comment"><span class="language-javascript"><span class="language-xml"> });</span></span></span></span><br><span class="line"><span class="comment"><span class="language-javascript"><span class="language-xml"> return await p </span></span></span></span><br><span class="line"><span class="comment"><span class="language-javascript"><span class="language-xml"> }, */</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">setup</span>(<span class="params"></span>) {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">let</span> name = <span class="string">"李白"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="keyword">return</span> <span class="keyword">new</span> <span class="title class_">Promise</span>(<span class="function">(<span class="params">resolve, reject</span>) =></span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="built_in">setTimeout</span>(<span class="function">() =></span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title function_">resolve</span>({ name });</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> }, <span class="number">3000</span>);</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> });</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">style</span>></span><span class="language-css"></span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"><span class="selector-class">.son</span> {</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">background-color</span>: green;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">padding</span>: <span class="number">30px</span>;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml">}</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"></span><span class="tag"></<span class="name">style</span>></span></span></span><br><span class="line"></span><br></pre></td></tr></table></figure><p><strong>App组件</strong></p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br></pre></td><td class="code"><pre><span class="line"><template></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">div</span> <span class="attr">class</span>=<span class="string">"app"</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">h1</span>></span>我是APP<span class="tag"></<span class="name">h1</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="comment"><!-- 为了不让显示这么突兀,我们就结合suspense组件(悬念,悬疑) --></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">suspense</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="comment"><!-- 提供二个插槽,一个加载完成后显示的,插槽名称为default,一个加载中时候的内容,插槽名称为fallback --></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">template</span> <span class="attr">v-slot:default</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">Son</span>></span><span class="tag"></<span class="name">Son</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">template</span>></span></span></span><br><span class="line"><span class="language-xml"></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">template</span> <span class="attr">v-slot:fallback</span>></span> 加载中..... <span class="tag"></<span class="name">template</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">suspense</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">div</span>></span></span></span><br><span class="line"></template></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">script</span>></span><span class="language-javascript"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="comment">//原来方式引入</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="comment">//import Son from "@/components/Son";</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="comment">// 异步组件引入</span></span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">import</span> { defineAsyncComponent } <span class="keyword">from</span> <span class="string">"vue"</span>;</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">const</span> <span class="title class_">Son</span> = <span class="title function_">defineAsyncComponent</span>(<span class="function">() =></span> <span class="keyword">import</span>(<span class="string">"@/components/Son.vue"</span>));</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"><span class="keyword">export</span> <span class="keyword">default</span> {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">name</span>: <span class="string">"App"</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="attr">components</span>: {</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> <span class="title class_">Son</span>,</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"> },</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml">};</span></span></span><br><span class="line"><span class="language-javascript"><span class="language-xml"></span><span class="tag"></<span class="name">script</span>></span></span></span><br><span class="line"></span><br><span class="line"><span class="language-xml"><span class="tag"><<span class="name">style</span>></span><span class="language-css"></span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"><span class="selector-class">.app</span> {</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">background-color</span>: hotpink;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"> <span class="attribute">padding</span>: <span class="number">40px</span>;</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml">}</span></span></span><br><span class="line"><span class="language-css"><span class="language-xml"></span><span class="tag"></<span class="name">style</span>></span></span></span><br><span class="line"></span><br></pre></td></tr></table></figure><h2 id="五-其他"><a href="#五-其他" class="headerlink" title="五.其他"></a>五.其他</h2><ul><li><p>我现在才知道,使用具名插槽还可以简写</p><ul><li>跟 v-on(简写为@xxx=”xxxx”) 和 v-bind(简写为:xxxx=”xxxx”) 一样,v-slot 也有缩写。</li><li><code>v-slot:</code> 替换为字符<code>#</code></li><li>例如 v-slot:header 可以被重写为 #header</li><li>所以上面使用<code>suspense组件插槽</code>还可以这样子写</li></ul><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><suspense></span><br><span class="line"> <!-- 提供二个插槽,一个加载完成后显示的,插槽名称为<span class="keyword">default</span>,一个加载中时候的内容,插槽名称为fallback --></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">template</span> #<span class="attr">default</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"><<span class="name">Son</span>></span><span class="tag"></<span class="name">Son</span>></span></span></span><br><span class="line"><span class="language-xml"> <span class="tag"></<span class="name">template</span>></span></span></span><br><span class="line"></span><br><span class="line"> <span class="language-xml"><span class="tag"><<span class="name">template</span> #<span class="attr">fallback</span>></span> 加载中..... <span class="tag"></<span class="name">template</span>></span></span></span><br><span class="line"></suspense></span><br></pre></td></tr></table></figure></li></ul><ul><li><p>data选项应始终被声明为一个函数。</p></li><li><p>过度类名的更改:</p><ul><li><p>Vue2.x写法</p><figure class="highlight css"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="selector-class">.v-enter</span>,</span><br><span class="line"><span class="selector-class">.v-leave-to</span> {</span><br><span class="line"> <span class="attribute">opacity</span>: <span class="number">0</span>;</span><br><span class="line">}</span><br><span class="line"><span class="selector-class">.v-leave</span>,</span><br><span class="line"><span class="selector-class">.v-enter-to</span> {</span><br><span class="line"> <span class="attribute">opacity</span>: <span class="number">1</span>;</span><br><span class="line">}</span><br></pre></td></tr></table></figure></li><li><p>Vue3.x写法</p><figure class="highlight css"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="selector-class">.v-enter-from</span>,</span><br><span class="line"><span class="selector-class">.v-leave-to</span> {</span><br><span class="line"> <span class="attribute">opacity</span>: <span class="number">0</span>;</span><br><span class="line">}</span><br><span class="line"></span><br><span class="line"><span class="selector-class">.v-leave-from</span>,</span><br><span class="line"><span class="selector-class">.v-enter-to</span> {</span><br><span class="line"> <span class="attribute">opacity</span>: <span class="number">1</span>;</span><br><span class="line">}</span><br></pre></td></tr></table></figure></li></ul></li><li><p><strong style="color:#dd5145">移除</strong>keyCode作为 v-on 的修饰符,同时也不再支持<code>config.keyCodes</code></p></li><li><p><strong style="color:#dd5145">移除</strong><code>v-on.native</code>修饰符</p><ul><li><p>父组件中绑定事件</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><my-component</span><br><span class="line"> v-on:close="handleComponentEvent"</span><br><span class="line"> v-on:click="handleNativeClickEvent"</span><br><span class="line">/></span><br></pre></td></tr></table></figure></li><li><p>子组件中声明自定义事件(<code>emit</code>配置对象接收到的就是自定义事件,否者就是原生事件),所以你即使在组件当中使用了<code>.native</code>修饰符,没有用<code>emit</code>接收的话,也是一个原生事件</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><script></span><br><span class="line"> export default {</span><br><span class="line"> emits: ['close']</span><br><span class="line"> }</span><br><span class="line"></script></span><br></pre></td></tr></table></figure></li></ul></li><li><p><strong style="color:#dd5145">移除</strong>过滤器(filter)</p><blockquote><p>过滤器虽然这看起来很方便,但它需要一个自定义语法,打破大括号内表达式是 “只是 JavaScript” 的假设,这不仅有学习成本,而且有实现成本!建议用方法调用或计算属性去替换过滤器。</p></blockquote></li><li><p>……</p></li></ul></article><div class="post-copyright"><div class="post-copyright__author"><span class="post-copyright-meta"><i class="fas fa-circle-user fa-fw"></i>文章作者: </span><span class="post-copyright-info"><a href="https://www.dreamlove.top">梦洁</a></span></div><div class="post-copyright__type"><span class="post-copyright-meta"><i class="fas fa-square-arrow-up-right fa-fw"></i>文章链接: </span><span class="post-copyright-info"><a href="https://www.dreamlove.top/2681a891.html">https://www.dreamlove.top/2681a891.html</a></span></div><div class="post-copyright__notice"><span class="post-copyright-meta"><i class="fas fa-circle-exclamation fa-fw"></i>版权声明: </span><span class="post-copyright-info">本博客所有文章除特别声明外,均采用 <a href="https://creativecommons.org/licenses/by-nc-sa/4.0/" target="_blank">CC BY-NC-SA 4.0</a> 许可协议。转载请注明来自 <a href="https://www.dreamlove.top" target="_blank">梦洁小站-属于你我的小天地</a>!</span></div></div><div class="tag_share"><div class="post-meta__tag-list"><a class="post-meta__tags" href="/tags/vue/">vue</a><a class="post-meta__tags" href="/tags/HTML/">HTML</a><a class="post-meta__tags" href="/tags/javscript/">javscript</a></div><div class="post_share"><div class="social-share" data-image="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251524226.jpg" data-sites="facebook,twitter,wechat,weibo,qq"></div><link rel="stylesheet" href="https://lib.baomitu.com/butterfly-extsrc/1.1.3/sharejs/dist/css/share.min.css" media="print" onload='this.media="all"'><script src="https://lib.baomitu.com/butterfly-extsrc/1.1.3/sharejs/dist/js/social-share.min.js" defer></script></div></div><nav class="pagination-post" id="pagination"><div class="prev-post pull-left"><a href="/ebe3cda6.html" title="订阅地址-发薪日-白嫖订阅"><img class="cover" src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202207042023301.jpg" onerror='onerror=null,src="/img/404.png"' alt="cover of previous post"><div class="pagination-info"><div class="label">上一篇</div><div class="prev_info">订阅地址-发薪日-白嫖订阅</div></div></a></div><div class="next-post pull-right"><a href="/77ecdc83.html" title="记录下bilibili(b站)小火箭页面上划动画效果的实现"><img class="cover" src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/20220228215037.png" onerror='onerror=null,src="/img/404.png"' alt="cover of next post"><div class="pagination-info"><div class="label">下一篇</div><div class="next_info">记录下bilibili(b站)小火箭页面上划动画效果的实现</div></div></a></div></nav><div class="relatedPosts"><div class="headline"><i class="fas fa-thumbs-up fa-fw"></i><span>相关推荐</span></div><div class="relatedPosts-list"><div><a href="/75bf0d7.html" title="webpack构建工具的学习"><img class="cover" src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202205291452280.jpg" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2022-05-28</div><div class="title">webpack构建工具的学习</div></div></a></div><div><a href="/e031a88b.html" title="前端面试可能会问到的知识点记录"><img class="cover" src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202207181536689.jpg" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2022-07-18</div><div class="title">前端面试可能会问到的知识点记录</div></div></a></div><div><a href="/7429306f.html" title="js正则匹配获取分组和正向反向的区别"><img class="cover" src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/20220228215037.png" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2022-11-13</div><div class="title">js正则匹配获取分组和正向反向的区别</div></div></a></div><div><a href="/be489729.html" title="navigator.clipboard.readtext开发的时候有用,编译后测试却不生效"><img class="cover" src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202210190919962.png" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2022-10-19</div><div class="title">navigator.clipboard.readtext开发的时候有用,编译后测试却不生效</div></div></a></div><div><a href="/cb27eea3.html" title="移动端前端的适配和rem,vm其他的一些的复习"><img class="cover" src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202205242024668.jpg" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2022-05-23</div><div class="title">移动端前端的适配和rem,vm其他的一些的复习</div></div></a></div><div><a href="/a816b0a1.html" title="深入自定义事件和原生DOM事件($attr等)"><img class="cover" src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202205061952720.jpg" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2022-05-06</div><div class="title">深入自定义事件和原生DOM事件($attr等)</div></div></a></div></div></div><hr class="custom-hr"><div id="post-comment"><div class="comment-head"><div class="comment-headline"><i class="fas fa-comments fa-fw"></i><span> 评论</span></div></div><div class="comment-wrap"><div><div id="artalk-wrap"></div></div></div></div></div><div class="aside-content" id="aside-content"><div class="card-widget card-info"><div class="is-center"><div class="avatar-img"><img src="https://oss.dreamlove.top/i/2024/02/02/nw24wu.png" onerror='this.onerror=null,this.src="/img/404.png"' alt="avatar"></div><div class="author-info__name">梦洁</div><div class="author-info__description">小小的字,有大大的梦想~分享我的前端学习过程,经历,错误,和一些其他折腾过程</div></div><div class="card-info-data site-data is-center"><a href="/archives/"><div class="headline">文章</div><div class="length-num">168</div></a><a href="/tags/"><div class="headline">标签</div><div class="length-num">90</div></a><a href="/categories/"><div class="headline">分类</div><div class="length-num">68</div></a></div><a id="card-info-btn" target="_blank" rel="noopener" href="https://github.com/superBiuBiuMan"><i class="fab fa-github"></i><span>关注下我(* ̄▽ ̄*)</span></a><div class="card-info-social-icons is-center"><a class="social-icon" href="mailto:[email protected]" target="_blank" title="Email"><i class="fas fa-envelope" style="color:#4a7dbe"></i></a></div></div><div class="card-widget card-announcement"><div class="item-headline"><i class="fas fa-bullhorn fa-shake"></i><span>公告</span></div><div class="announcement_content">不断更新中,有问题请留言回复(会通过邮箱提醒~)</div></div><div class="sticky_layout"><div class="card-widget" id="card-toc"><div class="item-headline"><i class="fas fa-stream"></i><span>目录</span><span class="toc-percentage"></span></div><div class="toc-content"><ol class="toc"><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%B8%80-%E5%88%9B%E5%BB%BAvue3-0%E5%B7%A5%E7%A8%8B"><span class="toc-number">1.</span> <span class="toc-text">一.创建vue3.0工程</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#1-%E4%BD%BF%E7%94%A8vue-cli%E5%88%9B%E5%BB%BA"><span class="toc-number">1.1.</span> <span class="toc-text">1.使用vue-cli创建</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#2-%E4%BD%BF%E7%94%A8-vite-%E5%88%9B%E5%BB%BA"><span class="toc-number">1.2.</span> <span class="toc-text">2.使用 vite 创建</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%B8%80-extra-%E5%88%86%E6%9E%90vue2-x%E5%92%8Cvue3-x%E7%BB%93%E6%9E%84"><span class="toc-number">2.</span> <span class="toc-text">一(extra).分析vue2.x和vue3.x结构</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#vue2-x%E7%9A%84-main-js-%E5%88%9D%E5%A7%8B%E6%97%B6%E7%9A%84%E4%BB%A3%E7%A0%81"><span class="toc-number">2.1.</span> <span class="toc-text">vue2.x的 main.js 初始时的代码</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#vue3-x%E7%9A%84-main-js-%E5%88%9D%E5%A7%8B%E5%8C%96%E6%97%B6%E7%9A%84%E4%BB%A3%E7%A0%81"><span class="toc-number">2.2.</span> <span class="toc-text">vue3.x的 main.js 初始化时的代码</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%BA%8C-%E5%B8%B8%E7%94%A8%E7%9A%84Composition-API-%E7%BB%84%E5%90%88API"><span class="toc-number">3.</span> <span class="toc-text">二.常用的Composition API(组合API)</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#1-setup"><span class="toc-number">3.1.</span> <span class="toc-text">1.setup</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#setup%E6%98%AFvue3-0%E6%96%B0%E5%A2%9E%E5%8A%A0%E7%9A%84%E4%B8%80%E4%B8%AA%E9%85%8D%E7%BD%AE%E9%A1%B9-%E4%B8%BA%E4%B8%80%E4%B8%AA%E5%87%BD%E6%95%B0-%E9%87%8C%E9%9D%A2%E5%8F%AF%E4%BB%A5%E5%86%99%E5%87%BD%E6%95%B0%E4%BB%A3%E7%A0%81-%E6%B3%A8%E6%84%8F%E5%8C%BA%E5%88%86%E4%B8%8Bmethods%E5%BD%93%E4%B8%AD%E7%9A%84%E5%86%99%E6%B3%95"><span class="toc-number">3.1.1.</span> <span class="toc-text">setup是vue3.0新增加的一个配置项,为一个函数,里面可以写函数代码,注意区分下methods当中的写法</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E7%BB%84%E4%BB%B6%E6%89%80%E7%94%A8%E5%88%B0%E7%9A%84%E6%95%B0%E6%8D%AE-%E6%96%B9%E6%B3%95-%E9%83%BD%E5%8F%AF%E4%BB%A5%E5%86%99%E5%9C%A8setup%E5%BD%93%E4%B8%AD-%E5%BD%93%E7%84%B6-%E4%BD%A0%E4%B9%9F%E5%8F%AF%E4%BB%A5%E5%86%99%E5%9C%A8vue2%E5%BD%93%E4%B8%AD%E7%9A%84data-methods%E7%AD%89%E5%BD%93%E4%B8%AD"><span class="toc-number">3.1.2.</span> <span class="toc-text">组件所用到的数据,方法,都可以写在setup当中,当然,你也可以写在vue2当中的data,methods等当中</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#setup%E7%9A%84%E8%BF%94%E5%9B%9E%E5%80%BC"><span class="toc-number">3.1.3.</span> <span class="toc-text">setup的返回值</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E6%B3%A8%E6%84%8F%E7%82%B9"><span class="toc-number">3.1.4.</span> <span class="toc-text">注意点</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#2-ref%E5%87%BD%E6%95%B0-%E5%A4%84%E7%90%86%E5%9F%BA%E6%9C%AC%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B"><span class="toc-number">3.2.</span> <span class="toc-text">2.ref函数-处理基本数据类型</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#ref%E5%87%BD%E6%95%B0%E4%BD%9C%E7%94%A8"><span class="toc-number">3.2.1.</span> <span class="toc-text">ref函数作用:</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#ref%E5%87%BD%E6%95%B0%E8%AF%AD%E6%B3%95"><span class="toc-number">3.2.2.</span> <span class="toc-text">ref函数语法:</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#3-ref%E5%87%BD%E6%95%B0-%E5%A4%84%E7%90%86%E5%AF%B9%E8%B1%A1%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B"><span class="toc-number">3.3.</span> <span class="toc-text">3.ref函数-处理对象数据类型</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#4-ref%E5%87%BD%E6%95%B0%E6%80%BB%E7%BB%93"><span class="toc-number">3.4.</span> <span class="toc-text">4.ref函数总结</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#5-reactive%E5%87%BD%E6%95%B0"><span class="toc-number">3.5.</span> <span class="toc-text">5.reactive函数</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#reactive%E4%BD%9C%E7%94%A8"><span class="toc-number">3.5.1.</span> <span class="toc-text">reactive作用:</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#reactive%E8%AF%AD%E6%B3%95"><span class="toc-number">3.5.2.</span> <span class="toc-text">reactive语法:</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E6%B3%A8%E6%84%8F%E7%82%B9-1"><span class="toc-number">3.5.3.</span> <span class="toc-text">注意点:</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E7%A4%BA%E4%BE%8B"><span class="toc-number">3.5.4.</span> <span class="toc-text">示例:</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E5%A4%B1%E5%8E%BB%E5%93%8D%E5%BA%94%E5%BC%8F%E7%A4%BA%E4%BE%8B"><span class="toc-number">3.5.5.</span> <span class="toc-text">失去响应式示例</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#6-reactive%E5%AF%B9%E6%AF%94ref"><span class="toc-number">3.6.</span> <span class="toc-text">6.reactive对比ref</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#7-vue2%E5%93%8D%E5%BA%94%E5%BC%8F%E5%8E%9F%E7%90%86-%E6%BC%94%E7%A4%BA%E7%AE%80%E7%89%88"><span class="toc-number">3.7.</span> <span class="toc-text">7.vue2响应式原理-演示简版</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#%E5%AE%9E%E7%8E%B0%E5%8E%9F%E7%90%86%EF%BC%9A"><span class="toc-number">3.7.1.</span> <span class="toc-text">实现原理:</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#vue2%E5%AF%B9%E5%93%8D%E5%BA%94%E5%BC%8F%E6%95%B0%E6%8D%AE%E5%AD%98%E5%9C%A8%E7%9A%84%E9%97%AE%E9%A2%98"><span class="toc-number">3.7.2.</span> <span class="toc-text">vue2对响应式数据存在的问题</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#8-vue3%E5%93%8D%E5%BA%94%E5%BC%8F%E5%8E%9F%E7%90%86%E5%92%8Cvue2%E5%93%8D%E5%BA%94%E5%BC%8F%E5%8E%9F%E7%90%86-%E5%88%86%E6%9E%90%E7%AE%80%E7%89%88"><span class="toc-number">3.8.</span> <span class="toc-text">8.vue3响应式原理和vue2响应式原理-分析简版</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#vue2%E5%93%8D%E5%BA%94%E5%BC%8F%E4%BB%A3%E7%A0%81%E7%A4%BA%E4%BE%8B%E6%BC%94%E7%A4%BA"><span class="toc-number">3.8.1.</span> <span class="toc-text">vue2响应式代码示例演示</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#vue3%E5%93%8D%E5%BA%94%E5%BC%8F%E5%8E%9F%E7%90%86%E4%BB%A3%E7%A0%81%E7%A4%BA%E4%BE%8B%E6%BC%94%E7%A4%BA"><span class="toc-number">3.8.2.</span> <span class="toc-text">vue3响应式原理代码示例演示</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#9-setup%E6%B3%A8%E6%84%8F%E7%9A%84%E4%BA%8C%E4%B8%AA%E7%82%B9"><span class="toc-number">3.9.</span> <span class="toc-text">9.setup注意的二个点</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#%E6%B3%A8%E6%84%8F%E7%82%B91-setup%E4%BC%98%E4%BA%8E%E6%89%80%E6%9C%89%E7%9A%84%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F%E5%85%88%E6%89%A7%E8%A1%8C"><span class="toc-number">3.9.1.</span> <span class="toc-text">注意点1-setup优于所有的生命周期先执行</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E6%B3%A8%E6%84%8F%E7%82%B92-setup%E7%9A%84%E5%8F%82%E6%95%B0"><span class="toc-number">3.9.2.</span> <span class="toc-text">注意点2-setup的参数</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E4%B8%BA%E4%BB%80%E4%B9%88%E8%87%AA%E5%AE%9A%E4%B9%89%E4%BA%8B%E4%BB%B6%E9%9C%80%E8%A6%81%E9%80%9A%E8%BF%87emit%E6%9D%A5%E5%8E%BB%E4%BD%BF%E7%94%A8%E5%91%A2"><span class="toc-number">3.9.3.</span> <span class="toc-text">为什么自定义事件需要通过emit来去使用呢?</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#10-vue3%E7%9A%84computed"><span class="toc-number">3.10.</span> <span class="toc-text">10.vue3的computed</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#%E5%9B%9E%E9%A1%BEvue2%E6%97%B6%E5%80%99%E7%9A%84computed"><span class="toc-number">3.10.1.</span> <span class="toc-text">回顾vue2时候的computed</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#vue3%E6%97%B6%E5%80%99%E7%9A%84computed%E8%AE%A1%E7%AE%97%E5%B1%9E%E6%80%A7"><span class="toc-number">3.10.2.</span> <span class="toc-text">vue3时候的computed计算属性</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#11-vue3%E7%9A%84watch"><span class="toc-number">3.11.</span> <span class="toc-text">11.vue3的watch</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#12-vue3%E7%9A%84watchEffect"><span class="toc-number">3.12.</span> <span class="toc-text">12.vue3的watchEffect</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#13-vue3%E7%9A%84%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F%E9%92%A9%E5%AD%90"><span class="toc-number">3.13.</span> <span class="toc-text">13.vue3的生命周期钩子</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#vue2%E7%9A%84%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F-vue2%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F%E4%BB%8B%E7%BB%8D%E5%AE%98%E7%BD%91"><span class="toc-number">3.13.1.</span> <span class="toc-text">vue2的生命周期 @vue2生命周期介绍官网</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#vue3%E7%9A%84%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F-vue3%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F%E4%BB%8B%E7%BB%8D%E5%AE%98%E7%BD%91"><span class="toc-number">3.13.2.</span> <span class="toc-text">vue3的生命周期 @vue3生命周期介绍官网</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#14-%E8%87%AA%E5%AE%9A%E4%B9%89hooks"><span class="toc-number">3.14.</span> <span class="toc-text">14.自定义hooks</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#%E6%AF%94%E5%A6%82%E8%AF%B4%E6%9C%89%E4%B8%80%E4%B8%AA%E9%9C%80%E6%B1%82-%E5%8D%95%E5%87%BB%E9%BC%A0%E6%A0%87%E5%8F%AF%E4%BB%A5%E8%8E%B7%E5%8F%96%E9%BC%A0%E6%A0%87%E7%9A%84%E4%BD%8D%E7%BD%AE%E7%9A%84%E5%87%BD%E6%95%B0%E5%8A%9F%E8%83%BD-%E6%88%91%E4%BB%AC%E7%94%A8hook%E7%9C%8B%E7%9C%8B"><span class="toc-number">3.14.1.</span> <span class="toc-text">比如说有一个需求,单击鼠标可以获取鼠标的位置的函数功能,我们用hook看看</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#15-toRef%E5%92%8CtoRefs"><span class="toc-number">3.15.</span> <span class="toc-text">15.toRef和toRefs</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#toRef"><span class="toc-number">3.15.1.</span> <span class="toc-text">toRef</span></a><ol class="toc-child"><li class="toc-item toc-level-5"><a class="toc-link" href="#%E8%AF%AD%E6%B3%95%E6%A0%BC%E5%BC%8F"><span class="toc-number">3.15.1.1.</span> <span class="toc-text">语法格式</span></a></li><li class="toc-item toc-level-5"><a class="toc-link" href="#%E7%94%A8%E9%80%94%E7%82%B9"><span class="toc-number">3.15.1.2.</span> <span class="toc-text">用途点</span></a></li></ol></li><li class="toc-item toc-level-4"><a class="toc-link" href="#toRefs"><span class="toc-number">3.15.2.</span> <span class="toc-text">toRefs</span></a><ol class="toc-child"><li class="toc-item toc-level-5"><a class="toc-link" href="#%E8%AF%AD%E6%B3%95%E6%A0%BC%E5%BC%8F-1"><span class="toc-number">3.15.2.1.</span> <span class="toc-text">语法格式</span></a></li><li class="toc-item toc-level-5"><a class="toc-link" href="#%E7%A4%BA%E4%BE%8B-1"><span class="toc-number">3.15.2.2.</span> <span class="toc-text">示例</span></a></li></ol></li></ol></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%B8%89-%E5%85%B6%E4%BB%96composition-API"><span class="toc-number">4.</span> <span class="toc-text">三.其他composition API</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#1-shallowRef%E5%92%8CshallowReactive"><span class="toc-number">4.1.</span> <span class="toc-text">1.shallowRef和shallowReactive</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#shallowRef"><span class="toc-number">4.1.1.</span> <span class="toc-text">shallowRef</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#shallowReactive"><span class="toc-number">4.1.2.</span> <span class="toc-text">shallowReactive</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#2-readonly%E5%92%8CshallowReadonly"><span class="toc-number">4.2.</span> <span class="toc-text">2.readonly和shallowReadonly</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#readonly"><span class="toc-number">4.2.1.</span> <span class="toc-text">readonly</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#shallowReadonly"><span class="toc-number">4.2.2.</span> <span class="toc-text">shallowReadonly</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E4%BA%8C%E8%80%85%E7%9A%84%E7%A4%BA%E4%BE%8B%E4%BB%A3%E7%A0%81"><span class="toc-number">4.2.3.</span> <span class="toc-text">二者的示例代码</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#3-toRaw%E5%92%8CmarkRaw"><span class="toc-number">4.3.</span> <span class="toc-text">3.toRaw和markRaw</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#toRaw"><span class="toc-number">4.3.1.</span> <span class="toc-text">toRaw</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#markRaw"><span class="toc-number">4.3.2.</span> <span class="toc-text">markRaw</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E4%BA%8C%E8%80%85%E7%9A%84%E7%A4%BA%E4%BE%8B%E4%BB%A3%E7%A0%81-1"><span class="toc-number">4.3.3.</span> <span class="toc-text">二者的示例代码</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#4-customRef"><span class="toc-number">4.4.</span> <span class="toc-text">4.customRef</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#5-provide%E5%92%8Cinject"><span class="toc-number">4.5.</span> <span class="toc-text">5.provide和inject</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#6-%E5%93%8D%E5%BA%94%E5%BC%8F%E6%95%B0%E6%8D%AE%E5%88%A4%E6%96%AD-isRef-isReactive-isProxy-isReadonly"><span class="toc-number">4.6.</span> <span class="toc-text">6.响应式数据判断-isRef,isReactive,isProxy,isReadonly</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%9B%9B-%E6%96%B0%E7%9A%84%E7%BB%84%E4%BB%B6"><span class="toc-number">5.</span> <span class="toc-text">四.新的组件</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#1-Fragment"><span class="toc-number">5.1.</span> <span class="toc-text">1.Fragment</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#2-Teleport"><span class="toc-number">5.2.</span> <span class="toc-text">2.Teleport</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#3-suspense-%E5%BC%82%E6%AD%A5%E5%8A%A0%E8%BD%BD"><span class="toc-number">5.3.</span> <span class="toc-text">3.suspense/异步加载</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#%E5%89%8D%E7%BD%AE%E4%BA%86%E8%A7%A3"><span class="toc-number">5.3.1.</span> <span class="toc-text">前置了解</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E6%B3%A8%E6%84%8F%E8%A6%81%E7%82%B9"><span class="toc-number">5.3.2.</span> <span class="toc-text">注意要点</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#%E5%8D%95%E7%BA%AFdefineAsyncComponent%E5%87%BD%E6%95%B0%E4%BD%BF%E7%94%A8-%E6%9C%AA%E4%BD%BF%E7%94%A8suspense%E7%9A%84%E5%BC%82%E6%AD%A5%E5%8A%A0%E8%BD%BD"><span class="toc-number">5.3.3.</span> <span class="toc-text">单纯defineAsyncComponent函数使用(未使用suspense的异步加载)</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#defineAsyncComponent%E5%87%BD%E6%95%B0%E5%92%8Csuspense%E7%BB%84%E4%BB%B6%E7%BB%84%E5%90%88%E4%BD%BF%E7%94%A8-%E5%BC%82%E6%AD%A5%E5%8A%A0%E8%BD%BD"><span class="toc-number">5.3.4.</span> <span class="toc-text">defineAsyncComponent函数和suspense组件组合使用(异步加载)</span></a><ol class="toc-child"><li class="toc-item toc-level-5"><a class="toc-link" href="#%E7%9B%AE%E7%9A%84"><span class="toc-number">5.3.4.1.</span> <span class="toc-text">目的:</span></a></li><li class="toc-item toc-level-5"><a class="toc-link" href="#%E4%BD%BF%E7%94%A8"><span class="toc-number">5.3.4.2.</span> <span class="toc-text">使用:</span></a></li><li class="toc-item toc-level-5"><a class="toc-link" href="#%E7%A4%BA%E4%BE%8B%E4%BB%A3%E7%A0%81"><span class="toc-number">5.3.4.3.</span> <span class="toc-text">示例代码</span></a></li></ol></li></ol></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%BA%94-%E5%85%B6%E4%BB%96"><span class="toc-number">6.</span> <span class="toc-text">五.其他</span></a></li></ol></div></div><div class="card-widget card-recent-post"><div class="item-headline"><i class="fas fa-history"></i><span>最新文章</span></div><div class="aside-list"><div class="aside-list-item"><a class="thumbnail" href="/50575b3e.html" title="独角数卡,打开商品列表出现Undefined variable form的解决办法"><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202408241535616.png" onerror='this.onerror=null,this.src="/img/404.png"' alt="独角数卡,打开商品列表出现Undefined variable form的解决办法"></a><div class="content"><a class="title" href="/50575b3e.html" title="独角数卡,打开商品列表出现Undefined variable form的解决办法">独角数卡,打开商品列表出现Undefined variable form的解决办法</a><time datetime="2024-08-24T15:31:38.000Z" title="发表于 2024-08-24 15:31:38">2024-08-24</time></div></div><div class="aside-list-item"><a class="thumbnail" href="/6ace453b.html" title="前端常用npm库大全-vue,react,通用(持续更新)"><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202408241528979.png" onerror='this.onerror=null,this.src="/img/404.png"' alt="前端常用npm库大全-vue,react,通用(持续更新)"></a><div class="content"><a class="title" href="/6ace453b.html" title="前端常用npm库大全-vue,react,通用(持续更新)">前端常用npm库大全-vue,react,通用(持续更新)</a><time datetime="2024-08-24T15:24:59.000Z" title="发表于 2024-08-24 15:24:59">2024-08-24</time></div></div><div class="aside-list-item"><a class="thumbnail" href="/f4cb1979.html" title="基于vue-pdf-embed的二开PDF预览的通用组件"><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202408241539662.png" onerror='this.onerror=null,this.src="/img/404.png"' alt="基于vue-pdf-embed的二开PDF预览的通用组件"></a><div class="content"><a class="title" href="/f4cb1979.html" title="基于vue-pdf-embed的二开PDF预览的通用组件">基于vue-pdf-embed的二开PDF预览的通用组件</a><time datetime="2024-08-11T08:53:00.000Z" title="发表于 2024-08-11 08:53:00">2024-08-11</time></div></div><div class="aside-list-item"><a class="thumbnail" href="/84b2339c.html" title="x64dbg反汇编技术入门学习笔记"><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202407311704593.png" onerror='this.onerror=null,this.src="/img/404.png"' alt="x64dbg反汇编技术入门学习笔记"></a><div class="content"><a class="title" href="/84b2339c.html" title="x64dbg反汇编技术入门学习笔记">x64dbg反汇编技术入门学习笔记</a><time datetime="2024-07-31T16:51:01.000Z" title="发表于 2024-07-31 16:51:01">2024-07-31</time></div></div><div class="aside-list-item"><a class="thumbnail" href="/30ebed6d.html" title="linux普通服务器和NAT服务器下载transmission制作种子"><img src="https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202407311703454.png" onerror='this.onerror=null,this.src="/img/404.png"' alt="linux普通服务器和NAT服务器下载transmission制作种子"></a><div class="content"><a class="title" href="/30ebed6d.html" title="linux普通服务器和NAT服务器下载transmission制作种子">linux普通服务器和NAT服务器下载transmission制作种子</a><time datetime="2024-07-31T16:50:14.000Z" title="发表于 2024-07-31 16:50:14">2024-07-31</time></div></div></div></div></div></div></main><footer id="footer" style="background-image:url(https://dreamos.oss-cn-beijing.aliyuncs.com/gitblog/202206251524226.jpg)"><div id="footer-wrap"><div class="copyright">©2021 - 2024 By 梦洁</div><div class="framework-info"><span>框架 </span><a target="_blank" rel="noopener" href="https://hexo.io">Hexo</a><span class="footer-separator">|</span><span>主题 </span><a target="_blank" rel="noopener" href="https://github.com/jerryc127/hexo-theme-butterfly">Butterfly</a></div></div></footer></div><div id="rightside"><div id="rightside-config-hide"><button id="readmode" type="button" title="阅读模式"><i class="fas fa-book-open"></i></button><button id="darkmode" type="button" title="浅色和深色模式转换"><i class="fas fa-adjust"></i></button><button id="hide-aside-btn" type="button" title="单栏和双栏切换"><i class="fas fa-arrows-alt-h"></i></button></div><div id="rightside-config-show"><button id="rightside-config" type="button" title="设置"><i class="fas fa-cog fa-spin"></i></button><button class="close" id="mobile-toc-button" type="button" title="目录"><i class="fas fa-list-ul"></i></button><a id="to_comment" href="#post-comment" title="直达评论"><i class="fas fa-comments"></i></a><button id="go-up" type="button" title="回到顶部"><span class="scroll-percent"></span><i class="fas fa-arrow-up"></i></button></div></div><div><script src="/js/utils.js?v=4.13.0"></script><script src="/js/main.js?v=4.13.0"></script><script src="https://lib.baomitu.com/fancyapps-ui/5.0.33/fancybox/fancybox.umd.min.js"></script><div class="js-pjax"><script>(()=>{let t=null;const e=()=>{if(t=Artalk.init(Object.assign({el:"#artalk-wrap",server:"https://artalk.dreamlove.top",site:"梦洁小站",pageKey:location.pathname,darkMode:"dark"===document.documentElement.getAttribute("data-theme")},null)),"null"===GLOBAL_CONFIG.lightbox)return;t.on("list-loaded",()=>{t.ctx.get("list").getCommentNodes().forEach(t=>{const e=t.getRender().$content;btf.loadLightbox(e.querySelectorAll("img:not([atk-emoticon])"))})});btf.addGlobalFn("pjax",()=>{t.destroy()},"destroyArtalk")},a=async()=>{"object"==typeof Artalk||(await getCSS("https://lib.baomitu.com/artalk/2.8.2/Artalk.min.css"),await getScript("https://lib.baomitu.com/artalk/2.8.2/Artalk.min.js")),e()};btf.addGlobalFn("themeChange",e=>{const a=document.getElementById("artalk-wrap");if(!a||!a.children.length)return;const l="dark"===e;t.setDarkMode(l)},"artalk"),a()})()</script></div><script id="canvas_nest" defer color="0,0,255" opacity="0.7" zindex="-1" count="99" mobile="false" src="https://lib.baomitu.com/butterfly-extsrc/1.1.3/canvas-nest.min.js"></script><script async data-pjax src="//busuanzi.ibruce.info/busuanzi/2.3/busuanzi.pure.mini.js"></script><div id="algolia-search"><div class="search-dialog"><nav class="search-nav"><span class="search-dialog-title">搜索</span><button class="search-close-button"><i class="fas fa-times"></i></button></nav><div class="search-wrap"><div id="algolia-search-input"></div><hr><div id="algolia-search-results"><div id="algolia-hits"></div><div id="algolia-pagination"></div><div id="algolia-info"><div class="algolia-stats"></div><div class="algolia-poweredBy"></div></div></div></div></div><div id="search-mask"></div><script src="https://lib.baomitu.com/algoliasearch/4.22.1/algoliasearch-lite.umd.min.js"></script><script src="https://lib.baomitu.com/instantsearch.js/4.65.0/instantsearch.production.min.js"></script><script src="/js/search/algolia.js?v=4.13.0"></script></div></div></body></html>