<div id="uploader">
<div class="queueList">
<div id="dndArea" class="placeholder">
<div id="filePicker"></div>
<p>或將照片拖到這里,單次最多可選30張</p>
</div>
</div>
<div class="statusBar" style="display:none;">
<div class="progress">
<span class="text">0%</span>
<span class="percentage"></span>
</div><div class="info"></div>
<div class="btns">
<div id="filePicker2"></div><div class="uploadBtn">開始上傳</div>
</div>
</div>
</div>
<script>
require(['jquery', 'webuploader' ], function($, WebUploader) {
return;
// 當domReady的時候開始初始化
$(function() {
var $wrap = $('#uploader'),
// 圖片容器
$queue = $( '<ul class="filelist"></ul>' )
.appendTo( $wrap.find( '.queueList' ) ),
// 狀態欄,包括進度和控制按鈕
$statusBar = $wrap.find( '.statusBar' ),
// 文件總體選擇信息。
$info = $statusBar.find( '.info' ),
// 上傳按鈕
$upload = $wrap.find( '.uploadBtn' ),
// 沒選擇文件之前的內容。
$placeHolder = $wrap.find( '.placeholder' ),
$progress = $statusBar.find( '.progress' ).hide(),
// 添加的文件數量
fileCount = 0,
// 添加的文件總大小
fileSize = 0,
// 優化retina, 在retina下這個值是2
ratio = window.devicePixelRatio || 1,
// 縮略圖大小
thumbnailWidth = 110 * ratio,
thumbnailHeight = 110 * ratio,
// 可能有pedding, ready, uploading, confirm, done.
state = 'pedding',
// 所有文件的進度信息,key為file id
percentages = {},
supportTransition = (function(){
var s = document.createElement('p').style,
r = 'transition' in s ||
'WebkitTransition' in s ||
'MozTransition' in s ||
'msTransition' in s ||
'OTransition' in s;
s = null;
return r;
})(),
// WebUploader實例
uploader;
// 實例化
uploader = WebUploader.create({
pick: {
id: '#filePicker',
label: '點擊選擇圖片'
},
dnd: '#dndArea',
paste: '#uploader',
// swf文件路徑
swf: '{$_W['siteroot']}app/resource/componets/webuploader/Uploader.swf',
// 文件接收服務端。
server: '{$_W['siteroot']}app/{php echo str_replace('./','',url('utility/file',array('do'=>'upload', 'type'=>'image'), true))}',
chunked: true,
// runtimeOrder: 'flash',
// sendAsBinary: true,
fileNumLimit: 30,
fileSizeLimit: 30 * 1024 * 1024, // 30 M
fileSingleSizeLimit: 4 * 1024 * 1024 // 1 M
});
// 添加「添加文件」的按鈕,
uploader.addButton({
id: '#filePicker2',
label: '繼續添加'
});
// 當有文件添加進來時執行,負責view的創建
function addFile( file ) {
var $li = $( '<li id="' + file.id + '">' +
'<p class="title">' + file.name + '</p>' +
'<p class="imgWrap"></p>'+
'<p class="progress"><span></span></p>' +
'</li>' ),
$btns = $('<div class="file-panel">' +
'<span class="cancel">刪除</span>' +
'<span class="rotateRight">向右旋轉</span>' +
'<span class="rotateLeft">向左旋轉</span></div>').appendTo( $li ),
$prgress = $li.find('p.progress span'),
$wrap = $li.find( 'p.imgWrap' ),
$info = $('<p class="error"></p>'),
showError = function( code ) {
switch( code ) {
case 'exceed_size':
text = '文件大小超出';
break;
case 'interrupt':
text = '上傳暫停';
break;
default:
text = '上傳失敗,請重試';
break;
}
$info.text( text ).appendTo( $li );
};
if ( file.getStatus() === 'invalid' ) {
showError( file.statusText );
} else {
// @todo lazyload
$wrap.text( '預覽中' );
uploader.makeThumb( file, function( error, src ) {
if ( error ) {
$wrap.text( '不能預覽' );
return;
}
var img = $('<img src="'+src+'">');
$wrap.empty().append( img );
}, thumbnailWidth, thumbnailHeight );
percentages[ file.id ] = [ file.size, 0 ];
file.rotation = 0;
}
file.on('statuschange', function( cur, prev ) {
if ( prev === 'progress' ) {
$prgress.hide().width(0);
} else if ( prev === 'queued' ) {
$li.off( 'mouseenter mouseleave' );
$btns.remove();
}
// 成功
if ( cur === 'error' || cur === 'invalid' ) {
console.log( file.statusText );
showError( file.statusText );
percentages[ file.id ][ 1 ] = 1;
} else if ( cur === 'interrupt' ) {
showError( 'interrupt' );
} else if ( cur === 'queued' ) {
percentages[ file.id ][ 1 ] = 0;
} else if ( cur === 'progress' ) {
$info.remove();
$prgress.css('display', 'block');
} else if ( cur === 'complete' ) {
$li.append( '<span class="success"></span>' );
}
$li.removeClass( 'state-' + prev ).addClass( 'state-' + cur );
});
$li.on( 'mouseenter', function() {
$btns.stop().animate({height: 30});
});
$li.on( 'mouseleave', function() {
$btns.stop().animate({height: 0});
});
$btns.on( 'click', 'span', function() {
var index = $(this).index(),
deg;
switch ( index ) {
case 0:
uploader.removeFile( file );
return;
case 1:
file.rotation += 90;
break;
case 2:
file.rotation -= 90;
break;
}
if ( supportTransition ) {
deg = 'rotate(' + file.rotation + 'deg)';
$wrap.css({
'-webkit-transform': deg,
'-mos-transform': deg,
'-o-transform': deg,
'transform': deg
});
} else {
$wrap.css( 'filter', 'progid:DXImageTransform.Microsoft.BasicImage(rotation='+ (~~((file.rotation/90)%4 + 4)%4) +')');
}
});
$li.appendTo( $queue );
}
// 負責view的銷毀
function removeFile( file ) {
var $li = $('#'+file.id);
delete percentages[ file.id ];
updateTotalProgress();
$li.off().find('.file-panel').off().end().remove();
}
function updateTotalProgress() {
var loaded = 0,
total = 0,
spans = $progress.children(),
percent;
$.each( percentages, function( k, v ) {
total += v[ 0 ];
loaded += v[ 0 ] * v[ 1 ];
} );
percent = total ? loaded / total : 0;
spans.eq( 0 ).text( Math.round( percent * 100 ) + '%' );
spans.eq( 1 ).css( 'width', Math.round( percent * 100 ) + '%' );
updateStatus();
}
function updateStatus() {
var text = '', stats;
if ( state === 'ready' ) {
text = '選中' + fileCount + '張圖片,共' + WebUploader.formatSize( fileSize ) + '。';
} else if ( state === 'confirm' ) {
stats = uploader.getStats();
if ( stats.uploadFailNum ) {
text = '已成功上傳' + stats.successNum+ '張照片至XX相冊,'+
stats.uploadFailNum + '張照片上傳失敗,<a class="retry" href="#">重新上傳</a>失敗圖片或<a class="ignore" href="#">忽略</a>'
}
} else {
stats = uploader.getStats();
text = '共' + fileCount + '張(' +
WebUploader.formatSize( fileSize ) +
'),已上傳' + stats.successNum + '張';
if ( stats.uploadFailNum ) {
text += ',失敗' + stats.uploadFailNum + '張';
}
}
$info.html( text );
}
function setState( val ) {
var file, stats;
if ( val === state ) {
return;
}
$upload.removeClass( 'state-' + state );
$upload.addClass( 'state-' + val );
state = val;
switch ( state ) {
case 'pedding':
$placeHolder.removeClass( 'element-invisible' );
$queue.hide();
$statusBar.addClass( 'element-invisible' );
uploader.refresh();
break;
case 'ready':
$placeHolder.addClass( 'element-invisible' );
$( '#filePicker2' ).removeClass( 'element-invisible');
$queue.show();
$statusBar.removeClass('element-invisible');
uploader.refresh();
break;
case 'uploading':
$( '#filePicker2' ).addClass( 'element-invisible' );
$progress.show();
$upload.text( '暫停上傳' );
break;
case 'paused':
$progress.show();
$upload.text( '繼續上傳' );
break;
case 'confirm':
$progress.hide();
$upload.text( '開始上傳' ).addClass( 'disabled' );
stats = uploader.getStats();
if ( stats.successNum && !stats.uploadFailNum ) {
setState( 'finish' );
return;
}
break;
case 'finish':
stats = uploader.getStats();
if ( stats.successNum ) {
alert( '上傳成功' );
} else {
// 沒有成功的圖片,重設
state = 'done';
location.reload();
}
break;
}
updateStatus();
}
uploader.onUploadProgress = function( file, percentage ) {
var $li = $('#'+file.id),
$percent = $li.find('.progress span');
$percent.css( 'width', percentage * 100 + '%' );
percentages[ file.id ][ 1 ] = percentage;
updateTotalProgress();
};
uploader.onFileQueued = function( file ) {
fileCount++;
fileSize += file.size;
if ( fileCount === 1 ) {
$placeHolder.addClass( 'element-invisible' );
$statusBar.show();
}
addFile( file );
setState( 'ready' );
updateTotalProgress();
};
uploader.onFileDequeued = function( file ) {
fileCount--;
fileSize -= file.size;
if ( !fileCount ) {
setState( 'pedding' );
}
removeFile( file );
updateTotalProgress();
};
uploader.on( 'all', function( type ) {
var stats;
switch( type ) {
case 'uploadFinished':
setState( 'confirm' );
break;
case 'startUpload':
setState( 'uploading' );
break;
case 'stopUpload':
setState( 'paused' );
break;
}
});
uploader.onError = function( code ) {
alert( 'Eroor: ' + code );
};
$upload.on('click', function() {
if ( $(this).hasClass( 'disabled' ) ) {
return false;
}
if ( state === 'ready' ) {
uploader.upload();
} else if ( state === 'paused' ) {
uploader.upload();
} else if ( state === 'uploading' ) {
uploader.stop();
}
});
$info.on( 'click', '.retry', function() {
uploader.retry();
} );
$info.on( 'click', '.ignore', function() {
alert( 'todo' );
} );
$upload.addClass( 'state-' + state );
updateTotalProgress();
});
});
</script>
『貳』 理解iOS中深淺拷貝-為什麼NSString使用
一直以為對深淺拷貝理解很透徹,最近面試中被問到這樣一個問題,
這個概念相比很好理解,直接看圖吧。
淺拷貝 :指針拷貝,復制一個新的指針,只想同一塊內存區域。實際內存並沒有發生拷貝
深拷貝 :內容拷貝,拷貝數據到一塊新內存區域,指針指向拷貝的數據區
strong: 淺拷貝,也就是指針引用,很明顯的。我們來測試一下
運行結果如下,實際對象是一致的。
這意味著A使用屬性對可變字元串做出了appendstring這樣的操作,B中的值也會發生修改。
:這里我們研究系統的NSstring,NSArray對象之後是怎麼樣的
先看一個有意思的現象,我們新建一個NSMutableString,然後,接著用這個對象調用MutableString特有的appendstring修改字元串
結果呢?
閃退了!這是為什麼?
細看一下,我們的MutableString對象調用了之後,拷貝出來的字元串內存地址發生了變化,也就是說這里是發生了深拷貝。
接著我們使用String調用appendString方法發生了很常規的閃退,日誌顯示我們拷貝出來的是NSTaggedPointerString,這是個不可變字元串。
也就是說可變字元串在之後會發生深拷貝,拷貝出來的是一個不可變字元串!
接下來我們測試下如果一個NSString對象是怎樣的
結果是這里是淺拷貝,地址沒有發生變化。
我們從這得出了結論:
並不一定是淺拷貝,出來的一定是不可變字元串或者數組,如果被拷貝的對象是可變數組或者字元串,這時候會發生深拷貝,反之則是淺拷貝。
MutableCopy
這里就不貼驗證了,直接上結果,對於字元串和數組MutableCopy一定是深拷貝,而且拷貝出來對象一定是可變字元串或者數組。即使被拷貝對象是不可變字元串。
1. 出來的字元串一定是不可變字元串,如果傳入的是可變字元串,會發生深拷貝為不可變字元串,否則為淺拷貝。
2. mutable,一定是深拷貝,拷貝出來的一定是可變字元串或者數組,即使傳入的是不可變字元串或者數組。
『叄』 switch無法備份什麼意思
可能是存檔太大,然後你網路和任天堂的伺服器不搭導致鏈接不穩定經常掉包導致失敗。比如arms的存檔文件好像是128MB,我大概備份了三次才成功,存檔小的比如死亡細胞才5.3MB每次都能成功。一般來說你可以開個加速器,或者換dns,或者就不要管他,等他自己多試個幾次說不定就成功了。經過4.0固件升級之後,任天堂Switch加入了更多的系統功能,正在趕上對手索尼和微軟,不過到現在為止仍然沒有Switch游戲存檔備份功能,這讓部分玩家很傷心,畢竟自己努力數百小時的進度如果丟失那感覺簡直如世界末日。對此,最近美國任天堂總裁雷吉接受了相關采訪。雷吉在采訪當中談到了自己對於游戲存檔重要性的理解,因為他也已經在Switch《塞爾達傳說:曠野之息》當中投入了大量時間,目前已經收集到了400個呀哈哈!他談到任天堂目前已經注意到了這個問題(存檔不能備份)。並表明任天堂是一家重視用戶的公司,希望用戶能夠開心快樂。接下來這一問題將是任天堂開始解決的方向。也有玩家可能會說,做一個雲備份存檔就這么難嗎?要知道,任天堂給出統一的賬戶系統還是經過了Wii、WiiU和Switch三個世代才做到,所以,還是耐心等待並祈禱自己的Switch游戲存檔吧。『肆』 switch破解版拷完游戲直接退出嗎
是的。1、在switch雙點游戲界面,點擊有手柄的「+」。
2、會出現游戲保存畫面,選擇保存選項,點擊按鍵A進行保存。出現保存完成畫面後,點擊右手柄的主頁鍵。直接退出遊戲即可。
『伍』 WebStorm啟動項目後報錯Switch language version to React JSX
webstorm啟動一個項目時,提示「Switch language version to React JSX」
解決方法:file——setting——language & frameworks——JavaScript改為ReactJSX即可
『陸』 適合初學者學習Web前端技術的學習路線匯總
今天小編要跟大家分享的文章是關於適合初學者學習Web前端技術的學習路線匯總。在當下來說Web前端開發工程師可謂是高福利、高薪水的職業了。所以現在學習Web前端開發的技術人員也是日益增多了,但是在學習Web前端開發中盲目的去學習而沒有一個完整的思路和學習路線也是不行的。
那麼想學好Web前端,該從哪裡入手學習呢?零基礎學習Web前端學習路線圖從哪裡可以找到呢?在此為大家整理完整的適合零基礎學員的Web前端學習路線分享給大家,來和小編一起看一看吧!
1.HTML5介紹
內容包括:(互聯網發展趨勢、H5語言的優勢、簡單易學人人都能編程、H5就業和薪資情況、H5常見的項目與產品、H5的未來與方向)
2.HTML基礎
內容包括:(HTML簡介與歷史版本、常用開發軟體、常見標簽與屬性、表格與表單、標簽規范與標簽語義化、實戰:網頁結構布局)
3.CSS基礎
內容包括:(css簡介與基本語法、常見的各種樣式屬性、CSS選擇器與標簽類型、理解盒子模型與CSS重置、浮動與定位、利用photoshop工具測量樣式、HTML+CSS開發網頁、實戰:高仿電商首頁效果)
4.CSS3基礎
內容包括:(css3常見樣式、css3選擇器、變形與動畫、3D效果與關鍵幀、彈性盒模型)
5.移動端布局
移動端基本概念、viewport窗口設置、移動端布局方案、rem、vh、vw等單位、響應式布局、bootstrap框架
6.JavaScript基礎
內容包括:(JS簡介、JS變數、數據類型與類型轉換、運算符與優先順序、流程式控制制-if..else流程式控制制-switch...case、流程式控制制-while、do..while、for循環、break、continue語法、函數定義與調用、全局變數與局部變數、函數傳參與返回值、函數作用域與變數作用域。
而且還有DOM的基本操作、定時器使用、this指向與修改指向、數組、字元串等方法操作、時間對象與正則對象、掌握常見BOM操作、常見事件與事件細節、JSON與AJAX、JSONP跨域操作、前端cookie的使用、實戰:JS配合HTML與CSS完成電商項目)
7.jquery框架
內容包括:(jquery框架介紹及優勢介紹、jquery核心思想、jquery常見方法、jquery動畫操作、jqueryAJAX操作、jquery工具方法、利用jquery快速開發網頁)
8.PHP基礎
內容包括:(PHP簡介與基本語法、mysql資料庫及sql語法、apache伺服器與集成開發工具、PHP鏈接資料庫、PHP與AJAX交互、實戰:留言板、登錄、注冊等)
9.H5基礎項目
內容包括:(項目簡介、項目功能演示、項目劃分及框架、編寫HTML頁面結構、設置CSS樣式、添加JS交互、可選框架:bootstrap、jquery、PHP等、項目調試及兼容、項目驗收)
如何成為合格的Web前端開發工程師(Web前端職業規劃+各階段薪資待遇)
原來是需要熟練的掌握HTML、CSS、JS、JQ等最基本的技術。
現在,只掌握這些已經遠遠不夠了。無論是開發難度上,還是開發方式上,Web前端開發不比從前,現在的功能非常強大。
而前端開發為什麼現在這么火,在於互聯網高速發展,和HTML5技術的不斷成熟,各大瀏覽器的不斷兼容,讓Web前端開發成為最熱的職業。
WEB前端初級開發工程師需要掌握的具體知識點包含:
HTML5基礎、CSS基礎、jquery框架、PHP基礎
此階段可達成學習效果:
可勝任Web前端開發工程師前端頁面布局與重構工程師。
薪資可以達到:4K-6K。
WEB前端中高級開發工程師所需要掌握的知識點包含:
面向對象、javascript、Nodejs、微信端開發
此階段可達成效果:
可勝任Web前端工程師、高級Web前端工程師、網站開發工程師、移動前端開發工程師等職位。
薪資可達到:6K-10K。
WEB前端大神級開發工程師需要掌握的知識點包含:
VueJS框架、ReactJS框架、AngularJS框架、HybridApp開發、前端架構
此階段可達成效果:
可勝任高級Web前端工程師、全棧工程師、移動前端App開發工程師、微信開發工程師、小程序開發工程師、數據可視化開發工程師等職位。
薪資可達到:10K-15K+。
以上就是小編今天為大家分享的關於適合初學者學習Web前端技術的學習路線匯總的文章,希望本篇文章能夠對正想要學習Web前端知識的小夥伴們有所幫助,想要了解更多Web前端相關知識記得關注北大青鳥Web培訓官網。最後祝願小夥伴們工作順利,成為一名優秀的Web前端工程師。
『柒』 web自動化測試之web自動化中操作要點
1、切換iframe:
driver.switch_to.frame(' xxx')
2、瀏覽器向右移動頁面(瀏覽器中執行JavaScript代碼)
driver.execute_script('window.scrollBy(200,0)') # window.scrollBy(x,y)
3、driver.implicitly_wait()和time.sleep()的區別
driver.implicitly_wait(10) #設置尋找元素最大等待時間;
implicitly_wait(5)屬於隱式等待,5秒鍾內只要找到了元素就開始執行,5秒鍾後未找到,就超時;
time.sleep(5)表示必須等待5秒定位。
4、切換到新的目標窗口
#切換webdriver到新的目標窗口
for handle in driver.window_handles:
driver.switch_to.window(handle)
#判斷是否進行了目標窗口
title=driver.title
if 'xxxxx' in title:
break
5、當頁面廣告遮擋了元素,可將頁面廣告元素刪除
element=driver.find_element_by_css_selector('#meiqia-container iframe[name=chat]') driver.execute_script('$(arguments[0]).remove()',element) #將element傳給了arguments[0] time.sleep(2)
6、切換瀏覽器標簽頁
使用switch_to_window(window),搭配句柄window_handles、current_window_handle使用。
import time
from selenium import webdriver
driver = webdriver.Chrome()
driver.get("http://www..com")
driver.implicitly_wait(10)
driver.find_element_by_id("kw").send_keys("python")
driver.find_element_by_id("su").click()
driver.find_element_by_xpath("//*[@id='2']/h3/a").click()
#獲取當前窗口所有句柄
all_windows = driver.window_handles
#獲取當前標簽頁窗口句柄
current_window = driver.current_window_handle
#切換標簽頁窗口
for window in all_windows:
if window !=current_window:
print("切換前的窗口名稱是:",driver.title)
driver.switch_to_window(window)
time.sleep(2)
print("切換後的窗口名稱是:",driver.title)
break
7、切換iframe頁面
使用switch_to_frame()、switch_to_default_content(),一般成套使用更好,以防止未切回導致定位失敗。
import time
from selenium import webdriver
driver = webdriver.Chrome()
driver.get("https://ke.qq.com/")
driver.implicitly_wait(10)
#點擊登錄
driver.find_element_by_class_name("btn-default").click()
time.sleep(0.5)
driver.find_element_by_xpath("//*[@class='js-btns-enter btns-enter btns-enter-qq']").click() time.sleep(2)
#點擊賬號密碼登錄
#這里直接定位會失敗,需要切換到登錄彈窗頁面後再進行定位,習慣使用的是2種切換方式
#1.iframe有唯一名稱
driver.switch_to_frame("login_frame_qq")
driver.find_element_by_id("switcher_plogin").click()
driver.find_element_by_id("u").send_keys("123456789")
#回切到主頁面
driver.switch_to_default_content()
time.sleep(2)
#2.iframe無名字,使用下標進行切換,且下標從0開始
#在頁面中查到到當前需要定位的iframe在第3個,所以下標是2
#再次切換到彈窗頁面 driver.switch_to_frame(2)
driver.find_element_by_id("p").send_keys("123456789")
driver.find_element_by_id("login_button").click()
driver.switch_to_default_content()
time.sleep(5)
driver.quit()
8、處理彈窗
使用switch_to_alert()中的accept()、dismiss()、send_keys、text進行操作,彈窗一般有三種類型,①.只有確認按鈕的;②.有確認/取消按鈕的;③.需要輸入文字的。
import time
from selenium import webdriver
driver = webdriver.Chrome()
driver.get("http://www..com")
driver.implicitly_wait(10)
#創建一個測試彈窗
driver.execute_script("window.alert('這是一個測試彈窗')")
time.sleep(2)
#1.彈窗中只有確認按鈕的
driver.switch_to_alert().accept()
time.sleep(1)
#2.彈窗中有確認/取消按鈕的
driver.execute_script("window.alert('這是一個測試彈窗')")
time.sleep(3)
#點擊取消
driver.switch_to_alert().dismiss()
time.sleep(1)
#彈窗中需要輸入文字的
# driver.switch_to_alert().send_keys("測試測試測試")
#獲取彈窗中的內容
driver.execute_script("window.alert('這是一個測試彈窗')")
res = driver.switch_to_alert().text
print(res)
『捌』 nintendo switch怎樣從手機拷游戲
如果是放在手機儲存里的XCI或者NSP游戲文件的話用USB線連接電腦拷貝出來,SWITCH關機取出SD卡放到讀卡器連接電腦就可以復制粘貼到卡里了。
如果你說的是把手游放到SWITCH上玩是無法實現的。手機游戲是APK格式和IPA的。格式都不同,怎麼用。