JavaScript學習筆記
和HTML和CSS不一樣,它是一門編程語言。
JS簡介
JS是一個客戶端腳本語言,不需要編譯,每一個瀏覽器都有JS的解析引擎。可以增強用戶和HTML頁面的交互,使網頁產生動態。
JS的生成是在當時網速所限,必須在客戶端就完成一些表單的校驗等工作以減少客戶端和服務器端的通信次數的實際要求下產生的
*注意BOM和DOM不是JS獨有的,幾乎每一種腳本語言都有,只是ECMA沒有將其標准化**
JS基礎語法
ECMASCRIPT
是客戶端腳本語言的標准。
基本語法
-
與HTML結合
- 內部JS
- 外部JS
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>JS與HTML結合</title> <!-- 內部JS:在HTML頁面內部定義SCRIPT標簽,且它可以寫在HTML頁面的任意位置 但是放在前面和放在后面會影響執行順序。 --> <script> while(true){ alert("hello,world"); } </script> <!-- 外部JS --> </head> <body> </body> </html>
-
常用的輸出方法
-
alert();
-
document.write();
可以在要輸出的語句之后加上字符串
"<br>"
來實現換行
-
-
注釋
單行注釋://
多行注釋:/* */
和Java以及C++完全一樣
-
數據類型
-
原始數據類型
-
引用數據類型
-
-
函數定義
function a{
}
-
變量
JS是弱類型的,在申請空間時不需要限制類型,內存空間中的變量類型可以是任意的。
eg: var a=10;
注意,JS中的限制所示真的寬松,定義變量時不寫var都可以,這樣定義的就是全局變量而非局部變量。
-
運算符
這里只選一些和C++或者Java不一樣的來說
- typeof(變量名);//返回變量的具體類型。
注意這里有一個bug,就是null返回的類型是object(原始類型中沒這個)而不是null,這個到現在也沒有解決,但是也說得通- =:嚴格相等運算符。由於JS是弱類型的,所以如果兩個對象類型不同,使用時也會轉換為同一類型進行比較,例如
'1'==1
會被判斷為true.但是嚴格相等運算符則不會主動進行類型的轉換。
-
流程控制語句
-
if-else
-
switch:
注意switch(變量)在Java中可以接受的數據類型有byte\int\short\char\枚舉\string。但是在JS中,switch可以接受任意原始數據類型。所以可以寫出這樣的鬼畜語句來:
-
while
-
do while
-
for
注意for循環中的條件不要再寫
for(int i=0;i<100;i++)
了,int要換成var
-
JS對象
基本對象
這里的Boolean\String\number就是原始數據類型的包裝類.
-
Function:描述方法(這里又叫函數了)的對象,是一個特殊的對象
-
創建
-
var fun=new function(形式參數列表,方法體)
鬼畜方法 -
function 方法名稱(形式參數列表){方法體}
。這是最常見的方法注意在方法定義中,形參的類型不用寫(弱類型就這樣)
-
var 方法名=function(形參){方法體}
-
-
function的屬性
- length:形參個數:fun.length//這個是屬性而不是成員方法,不需要()
注意,JS中如果定義了重名且形參也相同的方法,不會報錯,而會進行方法的覆蓋,后面的覆蓋前面的(腳本語言····)
在方法聲明中,有一個隱藏的內置對象(數組),叫arguements,其封裝了所有的實際參數,下面有一個示例:
nb不,方法的形參是空的~
-
-
Array對象:
JS中,數組元素的類型是可變的,長度也是可變的(我的天啊~)
例如:如果定義一個長度為4的數組,但是要打印第五個元素,那么數組會自動擴容為五個,且第五個元素為未定義(undefined)類型
-
創建
-
var arr=new Array(元素列表);
-
var arr=new Array(默認長度);
-
var arr=[元素列表];
例如:
? 如果未初始化數組就打印,則打印結果是只有一串逗號
-
-
屬性
length:數組長度
-
成員方法
join(參數):將數組元素安裝參數中指定的分隔符拼接為字符串
? 如果直接打印數組,則會默認將元素進行拼接並且用逗號分隔
-
JavaScript對象
Date對象
-
創建:
var date=new Date();
-
方法
- toLocalString(),返回當前date對象對應的字符串格式的本地時間,以當地的表示方式表示
- getTine(),返回1970年1月1日至今天的毫秒值,常作為時間戳使用
Math對象
-
創建
特點:該對象不需要創建,直接調用類方法即可,是一個工具類
-
方法
- random():產生一個[0-1)之間的隨機數,注意是包括0,不包括1的
- ceil(x):上取整
- floor(x):下取整
- round(x):四舍五入
-
屬性
- PI
RegExp 對象(正則表達式)
-
正則表達式回顧
-
對象的創建
-
var reg=new RegExp("正則表達式")
-
var reg=/正則表達式/;
大部分的時候使用第二種方式,因為這種方式中正則表達式不是字符串,不存在轉義的問題,直接寫就行
-
-
方法
test(String):驗證字符串是否符合規則
Global對象
-
特點:全局對象,這個對象中封裝的方法不需要對象(也就是調用時候不需要對象名或者類名)就可以直接調用
-
方法
encode和encodeURLComponent用於URL的編碼,decode和decodeURLComponent用於URL的解碼
在瀏覽器的訪問、做數據傳輸的時候,由於協議不支持中文數據,所以需要將中文數據進行轉碼再發送到服務器端,這個轉碼的工作一般由URL編碼完成,這也是默認的編碼方式。
例如我們在搜索引擎中輸入中文進行搜索時,在地址欄中呈現的、符號和字母混雜的就是用URL編碼后的內容
DOM
文檔對象模型 (DOM) 將 web 頁面與到腳本或編程語言連接起來。通常是指 JavaScript
將標記語言文檔的各個組成部分封裝為對象,可以使用這些對象進行操作
DOM將HTML文檔表達為樹結構:DOM樹
DOM標准
- 核心DOM:針對任何結構化文檔的標准
- XML DOM:針對XML
- HTML DOM:針對HTML
2和3都是對1的擴展和封裝,但是3對1的修改比較多,2其實更解決於1
核心DOM
- Document對象:文檔對象
-
屬性:
-
方法:
-
獲取element對象:
getElementByID()
getElementsByTagName()
getElementsByName()
區別在於,id是唯一的,而name則不是.而TagName其實是tag的類型,例如div\p等等
還有一個HTML DOM的一個方法:
getElementsByClassName()
-
創建DOM對象
- createElement()
- createElement()
-
創建的對象在內存里,是沒有顯示到頁面上的
這是創建方法中最常用的
2. createTextNode()
3. createComment()
4. createAttribute()
- Element對象:元素對象
-
獲取:通過document對象獲取和創建
-
方法
-
removeAttribute()
例如HTML中某個對象有個font的屬性,我們可以使用這個方法來去除掉
-
setAttribute()
-
-
屬性
-
Attribute對象:屬性對象
-
Text:文本對象
-
Comment:注釋對象
-
Node:節點對象
Node對象是整個DOM的主要數據類型
所有DOM對象都可以被認為是一個節點,可以應用Node的通用方法
-
方法
-
appendChild():向節點的子節點列表的結尾添加新的子節點
-
removeChild():刪除當前節點指定的子節點
-
replaceChild():新節點替代子節點
例如:
var elementById1 = document.getElementById("div1"); var elementById2 = document.getElementById("div2"); elementById1.removeChild()
-
-
屬性
- parentNode:返回當前節點的父節點
案例:動態表格
思路是使用node的通用方法操作表格,實現表格的動態變化
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Dynamic Table</title> <style> <!--design a css style for table --> table{ border: 1px solid; margin: auto; width: 500px; } td,th{ text-align: center; border: 1px solid; } div{ text-align: center; margin: 50px; } </style> </head> <body> <div> <input type="text" id="id" placeholder="請輸入編號"> <input type="text" id="name" placeholder="請輸入姓名"> <input type="text" id="gender" placeholder="請輸入性別"> <input type="button" id="btn_add" value="添加"> </div> <table> <caption>學生信息表</caption> <tr> <th>編號</th> <th>姓名</th> <th>性別</th> <th>操作</th> </tr> <tr> <td>1</td> <td>令狐沖</td> <td>男</td> <td><a href="" onclick="delTr(this)">刪除</a> </td> </tr> </table> <script> //添加 //1. 為添加按鈕綁定單機內容 //2. 獲取文本框的內容 //3.創建td,設置td的文本為文本框的內容 //4.創建tr //5.將td添加到tr中 //6.獲取table,將tr添加到table //7. document.getElementById("btn_add").onclick=function () { //獲取文本框內容 //這里我們應用了node的通用方法來處理DOM對象 var id = document.getElementById("id").value; var name = document.getElementById("name").value; var gender = document.getElementById("gender").value; //創建td,賦值td的標簽體 var td_id = document.createElement("td"); //先將字符串放入TextNode,再將這個node放入我們創建的node中,不能直接把字符串放入node中 var text_id =document.createTextNode(id); var td_name = document.createElement("td"); var text_name =document.createTextNode(name); var td_gender = document.createElement("td"); var text_gender =document.createTextNode(gender); var td_a = document.createElement("td"); //創建一個和a類型相同的節點 var ele_a = document.createElement("a"); //設置element的兩個屬性 ele_a.setAttribute("href","javascript:void(0);"); ele_a.setAttribute("onclick","delTr(this);") var text_a = document.createTextNode("刪除"); //填充內容 ele_a.appendChild(text_a); //將內容放入td中 td_id.appendChild(text_id); td_name.appendChild(text_name); td_gender.appendChild(text_gender); td_a.appendChild(ele_a); //創建tr,將各個td放入tr中 var tr = document.createElement("tr"); tr.appendChild(td_id); tr.appendChild(td_name); tr.appendChild(td_gender); tr.appendChild(td_a); //獲取table var table = document.getElementsByTagName("table")[0]; //為table添加子節點,這些Node的通用方法能反映到顯示上去,它相當於是用通用方法操作了元素 table.appendChild(tr); } function delTr(obj) { //不斷向樹型結構向上找,直到table var table = obj.parentNode.parentNode.parentNode; var tr = obj.parentNode.parentNode; table.removeChild(tr); } </script> </body> </html>
HTML DMO
- 標簽體的設置和獲取:innerHTML
- 使用HTML元素對象的屬性
- 控制樣式
使用HTML的innerHTML,我們可以對上面的案例進行優化。
先舉一個簡單的使用innerHTML獲取和修改標簽體的例子:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>HTMLDMO</title> </head> <body> <div id="div1"> div </div> <script> var div=document.getElementById("div1"); //獲取標簽體內容,這里就是文本div對應的對象 var innerHTML=div.innerHTML; //將對象替換為文本輸入框 div.innerHTML="<input type='text'>"; //還能追加呢 div.innerHTML+="<input type='text'>"; </script> </body> </html>
然后我們可以借助innerHTML,對上面的案例進行改進:
document.getElementById("btn_add").onclick=function () { var id = document.getElementById("id").value; var name = document.getElementById("name").value; var gender = document.getElementById("gender").value; var table = document.getElementsByTagName("table")[0]; table.innerHTML+=" <tr>\n" + " <td>"+id+"</td>\n" + " <td>"+name+"</td>\n" + " <td>"+gender+"</td>\n" + " <td><a href=\"\" onclick=\"delTr(this)\">刪除</a> </td>\n" + " </tr>"
可以大大簡化流程
-
控制樣式:
- 方式一
var div1=document.getElementById("div1");
div1.style.border="1px solid red";//設置樣式,使用style.樣式屬性可以對樣式進行設置
div1.style.fontSize="20px";//對css中樣式是段橫線連接的,例如font-size,這里就轉換為了fontSize
-
方式二
這種方式是說,如果我已經有了一個預先定義了css樣式,然后我想讓某個對象去動態地套用樣式的話,就要動態地給這個對象加上CSS樣式所需的判斷條件,例如class或者name等等
var div2=document.getElementById("div2"); div2.className="d1"
這樣d1控制的樣式就會生效了。
DOM的功能
-
控制HTML文檔的內容(增刪改查)
-
獲取頁面標簽(元素)對象 ELemen對象:
document.getElementById("id值")
:通過元素的id獲取元素對象 -
使用document.getELementById()來獲取對象時,注意script中命令對對象的獲取和對象在HTML中定義的先后:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> <script> var logoImg = document.getElementById("logo"); alert(logoImg); </script> </head> <body> <img id="logo" src="img/1.png"> </body> </html>
注意上面的代碼,由於script是先定義的,所以就先執行,此時我們名為logo的對象還沒有建立,這段script就沒辦法執行
放到body的下面就好了
-
操作Element對象:
-
設置屬性值:設置的屬性應該是對象中有的、可以設置的屬性
-
修改標簽體內容
alert方法有“阻塞”的效果,不點擊的話是不會執行后面的腳本的
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> </head> <body> <h1 id="text">我開燈了</h1> <img id="logo" src="img/1.png"> </body> <script> var logoImg = document.getElementById("logo"); alert("我要換圖片了"); logoImg.src="img/2.jpg"; var text = document.getElementById("text"); //innerText()方法可以修改DOM對象內部的text text.innerText="我關燈了"; </script> </html>
-
-
綁定事件
-
直接在html標簽上,指定事件的屬性(操作),屬性值就是js代碼或者函數的名稱
事件:例如onclick
-
通過js獲取元素對象(document.getELementById()),指定事件屬性,指定一個函數,即:
var light=document.getElementById("id") light.onclick=function(){ ; }
第二種方法HTML對JavaScript沒有侵入,耦合度更低,更適合於多人協作使用。
-
事件
事件是某些組建被執行了某些操作后,觸發某些代碼的執行
監聽器:代碼
注冊監聽:將事件、事件源、監聽器結合到一起,當事件源上發生了某個事件,則觸發執行某個監聽器代碼。
常見的事件
- 點擊事件
- onclick:
- ondblclick:雙擊事件
- 焦點事件
- onblur:失去焦點
- onfocus:獲得焦點
- 加載事件
- onload
- 鼠標事件
- onmousedown
- onmouseup
- 鍵盤事件
- onkeyup:
- onkeydown:
- onkeypress:
- 選中和改變
- onchange
- onselect
- 表單事件
- onsubmit
- onreset
BOM
BOM:Browser Object Model,瀏覽器對象模型,它將瀏覽器的各個組成部分封裝為了對象。
- 瀏覽器對象:Navigator
- 瀏覽器窗口對象:Window,其包含了DOM對象在內
- 地址欄對象:Location
- 歷史記錄對象:History
- 顯示器屏幕對象:Screen
瀏覽器對象和顯示器屏幕對象基本不用,瀏覽器對象可以獲取瀏覽器的一些學習,而顯示器對象則可以獲取分辨率、屏幕大小等信息,對於網站做適配還是有些意義的(對了還聽說當時洋蔥頭為什么固定一個瀏覽器大小,就是為了防止通過顯示器信息來尋找到人)
Window對象
Window對象不需要創建,可以直接使用它的方法(類方法)。並且,window的引用也可以省略,也就是直接寫方法名就行了,甚至不需要寫類名:例如我們常用的alert方法,其實就是window.alert()。還有window.document,我們也簡化為document了
-
與彈出框有關的方法
-
alert()
-
confirm():彈出確認-取消對話框,選擇確定則返回true,否則返回false
-
prompt():顯示用戶輸入框,例如我們使用ftp連接等需要輸入賬號密碼的就可以這么干
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Window對象</title> </head> <body> <h1 id="word"></h1> </body> <script> var result = prompt("你算老幾?"); var text = document.getElementById("word"); var age = prompt("你幾歲了?"); text.innerText=result+"你大爺!"+age+"就敢叫"+result+"了?"; </script> </html>
-
-
與窗口打開關閉有關的方法
- open():返回一個新的window對象
- close():關閉調用者
-
定時器方法
- setTimeout():在指定的毫秒數后調用函數或計算表達式,只執行一次
- clearTimeout():取消設置的timeout
- setInterval():和setTimeout一樣,但是循環執行
- clearInterval():取消Interval
-
屬性
- 獲取其他BOM對象:history\location\nevigator\screen
Location對象
location對象包含有關當前URL的信息
-
創建:window.location獲取
-
方法
reload():重新加載當前文檔,即刷新
-
屬性
href:設置中返回完整的URL
history對象
注意這里說的是當前窗口下的記錄,而不是該瀏覽器的記錄
-
方法:
- back:
- forward:
- go:加載歷史記錄中某個特點頁面
-
屬性:
length:當前窗口歷史記錄列表中的個數
舉個例子
寫了一個憨批例子,口吐芬芳網頁:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Window對象</title>
</head>
<body>
<h1 id="word"></h1>
<h3 id="show"></h3>
<input type="button" value="打開" id="openNew">
<input type="button" value="關閉"id="close">
<input type="button" value="別提醒我時間了行不行" id="checkTime" hidden="true">
<input type="button" value="百度搜索" id="baidu">
<input type="button" value="掉頭" id="backButton">
<h3 id="historyLabel"></h3>
</body>
<script>
var text = document.getElementById("word");
var result = prompt("你算老幾?");
var age = prompt("你幾歲了?");
var button = document.getElementById("openNew");
var label = document.getElementById("show");
var baiduButton = document.getElementById("baidu");
var backBut = document.getElementById("backButton");
backBut.onclick=function (ev) {
alert("這你不能點下瀏覽器解決嗎?")
history.back();
}
baiduButton.onclick=function (ev) {
alert("TMD去個百度你還要我幫忙?")
location.href="https://www.baidu.com";
}
text.innerText=result+"你大爺!"+age+"就敢叫"+result+"了?";
bai.onclick=function (ev) {
alert("別點我,你找倒霉啊是不是,給我關了!");
close()
}
text.onload=f1();
var timeButton = document.getElementById("checkTime");
var checkTime=0;
var interval =null;
timeButton.onclick=function (ev) {
label.innerText="我不急誰急?合着我不花電錢?這倒霉孩子,德行!";
clearInterval(interval);
}
function f2() {
timeButton.hidden=false;
}
function f1() {
interval = setInterval("alert(\"快點,別磨嘰,電費不要錢啊?\");checkTime++;if(checkTime>2)f2();",10000);
}
button.onclick=function (ev) {
label.innerText="打開你大爺!你有啥啊你就打開!"
count=1;
}
var closeButton = document.getElementById("close");
var count=1;
closeButton.onclick=function (ev) {
if(count==1)
label.innerText="關個Pi,憑啥你說關就關,我打開那么費勁說關就關了?你再關一個試試?"
else
f();
count++;
}
var newWindow=null;
function f() {
alert("看爺給你再開一個")
newWindow = open();
var ret = newWindow.confirm("叫爸爸");
while(!ret){
alert("看爺給你再開一個")
newWindow = open();
ret = newWindow.confirm("叫爸爸");
}
newWindow.close();
}
</script>
</html>