序言 vue.js介绍
1 安装与部署
-
通过script引入
-
通过CDN引入
2 创建第一个vue应用
new Vue生成一个全局变量
el是元素的缩写,使用id选择器进行元素绑定(也叫挂载)
3 数据与方法
vm是ViewModel,视图模型的缩写,vue受到mvvm的启发创造的,所以有时候变量命名为vm,表示致敬!
说明:该图创建Vue变量是Vue2的写法
一般是响应式,如果让变量变为非响应式,那么可以使用以下 Object.freeze() 方法
3-数据与方法.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>3 数据与方法</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body>
<div id="app">{{a}}--{{b}}</div>
<script>
var data = { a: 1 };
// 创建 Vue2 变量
var vm = new Vue({
el: "#app",
data: data,
});
data.a = "hello";
// data.b = "test"; // 没有输出,说明如果我们需要让我们的属性具有响应式,需要在创建Vue全局变量的时候就进行声明
vm.b = "test"; // 有输出
vm.$watch("a", function (newVal, oldVal) {
console.log(newVal, oldVal);
});
vm.$data.a = "a的值";
</script>
</body>
</html>
var data = { a: 1 };
var vm = new Vue({
el: "#app",
data: data,
});
<b>上面代码为什么能直接用vm.a访问到a属性?</b>
这是因为 Vue 在初始化实例的时候,会将
data对象中的属性代理到实例上。具体来说,Vue 会使用Object.defineProperty()方法将data对象中的属性转换成getter/setter,这样当我们访问实例上的属性时,实际上是在访问data对象中的对应属性。因此,当执行
var vm = new Vue({ el: "#app", data: data })时,Vue 会将data对象中的属性a转换成实例的属性,并将其挂载到el属性所对应的 DOM 元素上(即#app元素上)。这样,我们就可以通过访问vm.a来访问data对象中的属性a了。
那如果上面的data={a:{b:{c:100}}},可以直接使用vm.c访问到c属性吗
不能直接使用
vm.c访问到c属性,因为data中的a属性是一个对象,需要使用vm.a.b.c才能访问到c属性。即可以通过vm.a.b.c访问到c属性的值,其中a属性对应的是一个对象,需要通过a属性访问到该对象,然后才能通过b属性访问到该对象中的b属性,最后才能通过c属性访问到该对象中的c属性。
4 生命周期
注意:生命周期函数不能使用箭头函数,因为箭头函数没有this
4-生命周期.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>4-生命周期</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body>
<div id="app">{{msg}}</div>
<script>
var vm = new Vue({
el: "#app",
data: {
msg: "hi vue",
},
// 在实例初始化之后,数据观测(data observer)和 event/watcher 时间配置之前被调用
beforeCreate: function () {
console.log("beforeCreate");
},
// 在实例创建完成后被立即调用
// 在这一步,实例已完成以下的配置:数据观测(data observer),属性和方法的运算,watch/event 时间回调
// 然而,挂载阶段还没开始,$el 属性目前不可见
created() {
// 这是缩写形式,created:function(){} function可以省略缩写
console.log("created");
},
// 在挂载开始之前被调用:相关的渲染函数首次被调用
beforeMount: function () {
console.log("beforeMount");
},
// el 被新创建的 vm.$el 替换,挂载成功
mounted: function () {
console.log("mounted");
},
// 数据更新时调用
beforeUpdate() {
console.log("beforeUpdate");
},
// 组件 DOM 已经更新,组件更新完毕
updated() {
console.log("updated");
},
});
setTimeout(function () {
vm.msg = "change";
}, 3000);
</script>
</body>
</html>
运行结果:
setTimeout默认时长是多少
在浏览器和 Node.js 环境中,
setTimeout函数的默认时长是 0 毫秒。但是需要注意的是,这并不意味着回调函数会立即执行,因为 JavaScript 是单线程的,事件循环机制决定了回调函数必须等到当前代码执行完毕,才能被执行。
5 模板语法
但是没办法,我发现了下面的一个问题
为什么 <p v-html="rawHtml">Using v-html directive:</p> 这么写,Using v-html directive:会被覆盖
当使用
v-html指令时,绑定的表达式会被渲染成对应的HTML标签并替换掉包含v-html的元素。在这个例子中,
rawHtml中包含的HTML代码会替换掉包含v-html指令的<p>标签,因此Using v-html directive:这个文本内容就不再存在于DOM中,被替换成了rawHtml中的HTML代码。如果要保留Using v-html directive:这个文本内容,可以将它包裹在一个父元素内,如下所示:<div> <p>Using v-html directive:</p> <p v-html="rawHtml"></p> </div>这样就可以在页面上同时显示
Using v-html directive:文本和渲染后的HTML代码。
5-模板语法.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>5-模板语法</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body>
<div id="app" v-once>
{{msg}}
<p>Using mustaches:{{ rawHtml }}</p>
<!-- <p>Using v-html directive: <span v-html="rawHtml"></span></p> 这样写会多一个span标签,而目标span会嵌套在里面(笔记有截图)不过最终还是只能这么写-->
<p>Using v-html directive:</p>
<p v-html="rawHtml"></p>
<div v-bind:class="color">test...</div>
<p>{{number+1}}</p>
<p>{{ok?'YES':'NO'}}</p>
<p>{{message.split('').reverse().join('')}}</p>
</div>
<script>
var vm = new Vue({
el: "#app",
data: {
msg: "hi vue",
rawHtml: '<span style="color: red">this is should be red</span>',
color: "blue",
number: 42,
ok: 1 == 1, // Number(0、1、2、3...)/Boolean(true/false)/表达式都可以,其他的忘了
message: "vue", // 插值表达式完全支持JavaScript逻辑表达式
},
});
vm.msg = "hi..."; // 文本插值不会改变 因为v-once
// v-bind 动态绑定用户自定义属性,使用场景一:根据下面style样式举例子,通过某一个按钮进行点击切换class属性值,改变对应元素的样式
</script>
<style>
.red {
color: red;
}
.blue {
color: blue;
font-size: 50px;
}
</style>
</body>
</html>
运行结果:
6 模板语法-插值
6-模板语法-插值.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>6-模板语法-插值</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body>
<div id="app">
<p v-if="seen">现在你看到我了</p>
<a v-bind:href="url" target="_blank">我的博客</a>
<!-- v-bind: -> : -->
<div @click="click1">
<!-- v-on:click -> @click -->
<div @click.stop="click2">
<!-- 因为点击click me,会触发click2和click1 所以用.stop 进行阻止 -->
<!-- .stop 是vue的修饰符 表示当前点击事件执行完后就停下来,不再向外传播 -->
click me
</div>
</div>
</div>
<script>
var vm = new Vue({
el: "#app",
data: {
seen: true,
url: "http://ben314.top",
},
methods: {
click1: function () {
console.log("click1....");
},
click2() {
console.log("click2....");
},
},
});
</script>
</body>
</html>
7 class与style绑定
7 class与style绑定
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>7 class与style绑定</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body>
<div id="app">
<div
class="test"
:class="[isActive?'active':'',isGreen?'green':'']"
style="
width: 200px;
height: 200px;
text-align: center;
line-height: 200px;
"
>
<!--
如果不使用:class={} 对象来进行动态绑定,也可以用数组实现静态绑定和动态绑定(数组的动态没对象书写方便,是用三元运算符进行判断的)
对象写法 :class="{ active : isActive ,green:isGreen}"
数组静态写法 :class="['active','green']" 动态写法如上所示
-->
hi vue
</div>
<div :style="{color:color,fontSize:size,background:isRed?'pink':''}">
<!-- 只能用驼峰式,短横杆分割在这里行不通 -->
hi vue
</div>
</div>
<script>
var vm = new Vue({
//不要写成newVue 这样写是错误的,导致样式不生效
// #FF000是偏黑色,不是红色
el: "#app",
data: {
isActive: true,
isGreen: false,
color: "blue",
size: "50px",
isRed: true,
},
});
</script>
<style>
.test {
font-size: 30px;
}
.active {
background-color: aqua;
}
.green {
color: blueviolet;
}
</style>
</body>
</html>
8 条件渲染
8-条件渲染.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>8 条件渲染</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body>
<div id="app">
<div v-if="type==='A'">A</div>
<div v-else-if="type==='B'">B</div>
<div v-else-if="type==='C'">C</div>
<div v-else>Not A/B/C</div>
<h1 v-show="ok">Hello!</h1>
</div>
<script>
var vm = new Vue({
el: "#app",
data: {
type: "D",
ok: false,
},
});
</script>
</body>
</html>
9 列表渲染
为了给Vue一个提示,以便它能跟踪每个节点的身份,从而重用和重新排序现有元素,你需要为每 项提供一个唯一 key 属性
9-列表渲染
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>9 列表渲染</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body>
<div id="app">
<ul>
<li v-for="item,index in items" :key="index">
{{index+' '}}{{item.message}}
</li>
</ul>
<ul>
<li v-for="(value, key) in object" :key="key">
{{ key }}: {{ value }}
</li>
<!-- value 直接访问属性值,用key才是访问属性名 -->
</ul>
<!-- <p>{{object.title}}</p> -->
</div>
<script>
var vm = new Vue({
el: "#app",
data: {
items: [{ message: "Foo" }, { message: "Bar" }],
object: {
title: "How to do lists in Vue",
author: "Jane Doe",
publishedAt: "2016-04-10",
},
},
});
</script>
</body>
</html>
这里为什么<li v-for="value in object">{{value}}</li>这样就可以访问到object对象属性的属性值,不应该是<li v-for="value in object">{{value.value}}</li>吗
在这个例子中,
object是一个包含多个属性的 JavaScript 对象,每个属性都有一个属性名和一个属性值。在模板中,v-for指令用于循环遍历object对象的属性。循环遍历时,value变量被设置为当前属性的属性值,因此在模板中使用{{value}}就可以访问当前属性的属性值。如果在模板中使用
{{value.value}},则会尝试访问当前属性的value属性,但是在这个例子中,object对象的属性中没有名为value的属性,因此会输出undefined。如果我需要访问的是属性名而不是属性值应该怎么修改?
如果你想访问对象的属性名而不是属性值,可以使用Vue的特殊变量 $key,它可以在v-for指令的第二个参数中使用。例如,可以将代码修改为:
<ul> <li v-for="(value, key) in object">{{ key }}</li> </ul>这将输出对象的所有属性名。如果你想同时输出属性名和属性值,可以将代码修改为:
<ul> <li v-for="(value, key) in object">{{ key }}: {{ value }}</li> </ul>这将输出类似于"title: How to do lists in Vue"的结果。
10 事件绑定
10-事件绑定.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>10-事件绑定</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body>
<div id="app">
<div id="example-1">
<button v-on:click="counter+=1">数值:{{counter}}</button>
<br />
<button @click="greet('abc',$event)">greet</button>
<!-- $event 事件变量 -->
<br />
<button @dblclick="counter=0">双击清除counter</button>
<!-- 粗心把@click写成了:click -->
</div>
</div>
<script>
var vm = new Vue({
el: "#app",
data: {
counter: 0,
msg: "你好!",
},
methods: {
greet(str, e) {
// alert("Hi!");
// alert(this.msg);
alert(str);
console.log(e); //打印PointerEvent对象信息
},
},
});
</script>
</body>
</html>
11 表单输入绑定
这个属性通常用于显示多行文本内容,保留原有的格式和换行。pre-line是保留换行符的意思
讲一下reduce
reduce()是JavaScript中的数组方法之一,它可以用于从左到右迭代数组并返回一个最终的单一值。这个方法接受两个参数:回调函数和初始值。回调函数需要返回一个累加值,该值在下次调用回调函数时作为第一个参数传递给回调函数,然后继续进行迭代。最终结果是该方法迭代数组并将所有值收缩为一个单一值。以下是
reduce()方法的语法:array.reduce(callback[, initialValue])
callback:回调函数,包含四个参数:
accumulator:累加器累积回调函数的返回值。它是上一次回调返回的值,或者是提供的初始值。currentValue:当前处理的元素。currentIndex:当前元素在数组中的索引。array:调用reduce()的数组。
initialValue:可选的初始值,如果提供了则作为第一次调用回调函数时的第一个参数使用。如果未提供,则使用数组中的第一个元素。以下是一个例子,展示如何使用
reduce()计算数组中所有元素的总和:const numbers = [1, 2, 3, 4]; const sum = numbers.reduce((accumulator, currentValue) => { return accumulator + currentValue; }, 0); console.log(sum); // 输出 10在这个例子中,我们首先定义了一个数组
numbers,包含四个数字。然后我们调用reduce()方法来计算数组中所有元素的总和。我们使用一个回调函数作为第一个参数,将累加器初始化为0(作为第二个参数传递给reduce()方法),并将当前元素添加到累加器上。最终,reduce()方法返回累加器的值,即所有数字的总和。
reduce()方法非常有用,可以用于许多场景,例如查找最大值、计算平均值等。
const sum = numbers.reduce((accumulator, currentValue) => { return accumulator + currentValue; }, 0); 上面代码是把accumulator + currentValue赋值给accumulator然后返回吗是的,这里使用了
Array.prototype.reduce()方法对numbers数组进行累加求和操作。在这个方法中,accumulator表示累加器,currentValue表示当前数组元素的值,初始值为 0。在每一次执行回调函数时,将accumulator与currentValue相加得到新的值,并返回给accumulator,以便在下一次执行回调函数时使用。最后返回的是accumulator的最终值,即累加和。
如何获取到input输入框输入的信息
可以使用JavaScript的DOM操作来获取到input输入框输入的信息,具体步骤如下:
- 通过document对象的getElementById()方法或者querySelector()方法获取到需要操作的input元素。
- 获取input元素的value属性,该属性的值为用户在输入框中输入的内容。
- 可以在input元素上监听input或change事件,以便在用户输入内容时或者在用户停止输入并离开输入框时获取到输入的内容。
例如,以下是一个简单的示例代码:
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>获取input输入框输入的信息</title> </head> <body> <input type="text" id="myInput"> <button onclick="getInputValue()">获取输入框的值</button> <script> function getInputValue() { const input = document.getElementById('myInput'); const inputValue = input.value; console.log(inputValue); } </script> </body> </html>在这个示例中,当用户在输入框中输入了内容后,单击“获取输入框的值”按钮,就会在控制台中打印出输入框的值。
style="white-space: pre-line"
white-space: pre-line是一个CSS属性,表示元素中的连续空白(空格、换行符等)会被合并成一个空格,并且会在遇到<br>或者换行符时进行换行。这个属性通常用于显示多行文本内容,保留原有的格式和换行。
Jack
Jack是一个HTML标签,它可以关联一个表单控件,如下:
for属性指定该label所对应的表单控件的id,例如<input>标签的id属性。这样在点击label标签时,就会自动将焦点转移到对应的表单控件上。- 在一些屏幕阅读器或者视障人士使用的浏览器中,这个标签可以让他们更容易地与表单进行交互和使用。
举例来说,如果你有一个文本框:
<input type="text" id="jack" name="jack">那么你可以通过以下label标签关联该表单控件:
<label for="jack">Jack</label>
11-表单输入绑定.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Document</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body>
<div id="app">
<div id="example-1">
<input type="text" v-model="message" placeholder="edit me" />
<!-- placeholder 是占位符的意思,用来作为输入框的提示文本 -->
<p>Message is {{message}}</p>
<textarea
v-model="message2"
placeholder="add multiple lines"
></textarea>
<p style="white-space: pre-line">{{message2}}</p>
</div>
<hr />
<!-- 复选框 双向绑定 -->
<div style="margin-top: 20px">
<input type="checkbox" id="jack" value="Jack" v-model="checkedNames" />
<label for="jack">Jack</label>
<input type="checkbox" id="john" value="John" v-model="checkedNames" />
<label for="john">John</label>
<input type="checkbox" id="mike" value="Mike" v-model="checkedNames" />
<label for="mike">Mike</label>
<br />
<span>Checked names: {{checkedNames}}</span>
</div>
<!-- 单选框 双向绑定 -->
<div style="margin-top: 20px">
<input type="radio" id="man" value="Man" v-model="picked" />
<label for="man">Man</label>
<input type="radio" id="woman" value="Woman" v-model="picked" />
<label for="woman">Woman</label>
<br />
<span>Picked: {{picked}}</span>
</div>
<br />
<!-- 提交按钮 并创建点击事件 -->
<button @click="submit">提交</button>
</div>
<script>
var vm = new Vue({
el: "#app",
data: {
message: "test",
message2: "hi",
checkedNames: ["Jack", "John"], // 值是input.value的值,checkNames因为是复选框,这里用数组进行保存
picked: "Man", // 值是input.value的值,picked是单选框,所以用字符串进行保存
},
methods: {
submit() {
var postObj = {
msg1: this.message,
msg2: this.message2,
checkVal: this.checkedNames,
pickedVal: this.picked,
};
console.log(postObj);
},
},
});
</script>
</body>
</html>
12 组件基础
如果我们想要在组件内添加其他元素,我们需要一个根结点对其进行包裹,组件才能正常显示,不然只显示第一个,如下图所示
12-组件基础.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>12 组件基础</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body>
<div id="app">
<button-counter title="title1: " @clickknow="clickknow"></button-counter>
<h2>hi...h2</h2>
<button-counter title="title2: "></button-counter>
<h6>hi...h2</h6>
</div>
<script>
Vue.component("button-counter", {
props: ["title"],
data: function () {
return {
count: 0,
};
},
// 组件的样式和元素渲染在模板template中,script标签外面的html是new Vue全局变量的
template: `<div><h1>hi...</h1><button @click="clickfun">{{title}} you clicked {{count}} times.</button><slot></slot></div>`,
methods: {
clickfun: function () {
this.count++;
this.$emit("clickknow", this.count); // 第一个参数是事件名称,第二个参数是携带的属性
},
},
});
var vm = new Vue({
el: "#app",
data: {},
methods: {
clickknow: function (e) {
// 携带的属性变成实参传入
console.log(e);
},
},
});
</script>
</body>
</html>
13 组件注册
13-组件注册.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>13 组件注册</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body>
<div id="app">
<button-counter></button-counter>
<test></test>
</div>
<script>
// 全局注册
Vue.component("button-counter", {
props: ["title"],
data: function () {
return {};
},
// 组件的样式和元素渲染在模板template中,script标签外面的html是new Vue全局变量的
template: `<div><h1>hi...</h1></div>`,
methods: {},
});
var vm = new Vue({
el: "#app",
data: {},
methods: {
clickknow: function (e) {
// 携带的属性变成实参传入
console.log(e);
},
},
// 局部注册 局部组件也有它的template、data、methods
components: {
test: {
template: `<div><h2>h2...</h2></div>`,
},
},
});
</script>
</body>
</html>
14 单文件组件
按照以上命令进行插件安装
之后在终端启动vue ui 图形化管理界面创建vue项目
但是我不知道是什么原因自己不能通过ui创建,只能在终端使用vue create 文件夹名称 进行创建
下面是初始化项目目录结构
|-- root // 根目录
|-- .gitignore
|-- babel.config.js
|-- jsconfig.json
|-- package-lock.json
|-- package.json
|-- README.md
|-- vue.config.js
|-- public // 打包之后用于部署到生产环境下的目录
| |-- favicon.ico
| |-- index.html
|-- src // 开发目录
|-- App.vue // 项目的入口文件,去完成组件的引入工作
|-- main.js
|-- assets
| |-- logo.png
|-- components // 组件目录
|-- HelloWorld.vue
本节相关代码如下
快速上手Vue-官方视频\test\src\components\test-md-fuck.vue
<template>
<h2 class="red">test...{{msg}}</h2>
</template>
<script>
export default {
name:'test-md-fuck',
props:{
msg:{
type:String,
default:'test msg'
}
},
data(){
return {
}
},
methods: {
},
}
</script>
<style>
.red{
color:red;
}
</style>
快速上手Vue-官方视频\test\src\App.vue
<template>
<div id="app">
<img alt="Vue logo" src="./assets/logo.png">
<HelloWorld msg="Welcome to Your Vue.js App"/>
<test-md-fuck msg="test msg"></test-md-fuck>
</div>
</template>
<script>
import HelloWorld from './components/HelloWorld.vue'
// 组件注册
import testMdFuck from './components/test-md-fuck.vue'
export default {
name: 'App',
components: {
HelloWorld,
testMdFuck,
}
}
</script>
<style>
#app {
font-family: Avenir, Helvetica, Arial, sans-serif;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
text-align: center;
color: #2c3e50;
margin-top: 60px;
}
</style>
相关问题链接
[eslint报错:Parsing error: No Babel config file detected? ](www.cnblogs.com/hmy-666/p/1…)