|
@@ -1,1275 +0,0 @@
|
|
|
-window.Tracker = window.Tracker || {};
|
|
|
-
|
|
|
-Tracker.View = (function( window ){
|
|
|
- var global, host, location, push, join, version;
|
|
|
-
|
|
|
- version = "1.8.9";
|
|
|
- global = window;
|
|
|
- host = global.document;
|
|
|
- location = global.location;
|
|
|
-
|
|
|
- var View = function(){
|
|
|
- return {
|
|
|
- templates: {
|
|
|
- url: Tracker.Util.tmpl( "<a href='<%= url %>' target='_blank'><%= url %></a>" ),
|
|
|
-
|
|
|
- frameset: Tracker.Util.tmpl( [
|
|
|
- "<!DOCTYPE html>",
|
|
|
- "<html>",
|
|
|
- "<head>",
|
|
|
- "<meta charset='<%= charset %>'>",
|
|
|
- "<meta name='description' content='fehelper-tracker-frame'>",
|
|
|
- "<title><%= title %></title>",
|
|
|
- "<style type='text/css'>",
|
|
|
- "html, body{ margin: 0; padding: 0; overflow: hidden; width: 100%; height: 100%; position: relative; }",
|
|
|
- ".fullness{ position: absolute; left: 0; right: 0; top: 0; bottom: 0; }",
|
|
|
- "#tracker_proxy {display:none;}",
|
|
|
- "#wrapper{}",
|
|
|
- "#tracker_controller_ct{ z-index: 10; }",
|
|
|
- "#tracker_page_ct{ top: 43px; z-index: 20; background-color: #fff; }",
|
|
|
- "body.control-power-mode #tracker_page_ct{ z-index: 0; }",
|
|
|
- "body.hidden-page-mode #tracker_page_ct{ display: none; }",
|
|
|
- "iframe{ border: 0; width: 100%; height: 100%; }",
|
|
|
- "</style>",
|
|
|
- "</head>",
|
|
|
- "<body>",
|
|
|
- "<div id='wrapper' class='fullness'>",
|
|
|
- "<div id='tracker_proxy'><input type=\"button\" id=\"btnTrackerProxy\"></div>",
|
|
|
- "<div id='tracker_controller_ct' class='fullness'><iframe src='about:blank' id='tracker_controller' name='tracker_controller' frameborder='no'></iframe></div>",
|
|
|
- "<div id='tracker_page_ct' class='fullness'><iframe src='<%= url %>' id='tracker_page' name='tracker_page' frameborder='no'></iframe></div>",
|
|
|
- "</div>",
|
|
|
- "</body>",
|
|
|
- "</html>"
|
|
|
- ].join( "" ) ),
|
|
|
-
|
|
|
- controllerPage: Tracker.Util.tmpl( [
|
|
|
- "<!DOCTYPE html PUBLIC '-//W3C//DTD XHTML 1.0 Frameset//EN' 'http://www.w3.org/TR/xhtml1/DTD/xhtml1-frameset.dtd'>",
|
|
|
- "<html>",
|
|
|
- "<head>",
|
|
|
- "<meta charset='<%= charset %>'>",
|
|
|
- "<meta name='author' content='dron'>",
|
|
|
- "<title>Tracker!</title>",
|
|
|
- "<link href='<%= trackerCss %>' type='text/css' rel='stylesheet' />",
|
|
|
- "</head>",
|
|
|
- "<body>",
|
|
|
- "<%= header %>",
|
|
|
- "<div class='main' id='main'>",
|
|
|
- "<ul id='pages' class='unstyled tab-content'>",
|
|
|
- "<% if( mode == 'embed' ){ %>",
|
|
|
- "<li class='tab-content-active target-web-page'></li>",
|
|
|
- "<% } %>",
|
|
|
- "<li class='<%= mode == 'embed' ? '' : 'tab-content-active' %>'>",
|
|
|
- "<%= codeList %>",
|
|
|
- "<%= codeDetail %>",
|
|
|
- "</li>",
|
|
|
- "</ul>",
|
|
|
- "</div>",
|
|
|
- "<script> window.readyState = 'done'; </script>",
|
|
|
- "</body>",
|
|
|
- "</html>"
|
|
|
- ].join( "" ) ),
|
|
|
-
|
|
|
- controllerTopbar: Tracker.Util.tmpl( [
|
|
|
- "<div id='loading' class='navbar'>",
|
|
|
- "<div class='navbar-inner'>",
|
|
|
- "<span>请稍等,收集中...</span>",
|
|
|
- "<span id='waitTime'></span>",
|
|
|
- "</div>",
|
|
|
- "</div>",
|
|
|
- "<div id='top-navbar' class='navbar'>",
|
|
|
- "<div class='navbar-inner'>",
|
|
|
- '<a href="http://www.baidufe.com/feheler" target="_blank" class="fe-icon pull-left" action="frame#close">',
|
|
|
- '<img src="' + chrome.runtime.getURL('/static/img/fe-16.png') + '" alt="FeHelper">',
|
|
|
- "FeHelper:",
|
|
|
- '</a>',
|
|
|
- "<span class='fe-title'>Js覆盖面检测</span>",
|
|
|
- "<ul id='top-nav' class='nav pull-left' data-target='pages'>",
|
|
|
- "<% if( mode == 'embed' ){ %>",
|
|
|
- "<li><a href='' onclick='return false'>当前网页</a></li>",
|
|
|
- "<li data-name='code-list' class='active'><a href='' onclick='return false'>代码列表</a></li>",
|
|
|
- "<% }else{ %>",
|
|
|
- "<li class='active' data-name='code-list'><a href='' onclick='return false'>代码列表</a></li>",
|
|
|
- "<% } %>",
|
|
|
- "</ul>",
|
|
|
- "<ul class='nav pull-right'>",
|
|
|
- "<li class='dropdown'>",
|
|
|
- "<a href='' onclick='return false;' class='dropdown-toggle' data-toggle='dropdown'>",
|
|
|
- "视图切换",
|
|
|
- "<b class='caret'></b>",
|
|
|
- "</a>",
|
|
|
- "<ul class='dropdown-menu'>",
|
|
|
- "<li><a id='window-mode-trigger' action='frame#toggle' href='#' onclick='return false;'>单窗口模式</a></li>",
|
|
|
- "<li><a action='frame#close' href='#' onclick='return false;'>关闭控制台</a></li>",
|
|
|
- "</ul>",
|
|
|
- "</li>",
|
|
|
- "<li><a href='http://www.baidufe.com/fehelper/feedback.html' target='_blank'>意见反馈</a></li>",
|
|
|
- "</ul>",
|
|
|
- "</div>",
|
|
|
- "</div>",
|
|
|
- ].join( "" ) ),
|
|
|
-
|
|
|
- controllerCodeList: Tracker.Util.tmpl( [
|
|
|
- "<table class='table compact-width'>",
|
|
|
- "<thead>",
|
|
|
- "<tr>",
|
|
|
- "<th width='<%= widthIndex %>'>#</th>",
|
|
|
- "<th width='<%= widthName %>'>名称</th>",
|
|
|
- "<th width='<%= widthType %>'>类型</th>",
|
|
|
- "<th width='<%= widthCover %>'>执行覆盖</th>",
|
|
|
- "<th width='<%= widthCoverLine %>'>执行行数</th>",
|
|
|
- "<th width='<%= widthLines %>'>总行数</th>",
|
|
|
- "<th width='<%= widthSize %>'>原始大小</th>",
|
|
|
- "<th width='<%= widthBSize %>'>解压大小</th>",
|
|
|
- "<th width='<%= widthLoadConsum %>'>加载耗时</th>",
|
|
|
- "<th width='<%= widthRunConsum %>'>运行耗时</th>",
|
|
|
- "<th width='<%= widthRError %>'>执行报错</th>",
|
|
|
- "<th width='<%= widthSError %>'>语法错误</th>",
|
|
|
- "<th width='<%= widthState %>'>状态</th>",
|
|
|
- "<th width='*'> </th>",
|
|
|
- "</tr>",
|
|
|
- "</thead>",
|
|
|
- "</table>",
|
|
|
- "<div id='list-codes' class='scrollable'>",
|
|
|
- "<table class='table table-striped table-hover table-condensed'>",
|
|
|
- "<colgroup>",
|
|
|
- "<col width='<%= widthIndex %>'>",
|
|
|
- "<col width='<%= widthName %>'>",
|
|
|
- "<col width='<%= widthType %>'>",
|
|
|
- "<col width='<%= widthCover %>'>",
|
|
|
- "<col width='<%= widthCoverLine %>'>",
|
|
|
- "<col width='<%= widthLines %>'>",
|
|
|
- "<col width='<%= widthSize %>'>",
|
|
|
- "<col width='<%= widthBSize %>'>",
|
|
|
- "<col width='<%= widthLoadConsum %>'>",
|
|
|
- "<col width='<%= widthRunConsum %>'>",
|
|
|
- "<col width='<%= widthRError %>'>",
|
|
|
- "<col width='<%= widthSError %>'>",
|
|
|
- "<col width='<%= widthState %>'>",
|
|
|
- "</colgroup>",
|
|
|
- "<tbody id='list-codes-tbody'>",
|
|
|
- "</tbody>",
|
|
|
- "</table>",
|
|
|
- "</div>"
|
|
|
- ].join( "" ) ),
|
|
|
-
|
|
|
- controllerCodeDetail: Tracker.Util.tmpl( [
|
|
|
- "<div id='code-detail' class='absolute'>",
|
|
|
- "<div class='code-toolbar clearfix'>",
|
|
|
- "<ul class='code-toolbar-inner'>",
|
|
|
- "<li class='close-button-like'><button class='close' action='code#close'>×</button></li>",
|
|
|
-
|
|
|
- "<li class='tab-like'>",
|
|
|
- "<ul id='code-detail-head' class='nav nav-tabs' data-target='code-detail-body'>",
|
|
|
- "<li class='active'><a href='' onclick='return false;'>代码</a></li>",
|
|
|
- "<li><a href='' onclick='return false;'>信息</a></li>",
|
|
|
- "</ul>",
|
|
|
- "</li>",
|
|
|
-
|
|
|
- "<li class='label-like right tab-desc tab-desc-0'>新活动</li>",
|
|
|
- "<li class='image-like right tab-desc tab-desc-0'><div class='hooking image'></div></li>",
|
|
|
- "<li class='label-like right tab-desc tab-desc-0'>未执行</li>",
|
|
|
- "<li class='image-like right tab-desc tab-desc-0'><div class='unarrive image'></div></li>",
|
|
|
- "<li class='label-like right tab-desc tab-desc-0'>已执行</li>",
|
|
|
- "<li class='image-like right tab-desc tab-desc-0'><div class='arrive image'></div></li>",
|
|
|
- "<li class='label-like right tab-desc tab-desc-0'>图例:</li>",
|
|
|
- "</ul>",
|
|
|
- "</div>",
|
|
|
- "<ul class='unstyled tab-content' id='code-detail-body'>",
|
|
|
- "<li class='tab-content-active'>",
|
|
|
- "<div id='code-content' class='relative scrollable'></div>",
|
|
|
- "</li>",
|
|
|
- "<li class='scrollable'>",
|
|
|
- "<div id='code-info'></div>",
|
|
|
- "</li>",
|
|
|
- "</ul>",
|
|
|
- "</div>"
|
|
|
- ].join( "" ) ),
|
|
|
-
|
|
|
- controllerCodeInfo: Tracker.Util.tmpl( [
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>来源</dt>",
|
|
|
- "<dd><%= fileName %></dd>",
|
|
|
- "</dl>",
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>类型</dt>",
|
|
|
- "<dd><%= type %></dd>",
|
|
|
- "</dl>",
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>执行覆盖率</dt>",
|
|
|
- "<dd><%= rate %></dd>",
|
|
|
- "</dl>",
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>执行行数</dt>",
|
|
|
- "<dd><%= arriveRowsCount %></dd>",
|
|
|
- "</dl>",
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>总行数</dt>",
|
|
|
- "<dd><%= rowsCount %></dd>",
|
|
|
- "</dl>",
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>原始大小</dt>",
|
|
|
- "<dd><%= size %></dd>",
|
|
|
- "</dl>",
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>解压大小</dt>",
|
|
|
- "<dd><%= bsize %></dd>",
|
|
|
- "</dl>",
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>加载耗时</dt>",
|
|
|
- "<dd><%= loadConsum %></dd>",
|
|
|
- "</dl>",
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>运行耗时</dt>",
|
|
|
- "<dd><%= runConsum %></dd>",
|
|
|
- "</dl>",
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>执行报错</dt>",
|
|
|
- "<dd><%= rerror %></dd>",
|
|
|
- "</dl>",
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>语法错误</dt>",
|
|
|
- "<dd><%= serror %></dd>",
|
|
|
- "</dl>",
|
|
|
- "<dl class='group'>",
|
|
|
- "<dt>状态</dt>",
|
|
|
- "<dd><%= state %></dd>",
|
|
|
- "</dl>",
|
|
|
- ].join( "" ) ),
|
|
|
-
|
|
|
- codeListLine: Tracker.Util.tmpl( [
|
|
|
- "<tr data-code-id='<%= id %>'>",
|
|
|
- "<td><div class='ellipsisable' style='width: <%= widthIndex %>px;'><%= index %></div></td>",
|
|
|
- "<td><div class='ellipsisable' style='width: <%= widthName %>px;'><%= fileName %></div></td>",
|
|
|
- "<td><div class='ellipsisable' style='width: <%= widthType %>px;'><%= type %></div></td>",
|
|
|
- "<td><div id='code-<%= id %>-rate' class='ellipsisable' style='width: <%= widthCover %>px;'><%= rate %></div></td>",
|
|
|
- "<td><div id='code-<%= id %>-arriveRowsCount' class='ellipsisable' style='width: <%= widthCoverLine %>px;'><%= arriveRowsCount %></div></td>",
|
|
|
- "<td><div class='ellipsisable' style='width: <%= widthLines %>px;'><%= rowsCount %></div></td>",
|
|
|
- "<td><div class='ellipsisable' style='width: <%= widthSize %>px;'><%= size %></div></td>",
|
|
|
- "<td><div class='ellipsisable' style='width: <%= widthBSize %>px;'><%= bsize %></div></td>",
|
|
|
- "<td><div id='code-<%= id %>-loadConsum' class='ellipsisable' style='width: <%= widthLoadConsum %>px;'><%= loadConsum %></div></td>",
|
|
|
- "<td><div id='code-<%= id %>-runConsum' class='ellipsisable' style='width: <%= widthRunConsum %>px;'><%= runConsum %></div></td>",
|
|
|
- "<td><div id='code-<%= id %>-runErrors' class='ellipsisable' style='width: <%= widthRError %>px;'><%= rerror %></div></td>",
|
|
|
- "<td><div class='ellipsisable' style='width: <%= widthSError %>px;'><%= serror %></div></td>",
|
|
|
- "<td><div class='ellipsisable' style='width: <%= widthState %>px;'><%= state %></div></td>",
|
|
|
- "<td></td>",
|
|
|
- "</tr>"
|
|
|
- ].join( "" ) )
|
|
|
- },
|
|
|
-
|
|
|
- Loading: function(){
|
|
|
- var layer, span1, span2, animateTimer, count, progress, body;
|
|
|
-
|
|
|
- count = progress = 0;
|
|
|
- body = host.body;
|
|
|
-
|
|
|
- var create = function(){
|
|
|
- var span;
|
|
|
-
|
|
|
- layer = Tracker.Util.makeElement( "div", "position: fixed; padding: 30px; border: 1px solid rgba(255, 255, 255, .2); border-radius: 10px; background: #000; font-size: 20px; line-height: 20px; text-align: center; color: #fff; top: 50px; left: 50px; box-shadow: 0 0 5px #fff; z-index: 65535; font-family: 'Courier New', 'Heiti SC', 'Microsoft Yahei';" );
|
|
|
- layer.innerHTML = "正在分析网页 <span>...</span> <span>(0/0)</span>";
|
|
|
- body.appendChild( layer );
|
|
|
- host.documentElement.scrollTop = body.scrollTop = 0;
|
|
|
- span = layer.getElementsByTagName( "span" );
|
|
|
- span1 = span[0];
|
|
|
- span2 = span[1];
|
|
|
- };
|
|
|
-
|
|
|
- var animate = function(){
|
|
|
- var count, word, n, s, e;
|
|
|
-
|
|
|
- count = 0;
|
|
|
- word = "......";
|
|
|
- clearInterval( animateTimer );
|
|
|
- animateTimer = setInterval( function(){
|
|
|
- n = count % 7;
|
|
|
- s = word.substr( 0, n );
|
|
|
- e = word.substr( 0, 6 - n );
|
|
|
- span1.innerHTML = s + "<span style='color: #000;'>" +
|
|
|
- e + "</span>";
|
|
|
- count += 1;
|
|
|
- }, 100 );
|
|
|
- };
|
|
|
-
|
|
|
- return {
|
|
|
- show: function(){
|
|
|
- if( !layer )
|
|
|
- create();
|
|
|
- else
|
|
|
- layer.style.display = "block";
|
|
|
-
|
|
|
- animate();
|
|
|
- },
|
|
|
-
|
|
|
- hide: function(){
|
|
|
- if( layer )
|
|
|
- layer.style.display = "none";
|
|
|
-
|
|
|
- clearInterval( animateTimer );
|
|
|
- },
|
|
|
-
|
|
|
- text: function( text ){
|
|
|
- var me, pm;
|
|
|
-
|
|
|
- if( layer )
|
|
|
- layer.innerHTML = text;
|
|
|
-
|
|
|
- me = this;
|
|
|
- pm = new Tracker.Promise();
|
|
|
- clearInterval( animateTimer );
|
|
|
- setTimeout( function(){
|
|
|
- me.hide();
|
|
|
- pm.resolve();
|
|
|
- }, 2e3 );
|
|
|
-
|
|
|
- return pm;
|
|
|
- },
|
|
|
-
|
|
|
- addCount: function(){
|
|
|
- count ++;
|
|
|
- span2.innerHTML = "(" + ( progress / count * 100 ).toFixed( 2 ) + "%)";
|
|
|
- },
|
|
|
-
|
|
|
- addProgress: function(){
|
|
|
- progress ++;
|
|
|
- span2.innerHTML = "(" + ( progress / count * 100 ).toFixed( 2 ) + "%)";
|
|
|
- }
|
|
|
- }
|
|
|
- }(),
|
|
|
-
|
|
|
- ControlFrame: function(){
|
|
|
- var document = window.document, controlWindow, hasCreateEmbeded = false,
|
|
|
- currentMode = "embed", pageBuilder, controllerBuilder;
|
|
|
-
|
|
|
- var config = {
|
|
|
- windowWidth: 800,
|
|
|
- windowHeight: 600
|
|
|
- };
|
|
|
-
|
|
|
- var lookupForWindowReady = function( target ){
|
|
|
- var pm, timer, timer2, now, timeout, clear;
|
|
|
-
|
|
|
- pm = new Tracker.Promise();
|
|
|
- timeout = 5000;
|
|
|
- now = Tracker.Util.time();
|
|
|
-
|
|
|
- clear = function(){
|
|
|
- clearInterval( timer );
|
|
|
- clearTimeout( timer2 );
|
|
|
- };
|
|
|
-
|
|
|
- timer = setInterval( function(){
|
|
|
- if( target.readyState == "complete" ){
|
|
|
- clear();
|
|
|
- pm.resolve();
|
|
|
- }
|
|
|
- }, 10 );
|
|
|
-
|
|
|
- timer2 = setTimeout( function(){
|
|
|
- pm.reject();
|
|
|
- }, timeout );
|
|
|
-
|
|
|
- return pm;
|
|
|
- };
|
|
|
-
|
|
|
- return Tracker.Event.bind( {
|
|
|
- state: "preshow",
|
|
|
-
|
|
|
- pageBuilder: function( fn ){
|
|
|
- pageBuilder = fn;
|
|
|
- },
|
|
|
-
|
|
|
- controllerBuilder: function( fn ){
|
|
|
- controllerBuilder = fn;
|
|
|
- },
|
|
|
-
|
|
|
- show: function(){
|
|
|
- var controller, page, window;
|
|
|
-
|
|
|
- if( currentMode === "embed" ){
|
|
|
- controller = document.getElementById( "tracker_controller_ct" ),
|
|
|
- page = document.getElementById( "tracker_page_ct" ),
|
|
|
- controller.style.display = "block",
|
|
|
- page.style.top = "";
|
|
|
- }else if( currentMode === "window" ){
|
|
|
- window = this.getWindow( "tracker_controller" );
|
|
|
-
|
|
|
- if( window && !window.closed )
|
|
|
- window.focus();
|
|
|
- else
|
|
|
- this.createWindow();
|
|
|
- }
|
|
|
-
|
|
|
- this.state = "show";
|
|
|
- this.fire( "show" );
|
|
|
- },
|
|
|
-
|
|
|
- hide: function(){
|
|
|
- var controller, page;
|
|
|
-
|
|
|
- if( currentMode === "embed" )
|
|
|
- controller = document.getElementById( "tracker_controller_ct" ),
|
|
|
- page = document.getElementById( "tracker_page_ct" ),
|
|
|
- controller.style.display = "none",
|
|
|
- page.style.top = "0";
|
|
|
- else if( currentMode === "window" )
|
|
|
- controlWindow.close();
|
|
|
-
|
|
|
- this.state = "hide";
|
|
|
- this.fire( "hide" );
|
|
|
- },
|
|
|
-
|
|
|
- toggleMode: function(){
|
|
|
- this.removeControllerFrame();
|
|
|
-
|
|
|
- if( currentMode === "embed" )
|
|
|
- currentMode = "window",
|
|
|
- this.createWindow();
|
|
|
- else if( currentMode === "window" )
|
|
|
- currentMode = "embed",
|
|
|
- this.createEmbed(),
|
|
|
- this.show();
|
|
|
- },
|
|
|
-
|
|
|
- getMode: function(){
|
|
|
- return currentMode;
|
|
|
- },
|
|
|
-
|
|
|
- getWindow: function( name ){
|
|
|
- // name: tracker_main | tracker_page | tracker_controller
|
|
|
- var w;
|
|
|
- if( !arguments.length || name === "tracker_main" )
|
|
|
- return window;
|
|
|
-
|
|
|
- if( currentMode === "window" && name === "tracker_controller" )
|
|
|
- return controlWindow;
|
|
|
- else if( w = window.frames[ name ] )
|
|
|
- return window.document.getElementById( name ).contentWindow;
|
|
|
- },
|
|
|
-
|
|
|
- // privates
|
|
|
- createEmbed: function(){
|
|
|
- var page, controller;
|
|
|
-
|
|
|
- Tracker.Promise.when(
|
|
|
- hasCreateEmbeded ? [ controllerBuilder( "embed" ) ] :
|
|
|
- [ pageBuilder(), controllerBuilder( "embed" ) ]
|
|
|
- ).then( Tracker.Util.bind( function( pageHtml, controllerHtml ){
|
|
|
- if( !controllerHtml )
|
|
|
- controllerHtml = pageHtml,
|
|
|
- pageHtml = null;
|
|
|
-
|
|
|
- if( pageHtml ){
|
|
|
- window.name = "tracker_main";
|
|
|
-
|
|
|
- this.write( "tracker_main", View.templates.frameset( {
|
|
|
- url: location.href,
|
|
|
- title: document.title,
|
|
|
- charset: document.characterSet || "utf-8"
|
|
|
- } ) );
|
|
|
-
|
|
|
- this.write( "tracker_page", pageHtml );
|
|
|
- var pageWin = this.getWindow( "tracker_page" );
|
|
|
-
|
|
|
- // 整个页面都加载完成了,可以开始script inject了
|
|
|
- this.fire('pageLoad',window,pageWin);
|
|
|
- }
|
|
|
-
|
|
|
- this.write( "tracker_controller", controllerHtml );
|
|
|
- controller = this.getWindow( "tracker_controller" );
|
|
|
-
|
|
|
- lookupForWindowReady( controller.document ).then( Tracker.Util.bind( function(){
|
|
|
- this.fire( "controllerLoad", controller, controller.document );
|
|
|
- }, this ) );
|
|
|
- }, this ) );
|
|
|
-
|
|
|
- hasCreateEmbeded = true;
|
|
|
- },
|
|
|
-
|
|
|
- createWindow: function( conf ){
|
|
|
- var width = screen.width - 200, height = screen.height - 200,
|
|
|
- left = 100, top = 100, controller;
|
|
|
-
|
|
|
- controlWindow = window.open( "about:blank", "", "width=" + width +
|
|
|
- ", height=" + height + ", left=" + left + ", top=" + top +
|
|
|
- ", toolbar=no, menubar=no, resizable=yes, status=no, " +
|
|
|
- "location=no, scrollbars=yes" );
|
|
|
-
|
|
|
- controllerBuilder( "window" ).then( Tracker.Util.bind( function( html ){
|
|
|
- this.write( "tracker_controller", html );
|
|
|
- controller = this.getWindow( "tracker_controller" );
|
|
|
-
|
|
|
- lookupForWindowReady( controller.document ).then( Tracker.Util.bind( function(){
|
|
|
- this.fire( "controllerLoad", controller, controller.document );
|
|
|
- }, this ) );
|
|
|
- }, this ) );
|
|
|
- },
|
|
|
-
|
|
|
- removeControllerFrame: function(){
|
|
|
- this.hide();
|
|
|
-
|
|
|
- if( currentMode === "embed" )
|
|
|
- this.write( "tracker_controller", "about:blank" );
|
|
|
- else if( currentMode === "window" )
|
|
|
- controlWindow = null;
|
|
|
- },
|
|
|
-
|
|
|
- write: function( name, content ){
|
|
|
- var document, i, l, t, timer, write;
|
|
|
-
|
|
|
- document = this.getWindow( name ).document;
|
|
|
- document.open( "text/html", "replace" );
|
|
|
-
|
|
|
- if( name == "tracker_page" ){
|
|
|
- i = 0;
|
|
|
- t = 10240; // 10k/ms
|
|
|
-
|
|
|
- l = content.length;
|
|
|
-
|
|
|
- write = function(){
|
|
|
- c = content.substr( i, t );
|
|
|
- document.write( c );
|
|
|
- i += t;
|
|
|
-
|
|
|
- if( i > l )
|
|
|
- document.close(),
|
|
|
- clearInterval( timer );
|
|
|
- };
|
|
|
-
|
|
|
- timer = setInterval( write, 1 );
|
|
|
- }else{
|
|
|
- document.write( content );
|
|
|
- document.close();
|
|
|
- }
|
|
|
- }
|
|
|
- } );
|
|
|
- }(),
|
|
|
-
|
|
|
- ControlPanel: function(){
|
|
|
- var actions, window, document, currentSelectedCode, updateInterval, codeEl,
|
|
|
- codeIndex;
|
|
|
-
|
|
|
- actions = {};
|
|
|
- codeIndex = 0;
|
|
|
-
|
|
|
- var rate = function( code ){
|
|
|
- var r, c;
|
|
|
-
|
|
|
- r = code.arriveRowsCount / code.rowsCount * 100 || 0;
|
|
|
- c = r == 0 ? "stress" : "";
|
|
|
-
|
|
|
- return "<span class='" + c + "'>" + r.toFixed( 1 ) + "%</span>";
|
|
|
- };
|
|
|
-
|
|
|
- var size = function( number ){
|
|
|
- return ( number / 1024 ).toFixed( 1 ) + "k";
|
|
|
- };
|
|
|
-
|
|
|
- var yesno = function( bool ){
|
|
|
- return ( bool && bool.length ) ?
|
|
|
- "<span class='stress'>是<span>" : "否";
|
|
|
- };
|
|
|
-
|
|
|
- var state = function( state ){
|
|
|
- switch( state ){
|
|
|
- case "normal":
|
|
|
- return "正常";
|
|
|
- case "timeout":
|
|
|
- return "<span class='stress'>超时</span>";
|
|
|
- case "empty":
|
|
|
- return "<span class='stress'>无内容</span>";
|
|
|
- }
|
|
|
- };
|
|
|
-
|
|
|
- var type = function( code ){
|
|
|
- switch( code.type ){
|
|
|
- case "embed":
|
|
|
- return "内嵌";
|
|
|
- case "link":
|
|
|
- return "文件链接";
|
|
|
- case "append":
|
|
|
- return "动态插入";
|
|
|
- };
|
|
|
- };
|
|
|
-
|
|
|
- var time = function( time, s ){
|
|
|
- if( time == -1 )
|
|
|
- return "-1";
|
|
|
- if( !s )
|
|
|
- return time + "ms";
|
|
|
- else
|
|
|
- return ( time / 1000 ).toFixed( 2 ) + "s";
|
|
|
- };
|
|
|
-
|
|
|
- var width = function(){
|
|
|
- var mapping, offsets;
|
|
|
-
|
|
|
- mapping = {
|
|
|
- index: 30, name: 220, type: 90, cover: 60, "cover-line": 60, lines: 60,
|
|
|
- size: 60, bsize: 60, rerror: 60, serror: 60, state: 50, loadConsum: 60,
|
|
|
- runConsum: 60
|
|
|
- };
|
|
|
-
|
|
|
- offsets = {
|
|
|
- };
|
|
|
-
|
|
|
- return function( name, type ){
|
|
|
- return mapping[ name ] + ( offsets[ type ] || 0 );
|
|
|
- };
|
|
|
- }();
|
|
|
-
|
|
|
- var withWidths = function( data ){
|
|
|
- var widths = {
|
|
|
- widthIndex: width( "index" ),
|
|
|
- widthName: width( "name" ),
|
|
|
- widthType: width( "type" ),
|
|
|
- widthCover: width( "cover" ),
|
|
|
- widthCoverLine: width( "cover-line" ),
|
|
|
- widthLines: width( "lines" ),
|
|
|
- widthSize: width( "size" ),
|
|
|
- widthBSize: width( "bsize" ),
|
|
|
- widthRError: width( "rerror" ),
|
|
|
- widthSError: width( "serror" ),
|
|
|
- widthState: width( "state" ),
|
|
|
- widthLoadConsum: width( "loadConsum" ),
|
|
|
- widthRunConsum: width( "runConsum" )
|
|
|
- };
|
|
|
-
|
|
|
- if( !data )
|
|
|
- return widths;
|
|
|
-
|
|
|
- for( var i in widths )
|
|
|
- data[ i ] = widths[ i ];
|
|
|
-
|
|
|
- return data;
|
|
|
- };
|
|
|
-
|
|
|
- var codeTemplate = function( code ){
|
|
|
- return View.templates.codeListLine( withWidths( {
|
|
|
- id: code.id,
|
|
|
-
|
|
|
- index: ++ codeIndex,
|
|
|
- fileName: code.fileName,
|
|
|
- type: type( code ),
|
|
|
- rate: rate( code ),
|
|
|
- arriveRowsCount: code.arriveRowsCount,
|
|
|
- rowsCount: code.rowsCount,
|
|
|
- size: size( code.size ),
|
|
|
- bsize: size( code.beautifySize ),
|
|
|
- rerror: yesno( code.runErrors ),
|
|
|
- serror: yesno( code.syntaxErrors ),
|
|
|
- state: state( code.state ),
|
|
|
- runConsum: time( code.runConsum ),
|
|
|
- loadConsum: time( code.loadConsum )
|
|
|
- } ) );
|
|
|
- };
|
|
|
-
|
|
|
- var codeListTemplate = function( codeList ){
|
|
|
- var htmls;
|
|
|
-
|
|
|
- htmls = [];
|
|
|
-
|
|
|
- if( codeList.length ){
|
|
|
- Tracker.Util.forEach( codeList, function( code, index ){
|
|
|
- htmls[ index ] = codeTemplate( code );
|
|
|
- } );
|
|
|
-
|
|
|
- return htmls.join( "" );
|
|
|
- }else{
|
|
|
- return "<tr><td colspan='20'><div class='none'>该网页没有任何JS代码</div></td></tr>";
|
|
|
- }
|
|
|
- };
|
|
|
-
|
|
|
- var makeCodeTr = function( code ){
|
|
|
- var layer, html;
|
|
|
-
|
|
|
- layer = document.createElement( "tbody" );
|
|
|
- html = codeTemplate( code );
|
|
|
- layer.innerHTML = html;
|
|
|
-
|
|
|
- return layer.firstChild;
|
|
|
- };
|
|
|
-
|
|
|
- var asnyShowCode = function(){
|
|
|
- var timer, timeout, interval, prepare, partCount, nowIndex, init,
|
|
|
- currentDisposeLines, gutterEl, linesEl, regx1, regx2, ckeyIdRegx, result,
|
|
|
- linesCount, h1, h2, focusOnFlag, focusOnFlagTarget;
|
|
|
-
|
|
|
- timeout = 1;
|
|
|
- partCount = 100;
|
|
|
- regx1 = /\x00/g;
|
|
|
- regx2 = /\x01/g;
|
|
|
- ckeyIdRegx = /id=ckey-(\d+)/g;
|
|
|
- h1 = [];
|
|
|
- h2 = [];
|
|
|
-
|
|
|
- init = function(){
|
|
|
- nowIndex = 0;
|
|
|
- linesCount = 0;
|
|
|
- window.clearInterval( timer );
|
|
|
- };
|
|
|
-
|
|
|
- prepare = function(){
|
|
|
- var innerElId = Tracker.Util.id();
|
|
|
- var gutterId = Tracker.Util.id();
|
|
|
- var linesId = Tracker.Util.id();
|
|
|
-
|
|
|
- codeEl.innerHTML = "<div id='" + innerElId + "' class='block clearfix' " +
|
|
|
- "style='height: " + ( linesCount * 20 + 10 ) + "px;'>" +
|
|
|
- "<div id='" + gutterId + "' class='gutter'></div>" +
|
|
|
- "<div id='" + linesId + "' class='lines'></div></div>";
|
|
|
- codeEl.scrollTop = 0;
|
|
|
-
|
|
|
- gutterEl = document.getElementById( gutterId );
|
|
|
- linesEl = document.getElementById( linesId );
|
|
|
- };
|
|
|
-
|
|
|
- interval = function(){
|
|
|
- var t, p1, p2, a;
|
|
|
-
|
|
|
- h1.length = h2.length = 0;
|
|
|
-
|
|
|
- for( var i = 0; i < partCount; i ++ ){
|
|
|
- if( nowIndex >= linesCount ){
|
|
|
- init();
|
|
|
- break;
|
|
|
- }
|
|
|
-
|
|
|
- t = Tracker.Util.html( currentDisposeLines[ nowIndex ] ).replace( regx1, "<" )
|
|
|
- .replace( regx2, ">" );
|
|
|
-
|
|
|
- t = t.replace( ckeyIdRegx, function( all, id ){
|
|
|
- a = Tracker.StatusPool.arrivedSnippetGet( id );
|
|
|
-
|
|
|
- if( a & 2 )
|
|
|
- a = 2;
|
|
|
- else if( a & 1 )
|
|
|
- a = 1;
|
|
|
-
|
|
|
- if( focusOnFlag && !focusOnFlagTarget && focusOnFlag == a ){
|
|
|
- focusOnFlagTarget = id;
|
|
|
- focusOnFlag = 0;
|
|
|
- }
|
|
|
-
|
|
|
- return a ? all + " class='arrive arrive-" + a + "'" : all;
|
|
|
- } );
|
|
|
-
|
|
|
- h1.push( Tracker.Util.tag( nowIndex + 1, "pre" ) );
|
|
|
- h2.push( Tracker.Util.tag( t || " ", "pre" ) );
|
|
|
-
|
|
|
- nowIndex ++;
|
|
|
- }
|
|
|
-
|
|
|
- p1 = document.createElement( "div" );
|
|
|
- p2 = document.createElement( "div" );
|
|
|
-
|
|
|
- p1.innerHTML = h1.join( "" );
|
|
|
- p2.innerHTML = h2.join( "" );
|
|
|
-
|
|
|
- gutterEl.appendChild( p1 );
|
|
|
- linesEl.appendChild( p2 );
|
|
|
-
|
|
|
- if( focusOnFlagTarget ){
|
|
|
- document.getElementById( "ckey-" + focusOnFlagTarget ).scrollIntoView();
|
|
|
- focusOnFlagTarget = undefined;
|
|
|
- }
|
|
|
- };
|
|
|
-
|
|
|
- result = function( code, _focusOnFlag ){
|
|
|
- init();
|
|
|
-
|
|
|
- focusOnFlag = _focusOnFlag;
|
|
|
-
|
|
|
- if( code.state == "empty" ){
|
|
|
- codeEl.innerHTML = "<div class='empty-code'>" +
|
|
|
- "内容为空</div>"; // 内容为空
|
|
|
- }else if( code.state == "timeout" ){
|
|
|
- codeEl.innerHTML = "<div class='timeout-code'>" +
|
|
|
- "解析超时</div>"; // 解析超时
|
|
|
- }else{
|
|
|
- currentDisposeLines = code.linesViewHtml;
|
|
|
- linesCount = currentDisposeLines.length;
|
|
|
- prepare();
|
|
|
- timer = window.setInterval( interval, timeout );
|
|
|
- }
|
|
|
- };
|
|
|
-
|
|
|
- result.clear = init;
|
|
|
-
|
|
|
- return result;
|
|
|
- }();
|
|
|
-
|
|
|
- var setupBootstrapPatch = function(){
|
|
|
-
|
|
|
- var setupDropdownMenu = function(){
|
|
|
- var lastOpen;
|
|
|
-
|
|
|
- var setup = function( el ){
|
|
|
-
|
|
|
- var dropdownMenu = el.querySelector( ".dropdown-menu" );
|
|
|
-
|
|
|
- Tracker.Event.add( dropdownMenu, "click", function( e ){
|
|
|
- Tracker.Util.removeClass( el, "open" );
|
|
|
- lastOpen = null;
|
|
|
- e.stopPropagation();
|
|
|
- Tracker.TrackerGlobalEvent.fire( "bootstrap: dropdown.close" );
|
|
|
- } );
|
|
|
-
|
|
|
- Tracker.Event.add( el, "click", function( e ){
|
|
|
- Tracker.Util.addClass( el, "open" );
|
|
|
- if( lastOpen && lastOpen != el )
|
|
|
- Tracker.Util.removeClass( lastOpen, "open" );
|
|
|
- lastOpen = el;
|
|
|
- Tracker.TrackerGlobalEvent.fire( "bootstrap: dropdown.open" );
|
|
|
- e.stopPropagation();
|
|
|
- } );
|
|
|
- };
|
|
|
-
|
|
|
- return function(){
|
|
|
- var dropdowns = document.querySelectorAll( ".dropdown" );
|
|
|
- for( var i = 0, l = dropdowns.length; i < l; i ++ )
|
|
|
- setup( dropdowns[ i ] );
|
|
|
- Tracker.Event.add( document, "click", function(){
|
|
|
- var found;
|
|
|
-
|
|
|
- for( var i = 0, l = dropdowns.length; i < l; i ++ )
|
|
|
- if( Tracker.Util.hasClass( dropdowns[ i ], "open" ) )
|
|
|
- found = true,
|
|
|
- Tracker.Util.removeClass( dropdowns[ i ], "open" );
|
|
|
-
|
|
|
- if( found )
|
|
|
- Tracker.TrackerGlobalEvent.fire( "bootstrap: dropdown.close" );
|
|
|
- } );
|
|
|
- }
|
|
|
- }();
|
|
|
-
|
|
|
- var setupModalDialog = function(){
|
|
|
-
|
|
|
- var open = function( modal ){
|
|
|
- return function(){
|
|
|
- modal.style.display = "block";
|
|
|
- Tracker.TrackerGlobalEvent.fire( "bootstrap: dialog.open" );
|
|
|
- }
|
|
|
- };
|
|
|
-
|
|
|
- var close = function( modal ){
|
|
|
- return function(){
|
|
|
- modal.style.display = "none";
|
|
|
- Tracker.TrackerGlobalEvent.fire( "bootstrap: dialog.close" );
|
|
|
- }
|
|
|
- };
|
|
|
-
|
|
|
- var setup = function( modal ){
|
|
|
- var closeBtns = modal.querySelectorAll( ".modal-header .close, .modal-footer .btn" );
|
|
|
- var fclose = close( modal );
|
|
|
- var fopen = open( modal );
|
|
|
- for( var i = 0, l = closeBtns.length; i < l; i ++ )
|
|
|
- Tracker.Event.add( closeBtns[ i ], "click", fclose );
|
|
|
- modal.open = fopen;
|
|
|
- };
|
|
|
-
|
|
|
- return function(){
|
|
|
- var modals = document.querySelectorAll( ".modal" );
|
|
|
- for( var i = 0, l = modals.length; i < l; i ++ )
|
|
|
- setup( modals[ i ] );
|
|
|
- }
|
|
|
- }();
|
|
|
-
|
|
|
- var setupTab = function(){
|
|
|
-
|
|
|
- var setup = function( tab ){
|
|
|
- var target = tab.getAttribute( "data-target" );
|
|
|
-
|
|
|
- if( !target )
|
|
|
- return ;
|
|
|
-
|
|
|
- target = document.getElementById( target );
|
|
|
-
|
|
|
- var heads = tab.childNodes;
|
|
|
- var bodys = target.childNodes;
|
|
|
-
|
|
|
- tab.active = function( index ){
|
|
|
- Tracker.Util.removeClass( heads[ tab.actived ], "active" );
|
|
|
- Tracker.Util.removeClass( bodys[ tab.actived ], "tab-content-active" );
|
|
|
-
|
|
|
- Tracker.Util.addClass( heads[ index ], "active" );
|
|
|
- Tracker.Util.addClass( bodys[ index ], "tab-content-active" );
|
|
|
-
|
|
|
- tab.actived = index;
|
|
|
- tab.tabEvent.fire( "active",
|
|
|
- index, heads[ index ].getAttribute( "data-name" ) );
|
|
|
- };
|
|
|
-
|
|
|
- Tracker.Event.add( tab, "click", function( e ){
|
|
|
- var li;
|
|
|
-
|
|
|
- li = Tracker.Util.findParent( e.target, "li", this );
|
|
|
-
|
|
|
- Tracker.Util.forEach( this.childNodes, function( l, index ){
|
|
|
- if( li === l ){
|
|
|
- if( tab.actived == index )
|
|
|
- return ;
|
|
|
- tab.active( index );
|
|
|
- }
|
|
|
- } );
|
|
|
- } );
|
|
|
-
|
|
|
- tab.tabEvent = Tracker.Event.bind();
|
|
|
- tab.actived = 0;
|
|
|
- };
|
|
|
-
|
|
|
- return function(){
|
|
|
- var tabs = document.querySelectorAll( ".nav" );
|
|
|
- for( var i = tabs.length - 1; i >= 0; i -- )
|
|
|
- setup( tabs[ i ] );
|
|
|
- };
|
|
|
- }();
|
|
|
-
|
|
|
- return function(){
|
|
|
- setupDropdownMenu();
|
|
|
- setupModalDialog();
|
|
|
- setupTab();
|
|
|
- };
|
|
|
- }();
|
|
|
-
|
|
|
- var autoUpdateCodeFn = function(){
|
|
|
- Tracker.CodeList.each( function( code ){
|
|
|
- if( !code.lastUpdate || code.lastUpdate < code.lastModified )
|
|
|
- View.ControlPanel.updateCode( code );
|
|
|
- } );
|
|
|
- };
|
|
|
-
|
|
|
- return Tracker.Event.bind( {
|
|
|
- bindWindow: function( win ){
|
|
|
- window = win;
|
|
|
- document = window.document;
|
|
|
- codeEl = document.getElementById( "code-content" );
|
|
|
- },
|
|
|
-
|
|
|
- addCode: function( code ){
|
|
|
- var tbody, tr, index;
|
|
|
-
|
|
|
- if( !document )
|
|
|
- return ;
|
|
|
-
|
|
|
- tbody = document.getElementById( "list-codes-tbody" );
|
|
|
- index = Tracker.CodeList.count() - 1;
|
|
|
-
|
|
|
- if( code instanceof Array ){
|
|
|
- tbody.innerHTML = codeListTemplate( code );
|
|
|
- }else if( code instanceof Tracker.Code ){
|
|
|
- code.onReady( function(){
|
|
|
- // code.index = index;
|
|
|
- tr = makeCodeTr( code );
|
|
|
- tbody.appendChild( tr );
|
|
|
- } );
|
|
|
- }
|
|
|
- },
|
|
|
-
|
|
|
- showCodeDetail: function( id, focusOnFlag ){
|
|
|
- var codeDetailHeadTab, actived;
|
|
|
-
|
|
|
- codeDetailHeadTab = document.getElementById( "code-detail-head" );
|
|
|
- actived = codeDetailHeadTab.actived;
|
|
|
-
|
|
|
- currentSelectedCode = id || null;
|
|
|
-
|
|
|
- document.getElementById( "code-detail" ).style.display =
|
|
|
- id ? "block" : "none";
|
|
|
-
|
|
|
- if( id ){
|
|
|
- if( actived === 0 )
|
|
|
- this.showCode( id, focusOnFlag );
|
|
|
- else if( actived == 1 )
|
|
|
- this.showCodeInfo( id, focusOnFlag );
|
|
|
-
|
|
|
- var elementListCodes = document.getElementById( "list-codes" );
|
|
|
- var trs = elementListCodes.querySelectorAll( "tr" );
|
|
|
-
|
|
|
- Tracker.Util.forEach( trs, function( tr ){
|
|
|
- if( tr.getAttribute( "data-code-id" ) == id )
|
|
|
- Tracker.Util.addClass( tr, "info" );
|
|
|
- else
|
|
|
- Tracker.Util.removeClass( tr, "info" );
|
|
|
- } );
|
|
|
- }
|
|
|
- },
|
|
|
-
|
|
|
- showCode: function( id, focusOnFlag ){
|
|
|
- if( id ){
|
|
|
- code = Tracker.CodeList.get( id );
|
|
|
- asnyShowCode( code, focusOnFlag );
|
|
|
- }
|
|
|
- },
|
|
|
-
|
|
|
- showCodeInfo: function( id, focusOnFlag ){
|
|
|
- var elementCodeInfo, code;
|
|
|
-
|
|
|
- elementCodeInfo = document.getElementById( "code-info" );
|
|
|
- code = Tracker.CodeList.get( id );
|
|
|
-
|
|
|
- elementCodeInfo.innerHTML = View.templates.controllerCodeInfo( {
|
|
|
- // id: code.id,
|
|
|
- // index: ++ codeIndex,
|
|
|
- fileName: code.fullUrl ?
|
|
|
- View.templates.url( { url: code.fullUrl } ) :
|
|
|
- "来自页面",
|
|
|
- type: type( code ),
|
|
|
- rate: rate( code ),
|
|
|
- arriveRowsCount: code.arriveRowsCount,
|
|
|
- rowsCount: code.rowsCount,
|
|
|
- size: size( code.size ),
|
|
|
- bsize: size( code.beautifySize ),
|
|
|
- rerror: yesno( code.runErrors ),
|
|
|
- serror: yesno( code.syntaxErrors ),
|
|
|
- state: state( code.state ),
|
|
|
- loadConsum: time( code.loadConsum ),
|
|
|
- runConsum: time( code.runConsum )
|
|
|
- } );
|
|
|
- },
|
|
|
-
|
|
|
- updateCode: function( code ){
|
|
|
- if( currentSelectedCode == code.id )
|
|
|
- this.showCodeDetail( code.id );
|
|
|
-
|
|
|
- var rateEl, arriveRowsCountEl, runErrorsEl, runConsumEl, loadConsumEl;
|
|
|
-
|
|
|
- rateEl = document.getElementById( "code-" + code.id + "-rate" );
|
|
|
- arriveRowsCountEl = document.getElementById( "code-" + code.id +
|
|
|
- "-arriveRowsCount" );
|
|
|
- runErrorsEl = document.getElementById( "code-" + code.id + "-runErrors" );
|
|
|
- runConsumEl = document.getElementById( "code-" + code.id + "-runConsum" );
|
|
|
- loadConsumEl = document.getElementById( "code-" + code.id + "-loadConsum" );
|
|
|
-
|
|
|
- if( !rateEl )
|
|
|
- return;
|
|
|
-
|
|
|
- rateEl.innerHTML = rate( code );
|
|
|
- arriveRowsCountEl.innerHTML = code.arriveRowsCount;
|
|
|
- runErrorsEl.innerHTML = yesno( code.runErrors );
|
|
|
- runConsumEl.innerHTML = time( code.runConsum );
|
|
|
- loadConsumEl.innerHTML = time( code.loadConsum );
|
|
|
-
|
|
|
- code.lastUpdate = Tracker.Util.time();
|
|
|
- },
|
|
|
-
|
|
|
- autoUpdateCodeStart: function(){
|
|
|
- updateInterval = setInterval( autoUpdateCodeFn, 5e2 );
|
|
|
- },
|
|
|
-
|
|
|
- autoUpdateCodeStop: function(){
|
|
|
- clearInterval( updateInterval );
|
|
|
- },
|
|
|
-
|
|
|
- activeTab: function( name ){
|
|
|
- var topNav, baseIndex;
|
|
|
-
|
|
|
- topNav = document.getElementById( "top-nav" );
|
|
|
- baseIndex = 0;
|
|
|
-
|
|
|
- if( View.ControlFrame.getMode() == "embed" )
|
|
|
- baseIndex = 1;
|
|
|
-
|
|
|
- if( typeof name != "undefined" ){
|
|
|
- if( !topNav.active )
|
|
|
- return ;
|
|
|
-
|
|
|
- if( name == "code-list" )
|
|
|
- name = baseIndex + 0;
|
|
|
-
|
|
|
- topNav.active( name );
|
|
|
- }else{
|
|
|
- return topNav.actived;
|
|
|
- }
|
|
|
- },
|
|
|
-
|
|
|
- setControlPower: function( bool, hiddenPage ){
|
|
|
- var parent, window, b, c1, c2;
|
|
|
-
|
|
|
- if( View.ControlFrame.getMode() == "embed" ){
|
|
|
- parent = View.ControlFrame.getWindow( "tracker_main" );
|
|
|
- window = View.ControlFrame.getWindow( "tracker_controller" );
|
|
|
- c1 = bool ? Tracker.Util.addClass : Tracker.Util.removeClass;
|
|
|
- c2 = hiddenPage ? Tracker.Util.addClass : Tracker.Util.removeClass;
|
|
|
- b = parent.document.body;
|
|
|
- c1( b, "control-power-mode" );
|
|
|
- c2( b, "hidden-page-mode" );
|
|
|
- }
|
|
|
- },
|
|
|
-
|
|
|
- actions: function( acts ){
|
|
|
- for( var name in acts )
|
|
|
- actions[ name ] = acts[ name ];
|
|
|
- },
|
|
|
-
|
|
|
- htmlBuilder: function(){
|
|
|
- var pm = new Tracker.Promise(), mode;
|
|
|
-
|
|
|
- codeIndex = 0;
|
|
|
- mode = View.ControlFrame.getMode();
|
|
|
-
|
|
|
- Tracker.Util.delay( function(){
|
|
|
- pm.resolve( View.templates.controllerPage( withWidths( {
|
|
|
- charset: global.document.characterSet || "utf-8",
|
|
|
- trackerCss: chrome.runtime.getURL('/static/css/js-tracker.css'),
|
|
|
-
|
|
|
- header: View.templates.controllerTopbar( {
|
|
|
- mode: mode
|
|
|
- } ),
|
|
|
-
|
|
|
- codeList: View.templates.controllerCodeList( withWidths() ),
|
|
|
- codeDetail: View.templates.controllerCodeDetail(),
|
|
|
-
|
|
|
- mode: mode,
|
|
|
- version: version,
|
|
|
- uid: host.tracker_uid
|
|
|
- } ) ) );
|
|
|
- } );
|
|
|
-
|
|
|
- return pm;
|
|
|
- },
|
|
|
-
|
|
|
- eventBuilder: function(){
|
|
|
- var me = this;
|
|
|
-
|
|
|
- var elementListCodes = document.getElementById( "list-codes" );
|
|
|
- var elementCodeDetail = document.getElementById( "code-detail" );
|
|
|
- var elementCodeToolbarInner = document.querySelector( ".code-toolbar-inner" );
|
|
|
- var elementCodeDetailHead = document.getElementById( "code-detail-head" );
|
|
|
- var elementCodeContent = document.getElementById( "code-content" );
|
|
|
-
|
|
|
- var tr, focusInList;
|
|
|
- var tabDescRegx = /tab-desc-(\d+)/;
|
|
|
-
|
|
|
- Tracker.Event.add( elementListCodes, {
|
|
|
- click: function( e ){
|
|
|
- var codeId;
|
|
|
- if( tr = Tracker.Util.findParent( e.target, "tr", elementListCodes ) )
|
|
|
- if( codeId = tr.getAttribute( "data-code-id" ) )
|
|
|
- focusInList = true,
|
|
|
- codeId == currentSelectedCode ||
|
|
|
- View.ControlPanel.showCodeDetail( codeId );
|
|
|
- }
|
|
|
- } );
|
|
|
-
|
|
|
- Tracker.Event.add( elementCodeDetail, {
|
|
|
- click: function(){
|
|
|
- focusInList = false;
|
|
|
- }
|
|
|
- } );
|
|
|
-
|
|
|
- Tracker.Event.add( document, {
|
|
|
- mouseup: function( e ){
|
|
|
- var action;
|
|
|
- if( ( action = e.target.getAttribute( "action" ) ) &&
|
|
|
- actions[ action ] )
|
|
|
- actions[ action ].call( me, e.target );
|
|
|
- },
|
|
|
-
|
|
|
- keydown: function( e ){
|
|
|
-
|
|
|
- var selectId;
|
|
|
-
|
|
|
- // command + R, F5
|
|
|
- if( ( e.metaKey && e.keyCode == 82 ) || e.keyCode == 116 ){
|
|
|
- if( View.ControlFrame.getMode() == "window" ){
|
|
|
- e.preventDefault && e.preventDefault();
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
- if( focusInList && currentSelectedCode ){
|
|
|
- var offset = 0;
|
|
|
- if( e.keyCode == 38 ){ // up
|
|
|
- offset = -1;
|
|
|
- }else if( e.keyCode == 40 ){ // down
|
|
|
- offset = 1;
|
|
|
- }
|
|
|
- if( offset ){
|
|
|
- var trs = elementListCodes.querySelectorAll( "tr" ),
|
|
|
- nowIndex = -1, tr;
|
|
|
-
|
|
|
- for(var i = 0, l = trs.length; i < l; i ++){
|
|
|
- if( trs[i].getAttribute( "data-code-id" ) ==
|
|
|
- currentSelectedCode ){
|
|
|
- nowIndex = i;
|
|
|
- break;
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
- if( nowIndex > -1 ){
|
|
|
- nowIndex = ( nowIndex += offset ) < 0 ?
|
|
|
- 0 : nowIndex == trs.length ?
|
|
|
- nowIndex - 1 : nowIndex;
|
|
|
- tr = trs[ nowIndex ];
|
|
|
-
|
|
|
- selectId = tr.getAttribute( "data-code-id" );
|
|
|
- if( currentSelectedCode != selectId )
|
|
|
- View.ControlPanel.showCodeDetail( selectId );
|
|
|
-
|
|
|
- e.preventDefault && e.preventDefault();
|
|
|
- }
|
|
|
- }
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
- // mousewheel: function( e ){
|
|
|
- // e.preventDefault();
|
|
|
- // }
|
|
|
- } );
|
|
|
-
|
|
|
- if( !actions[ "code#close" ] ){
|
|
|
- actions[ "code#close" ] = function( e ){
|
|
|
- focusInList = true;
|
|
|
- View.ControlPanel.showCodeDetail( false );
|
|
|
- };
|
|
|
- }
|
|
|
-
|
|
|
- if( View.ControlFrame.getMode() == "window" )
|
|
|
- document.getElementById( "window-mode-trigger" ).innerHTML = "内嵌模式";
|
|
|
-
|
|
|
- var lastScrollLeft = 0;
|
|
|
- Tracker.Event.add( elementCodeContent, {
|
|
|
- scroll: function( e ){
|
|
|
-
|
|
|
- if( this.scrollLeft == 0 )
|
|
|
- this.scrollLeft = 1;
|
|
|
-
|
|
|
- if( this.scrollLeft == this.scrollWidth - this.clientWidth )
|
|
|
- this.scrollLeft -= 1;
|
|
|
-
|
|
|
- if( lastScrollLeft == this.scrollLeft )
|
|
|
- return ;
|
|
|
-
|
|
|
- var gutter = this.querySelector( ".gutter" );
|
|
|
- gutter.style.left = this.scrollLeft + "px";
|
|
|
- lastScrollLeft = this.scrollLeft;
|
|
|
- }
|
|
|
- } );
|
|
|
-
|
|
|
- setupBootstrapPatch();
|
|
|
-
|
|
|
- elementCodeDetailHead.tabEvent.on( "active", function( index ){
|
|
|
- if( this.currentShown != currentSelectedCode ){
|
|
|
- this.currentShown = currentSelectedCode;
|
|
|
- if( index == 0 )
|
|
|
- View.ControlPanel.showCode( currentSelectedCode );
|
|
|
- else if( index == 1 )
|
|
|
- View.ControlPanel.showCodeInfo( currentSelectedCode );
|
|
|
- }
|
|
|
-
|
|
|
- var tabDescs = elementCodeToolbarInner.querySelectorAll( ".tab-desc" );
|
|
|
- Tracker.Util.forEach( tabDescs, function( tabDesc ){
|
|
|
- tabDescRegx.test( tabDesc.className );
|
|
|
- tabDesc.style.display = RegExp.$1 == index ? "" : "none";
|
|
|
- } );
|
|
|
- } );
|
|
|
-
|
|
|
- if( currentSelectedCode )
|
|
|
- this.showCodeDetail( currentSelectedCode );
|
|
|
- }
|
|
|
- } );
|
|
|
- }()
|
|
|
- }
|
|
|
- }();
|
|
|
-
|
|
|
- return View;
|
|
|
-})(this);
|