zoukankan      html  css  js  c++  java
  • html与JacaScript中的重要思想:预留后路、向后兼容、js分离

    以一个简单的web程序为例

    详细设计模式请配合代码及凝视食用

    <!DOCTYPE html>
    <!--
    1 预留退路:假设用户禁用了js。链接还能正常显示吗?(href)
    2 分离js:行为层与结构层真的分开且互不干扰吗?(onclick)
    3 向后兼容:js代码中检測了浏览器的函数支持吗?(if(!xxx)return)
    -->
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>ImageGallery</title>
    
        <!--<script type="text/javascript" src="scripts/showPic.js"></script>-->
        <script type="text/javascript" src="scripts/preparegallery.js"></script>
        <!--<script type="text/javascript" src="scripts/popUp.js"></script> 測试弹窗脚本-->
        <link rel="stylesheet" href="css/layout.css" type="text/css" media="screen">
        <!--<link rel="stylesheet" href="css/.warning.css" type="text/css" media="screen">-->
    
    </head>
    
    <body>
        <h1>snapshots</h1>
            <!-- 測试通过链接调用js函数-->
            <!--<a href="javascript:popUp('http://www.baidu.com');">test 'javascript:'</a>-->
            <!-- 測试通过onclick调用js函数-->
            <!--<a href="#" onclick="popUp('http://www.baidu.com');return false">test on click popUp</a>-->
            <!-- 预留退路:将href地址与popup的url地址设为同样的-->
            <!--<a href="http://www.baidu.com" onclick="popUp('http://www.baidu.com');return false;">test popup</a>-->
            <!-- 使用弹窗的标准写法2个-->
            <!--<a href="http://www.baidu.com" onclick="popUp(this.getAttribute('href'));return false;">test popup</a>-->
            <!--<a href="http://www.baidu.com" onclick="popUp(this.href);return false;">test popup</a>-->
            <!-- test warning css-->
            <!--<p class="warning">Be careful!</p>-->
        <ul id="imagegallery"><!-- js分离的群体控制,挂钩子-->
            <li>
                <!--js分离前(onclick)<a href="images/fireworks.jpg"
                onclick="showPic(this);return false;" title="A firework display">Firework</a>-->
                <!--測试js分离(popup)(单个控制)<a href="images/fireworks.jpg"
                title= "A firework display" class="popup">Fireworks</a>-->
                <a href="images/fireworks.jpg" title="A firework display">
                    Fireworks</a>
            </li>
            <li>
                <a href="images/coffee.jpg" title="A cup of black coffee">
                    Coffee</a>
            </li>
            <li>
                <a href="images/rose.jpg" title="A red, red rose">
                    Rose</a>
            </li>
            <li>
                <a href="images/bigben.jpg" title="The famous clock">
                    BigBen</a>
            </li>
        </ul>
        <img id="placeholder" src="images/placeholder.gif" alt="my image gallery" onload="alert(3)"/> <!--img:alt 无法显示图片时用来替换的文本-->
        <p id="description">Choose an image.</p>
    </body>
    </html>


    window.onload = preparegallery;
    //addLoadEvent(preparegallery());
    //addLoadEvent(showPic());
    
    function preparegallery(){
        if (!document.getElementsByTagName) return false; // 向后兼容
        if (!document.getElementById) return false;
        if (!document.getElementById("imagegallery")) return false; // 预防性措施
    
        var gallery = document.getElementById("imagegallery");
        var links = gallery.getElementsByTagName("a");
        for (var i=0; i<links.length; i++) {
            links[i].onclick = function() {
                // 此处依据showPic的返回值控制了:onclick之后是否还要再打开一次链接(预留退路)
                //alert(showPic(this));
                return showPic(this);
            }
        }
    }
    
    // 改良后的showPic函数 (集成里替换图片、替换文字的两个功能)
    // 为什么检測的这么仔细呢,面对我们不可控制的html时写的js代码,不能主观觉得html里一定有什么,有点fuzzing的感觉
    function showPic(whichpic) {
        // 向后兼容。假设没有placeholder,那么onclick函数全然无用,
        // 考虑到“预留退路”,应该不取消onclick后面的return!
        // 此处用showPic的返回值进行控制是否取消onclick的"后摇"
        // (见调用showPic()的onclick函数!

    ) if (!document.getElementById("placeholder")) return true; // 向后兼容(不取消onclick之后的默认动作) var source = whichpic.getAttribute("href"); // 检查是否是图片 注意在nodeName中全是大写的 var placeholder = document.getElementById("placeholder"); if (placeholder.nodeName != "IMG") return true; placeholder.setAttribute("src", source); // 替换图片 if (!document.getElementById("description")) return false; // 向后兼容(取消默认动作) var description = document.getElementById("description"); if (whichpic.getAttribute("title")) { // 继续降低依赖性,用if推断 var text = whichpic.getAttribute("title"); } else { var text = ''; // 这样处理即使出错也不会影响视觉效果 } // 检查是否是文本 if (description.firstChild.nodeType == 3) { description.firstChild.nodeValue = text; // 替换文本 } return false; // 千万别忘了这一句 } /* // 载入js函数的通用方式 // 由于要将js分离,将onclick写到js里,所以须要在载入完html后、接受用户操作前载入js函数 // 为避免onload的冲突,採用下面两种通用方式 //1 为onload指定函数 window.onload = function(){ showPic(); preparegallery(); }; //2 程序化解决(在脚本库中加入addLoadEvent() 函数 并在加入时调用) addLoadEvent(preparegallery()); */

    function addLoadEvent(func) {
        var oldonload = window.onload;
        if (typeof window.onload != 'function') {
            window.onload = func;
        }
        else{
            window.onload = function(){
                oldonload();
                func();
            }
        }
    }
    
    //使用:
    //addLoadEvent(function_name)

    /**
     *
     * Created by xy on 7/18/15.
     */
    
    function popUp(winURL){
        window.open(winURL, "popUp", "width=320, height=480");
    }
    
    /*
    //分离js与html(将onclick方法放入js代码中)
    //script文档在html的head标签里被引入并载入,所以以下代码将会在body载入之前就执行,是无效的
    
    var links = document.getElementsByTagName("a");
    for (var i=0; i<links.length; i++) {
        links[i].onclick = function(){
            popUp(this.getAttribute("href"));
            return false;
        }
    }
    */
    
    /*
    //正确的处理方式(分离js)
    
    window.onload = prepareLinks;
    function prepareLinks(){
        var links = document.getElementsByTagName("a");
        for (var i=0; i<links.length; i++) {
            if(links[i].getAttribute("class") == "popup") { //对具有class=popup属性的标签载入onclick方法
                links[i].onclick = function() {
                    popUp(this.getAttribute("href"));  //调用popUp函数
                    return false;
                }
            }
        }
    }
    */
    
    //向后兼容(察看浏览器知否支持这种方法)
    //为了降低大括号层数,使用if(!xxx)return false;特别注意这里的方法不是调用。方法后面不要有小括号!

    //改动上例代码例如以下 //window.onload = prepareLinks; function prepareLinks(){ if (!document.getElementsByTagName) return false; // see this ! var links = document.getElementsByTagName("a"); for (var i=0; i<links.length; i++) { if(links[i].getAttribute("class") == "popup") { links[i].onclick = function() { popUp(this.getAttribute("href")); return false; } } } }



  • 相关阅读:
    mySQL教程 第1章 数据库设计
    数学符号大全
    C# 正则表达式 判断各种字符串(如手机号)
    C# 面向对象编程
    博客园 网址
    优化正则表达式的诀窍
    hdu 1596 floyd
    poj3259,简单判断有无负环,spfa
    hdu 1496 hash
    hdu 1429 bfs+二进制状态压缩
  • 原文地址:https://www.cnblogs.com/slgkaifa/p/6986212.html
Copyright © 2011-2022 走看看