• Three.JS-学习 The WebGL earth (1)---globe.html 分析


    【Three.JS】The WebGL earth (1)

      上一篇中总结了threejs的学习资料,将webgl earth 作为学习的一个目标。 初步通过学习想达到目的如下:

    (1)javascript 语言的深入理解

    (2)js 如何开发复杂的程序

    (3)globe 纹理是如何贴图的

      首先来看一个这个程序的构成,打开 earth.html  引用的几个js文件:

    1 <script type="text/javascript" src="./js/ThreeWebGL.js"></script>
    2 <script type="text/javascript" src="./js/ThreeExtras.js"></script>
    3 <script type="text/javascript" src="./js/RequestAnimationFrame.js"></script>
    4 <script type="text/javascript" src="./js/Detector.js"></script>
    5 <script type="text/javascript" src="./js/Tween.js"></script>
    6 <script type="text/javascript" src="./js/globe.js"></script>
    7 <script type="text/javascript">
    View Code

    1、ThreeWebGL.js   threejs的 JavaScript 3D library 库文件

    2、ThreeExtras.js  threejs 扩展库文件

    3、RequestAnimationFrame.js  这个与动画有关,有时间再仔细了解一下

    4、Detector.js  应该用来判断显卡、浏览器是不是支持webgl 的

    5、Tween.js  这个库用来实现缓动效果的,很好用,先不仔细研究

    6、globe.js   这个就是实现地球效果的 工程文件了。 下面主要研究这个globe js 和 earth .html 是怎么回事

    第一步,创建globe对象 。

      var globe = new DAT.Globe(container);

    javascript 创建类对象的方式很有意思。找到一点详细的资料,为了方便书写,这个博文叫资料1。http://www.cnblogs.com/lidabo/archive/2011/12/17/2291238.html

    打开globe.js 我们可以找到

    var DAT = DAT || {}; 

    按照资料1中的总结,看看这两个类的创建,DAT={} 表明 DAT 是一个类对象。DAT.Globe 实际上 是DAT 内部的一个对象,而创建DAT的目的,我想大概类似于命名空间的意思

    DAT.Globe = function(container, colorFn) {...}

    globe 对象的创建方法类似 资料1中的第四种: 带参数的构造函数。javascript 通过function 关键字创建函数和类。这个function的返回值是一个this。

    因此,第一步创建globe对象时,var globe =new DAT.Globe(container)  得到了一个 Globe 对象。好像有点废话,不过后面这个地方还会做比较。

    创建globe 对象后,我们在earth.html 文件中,可以搜索一下,发现 globe 类对象调用了一些函数方法:主要有:

    globe.addData(.....); 
    globe.createPoints(); 
    globe.animate();

    在globe.js中我们可以看到 :

      this.addData = addData;
      this.createPoints = createPoints;
      this.renderer = renderer;
      this.scene = scene;

    在函数内部通过var 创建的addData 等函数方法,只在 function内部可见 ,如果希望Globe.addData()这样来调用的话,就需要,使用上面的语句创建“成员函数” ,使其外部可见。

    第二步,从加载人口数据,解析并传入 globe 对象。主要通过如下代码:

     1    var xhr;
     2         TWEEN.start();
     3         xhr = new XMLHttpRequest();
     4         xhr.open('GET', './data/population909500.json', true);
     5         xhr.onreadystatechange = function(e) {
     6             if (xhr.readyState === 4) {
     7                 if (xhr.status === 200) {
     8                     var data = JSON.parse(xhr.responseText);
     9                     window.data = data;
    10                     for (i=0;i<data.length;i++) {
    11                         globe.addData(data[i][1], {format: 'magnitude', name: data[i][0], animated: true});
    12                     }
    13                     globe.createPoints();
    14                     settime(globe,0)();
    15                     globe.animate();
    16                 }
    17             }
    18         };
    19         xhr.send(null);
    View Code

     这里面值得学习的类有以下几个:

    (1)XMLHttpRequest 对象(参考http://www.w3school.com.cn/xmldom/dom_http.asp

    XMLHttpRequest 对象提供了对 HTTP 协议的完全的访问,包括做出 POST 和 HEAD 请求以及普通的 GET 请求的能力。XMLHttpRequest 可以同步或异步地返回 Web 服务器的响应,并且能够以文本或者一个 DOM 文档的形式返回内容。

    (2)鼠标事件的添加,函数调用,与函数引用

     1         var settime = function(globe, t) {
     2              return function() {
     3                 new TWEEN.Tween(globe).to({time: t/years.length},500).easing(TWEEN.Easing.Cubic.EaseOut).start();
     4                 var y = document.getElementById('year'+years[t]);
     5                 if (y.getAttribute('class') === 'year active') {
     6                     return;
     7                 }
     8                 var yy = document.getElementsByClassName('year');
     9                 for(i=0; i<yy.length; i++) {
    10                     yy[i].setAttribute('class','year');
    11                 }
    12                 y.setAttribute('class', 'year active');
    13            };
    14         };
    View Code

    settime()函数 在html 中两两次被调用 ,第一次 settime(globe,0)(); 第二次,是增加  鼠标响应事件。

            for(var i = 0; i<years.length; i++) {
                var y = document.getElementById('year'+years[i]);
                y.addEventListener('mouseover', settime(globe,i), false);
            }

    这里我觉得settime 函数 的申明 值得学习和分析一下。先来看:

            var settime = function(globe, t) {
                 return function() {
                    new TWEEN.Tween(globe).to({time: t/years.length},500).easing(TWEEN.Easing.Cubic.EaseOut).start();
                    var y = document.getElementById('year'+years[t]);
                    if (y.getAttribute('class') === 'year active') {
                        return;
                    }
                    var yy = document.getElementsByClassName('year');
                    for(i=0; i<yy.length; i++) {
                        yy[i].setAttribute('class','year');
                    }
                    y.setAttribute('class', 'year active');
               };
            };
    View Code

     由于settime 函数返回的是一个匿名函数的引用,所以 在调用settime(globe,0)() 后面这个括号就容易理解了。

    addEventListener('mouseover', settime(globe,i), false); 
    中间这个参数licener ,需要的正式一个函数参数的引用,或者 函数体。

    settime函数的写法好处是可以,向绑定的事件处理函数传递参数。

    第三步,实现缓动效果。这个主要用到了tween.js 这个库。网上比较多人用,找到一个不错的介绍,有时间再仔细看,先记录一下:

    View Code
    
    

    到这里,globe.html 这个也面的基本内容,都分析完了。从页面里面,我们可以学习到一下常用的 函数和知识点,罗列一下

    1、 script 文件的引用:<script type="text/javascript" src="./js/ThreeWebGL.js"></script>

    2、通过id 查找 dom 标签,document.getElementById('container');

    3、获取元素的属性,y.getAttribute('class') === 'year active' 。

    4、===表示,不但值要相同,类型也要相同 ,==表示值要相同。

    5、XMLHttpRequest  用来处理http 请求

    6、addEventListener  为 元素添加鼠标事件,响应函数 。

    btn1Obj.addEventListener("click",method1,false); 
    btn1Obj.addEventListener("click",method2,false); 
    btn1Obj.addEventListener("click",method3,false); 

    执行顺序为method1->method2->method3 

     7、最后是google 用于网站统计的代码,有时间再看

     1 <script type="text/javascript">
     2 
     3     var _gaq = _gaq || [];
     4     _gaq.push(['_setAccount', 'UA-23152241-1']);
     5     _gaq.push(['_trackPageview']);
     6 
     7     (function() {
     8         var ga = document.createElement('script'); ga.type = 'text/javascript'; ga.async = true;
     9         ga.src = ('https:' == document.location.protocol ? 'https://ssl' : 'http://www') + '.google-analytics.com/ga.js';
    10         var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(ga, s);
    11     })();
    12 
    13 </script>
    View Code

    这一篇,主要介绍了globe.html 页面的 基本结构, 从下一篇开始,重点关注 globe.js 的实现细节。

     

  • 相关阅读:
    面试6 在c#中如何声明一个类不能被继承
    面试5 如何理解静态变量,局部变量,全局变量
    面试4 你在什么情况下会用到虚方法?它与接口有什么不同
    面试3 不用系统自带的方法将字符串类型123456转换为值类型
    面试2 递归的算法求1,1,2,3,5,8.......的第30位数是多少,然后求这些数的和.
    面试1 SQL SERVER 查询第20行到30之间的数据
    ubuntu安装nginx
    ubuntu上使用ufw配置管理防火墙
    ubuntu上安装docker
    ubuntu上使用vim编辑文本内容
  • 原文地址:https://www.cnblogs.com/freesoul/p/3688328.html
Copyright © 2020-2023  润新知