如果您想訂閱本博客內容,每天自動發到您的郵箱中, 請點這里
說到前端, 大家第一反應是不是都是vue、react、webpack等這些大大小小的框架或者工具, 但其實這些都是和js相關的, 真正的樣式會被大家忽略。其實真正呈現給大家看到華麗的頁面, 都是樣式才讓他們多了那份色彩。那么大家覺得簡單的css樣式, 真的簡單么? 讓我們一起來看下, 開啟css的入坑之旅, 今天一起跟大家簡單聊聊盒模型的相關問題......
百度知道對此的解釋, 很有意思, 在此引用一下
CSS盒子模型, 內容(CONTENT)就是盒子里裝的東西; 而填充(PADDING)就是怕盒子里裝的東西(貴重的)損壞而添加的泡沫或者其它抗震的輔料; 邊框(BORDER)就是盒子本身了; 至于邊界(MARGIN)則說明盒子擺放的時候的不能全部堆在一起,要留一定空隙保持通風,同時也為了方便取出。 —— 百度知道
這段描述很有趣, 很好的解釋margin、border、padding之間的關系, 不同模式下, 盒模型的width也是不同的, 那么好, 盒模型的第一個坑來了, width的范圍問題。
通常瀏覽器里, 盒模型的分為兩種模式, 兩種模式(怪異模式和標準模式)下width和height的值不同, 怪異模式的width和height包含border、padding和content, 而標準模式下的width和height只包含content, 這就是為啥有些瀏覽器渲染出來的dom標簽排版會亂。解決也很簡單, 在標簽的上面, 加上doctype的設置就好了, 讓瀏覽器統一用同一種標準去解析頁面。 怪異模式(左圖)和標準模式(右圖)的如下:
當然, 還有用來改變盒模型width范圍的一個css3的屬性,
當設置為'border-box'時, width = border + padding + content;
當設置為'content-box'時, width = content。
那么第一個div的實際寬度為100px, 第二個div的實際寬度為120px。
說完盒模型的padding和border, 那么再來吐槽下margin, 盒模型的margin的折疊(margin collapsing)問題, 有些也叫外邊距合并。
通常我們說的折疊, 都是垂直方向上的折疊, 水平方向是不存在的。標準模式下, 上下兩個兄弟的塊級元素, margin是會重疊的, 并且以最大的那個間距為準(都為正數)。
比如下面這段代碼:
上圖灰色為重疊部分, 重疊10px的間距。
既然兄弟盒模型會有margin折疊, 那么父子呢? 答案是一定的, 父子也存在margin折疊的問題, 只不過條件稍微苛刻一點, 我們一起來看下。 父子組件的折疊觸發, 要求不能有間隙, 就是父組件不能設置border或padding值, 不能有空余的內容, 且同時有margin值, 比如下面這段代碼:
當然, 折疊后的空余部分, 也是取較大值, 且折疊觸發, 只存在于垂直方向。
上圖灰色為重疊部分, 重疊10px的間距。
剛才提到一個詞"間隙", 如果有間隙的話是不會觸發折疊的, 比如父級元素設置了padding, 或者子元素都設置了相對定位和top值等等。如下圖:
看到這里, 我想有些同學會問了, 對于這些
Margins between a floated box and any other box do not collapse (not even between a float and its in-flow children).
Margins of elements that establish new block formatting contexts (such as floats and elements with 'overflow' other than 'visible') do not collapse with their in-flow children.
Margins of absolutely positioned boxes do not collapse (not even with their in-flow children).
Margins of inline-block boxes do not collapse (not even with their in-flow children).
The bottom margin of an in-flow block-level element always collapses with the top margin of its next in-flow block-level sibling, unless that sibling has clearance.
The top margin of an in-flow block element collapses with its first in-flow block-level child's top margin if the element has no top border, no top padding, and the child has no clearance.
The bottom margin of an in-flow block box with a 'height' of 'auto' and a 'min-height' of zero collapses with its last in-flow block-level child's bottom margin if the box has no bottom padding and no bottom border and the child's bottom margin does not collapse with a top margin that has clearance.
A box's own margins collapse if the 'min-height' property is zero, and it has neither top or bottom borders nor top or bottom padding, and it has a 'height' of either 0 or 'auto', and it does not contain a line box, and all of its in-flow children's margins (if any) collapse.
這是從W3C里引用的原文, 這8條規則是特殊的不折疊的情況, 簡單翻譯過來(僅供參考):
浮動的盒模型不會margin折疊
創建BFC與子不折疊
設置定位的盒模型不會折疊
行內塊級元素的盒模型不折疊
兄弟元素有間隙不折疊
父子盒模型元素, 孩子元素有border、padding、有浮動就不折疊
height為auto、min-height為0的塊級盒模型, 和它的最后一個沒有border和padding的孩子盒模型底邊距折疊, 且孩子的底部外邊距和被清除浮動上邊距有間隙不折疊。
如果min-height為0, 上下border、上下padding都為0, height為0或auto, 且沒有行內盒模型, 他的孩子節點都會折疊
有點晦澀難懂, 大家不妨消化一下。說到這, 再補充一下, 盒模型margin折疊的計算問題, 總結了以下幾點:
同為正值時, 取較大者為兩者為間距
一正一負時, 正負相加為間距, 若結果為負值, 則兩者部分重合
都為負值時, 兩者重合, 且重合部分為絕對值大者
舉個例子:
兩者都為負值, 兩個div上下重合, 且重合間距為15px。
暫時就想到這么多, css的學習之路任重而道遠, 盒模型又是重中之重。上面有描述不對的地方也歡迎各位同學批評指正, 也歡迎大家來到大轉轉FE做客, 一起討論一起研究前端的技術問題。志同道合的同學, 也歡迎加入我們轉轉FE團隊, 咱們一起打拼。
盒模型
box-sizing
:
<div class="wrapper z1"></div>
<div class="wrapper z2"></div>
.wrapper{
width: 100px;
height: 50px;
padding: 10px;
background-color: #dedede;
}
.z1{
box-sizing: border-box;
}
.z2{
box-sizing: content-box;
}
<div class="wrapper"></div>
<div class="wrapper"></div>
.wrapper{
width: 100px;
height: 50px;
margin: 10px;
background-color: #dedede;
}
<div class="outer">
<div class="inner"></div>
</div>
.outer{
width: 200px;
height: 100px;
margin: 10px;
background-color: #dedede;
}
.inner{
width: 100px;
height: 50px;
margin: 10px;
background-color: #bcbcbc;
}
margin collapsing
, 有沒有一個統一的整理, 對于大轉轉的FEer, 我們當然想到了大家的前面, 請看下面:
<div class="wrapper z-01"></div>
<div class="wrapper z-02"></div>
.wrapper{
width: 100px;
height: 50px;
background-color: #dedede;
}
.z-01{
margin: -10px;
}
.z-02{
margin: -15px;
}
如果您想訂閱本博客內容,每天自動發到您的郵箱中, 請點這里
Ajax的核心是XMLHttpRequest對象(發送異步請求、接受響應及執行回調),它是ajax實現的關鍵
XMLHttpRequest對象的open()方法與send()方法
方法 | 描述 |
---|---|
open(method,url,async) |
規定請求的類型、URL 以及是否異步處理請求。
|
send(string) |
將請求發送到服務器。
|
請求類型,GET 還是 POST?
與 POST 相比,GET 更簡單也更快,并且在大部分情況下都能用。
然而,在以下情況中,請使用 POST 請求:
(1). GET請求
(2). POST請求
方法 | 描述 |
---|---|
setRequestHeader(header,value) |
向請求添加 HTTP 頭。
|
async參數設置
XMLHttpRequest對象如果要用于AJAX的話,其open()方法的async參數必須設置為true
通過 AJAX,JavaScript 無需等待服務器的響應,而是:
(1). 當使用 async=true 時,請規定在響應處于 onreadystatechange 事件中的就緒狀態時執行的函數:
(2). 當您使用 async=false 時,請不要編寫 onreadystatechange 函數 - 把代碼放到 send() 語句后面即可:
服務器響應
使用 XMLHttpRequest 對象的 responseText 或 responseXML 屬性。
屬性 | 描述 |
---|---|
responseText | 獲得字符串形式的響應數據。 |
responseXML | 獲得 XML 形式的響應數據。 |
(1). 如果來自服務器的響應并非 XML,請使用 responseText 屬性。
responseText 屬性返回字符串形式的響應,因此您可以這樣使用:
document.getElementById("myDiv").innerHTML=xmlhttp.responseText;
(2). 如果來自服務器的響應是 XML,而且需要作為 XML 對象進行解析,請使用 responseXML 屬性
[javascript] view plain copy
- xmlDoc=xmlhttp.responseXML;
- txt="";
- x=xmlDoc.getElementsByTagName("ARTIST");
- for (i=0;i<x.length;i++)
- {
- txt=txt + x[i].childNodes[0].nodeValue + "<br />";
- }
- document.getElementById("myDiv").innerHTML=txt;
當請求被發送到服務器時,我們需要執行一些基于響應的任務。
每當 readyState 改變時,就會觸發 onreadystatechange 事件。readyState 屬性存有 XMLHttpRequest 的狀態信息。
下面是 XMLHttpRequest 對象的三個重要的屬性:
屬性 | 描述 |
---|---|
onreadystatechange | 存儲函數(或函數名),每當 readyState 屬性改變時,就會調用該函數。 |
readyState |
存有 XMLHttpRequest 的狀態。從 0 到 4 發生變化。
|
status |
200: "OK" 404: 未找到頁面 |
Ajax()函數示例:
[javascript] view plain copy
- function Ajax(){
- //code
- }
[javascript] view plain copy
- var xmlHttpReq = null;
[javascript] view plain copy
- if(window.ActiveXObject){
- xmlHttpReq = new ActiveXObject("Microsoft.XMLHTTP");
- }else if(window.XMLHttpRequest){
- xmlHttpReq = new XMLHttpRequest();
- }
IE5、IE6是以ActiveXObject的方式引入XMLHttpRequest對象的,而其他瀏覽器的XMLHttpRequest對象是window的子對象。
[javascript] view plain copy
- xmlHttpReq.open("GET","test.php",true);
[javascript] view plain copy
- xmlHttpReq.onreadystatechange = RequestCallBack;
[javascript] view plain copy
- xmlHttpReq.send(null);
當請求改變時,XMLHttpRequest對象調用onreadystatechange屬性注冊的事件處理器,因此在處理該響應前,事件處理器首先應該檢查readyState的值和HTTP的狀態。當請求完成加載時(readyState==4)并且已經響應成功(status==200)時,就可以調用JavaScript函數來處理該響應內容。
[javascript] view plain copy
- function RequestCallBack(){
- if (xmlHttpReq.readyState == 4) {
- if (xmlHttpReq.status == 200) {
- //將xmlHttpReq.responText的值賦予id為resText的元素
- document.getElementById('resText').innerHTML = xmlHttpReq.responText;
- }
- }
- }
jQuery對Ajax操作進行了封裝,在jQuery中$.ajax()方法屬于最底層的方法,第2層是load()、$.get()、$.post()方法,第3層是$.getScript()、$.getJSON()方法
1、load()方法 通常用來從WEB服務器上獲取靜態的數據文件
最常用的Ajax方法,能載入遠程HTML代碼并插入DOM中
load(url[,data][,callback]);
- url:String 請求HTML頁面的URL地址
- data:Object 發送至服務器的key/value數據
- callback:Function 請求完成時的回調函數,無論請求成功或失敗
[javascript] view plain copy
- $(function(){
- $("#send").click(function(){
- $("#resText").load("test.html");
- })
- })
[javascript] view plain copy
- <button type="button" id="send">ajax加載</button>
- <div class="comment">已有評論:</div>
- <div id="resText">替換內容</div>
test.html代碼為:
[javascript] view plain copy
- <div class="comment">
- <h6>張三:</h6>
- <p class="para">沙發</p>
- </div>
- <div class="comment">
- <h6>李四:</h6>
- <p class="para">板凳</p>
- </div>
- <div class="comment">
- <h6>王五:</h6>
- <p class="para">地板</p>
- </div>
篩選載入的HTML文檔
load()方法的URL參數的語法結構為:“url selector”
[javascript] view plain copy
- $("#resText").load("test.html .para");
load()傳遞方式根據參數data自動指定,沒有參數 --> GET,反之為POST
[javascript] view plain copy
- // 無參數傳遞 GET
- $("#resText").load("test.html",function(){
- //code
- });
- // 有參數傳遞 POST
- $("#resText").load("test.html",{name:"rain",age:"22"},function(){
- //code
- });
回調函數:有三個參數,請求返回的內容、請求狀態、XMLHttpRequest對象
[javascript] view plain copy
- // 回調函數
- $("#resText").load("test.html",function(responseText,textStatus,XMLHttpRequest){
- //responseText 請求返回的內容
- //textStatus 請求狀態:success、error、notmodified、timeout
- //XMLHttpRequest XMLHttpRequest對象
- });
2、$.get()和$.post()方法 jQuery中的全局函數
2.1 $.get() 使用GET方式來進行異步請求
[javascript] view plain copy
- $.get(url[,data][,callback][,type]);
- url:String 請求HTML頁面的URL地址
- data:Object 發送至服務器的key/value數據會作為QueryString附加到請求URL中
- callback:Function 載入成功時回調函數(只有當response的返回狀態是success才調用該函數)自動將請求結果和狀態傳遞給該方法
- type:服務器返回內容的格式,包括html、xml、script、json、text、_default
[javascript] view plain copy
- $("#send").click(function(){
- $.get("get1.php",{
- username:$("#username").val(),
- content:$("#comment").val()
- },function(data,textStatus){
- // data:返回的內容
- // textStatus:請求狀態,success、error、notmodified、timeout
- })
- })
數據格式:服務器返回的數據格式
(1)HTML片段 較少工作量
[javascript] view plain copy
- $.get("get1.php",{
- username:$("#username").val(),
- content:$("#comment").val()
- },function(data,textStatus){
- // data:返回的內容
- // textStatus:請求狀態,success、error、notmodified、timeout
- $("#resText").html(data); //將返回的數據添加到頁面上
- });
(2) XML文檔 需要對返回的數據處理
方便使用
可以通過attr()、find()、filter()方法對數據進行處理
由于期待服務器返回的數據類型為XML文檔,因此需要在服務期端設置Content-Type類型[javascript] view plain copy
- $("#send").click(function(){
- $.get("get1.php", {
- username : $("#username").val() ,
- content : $("#content").val()
- }, function (data, textStatus){
- var username = $(data).find("comment").attr("username");
- var content = $(data).find("comment content").text();
- var txtHtml = "<div class='comment'><h6>"+username
- +":</h6><p class='para'>"+content+"</p></div>";
- $("#resText").html(txtHtml); // 把返回的數據添加到頁面上
- });
- })
[javascript] view plain copy
- header("Content-Type:text/html; charset=utf-8");
(3)JSON文件 需要對返回的數據處理
JSON相對于XML比較簡潔
[javascript] view plain copy
- $("#send").click(function(){
- $.get("get3.php", {
- username : $("#username").val() ,
- content : $("#content").val()
- }, function (data, textStatus){
- var username = data.username;
- var content = data.content;
- var txtHtml = "<div class='comment'><h6>"+username
- +":</h6><p class='para'>"+content+"</p></div>";
- $("#resText").html(txtHtml); // 把返回的數據添加到頁面上
- },"json");
- })
以上三種方法對比:
HTML返回數據最簡單,如果數據需要重用使用JSON(性能與文件大小方面有優勢),當遠程程序未知時使用XML。
2.2 $.post() 通過 HTTP POST 請求從服務器上請求數據
[javascript] view plain copy
- $.post(URL[,data][,callback]);
- url:String 請求的URL地址
- data:Object 發送至服務器的key/value數據
- callback:Function 載入成功時的回調函數
由于POST和GET方式提交的所有數據都可以通過$_REQUEST[]來獲取,因此只需要改變jQuery函數,就可以將程序在GET請求和POST請求之間切換。
![]()
當load()方法帶有參數傳遞時,會使用POST方式發送請求。因此也可以使用load()方法來完成同樣的功能。
![]()
$.post()與$.get()方法的區別:
- GET請求會將參數跟在URL后進行傳遞,而POST請求則是作為HTTP消息的實體內容發送給Web服務器。當然,在Ajax請求中,這種區別對用戶是不可見的。
- GET方式對傳輸的數據有大小限制(通常不能大于2KB),而使用POST方式傳遞的數據量要比GET方式大得多(理論上不受限制)。
- GET方式請求的數據會被瀏覽器緩存起來,因此其他人就可以從瀏覽器的歷史記錄中讀取到這些數據,例如賬號和密碼等。在某種情況下,GET方式會帶來嚴重的安全性問題,而POST方式相對來說就可以避免這些問題。
- GET方式和POST方式傳遞的數據在服務器端的獲取也不相同。在PHP中,GET方式的數據可以用$_GET[]獲取,而POST方式可以用$_POST[]獲取。兩種方式都可以用$_REQUEST[]來獲取。
上面使用load()、$.get()和$.post()方法完成了一些常規的Ajax程序,如果還需要編寫一些復雜的Ajax程序,那么就要用到jQuery中的$.ajax()方法。$.ajax()方法不僅能實現與load()、$.get()和$.post()方法同樣的功能,而且還可以設定beforeSend(提交前回調函數)、error(請求失敗后處理)、success(請求成功后處理)以及complete(請求完成后處理)回調函數,通過這些回調函數,可以給用戶更多的Ajax提示信息。另外,還有一些參數,可以設置Ajax請求的超時時間或者頁面的“最后更改”狀態等。
3、$.getScript()和$.getJSON()方法
3.1 $.getScript()
有時候,在頁面初次加載時就取得所需的全部JavaScript文件是完全沒有必要的。雖然可以在需要哪個JavaScript文件時,動態地創建<script>標簽
上述方法不理想,jQuery又提供了$.getScript()方法[javascript] view plain copy
- $(document.createElement("script").attr("src","test.js")).appenChild("head");
- //或
- $("<script type='text/javscript' src='test.js'></script>").appendChild("head");
有回調函數[javascript] view plain copy
- $(function(){
- $("#btn").click(function(){
- $.getScript("test.js");
- })
- })
[javascript] view plain copy
- $.getScript("test.js",function(){
- $(element).click(function(){
- $(element).animate({backgroundcolor:'pink'},1000)
- .animate({backgroundcolor:'coral'},1000);
- })
- });
3.2 $.getJSON()方法 用于加載JSON文件,用法同$.getScript()方法
[javascript] view plain copy
- $(function(){
- $("#btn").click(function(){
- $.getJSON("test.json");
- })
- })
上面函數雖然加載了JSON代碼,但是并沒有告訴JS對返回的數據如何處理,所以需要回調函數
[javascript] view plain copy
- $(function(){
- $("#btn").click(function(){
- $.getJSON("test.json",function(){
- //data:返回的數據
- });
- })
- })
jQuery遍歷方法 --> $.each()方法 遍歷對象和數組
$.each(data,callback) // 為全局函數 不同于each()方法
- data:數組或對象
- callback:回調函數,有兩個參數(對象的成員或數組的索引,對應變量或內容)
![]()
4、$.ajax()方法 jQuery最底層的Ajax實現
$.ajax(options);
參數名稱 | 類型 | 說明 |
---|---|---|
url | String | (默認為當前頁地址)發送請求的地址 |
type | String |
請求方式(POST/GET)默認GE 注意其他HTTP請求方法,例如PUT和DELETE,僅部分瀏覽器支持 |
timeout | Number |
設置請求超時時間(毫秒) 此設置將覆蓋$.ajaxSetup()方法的全局設置 |
data | Object/String |
發送到服務器的數據。如果已經不是字符串,將自動轉換為字符串格式。 GET請求中將附加在URL后。防止這種自動轉換,可以查看processData選項。 對象必須為key/value格式 例如:{foo1:"bar1",foo2:"bar2"}轉換為&foo1=bar1&foo2=bar2。 如果是數組,jQuery將自動為不同的值對應同一個名稱 例如:{foo:["bar1","bar2"]}轉換為&foo=bar1&foo=bar2 |
dataType | String |
預期服務器返回的數據類型。 如果不指定,jQuery將自動根據HTTP包MIME信息返回responseXML或responseText, 并作為回調函數參數傳遞。 可用類型, xml:返回XML文檔,可用jQuery處理 html:返回純文本HTML信息,包含的script標簽會在插入DOM是執行 script:返回純文本的JavaScript代碼,不會自動緩存結果。除非設置cache參數 注意在遠程請求時(不在同一個域下),所有POST請求都將轉換為GET請求 json:返回json數據 jsonp:jsonp格式,使用jsonp形式調用參數時,myurl?callback=? jQuery:將自動替換后一個“?”為正確的函數名,以執行回調函數 text:返回純文本字符串 |
beforeSend | Function |
發送請求前可以修改XMLHttpRequest對象的函數例如添加自定義HTTP頭。 在beforeSend中如果返回false可以取消本次Ajax請求。XMLHttpRequest對象是唯一的函數 function(XMLHttpRequest){ this;//調用本次Ajax請求時傳遞的options參數 } |
complete | Function |
請求完成后調用的函數(請求成功或失敗時均調用) 參數:XMLHttpRequest對象和一個描述成功請求類型的字符串 function(XMLHttpRequest,textStatus){
this;//調用本次Ajax請求時傳遞的options參數 } |
success | Function |
請求完成后調用的函數(請求成功或失敗時均調用) 參數:(1) 由服務器返回,并根據datatype參數進行設置 (2) 描述狀態的字符串 function(XMLHttpRequest,textStatus){ //data可能是XMLDoc、jsonObj、html、text等
this;//調用本次Ajax請求時傳遞的options參數 } |
error | Function |
請求失敗時被調用的函數 參數:(1) XMLHttpRequest對象 (2) 錯誤信息
(3) 捕獲的錯誤對象(可選) function(XMLHttpRequest,textStatus,errorThrown){ //通常情況下textStatus和errorThrown只有其中一個包含信息
this;//調用本次Ajax請求時傳遞的options參數 } |
global | Boolean |
默認為true。表示是否觸發全局Ajax事件。設置為false將不會觸發全局Ajax事件 AjaxStart或AjaxStop可用于控制各種Ajax事件 |
前面用到的$.load()、$.get()、$.post()、$.getScript()和$.getJSON()這些方法,都是基于$.ajax()方法構建的,$.ajax()方法是jQuery最底層的Ajax實現,因此可以用它來代替前面的所有方法。
[javascript] view plain copy
- $(function(){
- $("#btn").click(function(){
- $.getScript("test.js");
- })
- })
可被替換為
[javascript] view plain copy
- $(function(){
- $("#btn").click(function(){
- $.ajax({
- type:"GET",
- url:"test.js",
- dataType:"script"
- });
- });
- })
[javascript] view plain copy
- $(function(){
- $("#btn").click(function(){
- $.getJSON("test.json",function(data){
- $("#resText").empty();
- var html = " ";
- $.each(data,function(commentIndex,comment){
- html+='<div class="comment"><h6>'+comment['username']
- +'</h6><p class="para">'+comment['content']
- +'</p></div>'
- })
- $("resText").html(html);
- }
- });
- });
- })
可被替換為
[javascript] view plain copy
- $(function(){
- $("#btn").click(function(){
- $.ajax({
- type:"GET",
- url:"test.json",
- dataType:"json",
- success:function(data){
- $("#resText").empty();
- var html = " ";
- $.each(data,function(commentIndex,comment){
- html+='<div class="comment"><h6>'+comment['username']
- +'</h6><p class="para">'+comment['content']
- +'</p></div>'
- })
- $("resText").html(html);
} }); });
- })
1.serialize()方法
異步提交表單,并將服務器返回的數據顯示到當前頁面中
[javascript] view plain copy
- $.get("get1.php",{
- username:$("#username").val(),
- content:$("#comment").val()
- },function(data,textStatus){
- // data:返回的內容
- // textStatus:請求狀態,success、error、notmodified、timeout
- $("#resText").html(data); //將返回的數據添加到頁面上
- });
serialize()方法也是作用于一個jQuery對象,它能夠將DOM元素內容序列化為字符串,用于Ajax請求??蓪⑸鲜龃a簡化為:
[javascript] view plain copy
- $.get("get1.php",$("#form1").serialize(),function(data,textStatus){
- // data:返回的內容
- // textStatus:請求狀態,success、error、notmodified、timeout
- $("#resText").html(data); //將返回的數據添加到頁面上
- });
serialize()方法作用于jQuery對象,所以不光只有表單能使用它,其他選擇器選取的元素也都能使用它,如以下jQuery代碼:
[javascript] view plain copy
- $(":checkbox,:radio").serialize();
把復選框和單選框的值序列化為字符串形式,只會將選中的值序列化。
2.serializeArray()方法
該方法不是返回字符串,而是將DOM元素序列化后,返回JSON格式的數據
![]()
3.$.param()方法
它是serialize()方法的核心,用來對一個數組或對象按照key/value進行序列化。
比如將一個普通的對象序列化:
![]()
四、jQuery中的全局事件
jQuery簡化Ajax操作不僅體現在調用Ajax方法和處理響應方面,而且還體現在對調用Ajax方法的過程中的HTTP請求的控制。通過jQuery提供的一些自定義全局函數,能夠為各種與Ajax相關的事件注冊回調函數。例如當Ajax請求開始時,會觸發ajaxStart()方法的回調函數;當Ajax請求結束時,會觸發ajaxStop()方法的回調函數。這些方法都是全局的方法,因此無論創建它們的代碼位于何處,只要有Ajax請求發生時,就會觸發它們。
有時,當網頁加載過慢時,就需要為網頁添加一個提示信息,常用的提示信息是“加載中…”,代碼如下:
然后通過CSS控制元素隱藏,當Ajax請求開始的時候,將此元素顯示,用來提示用戶Ajax請求正在進行。當Ajax請求結束后,將此元素隱藏。[javascript] view plain copy
- <div class="loading">加載中...</div>
[javascript] view plain copy
- $("$loading").ajaxStart(function(){
- $(this).show();
- }).ajaxStop(function(){
- $(this).hide();
- });
jQuery的Ajax全局事件中還有幾個方法,也可以在使用Ajax方法的過程中為其帶來方便。
方法名稱 說明 ajaxComplete(callback) Ajax請求完成時執行的函數 ajaxError(callback) Ajax請求發生錯誤時執行的函數,捕捉到的錯誤可以作為最后一個參數傳遞 ajaxSend(callback) Ajax請求發送前執行的函數 ajaxSuccess(callback) Ajax請求成功時執行的函數 注意:
1,如果想使某個Ajax請求不受全局方法的影響,那么可以在使用$.ajax(options)方法時,將參數中的global設置為false,jQuery代碼如下
[javascript] view plain copy
- $.ajax({
- url:"test.html",
- global:false
- });
2,在jQuery1.5版本之后,如果Ajax請求不觸發全局方法,那么可以設置:
[javascript] view plain copy
- $.ajaxPrefilter(function(options){
- options.global = true;
- })
藍藍設計( www.syprn.cn )是一家專注而深入的界面設計公司,為期望卓越的國內外企業提供卓越的UI界面設計、BS界面設計 、 cs界面設計 、 ipad界面設計 、 包裝設計 、 圖標定制 、 用戶體驗 、交互設計、 網站建設 、平面設計服務
如果您想訂閱本博客內容,每天自動發到您的郵箱中, 請點這里
效果圖
-----------------------------------------------------------------------更新---------------------------------------------------------
去掉連續顯示多個點,每次只顯示一個點
涉及setInterval傳參的問題。
發現用addMarker(jdata.data[i].gpsx,jdata.data[i].gpsy);時程序可正常運行,但是將該函數 放到setInterval中后卻出現了問題,可通過閉包解決。
<?php echo <<<_END <!doctype html>
<html>
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="initial-scale=1.0, user-scalable=no, width=device-width">
<title>點標記</title>
<link rel="stylesheet" />
<style>
.marker {
color: #ff6600; padding: 4px 10px;
border: 1px solid #fff; white-space: nowrap;
font-size: 12px;
font-family: "";
background-color: #0066ff; } </style>
<script src="http://webapi.amap.com/maps?v=1.3&key=您申請的key值"></script>
<script type="text/javascript" src="http://cache.amap.com/lbs/static/addToolbar.js"></script>
</head>
<body>
<div id="container"></div>
<script> var marker, map = new AMap.Map("container", {
resizeEnable: true, center: [126.60580555556, 45.702363888889], zoom: 13 }); var getJSON = function(url) { return new Promise(function(resolve, reject) { var xhr = new XMLHttpRequest();
xhr.open('get', url, true);
xhr.responseType = 'json';
xhr.onload = function() { var status = xhr.status; if (status == 200) {
resolve(xhr.response);
} else {
reject(status);
}
};
xhr.send();
});
};
getJSON('http://web.cellpies.com/api/driving/getVehicleLocationPoints?vehicleDeviceId=0400000000030603&timeType=4&startTime=2017-03-17%2013:00:00&stopTime=2017-03-17%2014:00:00').then(function(jdata) { //alert('Your Json result is: ' + jdata); //you can comment this, i used it to debug
//alert(jdata.data[0].gpsx);
//alert(jdata.data[0].gpsy); window.i=0; //addMarker(jdata.data[i].gpsx,jdata.data[i].gpsy); setInterval(function () { addMarker(jdata.data[window.i].gpsx,jdata.data[window.i].gpsy); },"1000");
}, function(status) { //error detection.... alert('Something went wrong.');
}); // 實例化點標記 function addMarker(v1,v2) {
window.i+=10;
marker = new AMap.Marker({
icon: "http://webapi.amap.com/theme/v1.3/markers/n/mark_b.png", position: [v1,v2]
});
marker.setMap(map);
} </script>
</body>
</html>
</script>
</body>
</html> _END; ?>
<?php echo<<<_END <!doctype html>
<html>
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="initial-scale=1.0, user-scalable=no, width=device-width">
<title>點標記</title>
<link rel="stylesheet" />
<style>
.marker {
color: #ff6600; padding: 4px 10px;
border: 1px solid #fff; white-space: nowrap;
font-size: 12px;
font-family: "";
background-color: #0066ff; } </style>
<script src="http://webapi.amap.com/maps?v=1.3&key=您申請的key值"></script>
<script type="text/javascript" src="http://cache.amap.com/lbs/static/addToolbar.js"></script>
</head>
<body>
<div id="container"></div>
<script> var marker, map = new AMap.Map("container", {
resizeEnable: true, center: [126.60580555556, 45.702363888889], zoom: 13 }); var getJSON = function(url) { return new Promise(function(resolve, reject) { var xhr = new XMLHttpRequest();
xhr.open('get', url, true);
xhr.responseType = 'json';
xhr.onload = function() { var status = xhr.status; if (status == 200) {
resolve(xhr.response);
} else {
reject(status);
}
};
xhr.send();
});
};
getJSON('http://web.cellpies.com/api/driving/getVehicleLocationPoints?vehicleDeviceId=0400000000030603&timeType=4&startTime=2017-03-17%2013:00:00&stopTime=2017-03-17%2014:00:00').then(function(jdata) {
addMarker(jdata.data[0].gpsx,jdata.data[0].gpsy);
window.i=1; //updateMarker(jdata.data[1].gpsx,jdata.data[1].gpsy); setInterval(function () { updateMarker(jdata.data[window.i].gpsx,jdata.data[window.i].gpsy); },"1000");
}, function(status) { //error detection.... alert('Something went wrong.');
}); // 實例化點標記 function addMarker(v1,v2) {
marker = new AMap.Marker({
icon: "http://webapi.amap.com/theme/v1.3/markers/n/mark_b.png", position: [v1,v2]
});
marker.setMap(map);
} function updateMarker(v1,v2) { //在地圖上更新標記
// 自定義點標記內容 window.i+=10; var markerContent = document.createElement("div"); // 點標記中的圖標 var markerImg = document.createElement("img");
markerImg.className = "markerlnglat";
markerImg.src = "http://webapi.amap.com/theme/v1.3/markers/n/mark_r.png";
markerContent.appendChild(markerImg); // 點標記中的文本 var markerSpan = document.createElement("span");
markerSpan.className = 'marker';
markerSpan.innerHTML = "Hi,我換新裝備啦!";
markerContent.appendChild(markerSpan);
marker.setContent(markerContent); //更新點標記內容 marker.setPosition([v1,v2]); //更新點標記位置 } </script>
</body>
</html>
</script>
</body>
</html> _END; ?>
如果您想訂閱本博客內容,每天自動發到您的郵箱中, 請點這里
javascript部分
document.form.item 問題
集合類對象問題
HTML對象的 id 作為對象名的問題
用 idName 字符串取得對象的問題
變量名與某HTML對象 id 相同的問題
event.x 與 event.y 問題
關于frame
取得元素的屬性
在FF中沒有 parentElement,parement.children 而用 parentNode,parentNode.childNodes
FF中 input.parentNode 的值為form,而IE中 input.parentNode 的值為空節點
const 問題
body 對象
url encoding
nodeName 和 tagName 問題
元素屬性
document.getElementsByName() 和 document.all[name] 的問題
調用子框架或者其它框架中的元素的問題
在FF中則需要改成如下形式來執行,與IE兼容:
對象寬高賦值問題
innerText的問題
event.srcElement和event.toElement問題
CSS部分
div類
居中問題
高度問題
clear:both;
IE浮動 margin 產生的雙倍距離
padding 問題
div嵌套時 y 軸上 padding 和 marign 的問題
padding,marign,height,width 的傻瓜式解決技巧
高盡量用padding,慎用margin,height盡量補上100%,父級height有定值子級height不用100%,子級全為浮動時底部補個空clear:both的div
列表類
ul 標簽在FF中默認是有 padding 值的,而在IE中只有margin有值
ul和ol列表縮進問題
顯示類
最好兩個都寫,并將opacity屬性放在下面
css和js的瀏覽器兼容問題匯總2009-05-31 13:48首先談一下瀏覽器,雖然現在ie依然是瀏覽器市場的老大,大約占有67%的份額,但是由于其各方面的欠缺,用戶開始選擇其他瀏覽器作為自己瀏覽網頁的主要 工具,比如firefox、theworld、maxthon、chrome、opera等等,在用戶使用比較多的瀏覽器中,分為2大派系 - ie內核和非ie內核,像theworld、maxthon、greenbrower等等都屬于ie內核,而firefox、chrome、opera則 為非ie內核,眾多的瀏覽器使我們的web程序就出現了兼容問題,像ie就有ie 6、ie7、ie8之分,同樣的樣式控制和js腳本,在不同的ie版本中也會出現不同的效果,甚至bug,何況在非ie內核的firefox、 chrome、opera了。從市場份額分析,目前ie依然是瀏覽器市場老大,并會在很長一段時間內很難改變,不過我們不能忽略firefox以及其他瀏 覽器的快速成長,未來我們沒有辦法估計,很多初級用戶還沒有看到其他非ie內核的優勢,當他們發現時,我們的在去滿足他們的需求是否已經晚了呢,所以我們 必須做到多瀏覽器的兼容。現在市場上大多web開發著選擇兼容ie7和firefox作為主要兼容對象,這兩款也是目前用戶使用最多的,那好我們就主要講 兼容這兩款瀏覽器。
眾多的瀏覽器使我們就要面臨多種瀏覽器測試的尷尬,比如ie在一臺機器上只能安裝一個版本,我們要測試程序在ie 3個版本中的顯示效果,就要在安裝3個版本的機器上分別測試將是一件非常繁瑣的事情,這里推薦一款工具,ietester可以同時測試3個版本的ie程 序,非常不錯。至于其他瀏覽器在同一臺機器上安裝是沒有問題的,所以我們準備好了測試環境。
Firefox是一款有著豐富插件的瀏覽器,這里我推薦3款web開發人員必備的開發工具 - Firebug、web developer、ie tab。
Firefox瀏覽器良好支持W3C標準,是目前對CSS支持最好的瀏覽器,而ie是出現的比較早,在w3c支持方面做的一直不是很好,所以兩種瀏覽器在很多方面不盡相同。
2.HTML對象獲取問題
3.const問題
4.window.event問題
5.event.x與event.y問題
6.event.srcElement問題
7.window.location.href問題
8.模態和非模態窗口問題
9.frame問題
(1)訪問frame對象:
(2)切換frame內容:
10.body問題
事件委托方法
firefox與IE的父元素(parentElement)的區別
13.cursor:hand VS cursor:pointer
14.innerText在IE中能正常工作,但是innerText在FireFox中卻不行. 需用textContent。
FireFox中設置HTML標簽的style時,所有位置性和字體尺寸的值必須后跟px。這個ie也是支持的。
ie,firefox以及其它瀏覽器對于 table 標簽的操作都各不相同,
padding 問題
消除ul、ol等列表的縮進時
CSS透明
CSS圓角
對select的options集合操作
XMLHTTP的區別
24.css中的width和padding
25.css hack
該樣式顯示的效果是:在FireFox中背景色為green;在IE7中背景色為red;在IE6中背景色為blue。
此外,!important聲明也可以很好地提升指定樣式規則的應用優先權。在IE6和FF中用!important聲明可以提高優先級別,但在 IE6中 的!important聲明會被之后的同名屬性定義替換。所以,通過*和!important聲明兩者的搭配也可以很好地解決IE6,IE7和FF三者之 間的兼容性問題。
區別FF,IE7,IE6:background:red; *background:green !important; *background:blue;
注:IE都能識別;FF不能識別;IE6能識別,但不能識別 !important;IE7能識別,也能識別!important;FF不能識別*,但能識別!important;
針對IE7/firefox 在css的前面加 [xmlns], 如下面的left屬性,如果我想要只針對IE7/firefox起作用,寫法如下:
只針對IE7起作用,在css里前面加*+html,如:
書寫的順序都是FireFox的寫在前面,IE7的寫在中間,IE6的寫在最后面。
26.使用IE專用的條件注釋
27.div 的垂直居中問題: vertical-align:middle; 將行距增加到和整個DIV一樣高 line-height:200px; 然后插入文字,就垂直居中了。缺點是要控制內容不要換行
28.cursor: pointer 可以同時在 IE FF 中顯示游標手指狀, hand 僅 IE 可以
29.FF: 鏈接加邊框和背景色,需設置 display: block, 同時設置 float: left 保證不換行。參照 menubar, 給 a 和 menubar 設置高度是為了避免底邊顯示錯位, 若不設 height, 可以在 menubar 中插入一個空格。
30.在mozilla firefox和IE中的BOX模型解釋不一致導致相差2px解決方法:div{margin:30px!important;margin:28px;}
31.IE5 和IE6的BOX解釋不一致
藍藍設計( www.syprn.cn )是一家專注而深入的界面設計公司,為期望卓越的國內外企業提供卓越的UI界面設計、BS界面設計 、 cs界面設計 、 ipad界面設計 、 包裝設計 、 圖標定制 、 用戶體驗 、交互設計、 網站建設 、平面設計服務
問題:
代碼中存在 document.formName.item(“itemName”) 這樣的語句,不能在FF下運行
解決方法:
改用 document.formName.elements[“elementName”]
問題:
代碼中許多集合類對象取用時使用(),IE能接受,FF不能
解決方法:
改用 [] 作為下標運算,例:
document.getElementsByName("inputName")(1) 改為 document.getElementsByName("inputName")[1]
問題:
使用 window.event 無法在FF上運行
解決方法:
FF的 event 只能在事件發生的現場使用,此問題暫無法解決。可以把 event 傳到函數里變通解決:
onMouseMove = "functionName(event)" function functionName (e) { e = e || window.event;
......
}
問題:
在IE中,HTML對象的 ID 可以作為 document 的下屬對象變量名直接使用,在FF中不能
解決方法:
使用對象變量時全部用標準的 getElementById(“idName”)
問題:
在IE中,利用 eval(“idName”) 可以取得 id 為 idName 的HTML對象,在FF中不能
解決方法:
用 getElementById(“idName”) 代替 eval(“idName”)
問題:
在FF中,因為對象 id 不作為HTML對象的名稱,所以可以使用與HTML對象 id 相同的變量名,IE中不能
解決方法:
在聲明變量時,一律加上 var ,以避免歧義,這樣在IE中亦可正常運行
最好不要取與HTML對象 id 相同的變量名,以減少錯誤
問題:
在IE中,event 對象有x,y屬性,FF中沒有
解決方法:
在FF中,與 event.x 等效的是 event.pageX ,但event.pageX IE中沒有
故采用 event.clientX 代替 event.x ,在IE中也有這個變量
event.clientX 與 event.pageX 有微妙的差別,就是滾動條
要完全一樣,可以這樣:
mX = event.x ? event.x : event.pageX;
然后用 mX 代替 event.x
問題:
在IE中可以用 window.testFrame 取得該frame,FF中不行
解決方法:
window.top.document.getElementById("testFrame").src = 'xx.htm' window.top.frameName.location = 'xx.htm'
在FF中,自己定義的屬性必須 getAttribute() 取得
問題:
childNodes 的下標的含義在IE和FF中不同,FF的 childNodes 中會插入空白文本節點
解決方法:
可以通過 node.getElementsByTagName() 來回避這個問題
問題:
當html中節點缺失時,IE和FF對 parentNode 的解釋不同,例如:
<form> <table> <input/> </table> </form>
問題:
FF中節點自己沒有 removeNode 方法
解決方法:
必須使用如下方法 node.parentNode.removeChild(node)
問題:
在IE中不能使用 const 關鍵字
解決方法:
以 var 代替
FF的 body 在 body 標簽沒有被瀏覽器完全讀入之前就存在,而IE則必須在 body 完全被讀入之后才存在
這會產生在IE下,文檔沒有載入完時,在body上appendChild會出現空白頁面的問題
解決方法:
一切在body上插入節點的動作,全部在onload后進行
問題:
一般FF無法識別js中的&
解決方法:
在js中如果書寫url就直接寫&不要寫&
問題:
在FF中,所有節點均有 nodeName 值,但 textNode 沒有 tagName 值,在IE中,nodeName 的使用有問題
解決方法:
使用 tagName,但應檢測其是否為空
IE下 input.type 屬性為只讀,但是FF下可以修改
問題:
在IE中,getElementsByName()、document.all[name] 均不能用來取得 div 元素
是否還有其它不能取的元素還不知道(這個問題還有爭議,還在研究中)
在IE中,可以用如下方法來取得子元素中的值
document.getElementById("frameName").(document.)elementName
window.frames["frameName"].elementName
window.frames["frameName"].contentWindow.document.elementName window.frames["frameName"].document.elementName
問題:
FireFox中類似 obj.style.height = imgObj.height 的語句無效
解決方法:
統一使用 obj.style.height = imgObj.height + “px”;
問題:
innerText 在IE中能正常工作,但是 innerText 在FireFox中卻不行
解決方法:
在非IE瀏覽器中使用textContent代替innerText
問題:
IE下,even對象有srcElement屬性,但是沒有target屬性;Firefox下,even對象有target屬性,但是沒有srcElement屬性
解決方法:
var source = e.target || e.srcElement; var target = e.relatedTarget || e.toElement;
問題:
FF需要用CSS禁止,IE用JS禁止
解決方法:
IE: obj.onselectstart = function() {return false;}
FF: -moz-user-select:none;
問題:
FF沒有setCapture()、releaseCapture()方法
解決方法:
IE: obj.setCapture(); obj.releaseCapture(); FF: window.captureEvents(Event.MOUSEMOVE|Event.MOUSEUP); window.releaseEvents(Event.MOUSEMOVE|Event.MOUSEUP); if (!window.captureEvents) {
o.setCapture(); }else {
window.captureEvents(Event.MOUSEMOVE|Event.MOUSEUP); }
if (!window.captureEvents) {
o.releaseCapture(); }else {
window.releaseEvents(Event.MOUSEMOVE|Event.MOUSEUP); }
div里的內容,IE默認為居中,而FF默認為左對齊
可以嘗試增加代碼margin:auto
兩上下排列或嵌套的div,上面的div設置高度(height),如果div里的實際內容大于所設高度,在FF中會出現兩個div重疊的現象;但在IE中,下面的div會自動給上面的div讓出空間
所以為避免出現層的重疊,高度一定要控制恰當,或者干脆不寫高度,讓他自動調節,比較好的方法是 height:100%;
但當這個div里面一級的元素都float了的時候,則需要在div塊的最后,閉和前加一個沉底的空div,對應CSS是:
.float_bottom { clear:both; font-size:0px; margin:0; line-height:0px; }
不想受到float浮動的,就在div中寫入clear:both;
#box { float:left; width:100px; margin:0 0 0 100px; //這種情況之下IE會產生200px的距離 display:inline; //使浮動忽略 }
FF設置 padding 后,div會增加 height 和 width,但IE不會 (* 標準的 XHTML1.0 定義 dtd 好像一致了)
高度控制恰當,或嘗試使用 height:100%;
寬度減少使用 padding
但根據實際經驗,一般FF和IE的 padding 不會有太大區別,div 的實際寬 = width + padding ,所以div寫全 width 和 padding,width 用實際想要的寬減去 padding 定義
FF里 y 軸上 子div 到 父div 的距離為 父padding + 子marign
IE里 y 軸上 子div 到 父div 的距離為 父padding 和 子marign 里大的一個
FF里 y 軸上 父padding=0 且 border=0 時,子div 到 父div 的距離為0,子marign 作用到 父div 外面
注意是技巧,不是方法:
寫好標準頭
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml">
寬盡量用margin,慎用padding,width算準實際要的減去padding
先定義 ul {margin:0;padding:0;}
消除ul、ol等列表的縮進時,樣式應寫成: {list-style:none;margin:0px;padding:0px;}
display:block; //可以為內嵌元素模擬為塊元素
display:inline; //實現同一行排列的的效果
display:table; //for FF,模擬table的效果
display:block 塊元素,元素的特點是:
總是在新行上開始;
高度,行高以及頂和底邊距都可控制;
寬度缺省是它的容器的100%,除非設定一個寬度
IE: filter: progid: DXImageTransform.Microsoft.Alpha(style=0,opacity=60); IE: filter: alpha(opacity=10); FF: opacity:0.6; FF: -moz-opacity:0.10;
Firebug 是Firefox下的一款開發類插件,現屬于Firefox的五星級強力推薦插件之一。它集HTML查看和編輯、Javascript控制臺、網絡狀況監 視器于一體,是開發JavaScript、CSS、HTML和 Ajax的得力助手。Firebug如同一把精巧的瑞士軍刀,從各個不同的角度剖析Web頁面內部的細節層面,給Web開發者帶來很大的便利。
Web Developer 插件以工具欄的形式對網頁的(X)HTML、腳本、多媒體、CSS、緩存、圖象等多方面的實用工具。使我們能輕易的獲得網頁的更多信息,使我們進一步的了解當前所瀏覽的網頁。
ie tab是firefox下一款firefox和ie互相切換的插件,這樣開發人員可以很輕松的一鍵查看2中主流瀏覽器的兼容效果。
以上3款工具具體使用方法到Google、baidu中搜索使用關鍵字即可。
debugBar是在ie中類似firebug的工具,不過功能就差很遠了,不過這里也推薦一下。
下面總結一下這兩種瀏覽器的兼容問題:
1.集合類對象問題
說明:IE下,可以使用()或[]獲取集合類對象;
Firefox下,只能使用[]獲取集合類對象.
解決方法:統一使用[]獲取集合類對象.
FireFox:document.getElementById(“idName”);
ie:document.idname或者document.getElementById(“idName”).
解決辦法:統一使用document.getElementById(“idName”);
說明:Firefox下,可以使用const關鍵字或var關鍵字來定義常量;
IE下,只能使用var關鍵字來定義常量.
解決方法:統一使用var關鍵字來定義常量.
說明:window.event只能在IE下運行,而不能在Firefox下運行,這是因為Firefox的event只能在事件發生的現場使用. Firefox必須從源處加入event作參數傳遞。Ie忽略該參數,用window.event來讀取該event。
解決方法:
IE&Firefox:
Submitted(event)”/> …
說明:IE下,even對象有x,y屬性,但是沒有pageX,pageY屬性;
Firefox下,even對象有pageX,pageY屬性,但是沒有x,y屬性.
解決方法:使用mX(mX = event.x ? event.x : event.pageX;)來代替IE下的event.x或者Firefox下的event.pageX.
說明:IE下,event對象有srcElement屬性,但是沒有target屬性;
Firefox下,even對象有target屬性,但是沒有srcElement屬性.
解 決方法:使用obj(obj = event.srcElement ? event.srcElement : event.target;)來代替IE下的event.srcElement或者Firefox下的event.target. 請同時注意event的兼容性問題。
說明:IE或者Firefox2.0.x下,可以使用window.location或window.location.href;
Firefox1.5.x下,只能使用window.location.
解決方法:使用window.location來代替window.location.href.
說明:IE下,可以通過showModalDialog和showModelessDialog打開模態和非模態窗口;Firefox下則不能.
解決方法:直接使用window.open(pageURL,name,parameters)方式打開新窗口。
如果需要將子窗口中的參數傳遞回父窗口,可以在子窗口中使用window.opener來訪問父窗口.
例如:var parWin = window.opener; parWin.document.getElementById(“Aqing”).value = “Aqing”;
以下面的frame為例:
IE:使用window.frameId或者window.frameName來訪問這個frame對象. frameId和frameName可以同名。
Firefox:只能使用window.frameName來訪問這個frame對象.
另外,在IE和Firefox中都可以使用window.document.getElementById(“frameId”)來訪問這個frame對象.
在 IE和Firefox中都可以使用window.document.getElementById(“testFrame”).src = “xxx.html”或window.frameName.location = “xxx.html”來切換frame的內容.
如果需要將frame中的參數傳回父窗口(注意不是opener,而是parent frame),可以在frame中使用parent來訪問父窗口。例如:parent.document.form1.filename.value=”Aqing”;
Firefox的body在body標簽沒有被瀏覽器完全讀入之前就存在;而IE的body則必須在body標簽被瀏覽器完全讀入之后才存在.
IE:document.body.onload = inject; //Function inject()在這之前已被實現
Firefox:document.body.onload = inject();
IE:obj.parentElement
firefox:obj.parentNode
解決方法: 因為firefox與IE都支持DOM,因此使用obj.parentNode是不錯選擇.
firefox不支持hand,但ie支持pointer
解決方法: 統一使用pointer
解決方法:
if(navigator.appName.indexOf(“Explorer”) > -1){
document.getElementById(‘element’).innerText = “my text”;
} else{
document.getElementById(‘element’).textContent = “my text”;
}
在ie中不允許對table和tr的innerHTML賦值,使用js增加一個tr時,使用appendChild方法也不管用。
解決方法:
//向table追加一個空行:
var row = otable.insertRow(-1); var cell = document.createElement("td"); cell.innerHTML = " "; cell.className = "XXXX"; row.appendChild(cell);
padding 5px 4px 3px 1px FireFox無法解釋簡寫,
必須改成 padding-top:5px; padding-right:4px; padding-bottom:3px; padding-left:1px;
樣式應寫成:list-style:none;margin:0px;padding:0px;
其中margin屬性對IE有效,padding屬性對FireFox有效
IE:filter:progid:DXImageTransform.Microsoft.Alpha(style=0,opacity=60)。
FF:opacity:0.6。
IE:不支持圓角。
FF: -moz-border-radius:4px,或者-moz-border-radius-topleft:4px;-moz-border- radius-topright:4px;-moz-border-radius-bottomleft:4px;-moz-border-radius- bottomright:4px;。
IE:border:2px outset;。
FF: -moz-border-top-colors: #d4d0c8 white;-moz-border-left-colors: #d4d0c8 white;-moz-border-right-colors:#404040 #808080;-moz-border-bottom-colors:#404040 #808080;
枚 舉元素除了[]外,SelectName.options.item()也是可以的, 另外SelectName.options.length, SelectName.options.add/remove都可以在兩種瀏覽器上使用。注意在add后賦值元素,否則會失敗。
//mf if (window.XMLHttpRequest) //mf {
xmlhttp=new XMLHttpRequest()
xmlhttp.onreadystatechange=xmlhttpChange
xmlhttp.open("GET",url,true)
xmlhttp.send(null)
} //ie else if (window.ActiveXObject) // code for IE {
xmlhttp=new ActiveXObject("Microsoft.XMLHTTP") if (xmlhttp)
{
xmlhttp.onreadystatechange=xmlhttpChange
xmlhttp.open("GET",url,true)
xmlhttp.send()
}
}
}
在IE7和FF中width寬度不包括padding,在Ie6中包括padding.
根據不同瀏覽器對CSS樣式的支持程度,解析結果和識別CSS的優先級不同,設計師們就可以根據這些不同瀏覽器 的特點來書寫不同的CSS樣式代碼。IE6能識別下劃線和星號*,IE7能識別星號*,不能識別下劃線,而firefox兩個都不能識別,如此,就可 以針對IE6.IE7和FF通過對這些特殊符號的使用寫不同的代碼了。
<style> div{ background:green; /* for FireFox */ *background:red; /* for IE7 */ _background:blue; /* for IE6 */ } </style>
[xmlns] #left {
float:left;
border:4px solid #999;
padding:5px;
width:200px;
height:200px;
}
只針對IE6起作用,可以在css前面加* html,如:
* html #left {
clear:both;
}
*+html #left {
clear:both;
}
<!--其他瀏覽器 --> <link rel="stylesheet" type="text/css" href="css.css" /> <!--[if IE 7]>
<!-- 適合于IE7 --> <link rel="stylesheet" type="text/css" href="ie7.css" /> <![endif]--> <!--[if lte IE 6]>
<!-- 適合于IE6及一下 --> <link rel="stylesheet" type="text/css" href="ie.css" /> <![endif]-->
注意這兩個margin的順序一定不能寫反,據阿捷的說法!important這個屬性IE不能識別,但別的瀏覽器可以識別。所以在IE下其實解釋成這樣:div{maring:30px;margin:28px}
重復定義的話按照最后一個來執行,所以不可以只寫margin:XXpx!important;
IE5下div{width:300px;margin:0 10px 0 10px;}
div 的寬度會被解釋為300px-10px(右填充)-10px(左填充)最終div的寬度為280px,而在IE6和其他瀏覽器上寬度則是以 300px+10px(右填充)+10px(左填充)=320px來計算的。這時我們可以做如下修改 div{width:300px!important;width /**/:340px;margin:0 10px 0 10px}
如果您想訂閱本博客內容,每天自動發到您的郵箱中, 請點這里
如何優化網站的內部結構?網站內部結構優化是網站SEO過程中不可缺少的環節,在網站建設的初期就要做好設置工作。網站內部結構的優化主要包括:網站結構、頁面元素、后期優化等,下面就從這幾個方面為大家講解,希望能給一些不了解的朋友提供實質性的指導作用。
1、結構目錄
目錄的設計是網站建設中很關鍵的環節,是一個網站的骨架,所以網站目錄直接關系到用戶的體驗。建議:目錄的組織結構從首頁到內容頁點擊不超過三次,也就是三級:首頁-欄目頁-內容頁。目錄名可采用網站的一些核心產品詞。
2、鏈接
我們說一個網站的優化最重要的兩點是什么?對,是鏈接和關鍵詞。如果說目錄是一個網站的骨架,那么鏈接就是網站的血液。建議:網站鏈接的設置以英文形式展現,簡短易懂,使用靜態化URL,迎合搜索引擎的喜好,更好的服務于網站優化。
3、robots協議
robots.txt相當于網站的一張臉,一張接客的臉,接的搜索引擎的蜘蛛(或機器人、爬蟲)。它是一種抓取協議文件,用于告訴搜索引擎spider,此網站中的哪些內容是不應被搜索引擎的索引,哪些是可以被索引的。
現在很多地方都有自動生成工具,百度站長工具,或者一些插件等,根據自己的喜好選擇使用。這里有一個小技巧,將網站的地圖鏈接放置在robots內,對網站的收錄絕對是不小的幫助。具體方法:在最后一行增加 Sitemap:http://www.example.com/sitemap.xml。
4、Sitemaps
Sitemaps就是一個管家,總結統計網站的數據鏈接,將匯總的結果更好的展現給網站的客人-搜索引擎spider。
Sitemaps一般有html與XML兩種格式。目前百度、Google、雅虎、微軟等搜索引擎都支持Sitemaps,Sitemaps的提交可以通過各個搜索引擎的站長平臺提交,也可以將其地址放在robots.txt文件里,上面已經說過了。
5、404頁面
404頁面是客戶端在瀏覽網頁時,服務器無法正常提供信息,或是服務器無法回應,且不知道原因所返回的頁面。據說在第三次科技革命之前,互聯網的形態就是一個大型的中央數據庫,這個數據庫就設置在404房間里面。那時候所有的請求都是由人工手動完成的,如果在數據庫中沒有找到請求者所需要的文件,或者由于請求者寫錯了文件編號,用戶就會得到一個返回信息:room 404 : file not found。404錯誤信息通常是在目標頁面被更改或移除,或客戶端輸入頁面地址錯誤后顯示的頁面,人們也就習慣了用404作為服務器未找到文件的錯誤代碼了。當然實際考證傳說中的room 404是不存在的,在http請求3位的返回碼中,4開頭的代表客戶錯誤,5開頭代表服務器端錯誤。
6、nofollow標簽
nofollow標簽是盡量減少垃圾鏈接對搜索引擎的影響,當超鏈接中出現nofollow標簽后,搜索引擎會不考慮這些鏈接的權重,也不用使用這些鏈接用于排名。
nofollow標簽通常有兩種使用方法:一種方法是將"nofollow"寫在網頁上的meta標簽上,例如:。另一種方法是將"nofollow"放在超鏈接中,例如: 。
需要注意的是,如果一個網站鏈向了某些被搜索引擎認為是垃圾網站的地址,那么這個網站的權重也會受到影響。因此對于一個網站來說,nofollow標簽的使用十分必要。
7、統計代碼
網站統計分析工具應該是每一位站長都了解的,現在常用的就是百度統計、cnzz、谷歌分析、51等,具體的就不做介紹了。網站統計代碼添加時,為了不 影響網站的加載速度,最好放在網站底部。
相關拓展:關鍵詞的爬行和抓取
搜索引擎派出一個能夠在網上發現新網頁并抓文件的程序,這個程序通常稱之為蜘蛛。搜索引擎從已知的數據庫出發,就像正常用戶的瀏覽器一樣訪問這些網頁并抓取文件。搜索引擎會跟蹤網頁中的鏈接,訪問更多的網頁,這個過程就叫爬行。這些新的網址會被存入數據庫等待抓取。所以跟蹤網頁鏈接是搜索引擎蜘蛛發現新網址的最基本的方法,所以反向鏈接成為搜索引擎優化的最基本因素之一。沒有反向鏈接,搜索引擎連頁面都發現不了,就更談不上排名了。
搜索引擎抓取的頁面文件與用戶瀏覽器得到的完全一樣,抓取的文件存入數據庫。
藍藍設計( www.syprn.cn )是一家專注而深入的界面設計公司,為期望卓越的國內外企業提供卓越的UI界面設計、BS界面設計 、 cs界面設計 、 ipad界面設計 、 包裝設計 、 圖標定制 、 用戶體驗 、交互設計、 網站建設 、平面設計服務
如果您想訂閱本博客內容,每天自動發到您的郵箱中, 請點這里
編者按:作為今年大熱的設計趨勢,響應式已然是設計師的標配技能。今天阿里的同學從響應式設計的布局類型、布局實現兩方面深入講解,有哪些實現布局的方式,該采用何種方式,都有相當專業細致的解答,不多說,來收 >>>
Heyuchan :在談響應式布局前,我們先梳理下網頁設計中整體頁面排版布局,常見的主要有如下幾種類型:
采用何種方式實現布局設計,也有不同的方式,這里基于頁面的實現單位而言,分為四種類型:固定布局、可切換的固定布局、彈性布局、混合布局。
?固定布局:以像素作為頁面的基本單位,不管設備屏幕及瀏覽器寬度,只設計一套尺寸;
?可切換的固定布局:同樣以像素作為頁面單位,參考主流設備尺寸,設計幾套不同寬度的布局。通過設別的屏幕尺寸或瀏覽器寬度,選擇最合適的那套寬度布局;
?彈性布局:以百分比作為頁面的基本單位,可以適應一定范圍內所有尺寸的設備屏幕及瀏覽器寬度,并能完美利用有效空間展現最佳效果;
?混合布局:同彈性布局類似,可以適應一定范圍內所有尺寸的設備屏幕及瀏覽器寬度,并能完美利用有效空間展現最佳效果;只是混合像素、和百分比兩種單位作為頁面單位。
可切換的固定布局、彈性布局、混合布局都是目前可被采用的響應式布局方式。
其中可切換的固定布局的實現成本,但拓展性比較差;而彈性布局與混合布局效果具響應性,都是比較理想的響應式布局實現方式。
只是對于不同類型的頁面排版布局實現響應式設計,需要采用不用的實現方式。通欄、等分結構的適合采用彈性布局方式、而對于非等分的多欄結構往往需要采用混合布局的實現方式。
布局響應 對頁面進行響應式的設計實現,需要對相同內容進行不同寬度的布局設計,有兩種方式:
桌面優先(從桌面端開始向下設計);
移動優先(從移動端向上設計);
無論基于那種模式的設計,要兼容所有設備,布局響應時不可避免地需要對模塊布局做一些變化(發生布局改變的臨界點稱之為斷點), 我們通過JS獲取設備的屏幕寬度,來改變網頁的布局,這一過程我們可以稱之為布局響應屏幕。
常見的主要有如下幾種方式:
布局不變,即頁面中整體模塊布局不發生變化,主要有:
?模塊中內容:擠壓-拉伸;
?模塊中內容:換行-平鋪;
?模塊中內容:刪減-增加;
布局改變,即頁面中的整體模塊布局發生變化,主要有:
?模塊位置變換;
?模塊展示方式改變:隱藏-展開;
?模塊數量改變:刪減-增加;
很多時候,單一方式的布局響應無法滿足理想效果,需要結合多種組合方式,但原則上盡可能時保持簡單輕巧,而且同一斷點內(發生布局改變的臨界點稱之為斷點)保持統一邏輯。
否則頁面實現得太過復雜,也會影響整體體驗和頁面性能。
promise的概念和實現最初來源于社區,用于解決異步編程的回調嵌套問題,即將多級的嵌套改良成順序的代碼行。ES6將其寫入了語言標準,統一了用法,提供了原生的Promise。
Promise是一個構造函數,用于生成一個Promise實例。Promise實例代表一次異步操作。 它只可能有3種轉態,分別是Pending(未決議), Resolved(完成) 和 Rejected(出錯) 。
創建一個Promise實例時,其處于Pending狀態,當異步操作完成,執行回調函數的時候,根據回調函數中的err
的值,如果err
為空則異步操作成功,否則異步操作失敗。此后,Promise實例的狀態將不再改變。
var pro = function () { return new Promise(function(resolve, reject) { fs.readdir(_dirname, function(err, data) { if (err) {
reject(err); //失敗則將Promise對象置為rejected狀態 } else {
resolve(data); //成功則將Promise對象置為resolved轉態 }
});
});
} /*pro是一個函數
調用該函數返回一個Promise實例
*/ var promiseObject = pro(); /*then方法執行Resolved和Rejected狀態的回調函數*/ promiseObject
.then(doneCallbacks, failCallbacks)
.catch(function(err) { console.log(err);
}); var doneCallbacks = function(data) { console.log(data);
}; var failCallbacks = function(err) { console.log(err)
};
catch是then的一個語法糖,相當于
promiseObject.then(undefined, function(err) {
console.log(err)
});
Promise對象的錯誤具有向后傳遞的性質,因此,如果在調用過程拋出異常,則異常總能被最后一個catch捕獲。這也是為什么我們習慣在then的調用后跟隨一個catch調用。
then 方法是定義在構造函數Promise 的原型對象上的。這個方法為Promise實例添加狀態改變時的回調函數。then方法返回一個新的Promise實例,因此then方法后面可以調用then()方法。傳給then()方法的函數,可返回三類值,分別如下:
如果返回的是一個新的Promise對象,則下一級的then接收函數在這個Promise實例 狀態發生改變時被觸發執行。因此,then的鏈式寫法,可以按順序執行一系列的異步操作,并且后一個異步操作在前一個完成之后開始。如下代碼實例所示:
var fs = require('fs'); var pro = function () { return new Promise(function(resolve, reject) { fs.readdir(_dirname, function(err, data) { if (err) {
reject(err); //失敗則將Promise對象置為rejected狀態 } else {
resolve(data); //成功則將Promise對象置為resolved轉態 }
});
});
} var newPro = function(data) { return new Promise(function(resolve, reject) { setTimeout(function(){ resolve(data);
},2000);
});
}; /*pro是一個函數
調用該函數返回一個Promise實例
*/ var promiseObject = pro(); /*then方法執行Resolved和Rejected狀態的回調函數*/ promiseObject
.then(function(data){ console.log("fisrt sync op");
console.log(data); return newPro(data);//返回一個新的Promise對象 })
.then(function(data) { console.log("second sync op");
console.log(data);//兩秒鐘后才會被執行 })
.catch(function(err) { console.log(err);
});
promiseObject.then(undefined, function(err) { console.log(err)
}); var doneCallbacks = function(data) { console.log(data);
}; var failCallbacks = function(err) { console.log(err)
};
把上一級異步調用的結果返回給下一級調用,then這樣的鏈式寫法,解決了回調函數的多層嵌套調用。
多層嵌套
如果您想訂閱本博客內容,每天自動發到您的郵箱中, 請點這里
隨著越來越的的app使用沉浸式狀態欄,有必要對沉浸式狀態欄學習一下,查看了很多資料,沉浸式狀態欄重要的無法三點:1.實現全屏 (Android4.4跟5.0全屏處理方式有別需分開處理 )2.設置全屏之后為了保證自己寫的布局不與狀態欄重疊,需要在跟xml的跟布局設置android:fitsSystemWindows=”true” ?;谶@幾點處理方式可能很多,但是為了便于項目中工具類封裝,本編實現方式均已代碼方式呈現,xml設置方式可以自行查閱相關資料 3.改變狀態欄顏色
—1.全屏設置
對于4.4以上系統,因4.4以上系統是可以設置全屏,代碼如下:
window.addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS); window.addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION);
對于5.0系統 具體代碼
window.clearFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS|WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION); window.getDecorView().setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN|View.SYSTEM_UI_FLAG_LAYOUT_STABLE|View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION); window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
僅僅做全屏處理,我們會發現不管是在4.4系統上還是在5.0系統上,我們的布局內容會與狀態欄內容出現重疊。
下圖為4.4系統
下圖為8.0系統
為了解決全屏設置重疊狀態欄,我們需要在全屏之上預留狀態欄的高度以便正常顯示狀態欄,而處理方式也很簡單 activity layout根目錄添加下面代碼
android:fitsSystemWindows=”true” 而此處我建議用代碼設置,因為通常我們項目中會提取BaseActivity基類抽出一些共性,這種方式比在每個xml中設置屬性更方便
rootView.setFitsSystemWindows(true) 此處的rootView指的就是activity對應的跟布局;
進行以上處理之后我們會發現現在狀態欄跟我們的布局內容不再重疊了,接下來我們就只需要處理狀態欄的顏色問題了。具體代碼如下
ViewGroup content= (ViewGroup) findViewById(android.R.id.content); ViewGroup childView= (ViewGroup) content.getChildAt(0); if(childView!=null){
childView.setFitsSystemWindows(true); }
對于4.4系統因為沒有改變狀態欄顏色的api,我們可以通過添加一個與狀態欄等高的View到根布局的父容器中,而根布局的父容器就是一個ID為android.R.id.content的幀布局被裝飾的容器中,這樣只需要設置View的顏色即可。對于5.0及以上系統,因已提供設置狀態欄和導航欄顏色的api,直接設置即可;
對于4.4以上5.0一下系統
View view=new View(this); view.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,getStatusHeight())); view.setBackgroundColor(Color.RED); content.addView(view);
對于5.0及以上系統
window.setStatusBarColor(Color.RED);
獲取狀態欄高度
private int getStatusHeight() { int statusHeight=-1; int resourceId=getResources().getIdentifier("status_bar_height","dimen","android"); if(resourceId>0){ return getResources().getDimensionPixelSize(resourceId);
} return 0;
}
以上就是實現沉浸式狀態欄的具體過程。整體代碼如下:
package com.example.administrator.myjavadeamo.activity; import android.graphics.Color; import android.os.Build; import android.support.v7.app.AppCompatActivity; import android.os.Bundle; import android.view.View; import android.view.ViewGroup; import android.view.Window; import android.view.WindowManager; import com.example.administrator.myjavadeamo.R; public class StatusBarActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState); supportRequestWindowFeature(Window.FEATURE_NO_TITLE);//隱藏標題欄 setContentView(R.layout.activity_status_bar); initWindow(); }
private void initWindow() {
Window window=getWindow(); if(Build.VERSION.SDK_INT>=Build.VERSION_CODES.LOLLIPOP){
//5.0以上的手機
window.clearFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS|WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION); window.getDecorView().setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN|View.SYSTEM_UI_FLAG_LAYOUT_STABLE|View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION); window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS); ViewGroup content= (ViewGroup) findViewById(android.R.id.content); ViewGroup childView= (ViewGroup) content.getChildAt(0); if(childView!=null){
childView.setFitsSystemWindows(true); }
window.setStatusBarColor(Color.GREEN); }else if(Build.VERSION.SDK_INT>=Build.VERSION_CODES.KITKAT){
//4.4以上5.0一下的手機
window.addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS); window.addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION); ViewGroup content= (ViewGroup) findViewById(android.R.id.content); ViewGroup childView= (ViewGroup) content.getChildAt(0); if(childView!=null){
childView.setFitsSystemWindows(true); }
View view=new View(this); view.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,getStatusHeight())); view.setBackgroundColor(Color.GREEN); content.addView(view); }
} /**
* 獲取狀態欄高度
* @return
*/ private int getStatusHeight() {
int statusHeight=-1; int resourceId=getResources().getIdentifier("status_bar_height","dimen","android"); if(resourceId>0){
return getResources().getDimensionPixelSize(resourceId); }
return 0; }
}
最終實現結果:
4.4系統
8.0系統
藍藍設計( www.syprn.cn )是一家專注而深入的界面設計公司,為期望卓越的國內外企業提供卓越的UI界面設計、BS界面設計 、 cs界面設計 、 ipad界面設計 、 包裝設計 、 圖標定制 、 用戶體驗 、交互設計、 網站建設 、平面設計服務
JavaScript 創建動態頁面。事件是可以被 JavaScript 偵測到的行為。 網頁中的每個元素都可以產生某些可以觸發 JavaScript 函數或程序的事件。比如說,當用戶單擊按鈕或者提交表單數據時,就發生一個鼠標單擊(onclick)事件,需要瀏覽器做出處理,返回給用戶一個結果。主要事件表總結如下:
如果您想訂閱本博客內容,每天自動發到您的郵箱中, 請點這里
藍藍設計( www.syprn.cn )是一家專注而深入的界面設計公司,為期望卓越的國內外企業提供卓越的UI界面設計、BS界面設計 、 cs界面設計 、 ipad界面設計 、 包裝設計 、 圖標定制 、 用戶體驗 、交互設計、 網站建設 、平面設計服務
藍藍設計的小編 http://www.syprn.cn