[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

时间:2021-11-04 23:44:44

新手练习,尝试使用angularjs2

【angularjs2 数据绑定,监听数据变化自动修改相应dom值,非常方便好用,但与传统js(jquery)的使用方法会很不同,Dom操作也不太习惯】

应用效果图:

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

转载请标明出处:cnblogs.com/wangxinsheng
@望星辰

-----

具体步骤如下:

1.通过应用生成器工具 express 可以快速创建一个应用的骨架
全局安装 应用生成器工具:$ npm install express-generator -g
在当前工作目录下创建一个命名为 lolHeros 的应用:$ express lolHeros
2.添加并修改 package.json 配置文件,加入依赖
3.运行命令 npm install 安装依赖
4.启动这个应用
(MacOS 或 Linux 平台):$ DEBUG=lolHeros npm start
Windows 平台使用如下命令:set DEBUG=lolHeros & npm start
URL:http://127.0.0.1:3000/
5.应用生成器创建的应用一般都有如下目录结构:
.
├── app.js
├── bin
│ └── www
├── package.json
├── public
│ ├── images
│ ├── javascripts
│ └── stylesheets
│ └── style.css
├── routes
│ ├── index.js
│ └── users.js
└── views
├── error.jade
├── index.jade
└── layout.jade

7 directories, 9 files
6.使用supervisor
npm -g install supervisor
修改 package.json script 节点
node => supervisor
启动服务命令改为:npm start
7.选择性使用 html2jade
npm install -g html2jade
这里偷懒,用在线转换页面
8.先做一个html,看效果
9.用工具转为 jade 模板,看看nodejs 运行效果
http://www.html2jade.org/
10.做lol英雄数据抓取功能
轻量级应用,就不用DB了,用systemFile来替代DB功能
nodejs http抓取和文件读写操作,由于这次需要同步告知执行结果,就用了同步方法处理
http 同步模块使用 sync-request[npm install sync-request]
下载数据:1.英雄列表,2.英雄详细数据,3.英雄头像,4.皮肤,5.技能图标
11.最后,整合AngularJS2前端框架
package.json 中加入AngularJS依赖,npm install

注:npm下载插件速度慢时,可以使用阿里巴巴在国内的镜像服务器,命令如下:
npm install -gd express --registry=http://registry.npm.taobao.org
可以使用如下命令进行永久设置:
npm config set registry http://registry.npm.taobao.org

-----

关键代码如下:

依赖包 package.json:

 {
"name": "lol_Heros",
"version": "1.0.0",
"description": "get and show lolHeros from qq with NodeJS-Server,ExpressJS-RouteAndTemplate,AngularJS2-JSFrontFramework,Bootstrap-CSS",
"private": true,
"keywords": [
"lol",
"Heros"
],
"author": "Wang Xinsheng",
"license": "MIT",
"scripts": {
"start": "tsc && concurrently \"tsc -w\" \"supervisor ./bin/www\" ",
"tsc": "tsc",
"tsc:w": "tsc -w"
},
"dependencies": {
"@angular/common": "~2.4.0",
"@angular/compiler": "~2.4.0",
"@angular/core": "~2.4.0",
"@angular/forms": "~2.4.0",
"@angular/http": "~2.4.0",
"@angular/platform-browser": "~2.4.0",
"@angular/platform-browser-dynamic": "~2.4.0",
"@angular/router": "~3.4.0",
"@types/jquery": "^2.0.39",
"angular-in-memory-web-api": "~0.2.4",
"body-parser": "~1.15.2",
"cookie-parser": "~1.4.3",
"core-js": "^2.4.1",
"debug": "~2.2.0",
"express": "~4.14.0",
"jade": "~1.11.0",
"morgan": "~1.7.0",
"rxjs": "5.0.1",
"serve-favicon": "~2.3.0",
"sync-request": "~3.0.1",
"systemjs": "0.19.40",
"zone.js": "^0.7.4"
},
"devDependencies": {
"concurrently": "^3.1.0",
"typescript": "~2.0.10",
"tslint": "^3.15.1",
"@types/node": "^6.0.46"
}
}

Express路由:省略,详细可查看附件

Nodejs 抓取数据代码(getHeroList.js):

 /* GET Hreo List Data. */
/*写入文件系统*/
var fs= require('fs');
var path = require('path');
/*同步抓取*/
var request = require('sync-request'); // 所有英雄列表
var heroListPath = 'http://lol.qq.com/biz/hero/champion.js';
// 单图 image full:http://ossweb-img.qq.com/images/lol/img/champion/Aatrox.png
var fullImgPath = 'http://ossweb-img.qq.com/images/lol/img/champion/';
//英雄信息:Aatrox=data.ID.js
var heroDetailPath = 'http://lol.qq.com/biz/hero/';
// skins.id http://ossweb-img.qq.com/images/lol/web201310/skin/big266000.jpg
var heroDetailSkinPath = 'http://ossweb-img.qq.com/images/lol/web201310/skin/big';
// 技能:Aatrox_Passive.png=>http://ossweb-img.qq.com/images/lol/img/passive/Aatrox_Passive.png
var heroDetailPSkillPath = 'http://ossweb-img.qq.com/images/lol/img/passive/';
// Q技能:http://ossweb-img.qq.com/images/lol/img/spell/AatroxQ.png Aatrox.png
var heroDetailSkillPath = 'http://ossweb-img.qq.com/images/lol/img/spell/'; var heroVerPath = '';
var heroVerSkinPath = '';
var heroVerSkillPath = '';
var heroVerImgPath = '';
var heroListJson = null;
module.exports = function() {
console.log('GET Hreo List Data starting...'); // 新建文件夹
// process.cwd() 启动目录
// process.execPath node.exe文件路劲
// __dirname 代码所在的目录
var heroDataPath = process.cwd() + '\\heroData';
var exists = fs.existsSync(heroDataPath);
if(!exists){
// 不存在创建目录
try{
fs.mkdirSync(heroDataPath);
console.log('创建目录成功:'+heroDataPath);
}catch(e){
console.log('创建目录失败',heroDataPath,e);
return '创建目录失败:'+'\n'+heroDataPath+'\n'+e;
}
}
// 抓取数据-所有英雄
var r = getHList(heroDataPath);
if(r!='')
return r;
// 抓取数据-所有英雄小头像
var r = getHListImg();
if(r!=''){
deleteFolderRecursive(heroVerPath);
return r;
}
console.log('GET Hreo List Data Finished');
return '';
}; // 获取英雄列表,英雄版本重复检查,创建版本文件夹,写入英雄列表
function getHList(parentPath){
console.log('GET Hreo List Data...');
var opt = getRequireOption(heroListPath);
var res = request(opt.method,opt.path,opt);
var data = res.getBody("utf8");
// jsonp 解析
data = data.replace('if(!LOLherojs)var LOLherojs={};LOLherojs.champion=','');
data = data.substr(0 ,data.length-1);
data = reconvert(data);
heroListJson = JSON.parse(data);
console.log(heroListJson.version,heroListJson.updated);
//JSON.stringify(obj)
heroVerPath = parentPath + '\\'+heroListJson.version;
var exists = fs.existsSync(heroVerPath); if(exists){
console.log('存在该版本',heroListJson.version);
return '存在该版本';
}else{
try{
fs.mkdirSync(heroVerPath);
}catch(e){
console.log('创建目录失败',heroVerPath,e);
return '创建目录失败:'+"\n"+heroVerPath+"\n"+e;
} var heroVerListPath = heroVerPath + '\\herolist.json';
try{
var w = fs.writeFileSync(heroVerListPath, JSON.stringify(heroListJson));
}catch(e){
console.log('写入错误',heroVerListPath,e);
return '写入错误:'+"\n"+heroVerListPath+"\n"+e;
}
console.log('写入成功',heroVerListPath);
}
console.log('GET Hreo List Data Finished');
return '';
} function getHListImg(){
// 抓取图片
// 创建头像目录
heroVerImgPath = heroVerPath + "\\" + "imgs";
var exists = fs.existsSync(heroVerImgPath);
if(!exists){
// 不存在创建目录
try{
fs.mkdirSync(heroVerImgPath);
console.log('创建目录成功:'+heroVerImgPath);
}catch(e){
console.log('创建目录失败',heroVerImgPath,e);
return '创建目录失败:'+'\n'+heroVerImgPath+'\n'+e;
}
}
// 皮肤目录
heroVerSkinPath = heroVerPath + "\\" + "skin";
var exists = fs.existsSync(heroVerSkinPath);
if(!exists){
// 不存在创建目录
try{
fs.mkdirSync(heroVerSkinPath);
console.log('创建目录成功:'+heroVerSkinPath);
}catch(e){
console.log('创建目录失败',heroVerSkinPath,e);
return '创建目录失败:'+'\n'+heroVerSkinPath+'\n'+e;
}
}
// 技能目录
heroVerSkillPath = heroVerPath + "\\" + "skill";
var exists = fs.existsSync(heroVerSkillPath);
if(!exists){
// 不存在创建目录
try{
fs.mkdirSync(heroVerSkillPath);
console.log('创建目录成功:'+heroVerSkillPath);
}catch(e){
console.log('创建目录失败',heroVerSkillPath,e);
return '创建目录失败:'+'\n'+heroVerSkillPath+'\n'+e;
}
}
for (var key in heroListJson.keys) {
// 下载头像图片
var imgName = heroListJson.data[heroListJson.keys[key]].image.full;
var fullImgUrl = fullImgPath+imgName;
console.log("抓取头像图片",imgName,fullImgUrl);
var opt = getRequireOption(fullImgUrl);
var res = request(opt.method,opt.path,opt);
var data = res.getBody();
var heroVerFullImgPath = heroVerImgPath + '\\'+imgName;
try{
var w = fs.writeFileSync(heroVerFullImgPath, data);
}catch(e){
console.log('写入错误',heroVerFullImgPath,e);
return '写入错误:'+"\n"+heroVerFullImgPath+"\n"+e;
}
console.log('写入成功',heroVerFullImgPath); // 下载英雄详细文件
var heroDataId = heroListJson.keys[key];
var heroDataUrl = heroDetailPath+heroDataId+'.js';
console.log("抓取英雄详细数据",heroDataId,heroDataUrl);
var opt = getRequireOption(heroDataUrl);
var res = request(opt.method,opt.path,opt);
var data = res.getBody('utf8');
// jsonp 解析
data = data.replace('if(!LOLherojs)var LOLherojs={champion:{}};LOLherojs.champion.'+heroDataId+'=','');
data = data.substr(0 ,data.length-1);
data = reconvert(data);
var heroDetailJson = JSON.parse(data);
var heroVerDetailPath = heroVerPath + '\\'+heroDataId+'.json';
try{
var w = fs.writeFileSync(heroVerDetailPath, data);
}catch(e){
console.log('写入错误',heroVerDetailPath,e);
return '写入错误:'+"\n"+heroVerDetailPath+"\n"+e;
}
console.log('写入成功',heroVerDetailPath); // 下载英雄皮肤图片
for(var skin in heroDetailJson.data.skins){
skin = heroDetailJson.data.skins[skin];
var skinImgUrl = heroDetailSkinPath + skin.id + '.jpg';
console.log("抓取皮肤图片",skin.id,skinImgUrl);
var opt = getRequireOption(skinImgUrl);
var res = request(opt.method,opt.path,opt);
var data = res.getBody();
var heroVerSkinImgPath = heroVerSkinPath + '\\'+skin.id + '.jpg';
try{
var w = fs.writeFileSync(heroVerSkinImgPath, data);
}catch(e){
console.log('写入错误',heroVerSkinImgPath,e);
return '写入错误:'+"\n"+heroVerSkinImgPath+"\n"+e;
}
console.log('写入成功',heroVerSkinImgPath);
}
// 下载英雄技能图片 主动
for(var spell in heroDetailJson.data.spells){
spell = heroDetailJson.data.spells[spell];
var spellImgUrl = heroDetailSkillPath + spell.image.full;
console.log("抓取主动技能图片",spell.image.full,spellImgUrl);
var opt = getRequireOption(spellImgUrl);
var res = request(opt.method,opt.path,opt);
var data = res.getBody();
var heroVerSpellImgPath = heroVerSkillPath + '\\'+spell.image.full;
try{
var w = fs.writeFileSync(heroVerSpellImgPath, data);
}catch(e){
console.log('写入错误',heroVerSpellImgPath,e);
return '写入错误:'+"\n"+heroVerSpellImgPath+"\n"+e;
}
console.log('写入成功',heroVerSpellImgPath);
}
// 下载英雄技能图片 被动
var passiveImgUrl = heroDetailPSkillPath + heroDetailJson.data.passive.image.full;
console.log("抓取被动技能图片",heroDetailJson.data.passive.image.full,passiveImgUrl);
var opt = getRequireOption(passiveImgUrl);
var res = request(opt.method,opt.path,opt);
var data = res.getBody();
var heroVerPassiveImgPath = heroVerSkillPath + '\\'+heroDetailJson.data.passive.image.full;
try{
var w = fs.writeFileSync(heroVerPassiveImgPath, data);
}catch(e){
console.log('写入错误',heroVerPassiveImgPath,e);
return '写入错误:'+"\n"+heroVerPassiveImgPath+"\n"+e;
}
console.log('写入成功',heroVerPassiveImgPath); //break; //test
}
return '';
} function reconvert(str){
str = str.replace(/(\\u)(\w{1,4})/gi,function($0){
return (String.fromCharCode(parseInt((escape($0).replace(/(%5Cu)(\w{1,4})/g,"$2")),16)));
});
str = str.replace(/(&#x)(\w{1,4});/gi,function($0){
return String.fromCharCode(parseInt(escape($0).replace(/(%26%23x)(\w{1,4})(%3B)/g,"$2"),16));
});
str = str.replace(/(&#)(\d{1,6});/gi,function($0){
return String.fromCharCode(parseInt(escape($0).replace(/(%26%23)(\d{1,6})(%3B)/g,"$2")));
});
return str;
} function deleteFolderRecursive(path) {
var files = [];
if( fs.existsSync(path) ) {
files = fs.readdirSync(path);
files.forEach(function(file,index){
var curPath = path + "/" + file;
if(fs.statSync(curPath).isDirectory()) { // recurse
deleteFolderRecursive(curPath);
} else { // delete file
fs.unlinkSync(curPath);
}
});
fs.rmdirSync(path);
}
}; function getRequireOption(pathStr){
return op={
host:pathStr.match(/http[s]?:\/\/[^\\|\/]*/)[0].replace(/http[s]?:\/\//,''),
port:80,
method:'GET',
path:pathStr,
headers:{
'Host':pathStr.match(/http[s]?:\/\/[^\\|\/]*/)[0].replace(/http[s]?:\/\//,''),
"User-Agent":"Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.1 (KHTML, like Gecko) Chrome/21.0.1180.92 Safari/537.1 LBBROWSER",
"Referer":pathStr.match(/http[s]?:\/\/[^\\|\/]*/)[0].replace(/http[s]?:\/\//,'')
}
}
}

jade模板代码(indexTemplate.jade):

 doctype html
html
head
title LOL英雄
script(src='/javascripts/jquery-3.1.1.min.js')
script(src='/javascripts/bootstrap.min.js')
script(src='/core-js/client/shim.min.js')
script(src='/zone.js/dist/zone.js')
script(src='/jade/jade.js')
script(src='/systemjs/dist/system.src.js')
script(src='/javascripts/systemjs.config.js')
script.
System.import('app').catch(function(err){ console.error(err); });
link(href='/stylesheets/bootstrap.min.css', rel='stylesheet')
style.
html,body{background-color: black;color:rgb(255,215,000); overflow: hidden; height:100%;}
.main,.selHeroMain{
width:100%;height:100%;
}
.selHeroContain{
border-radius: 50%;
border:3px rgb(255,215,000) solid;
width:60%;
height:90%;
margin: 0 auto;
}
.selHeroDivOut{
border:1px black solid;
width:50%;
height:300%;
margin: auto;
margin-top: -50%;
background-color: black;
}
.selHeroDiv{
position:absolute;
display: none;
border-radius: 50%;
border:2px rgb(255,215,000) solid;
background-size:196% 100%;
background-repeat:no-repeat;
background-position:100% 100%;
overflow: hidden;
box-shadow: 0px 0px 30px rgb(255,215,000);
}
.selHeroDiv img{
height:100%;
border-radius: 50%;
}
.leftHeros,.rightHeros{
width:15%;
height:90%;
position:absolute;
top:0px;
overflow: hidden;
}
.leftHeros{
left:0px;
}
.rightHeros{
right:0px;
}
.leftHeros ul,.rightHeros ul{
height:90%;
margin-top: 30%;
padding-left: 0px;
}
.leftHeros li,.rightHeros li{
white-space:nowrap;
font-size:20px;
list-style-type:none;
height:18%;
padding:1% 0;
border-bottom: 1px rgb(255,215,000) solid;
overflow: hidden;
}
.leftHeros li{
text-align: left;
}
.rightHeros li{
text-align: right;
}
.leftHeros img,.rightHeros img{
vertical-align: bottom;
height:100%;
overflow: hidden;
}
.leftHeros span,.rightHeros span{
overflow: hidden;
}
/* css3实现图片划过一束光闪过效果 */
.selHeroDiv:before {
content: ""; position: absolute; width:200px; height: 100%; top: 0; left: -350px; overflow: hidden;
background: -moz-linear-gradient(left, rgba(255,255,255,0)0, rgba(255,255,255,.2)50%, rgba(255,255,255,0)100%);
background: -webkit-gradient(linear, left top, right top, color-stop(0%, rgba(255,255,255,0)), color-stop(50%, rgba(255,255,255,.2)), color-stop(100%, rgba(255,255,255,0)));
background: -webkit-linear-gradient(left, rgba(255,255,255,0)0, rgba(255,255,255,.2)50%, rgba(255,255,255,0)100%);
background: -o-linear-gradient(left, rgba(255,255,255,0)0, rgba(255,255,255,.2)50%, rgba(255,255,255,0)100%);
-webkit-transform: skewX(-25deg);
-moz-transform: skewX(-25deg);
animation:selHeroDivAnimate 9s infinite linear;
}
.selHeroDiv:hover:before { left: 150%; animation:selHeroDivAnimateHover 1s 1 ease 0s; /*transition: left 1s ease 0s;*/}
@keyframes selHeroDivAnimate
{
0% {left: -350px;}
90% {left: -350px;}
100% {left: 150%;}
}
@keyframes selHeroDivAnimateHover
{
0% {left: -350px;}
100% {left: 150%;}
}
.pullDown{
width:100%;
height:10%;
position:absolute;
top:0px;
text-align: center;
vertical-align: middle;
font-size: 50px;
color:white;
cursor:pointer;
}
.pullDown span{width:100%;position: absolute;top: 0px;left:0px;animation:pullDown 2s infinite linear;}
@keyframes pullDown
{
0% {top: 0px;}
50% {top: 20px;}
100% {top: 0px;}
}
.heroList{
width:100%;
height:60%;
position:absolute;
opacity:0.2;
background: gray;
top:90%;
}
/*.heroList:hover{
opacity:1;
background: black;
top:40%;
transition: opacity,top 1s ease 0s;
}*/
.pullUp{
position:relative;
top:0px;
color:white;
text-align: right;
display: none;
cursor:pointer;
}
.hListMain{display: none; height: 95%;}
.hListSearchBar{height: 10%;}
.hListStyle1,.hListStyle2{vertical-align: middle; font-size: 30px; height:85%; overflow-y: auto; overflow-x: hidden;}
.hListStyle1 .row,.hListStyle2 .row{ margin-top: 15px; border-bottom: 1px rgb(255,215,000) solid; }
.hListStyle1 .row{cursor: pointer;}
.hListStyle2 .row{border: none;}
.hListStyle1 .row div{ height: 100px; line-height: 100px;}
.hListStyle2 .row {width:70%; margin:0 auto;}
.hListStyle2 .row div{cursor: pointer;}
.hListStyle2{display: none;}
.hero{position: absolute;width:80%; border: 1px rgb(255,215,000) solid;top:-100%;
border-radius: 30px; top:10%;left:10%;background: #2B2B2B; font-size: 30px; height: 80%; /*display: none;*/}
.heroTitle{height:20%;width:100%;}
.heroData{overflow-y: auto; overflow-x: hidden;height:75%;width:100%;font-size: 15px;}
.heroData .row{margin-bottom: 5px; }
.heroClose{color:white; font-size: 10px; cursor: pointer;}
.getHeroList{position: absolute;top:0px; right: 0px; color: black;font-style: 13px;cursor: pointer;z-index:99;}
.leftHeros li:first-child img{border:1px rgb(255,215,000) solid}
.loadingDiv{width:100%;height:100%;top:0px;left:0px;background:gray;font-size:40px;position:absolute;text-align:center;padding:20% 0;opacity:0.75;text-shadow: 0px 0px 40px rgb(255,000,000);}
body
script.
window.onresize = function(){
var selHeroDivHW = $(".selHeroDivOut").width();
$(".selHeroDiv").width(selHeroDivHW);
$(".selHeroDiv").height(selHeroDivHW);
$(".selHeroDiv").offset({"left":$(".selHeroContain").offset().left+($(".selHeroContain").width()-selHeroDivHW)*0.5
,"top":$(".selHeroContain").offset().top+($(".selHeroContain").height()-selHeroDivHW)*0.5});
$(".selHeroDiv").show();
};
function stopPropagation(e){
window.event? window.event.cancelBubble = true : e.stopPropagation();
}
Array.prototype.contains=function(obj) {
var index=this.length;
while (index--){
if(this[index]===obj){
return true;
}
}
return false;
}
.main

Angularjs2 模板代码(selectHero.html)【理论上应该分组件,通过组件父子间通信来完成】:

       <div class='selHeroMain' (mousewheel)="showHideHeroListPanel()" >
<div class='selHeroContain' #selHeroContain>
<div class='selHeroDivOut' #selHeroDivOut>
<div class='selHeroDiv' [ngStyle]="{'background-image': styleExp}" #selHeroDiv>
</div>
</div>
</div>
<div class='leftHeros'>
<ul>
<li>玩家1:<span><img src='{{leftPlayImg1}}' width='133' height='120' /></span></li>
<li>玩家2:<span><img src='{{leftPlayImg2}}' width='133' height='120' /></span></li>
<li>玩家3:<span><img src='{{leftPlayImg3}}' width='133' height='120' /></span></li>
<li>玩家4:<span><img src='{{leftPlayImg4}}' width='133' height='120' /></span></li>
<li>玩家5:<span><img src='{{leftPlayImg5}}' width='133' height='120' /></span></li>
</ul>
</div>
<div class='rightHeros'>
<ul>
<li><span><img src='{{rightPlayImg1}}' width='133' height='120' />:玩家1</span></li>
<li><span><img src='{{rightPlayImg2}}' width='133' height='120' />:玩家2</span></li>
<li><span><img src='{{rightPlayImg3}}' width='133' height='120' />:玩家3</span></li>
<li><span><img src='{{rightPlayImg4}}' width='133' height='120' />:玩家4</span></li>
<li><span><img src='{{rightPlayImg5}}' width='133' height='120' />:玩家5</span></li>
</ul>
</div>
<!--<div class='pullDown'><span>下拉/点击 选择英雄</span></div>-->
</div>
<div class='heroList container' [@openClosePanel]="statePanelExpression" #heroList >
<div class='pullDown' (click)="showHeroListPanel()" #pullDown ><span>下拉/点击 选择英雄</span></div>
<div class='pullUp' (click)="hideHeroListPanel()" #pullUp >关闭</div>
<div class='hListMain' #hListMain >
<div class='hListSearchBar form-inline text-center'>
<div class="row">
<div class="col-lg-1 col-md-1 col-sm-1">
<div class="dropdown">
<button type="button" class="btn dropdown-toggle btn-primary" id="dropdownMenuVer" data-toggle="dropdown">版本
<span class="caret"></span>
</button>
<ul class="dropdown-menu" role="menu" aria-labelledby="dropdownMenuVer">
<li role="presentation" *ngFor="let ver of heroVers.vers; let i = index" [ngClass]="{'active':ver==curVer}" (click)="getNewVersion(ver)">
<a role="menuitem" tabindex="-1" href="#" >{{ver}}</a>
</li>
</ul>
</div>
</div>
<div class="col-lg-1 col-md-1 col-sm-1">
<div class="dropdown">
<button type="button" class="btn dropdown-toggle btn-primary" id="dropdownMenuVer" data-toggle="dropdown">英雄类型
<span class="caret"></span>
</button>
<ul class="dropdown-menu" role="menu" aria-labelledby="dropdownMenuVer">
<li role="presentation" *ngFor="let htc of heroTypeCList; let i = index" [ngClass]="{'active':htc==heroTypeCCur}" (click)="filterType(heroTypeCList[i])">
<a role="menuitem" tabindex="-1" href="#">{{heroTypeCList[i]}}</a>
</li>
</ul>
</div>
</div>
<div class="col-lg-1 col-md-1 col-sm-1"><input type="text" class="form-control" id="name" placeholder="输入英雄名称" #heroFilterName (keyup)="searchHeroByName(heroFilterName.value)"></div>
<div class="col-lg-8 col-md-8 col-sm-8">检索条件: {{heroTypeCCur}}英雄 | 名称:{{heroFilterName.value}}</div>
<div class="col-lg-1 col-md-1 col-sm-1">
<div class="dropdown pull-right">
<button type="button" class="btn dropdown-toggle btn-primary" id="dropdownMenuVer" data-toggle="dropdown">显示方式
<span class="caret"></span>
</button>
<ul class="dropdown-menu" role="menu" aria-labelledby="dropdownMenuVer">
<li role="presentation" [ngClass]="{'active':showListTypeCur=='LB'}">
<a role="menuitem" tabindex="-1" href="#" #menuitemLB (click)="heroListLB()" >列表</a>
</li>
<li role="presentation" [ngClass]="{'active':showListTypeCur=='TZ'}">
<a role="menuitem" tabindex="-1" href="#" #menuitemTZ (click)="heroListTZ()" >图阵</a>
</li>
</ul>
</div>
</div>
</div>
</div>
<div class='hListStyle1' #hListStyle1 >
<div class="row text-center" (click)="showHeroDetail(heroData)" (mouseenter)="showBigPic(heroData)" *ngFor="let heroData of heroDataList; let i = index">
<div class="col-lg-1 col-md-1 col-sm-1">
</div>
<div class="col-lg-2 col-md-2 col-sm-2">
<img src='/{{curVer}}/imgs/{{heroData.image.full}}' width="90" />
</div>
<div class="col-lg-1 col-md-1 col-sm-1">
{{heroData.id}}
</div>
<div class="col-lg-2 col-md-2 col-sm-2">
{{heroData.name}}
</div>
<div class="col-lg-2 col-md-2 col-sm-2">
{{heroData.title}}
</div>
<div class="col-lg-2 col-md-2 col-sm-2">
{{heroData.tags}}
</div>
<div class="col-lg-2 col-md-2 col-sm-2">
</div>
</div>
</div>
<div class='hListStyle2' #hListStyle2 >
<div class="row text-center">
<div class="col-lg-2 col-md-2 col-sm-2" (click)="showHeroDetail(heroData)" (mouseenter)="showBigPic(heroData)" *ngFor="let heroData of heroDataList; let i = index">
<a data-toggle="tooltip" data-placement="top" title="{{heroData.id}}:{{heroData.name}}:{{heroData.title}}:{{heroData.tags}}">
<img src='/{{curVer}}/imgs/{{heroData.image.full}}' width="120" />
</a>
</div>
</div>
</div>
</div>
</div>
<div *ngIf="heroShowDetailAllytips && heroShowDetailAllytips.length>0" class='hero container' [@openCloseHero]="stateHeroExpression" #hero >
<p class="heroClose text-right" (click)="hideHeroDetail()" >关闭</p>
<div class="heroTitle">
<div class="row">
<div class="col-lg-2 col-md-2 col-sm-2">
<img src='/{{curVer}}/imgs/{{heroShowDetail.id}}.png' width="120" />
</div>
<div class="col-lg-6 col-md-6 col-sm-6">
({{heroShowDetail.id}}) {{heroShowDetail.name}} : {{heroShowDetail.title}}
</div>
<div class="col-lg-2 col-md-2 col-sm-2 text-right">
<span class="badge">[{{heroShowDetail.tags}}]</span>
</div>
</div>
</div>
<div class="heroData">
<div class="row">
<div class="col-lg-2 col-md-2 col-sm-2"></div>
<div class="col-lg-8 col-md-8 col-sm-8">
<div id="myCarousel" class="carousel slide" #myCarousel>
<!-- 轮播(Carousel)指标 -->
<ol class="carousel-indicators">
<li data-target="#myCarousel" [ngClass]="{'active':i==0}" *ngFor="let skin of heroShowDetailSkins; let i = index" ></li>
</ol>
<!-- 轮播(Carousel)项目 -->
<div class="carousel-inner">
<div class="item" [ngClass]="{'active':i==0}" *ngFor="let skin of heroShowDetailSkins; let i = index" >
<img src="/{{curVer}}/skin/{{skin.id}}.jpg" alt="{{skin.name}}">
<div class="carousel-caption">{{skin.name}}</div>
</div>
</div>
<!-- 轮播(Carousel)导航 -->
<a class="carousel-control left" href="#myCarousel"
data-slide="prev">&lsaquo;
</a>
<a class="carousel-control right" href="#myCarousel"
data-slide="next">&rsaquo;
</a>
</div>
</div>
<div class="col-lg-2 col-md-2 col-sm-2"></div>
</div>
<div class="row">
<div class="col-lg-1 col-md-1 col-sm-1"></div>
<div class="col-lg-1 col-md-1 col-sm-1">故事
</div>
<div class="col-lg-10 col-md-10 col-sm-10">
</div>
</div>
<div class="row">
<div class="col-lg-2 col-md-2 col-sm-2"></div>
<div class="col-lg-8 col-md-8 col-sm-8">{{heroShowDetail.lore}}
</div>
<div class="col-lg-2 col-md-2 col-sm-2"></div>
</div>
<div class="row">
<div class="col-lg-1 col-md-1 col-sm-1"></div>
<div class="col-lg-1 col-md-1 col-sm-1">技能
</div>
<div class="col-lg-10 col-md-10 col-sm-10">
</div>
</div>
<div class="row">
<div class="col-lg-2 col-md-2 col-sm-2"></div>
<div class="col-lg-1 col-md-1 col-sm-1"><img src='/{{curVer}}/skill/{{heroShowDetailPassiveImg.full}}' width="80" /></div>
<div class="col-lg-7 col-md-7 col-sm-7">
{{heroShowDetailPassive.name}}<br/>{{heroShowDetailPassive.description}}
</div>
<div class="col-lg-2 col-md-2 col-sm-2"></div>
</div>
<div class="row">
<div class="col-lg-2 col-md-2 col-sm-2"></div>
<div class="col-lg-1 col-md-1 col-sm-1"><img src='/{{curVer}}/skill/{{heroShowDetailSpells1.image}}' width="80" /></div>
<div class="col-lg-3 col-md-3 col-sm-3">
{{heroShowDetailSpells1.id}}<br/>
{{heroShowDetailSpells1.name}}<br/>
{{heroShowDetailSpells1.description}}<br/>
{{removeTag(heroShowDetailSpells1.tooltip)}}
</div>
<div class="col-lg-1 col-md-1 col-sm-1"><img src='/{{curVer}}/skill/{{heroShowDetailSpells2.image}}' width="80" /></div>
<div class="col-lg-3 col-md-3 col-sm-3">
{{heroShowDetailSpells2.id}}<br/>
{{heroShowDetailSpells2.name}}<br/>
{{heroShowDetailSpells2.description}}<br/>
{{removeTag(heroShowDetailSpells2.tooltip)}}
</div>
<div class="col-lg-2 col-md-2 col-sm-2"></div>
</div>
<div class="row">
<div class="col-lg-2 col-md-2 col-sm-2"></div>
<div class="col-lg-1 col-md-1 col-sm-1"><img src='/{{curVer}}/skill/{{heroShowDetailSpells3.image}}' width="80" /></div>
<div class="col-lg-3 col-md-3 col-sm-3">
{{heroShowDetailSpells3.id}}<br/>
{{heroShowDetailSpells3.name}}<br/>
{{heroShowDetailSpells3.description}}<br/>
{{removeTag(heroShowDetailSpells3.tooltip)}}
</div>
<div class="col-lg-1 col-md-1 col-sm-1"><img src='/{{curVer}}/skill/{{heroShowDetailSpells4.image}}' width="80" /></div>
<div class="col-lg-3 col-md-3 col-sm-3">
{{heroShowDetailSpells4.id}}<br/>
{{heroShowDetailSpells4.name}}<br/>
{{heroShowDetailSpells4.description}}<br/>
{{removeTag(heroShowDetailSpells4.tooltip)}}
</div>
<div class="col-lg-2 col-md-2 col-sm-2"></div>
</div>
<div class="row">
<div class="col-lg-1 col-md-1 col-sm-1"></div>
<div class="col-lg-1 col-md-1 col-sm-1">技巧
</div>
<div class="col-lg-10 col-md-10 col-sm-10">
</div>
</div>
<div class="row">
<div class="col-lg-2 col-md-2 col-sm-2"></div>
<div class="col-lg-1 col-md-1 col-sm-1">己方技巧:</div>
<div class="col-lg-7 col-md-7 col-sm-7">
<div class="row" *ngFor="let str of heroShowDetailAllytips; let i = index">{{str}}</div>
</div>
<div class="col-lg-2 col-md-2 col-sm-2"></div>
</div>
<div class="row">
<div class="col-lg-2 col-md-2 col-sm-2"></div>
<div class="col-lg-1 col-md-1 col-sm-1">敌方技巧:</div>
<div class="col-lg-7 col-md-7 col-sm-7">
<div class="row" *ngFor="let str of heroShowDetailEnemytips; let i = index">{{str}}</div>
</div>
<div class="col-lg-2 col-md-2 col-sm-2"></div>
</div>
</div> </div>
<div class="getHeroList" #getHeroList (click)="doGetHeroList()" [style.color]="loadFinished?'black':'gold'">点此抓取LOL英雄列表 ^-^</div>
<div class='loadingDiv' [style.display]="loadFinished?'none':'block'">{{loadingText}}</div>

Angularjs2 ts代码(app.component.ts):

 import {Component, OnInit, ViewChild, Renderer, ElementRef, AfterViewInit, animate, trigger,state,style,transition} from '@angular/core';
import {Http,Response} from '@angular/http';
import 'rxjs/add/operator/toPromise';
import 'rxjs/add/operator/catch';
import 'rxjs/add/operator/debounceTime';
import 'rxjs/add/operator/distinctUntilChanged';
import 'rxjs/add/operator/map';
import 'rxjs/add/operator/switchMap'; @Component({
selector: '.main',
animations: [
trigger(
'openClosePanel',
[
state('close, void', style({opacity:'0.2',top:'90%'})),
state('open', style({opacity:'1',top:'40%'})),
transition(
'close <=> open', [animate(500)])
]),
trigger(
'openCloseHero',
[
state('close, void', style({opacity:'0',top:'-100%'})),
state('open', style({opacity:'1',top:'10%'})),
transition(
'close <=> open', [animate(500)]),
transition(
'void => open', [animate(500)])
])
],
templateUrl: '/selectHero.html'
})
export class AppComponent implements AfterViewInit,OnInit {
styleExp = 'url("/images/main.jpg")';
leftPlayImg1 = '/images/angularjs.png';
leftPlayImg2 = '/images/expressjs.jpg';
leftPlayImg3 = '/images/bootstrap.jpg';
leftPlayImg4 = '/images/nodejs.png';
leftPlayImg5 = '/images/npm.jpg';
rightPlayImg1 = '/images/spring.jpg';
rightPlayImg2 = '/images/struts2.jpg';
rightPlayImg3 = '/images/typescript.jpg';
rightPlayImg4 = '/images/tomcat.jpg';
rightPlayImg5 = '/images/java.png';
heroTypeCList = ["所有","战士","坦克","刺客","法师","射手","辅助"];
heroTypeCCur = "所有";
showListTypeCur = "LB";
// loading
loadFinished = false;
loadingText = 'Hellow World! 你好!'; // 获取dom元素 start
// 英雄大头像圈
@ViewChild('selHeroDiv') selHeroDiv: ElementRef;
@ViewChild('selHeroDivOut') selHeroDivOut: ElementRef;
@ViewChild('selHeroContain') selHeroContain: ElementRef;
// 英雄列表面板
@ViewChild('heroList') heroList: ElementRef;
@ViewChild('hListMain') hListMain: ElementRef;
@ViewChild('pullDown') pullDown: ElementRef;
@ViewChild('pullUp') pullUp: ElementRef;
// 英雄列表 图阵 切换
@ViewChild('hListStyle1') hListStyle1: ElementRef;
@ViewChild('hListStyle2') hListStyle2: ElementRef;
// 抓取LOL服务器数据
@ViewChild('getHeroList') getHeroListDom: ElementRef;
// 显示英雄详细信息
@ViewChild('hero') hero: ElementRef;
// 英雄过滤名称
@ViewChild('heroFilterName') heroFilterName: ElementRef; // 获取dom元素 end constructor(private renderer: Renderer,private http: Http) {
// 初始:英雄列表隐藏
this.statePanelExpression = 'close';
// 初始:英雄详细隐藏
this.stateHeroExpression = 'close';
} ngAfterViewInit() {
// 初期设置大头像位置 start
var selHeroDivHW = this.selHeroDivOut.nativeElement.clientWidth;
var selHeroContainHeight = this.selHeroContain.nativeElement.clientHeight;
var selHeroContainWidth = this.selHeroContain.nativeElement.clientWidth;
var selHeroContainLeft = this.selHeroContain.nativeElement.offsetLeft;
var selHeroContainTop = this.selHeroContain.nativeElement.offsetTop; this.renderer.setElementStyle(this.selHeroDiv.nativeElement, 'width', selHeroDivHW+'px');
this.renderer.setElementStyle(this.selHeroDiv.nativeElement, 'height', selHeroDivHW+'px');
this.renderer.setElementStyle(this.selHeroDiv.nativeElement, 'left', selHeroContainLeft+(selHeroContainWidth-selHeroDivHW)*0.5 +'px');
this.renderer.setElementStyle(this.selHeroDiv.nativeElement, 'top', selHeroContainTop+(selHeroContainHeight-selHeroDivHW)*0.5 +'px'); this.renderer.setElementStyle(this.selHeroDiv.nativeElement, 'display', 'block');
// 初期设置大头像位置 end
} // 英雄列表面板显示隐藏控制 start
statePanelExpression: string;
showHeroListPanel() {
this.renderer.setElementStyle(this.pullDown.nativeElement, 'display', 'none');
this.statePanelExpression = 'open';
this.renderer.setElementStyle(this.pullUp.nativeElement, 'display', 'block');
this.renderer.setElementStyle(this.heroList.nativeElement, 'background', 'black');
this.renderer.setElementStyle(this.hListMain.nativeElement, 'display', 'block');
}
hideHeroListPanel() {
this.renderer.setElementStyle(this.pullUp.nativeElement, 'display', 'none');
this.statePanelExpression = 'close';
this.renderer.setElementStyle(this.pullDown.nativeElement, 'display', 'block');
this.renderer.setElementStyle(this.heroList.nativeElement, 'background', 'gray');
this.renderer.setElementStyle(this.hListMain.nativeElement, 'display', 'none');
}
showHideHeroListPanel(){
if(this.statePanelExpression == 'close'){
this.showHeroListPanel();
}else{
this.hideHeroListPanel();
}
}
// 英雄列表面板显示隐藏控制 end // 英雄列表 图阵 切换 start
heroListLB(){
this.renderer.setElementStyle(this.hListStyle2.nativeElement, 'display', 'none');
this.renderer.setElementStyle(this.hListStyle1.nativeElement, 'display', 'block');
this.showListTypeCur = "LB";
}
heroListTZ(){
this.renderer.setElementStyle(this.hListStyle1.nativeElement, 'display', 'none');
this.renderer.setElementStyle(this.hListStyle2.nativeElement, 'display', 'block');
this.showListTypeCur = "TZ";
}
// 英雄列表 图阵 切换 end // 抓取LOL服务器数据
doGetHeroList(){
this.renderer.setElementStyle(this.getHeroListDom.nativeElement, 'display', 'none');
this.http.get('/getHeroList').toPromise().
then(res =>
{
alert(res.text());
this.renderer.setElementStyle(this.getHeroListDom.nativeElement, 'display', 'block');
this.ngAfterViewInit();
this.ngOnInit();
}).catch((e)=>console.log(e));
} // 显示英雄详细信息 start
stateHeroExpression: string;
curHeroDataId = '';
heroShowDetail:any = {};
heroShowDetailPassive:any = {};
heroShowDetailPassiveImg = '';
heroShowDetailSkins : Array<any> = [];
heroShowDetailSpells1 :any = {};
heroShowDetailSpells2 :any = {};
heroShowDetailSpells3 :any = {};
heroShowDetailSpells4 :any = {};
heroShowDetailAllytips : Array<any> = [];
heroShowDetailEnemytips : Array<any> = [];
showHeroDetail(heroData:any){
// 获取英雄详细数据
this.curHeroDataId = heroData.id;
this.http.get('/' + this.curVer + '/'+ heroData.id +'.json').toPromise()
.then((res:Response)=>{
if(JSON.parse(res.text()).data.id == this.curHeroDataId){
this.heroShowDetail = JSON.parse(res.text()).data;
this.heroShowDetailSkins = JSON.parse(res.text()).data.skins;
this.heroShowDetail.tags = this.heroTypeEC2C(this.heroShowDetail.tags);
this.heroShowDetailPassive = JSON.parse(res.text()).data.passive;
this.heroShowDetailPassiveImg = JSON.parse(res.text()).data.passive.image; this.heroShowDetailSpells1 = JSON.parse(res.text()).data.spells[0];
this.heroShowDetailSpells2 = JSON.parse(res.text()).data.spells[1];
this.heroShowDetailSpells3 = JSON.parse(res.text()).data.spells[2];
this.heroShowDetailSpells4 = JSON.parse(res.text()).data.spells[3];
this.heroShowDetailSpells1.image = JSON.parse(res.text()).data.spells[0].image.full;
this.heroShowDetailSpells2.image = JSON.parse(res.text()).data.spells[1].image.full;
this.heroShowDetailSpells3.image = JSON.parse(res.text()).data.spells[2].image.full;
this.heroShowDetailSpells4.image = JSON.parse(res.text()).data.spells[3].image.full;
this.heroShowDetailAllytips = JSON.parse(res.text()).data.allytips;
this.heroShowDetailEnemytips = JSON.parse(res.text()).data.enemytips;
}
}).catch(this.handleError);
this.stateHeroExpression = 'open';
}
hideHeroDetail() {
this.stateHeroExpression = 'close';
}
// 显示英雄详细信息 end // 英雄列表所有版本号
heroVers = JSON.parse('{}');
heroDataList : Array<any> = [];
bakHeroDataList : Array<any> = [];
curVer = '';
ngOnInit(){
// 取得英雄列表所有版本号
// console.log('client get hero version');
this.loadingText = '开始取得英雄列表所有版本号';
this.http.get('/getHeroVers').toPromise()
.then((res:Response)=>{
this.heroVers = this.extractVersData(res);
if(!this.heroVers && !this.heroVers.vers){
this.loadingText = '服务器尚未抓取英雄列表,请点击右上角文字抓取数据。';
return;
}
this.curVer = (this.heroVers && this.heroVers.vers &&this.heroVers.vers.length>0)?this.heroVers.vers[0]:'';
if(this.curVer!=''){
// 获取英雄列表json
this.loadingText = '开始取得英雄列表';
this.http.get('/' + this.curVer + '/herolist.json').toPromise()
.then((res:Response)=>{
if(JSON.parse(res.text()).version == this.curVer){
this.heroDataList = [];
for (var key in JSON.parse(res.text()).keys) {
var heroIdTmp = JSON.parse(res.text()).keys[key];
this.heroDataList.push(
JSON.parse(res.text()).data[heroIdTmp]
);
this.bakHeroDataList.push(
JSON.parse(res.text()).data[heroIdTmp]
);
}
for (var i = this.heroDataList.length - 1; i >= 0; i--) {
this.heroDataList[i].tags = this.heroTypeEC2C(this.heroDataList[i].tags);
this.bakHeroDataList[i].tags = this.heroTypeEC2C(this.bakHeroDataList[i].tags);
}
this.heroDataTypeList = this.heroDataList;
this.loadingText = '随机生成对战英雄';
this.genFight();
this.loadingText = '加载完成';
this.loadFinished = true;
}
}).catch(this.handleError);
}else{
this.loadingText = '服务器尚未抓取英雄列表,请点击右上角文字抓取数据。';
}
}).catch(this.handleError);
} genFight(){
// 随机生成对战英雄
var max = this.heroDataList.length;
var randomI = Math.floor(Math.random()*max);
this.leftPlayImg1 = '/'+this.curVer+'/imgs/'+this.heroDataList[randomI].id+'.png';
var myHero = this.heroDataList[randomI];
randomI = Math.floor(Math.random()*max);
this.leftPlayImg2 = '/'+this.curVer+'/imgs/'+this.heroDataList[randomI].id+'.png';
randomI = Math.floor(Math.random()*max);
this.leftPlayImg3 = '/'+this.curVer+'/imgs/'+this.heroDataList[randomI].id+'.png';
randomI = Math.floor(Math.random()*max);
this.leftPlayImg4 = '/'+this.curVer+'/imgs/'+this.heroDataList[randomI].id+'.png';
randomI = Math.floor(Math.random()*max);
this.leftPlayImg5 = '/'+this.curVer+'/imgs/'+this.heroDataList[randomI].id+'.png';
randomI = Math.floor(Math.random()*max);
this.rightPlayImg1 = '/'+this.curVer+'/imgs/'+this.heroDataList[randomI].id+'.png';
randomI = Math.floor(Math.random()*max);
this.rightPlayImg2 = '/'+this.curVer+'/imgs/'+this.heroDataList[randomI].id+'.png';
randomI = Math.floor(Math.random()*max);
this.rightPlayImg3 = '/'+this.curVer+'/imgs/'+this.heroDataList[randomI].id+'.png';
randomI = Math.floor(Math.random()*max);
this.rightPlayImg4 = '/'+this.curVer+'/imgs/'+this.heroDataList[randomI].id+'.png';
randomI = Math.floor(Math.random()*max);
this.rightPlayImg5 = '/'+this.curVer+'/imgs/'+this.heroDataList[randomI].id+'.png';
this.curHeroBigDataId = myHero.id;
this.http.get('/' + this.curVer + '/'+ myHero.id +'.json').toPromise()
.then((res:Response)=>{
if(JSON.parse(res.text()).data.id == this.curHeroBigDataId){
var max = JSON.parse(res.text()).data.skins.length;
var randomI = Math.floor(Math.random()*max);
this.styleExp = 'url("/'+this.curVer+'/skin/'
+JSON.parse(res.text()).data.skins[randomI].id
+'.jpg")';
}
}).catch(this.handleError);
} // 处理英雄列表所有版本号
private extractVersData(res: Response) {
let body = JSON.parse(res.text());
if(body && body.vers){
body.vers.sort((a : any,b : any)=>b>a); // 简单排序,需要加工
}
return body || { };
}
private handleError (error: Response | any) {
console.error(error);
return { };
} private heroTypeEC2C(ht:Array<string>): Array<string>{
let result : Array<string> = [];
for (var i = ht.length - 1; i >= 0; i--) {
result.push(ht[i].replace('Mage','法师')
.replace('Fighter','战士')
.replace('Tank','坦克')
.replace('Assassin','刺客')
.replace('Marksman','射手')
.replace('Support','辅助'));
}
return result;
}
removeTag(str:string):string{
if(str)
return str.replace(/<.*?>/ig,"");
return '';
} curHeroBigDataId = '';
showBigPic(heroData:any){
// 修改大图像
this.leftPlayImg1 = '/'+this.curVer+'/imgs/'+heroData.id+'.png';
this.curHeroBigDataId = heroData.id;
this.http.get('/' + this.curVer + '/'+ heroData.id +'.json').toPromise()
.then((res:Response)=>{
if(JSON.parse(res.text()).data.id == this.curHeroBigDataId){
var max = JSON.parse(res.text()).data.skins.length;
var randomI = Math.floor(Math.random()*max);
this.styleExp = 'url("/'+this.curVer+'/skin/'
+JSON.parse(res.text()).data.skins[randomI].id
+'.jpg")';
}
}).catch(this.handleError);
}
heroDataTypeList : Array<any> = [];
filterType(type:string):void{
// 选择英雄类型
this.heroTypeCCur = type;
this.heroDataList = this.bakHeroDataList.filter(
(hero:any)=>this.heroTypeCCur =='所有' || hero.tags.contains(this.heroTypeCCur));
this.heroDataTypeList = this.heroDataList;
}
filterTypeFun(hero:any){
return hero.tags.contains(this.heroTypeCCur);
}
searchHeroByName(value: string){
// 过滤英雄名称
this.heroDataList = this.heroDataTypeList.filter(
(hero:any)=>value ==''
|| hero.id.toLowerCase().indexOf(value.toLowerCase())>=0
|| hero.name.toLowerCase().indexOf(value.toLowerCase())>=0
|| hero.title.toLowerCase().indexOf(value.toLowerCase())>=0);
}
tempVer = '';
getNewVersion(ver: string){
// 重新获取英雄版本
this.tempVer = ver;
if(this.tempVer!='')
// 获取英雄列表json
this.http.get('/' + this.tempVer + '/herolist.json').toPromise()
.then((res:Response)=>{
if(JSON.parse(res.text()).version == this.tempVer){
this.heroDataList = [];
for (var key in JSON.parse(res.text()).keys) {
var heroIdTmp = JSON.parse(res.text()).keys[key];
this.heroDataList.push(
JSON.parse(res.text()).data[heroIdTmp]
);
this.bakHeroDataList.push(
JSON.parse(res.text()).data[heroIdTmp]
);
}
for (var i = this.heroDataList.length - 1; i >= 0; i--) {
this.heroDataList[i].tags = this.heroTypeEC2C(this.heroDataList[i].tags);
this.bakHeroDataList[i].tags = this.heroTypeEC2C(this.bakHeroDataList[i].tags);
}
this.heroDataTypeList = this.heroDataList;
this.genFight();
this.curVer = ver;
this.heroTypeCCur = '所有';
this.heroFilterName.nativeElement.value = '';
}
}).catch((error: Response | any)=>{
alert('错误:找不到改版本信息');
return {};
});
} }

-----

中间效果图如下:

html模板制作:

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

抓取数据:

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

数据:

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

用angularjs2 绑定数据后:

首页:

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

列表:

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

详细:

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

检索:

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

没数据时:

[nodejs,expressjs,angularjs2] LOL英雄列表数据抓取及查询显示应用

转载请标明出处:cnblogs.com/wangxinsheng
@望星辰

全部源码地址:

http://download.csdn.net/user/wangxsh42

http://download.csdn.net/detail/wangxsh42/9737390