zoukankan      html  css  js  c++  java
  • 网页版台球小游戏

    主要是用html  js  css 做的一个网页版小游戏,从网上看到的所以整理下面给大家看看

    先来看效果图

    然后随便点击一个地方

    这个和网页版的台球小游戏是一样的操作

    下面是源代码

    html文件

    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    <html xmlns="http://www.w3.org/1999/xhtml">
    <head>
    <meta http-equiv="Content-Type" content="text/html; charset=gb2312" />
    <title></title>
    <link href="css/zzsc.css" rel="stylesheet" type="text/css">
    <script type="text/javascript" src="js/zzsc.js"></script>
    </head>
    <body>
        <div id="table">
            <div id="scoreBoard"></div>
        </div>
        <div class="bot">
            <div id="tips"></div>
            <div class = "ctrl">
                <div id="force"></div>
                <div id="shootPos"> 
                    <div id="dot"></div>
                </div>
            </div>
        </div>
    
    </body>
    </html>

    然后css文件

    * {margin:0; padding:0}
    body {background:black; text-align:center}
    h1 {font-size:12px; color:gray; font-weight:normal; line-height:200%}
    h1 .sub {vertical-align:super; color:red; font-size:9px; }
    .info {position:absolute; right:0}
    #table {position:relative; width:800px; margin:20px auto 10px; height:544px; background:url(images/table.jpg) no-repeat}
    .ball {position:absolute; width:30px; height:30px}
    #dotWrap {position:absolute; z-index:2; left:32px; top:32px; width:736px; height:480px}
    .guide {z-index:3; background-image:url(images/dashed_ball.png); _background:none; _filter: progid:DXImageTransform.Microsoft.AlphaImageLoader(enabled='true', sizingMethod='scale', src="images/dashed_ball.png"); background-repeat:no-repeat}
    .target {left:500px; top:250px; background-image:url(images/yellow_ball.png); _background:none; _filter: progid:DXImageTransform.Microsoft.AlphaImageLoader(enabled='true', sizingMethod='scale', src="images/yellow_ball.png"); background-repeat:no-repeat}
    .cue {background-image:url(images/white_ball.png); _background:none; _filter: progid:DXImageTransform.Microsoft.AlphaImageLoader(enabled='true', sizingMethod='scale', src="images/white_ball.png"); background-repeat:no-repeat}
    .bot {position:relative; width:800px; margin:10px auto 10px; height:70px}
    .ctrl {position:absolute; top:0; right:0; width:200px; height:80px; background:url(images/bg_controler.png) no-repeat}
    #force {position:absolute; left:0; top:18px; width:75px; height:20px; background:url(images/force_conver.png) no-repeat}
    #shootPos {position:absolute; top:0; right:14px; width:52px; height:52px}
    #dot {position:absolute; top:22px; left:22px; width:8px; height:8px; background:url(images/bule_dot.png) no-repeat; font-size:1px}
    #scoreBoard {position:absolute; z-index:3; top:230px; left:346px; font-size:50px; color:white; filter:alpha(opacity=0); -moz-opacity:0; opacity:0}
    #tips {padding:15px 0 0 20px; text-align:left; color:red; font-size:12px}

    js文件

    // common 
    function $(str) {
        return document.getElementById(str);
    }
    
    function $tag(str,target) {
        target = target || document;
        return target.getElementsByTagName(str);
    }
    
    function addEventHandler(obj,eType,fuc){
        if(obj.addEventListener){ 
            obj.addEventListener(eType,fuc,false); 
        }else if(obj.attachEvent){ 
            obj.attachEvent("on" + eType,fuc); 
        }else{ 
            obj["on" + eType] = fuc; 
        } 
    } 
    
    function removeEventHandler(obj,eType,fuc){
        if(obj.removeEventListener){ 
            obj.removeEventListener(eType,fuc,false); 
        }else if(obj.attachEvent){ 
            obj.detachEvent("on" + eType,fuc); 
        } 
    }
    
    function randowNum(start,end) {
        return Math.floor(Math.random()*(end - start)) + start;
    }
    
    Array.prototype.remove=function(dx) {
        if(isNaN(dx)||dx>this.length){return false;}
        for(var i=0,n=0;i<this.length;i++)
        {
            if(this[i]!=this[dx])
            {
                this[n++]=this[i]
            }
        }
        this.length-=1
    }
    
    //const
    var TOTALR = 15, //球的半径(包括阴影)
        R = 12, //球真实半径
        POKER = 20,
        W = 736, //案宽
        H = 480, //案高
        THICKNESS =  32, //边缘厚度
        RATE = 100, //刷新频率
        F = 0.01, //摩擦力
        LOSS = 0.2, // 碰撞速度损失
        TIPS = ["Tip1: 参考球,目标球,目标袋,三点一线,这是最基本的进球方法","Tip2: 右下角蓝条代表击球力度,小的力度更便于控制母球位置","Tip3: 右下角白球上的蓝点控制击球点,高杆,低杆,加塞都由它控制,高手与菜鸟的区别往往在此","Tip4: 桌球,其实打的不是目标球,是母球"];
    var table, //案子
        cueBall, //母球
        guideBall, //参考球
        dotWrap, //参考线
        speed = 12,
        rollUp = 0,
        rollRight = 0,
        timer,
        forceTimer,
        balls = [],
        movingBalls = [],
        pokes = [[0,0],[W/2,-5],[W,0],[0,H],[W/2,H+5],[W,H]],
        hasShot = false;
        shots = 0; //连击次数
        
    window.onload = function() {
        initTable();
        initShootPos();
        showTips();
        startGame();
    }
    
    function startGame() {
        initBall();
        addEventHandler(table,"mousemove",dragCueBall);
        addEventHandler(table,"mouseup",setCueBall);
    }
    
    function initTable() {
        table = $("table");
        var dotWrapDiv = document.createElement("div"),
            guideBallDiv = document.createElement("div");
        dotWrapDiv.id = "dotWrap";
        guideBallDiv.className = "guide ball";
        setStyle(guideBallDiv,"display","none");
        dotWrap = table.appendChild(dotWrapDiv);
        guideBall = table.appendChild(guideBallDiv);
    }
    
    function initBall() {
    
        //添加母球
        cueBall = new Ball("cue",170,H/2);
        balls.push(cueBall);
        
        //添加目标球
        for(var i = 0; i < 5; i++) {
            for(var j = 0; j <= i; j++)    {
                var ball = new Ball("target",520 + i*2*R, H/2 - R*i + j*2*R);
                balls.push(ball);
            }
        }
    }
    
    function initShootPos() {
        var wrap = $("shootPos"),
            handler = $("dot"),
            arrowR = 18;
        addEventHandler(wrap,"mousedown",selectDot);
        function selectDot(e) {
            e = e || event;
            var pos = getElemPos(wrap),
                x = e.clientX - pos[0] - handler.offsetWidth/2,
                y = e.clientY - pos[1] - handler.offsetHeight/2;
                
            if(Math.sqrt((x-22)*(x-22) + (y-22)*(y-22)) > arrowR) {
                var angle = Math.atan2(x-22,y-22);
                x = arrowR*Math.sin(angle) + 22;
                y = arrowR*Math.cos(angle) + 22;
            }
            setPos(handler,x,y);        
        }
    }
    
    function getElemPos(target,reference) {
        reference = reference || document;
        var left = 0,top = 0;
        return getPos(target);
        function getPos(target) {
            if(target != reference) {
                left += target.offsetLeft;
                top += target.offsetTop;
                return getPos(target.parentNode);
            } else {
                return [left,top];
            }
        }
    }
    
    // ball class
    function Ball(type,x,y) {
        var div = document.createElement("div");
        div.className = type + " ball";
        this.elem = table.appendChild(div);
        this.type = type;
        this.x = x; //位置
        this.y = y;
        this.angle = 0; //角度
        this.v = 0; //速度(不包含方向)
        setBallPos(this.elem,x,y);
        return this;
    }
    
    function setCueBall() {
        removeEventHandler(table,"mousemove",dragCueBall);
        removeEventHandler(table,"mouseup",setCueBall);
        startShot();
    }
    
    function startShot() {
        show(cueBall.elem);
        addEventHandler(table,"mousemove",showGuide);
        addEventHandler(table,"mousedown",updateForce);
        addEventHandler(table,"mouseup",shotCueBall);
        
    }
    
    function dragCueBall(e) {
        var toX,toY;
        e = e || event;
        toX = e.clientX - table.offsetLeft - THICKNESS,
        toY = e.clientY - table.offsetTop - THICKNESS;
        
        toX = toX >= R ? toX : R;
        toX = toX <= 170 ? toX : 170;
        toY = toY >= R ? toY : R;
        toY = toY <= H - R ? toY : H - R;
            
        setBallPos(cueBall,toX,toY);
    }
    
    function shotCueBall() {
        removeEventHandler(table,"mousemove",showGuide);
        removeEventHandler(table,"mousedown",updateForce);
        removeEventHandler(table,"mouseup",shotCueBall);
        window.clearInterval(forceTimer);
        speed = $("force").offsetWidth * 0.15;
        var dotDisX = $("dot").offsetLeft-22,
            dotDisY = $("dot").offsetTop-22,
            dotDis = Math.sqrt(dotDisX*dotDisX + dotDisY*dotDisY),
            dotAngle = Math.atan2(dotDisX,dotDisY);
        rollRight = Math.round(dotDis*Math.sin(dotAngle))/5;
        rollUp = -Math.round(dotDis*Math.cos(dotAngle))/5;
    
        var formPos = getBallPos(cueBall.elem),
            toPos = getBallPos(guideBall),
            angle = Math.atan2(toPos[0] - formPos[0],toPos[1] - formPos[1]);
            
        hide(dotWrap);
        hide(guideBall);
        cueBall.v = speed;
        cueBall.angle = angle;
        movingBalls.push(cueBall);
        
        timer = window.setInterval(roll,1000 / RATE);
    }
    
    function showGuide(e) {
        var fromX,fromY,toX,toY;
        e = e || event;
        toX = e.clientX - table.offsetLeft - THICKNESS,
        toY = e.clientY - table.offsetTop - THICKNESS;
        setBallPos(guideBall,toX,toY);
        show(dotWrap);
        show(guideBall);
        drawLine();
        
        //参考线
        function drawLine() {
            var dotNum = 16,
                pos = getBallPos(cueBall.elem);
            dotWrap.innerHTML = "";
            fromX = pos[0];
            fromY = pos[1];
            var partX = (toX - fromX) / dotNum,
                partY = (toY - fromY) / dotNum;
            for(var i = 1; i < dotNum; i++) {
                var x = fromX + partX * i,
                    y = fromY + partY * i;
                drawDot(dotWrap, x, y);
            }        
        }
    }
    
    function roll() {
        if(movingBalls.length <= 0) {
            if(!hasShot) shots = 0;
            else shots ++; //累计连击
    
            hasShot = false;
            setStyle($("force"),"width",80+"px");
            setPos($("dot"),22,22);        
            window.clearInterval(timer);
            
            if(shots > 1) showScore(shots); //显示连击数
            startShot();
        }
        for(var i = 0; i < movingBalls.length; i++) {
            var ball = movingBalls[i],
                sin = Math.sin(ball.angle),
                cos = Math.cos(ball.angle);
            ball.v -= F;
            //移除静止的小球
            if(Math.round(ball.v) == 0) {
                ball.v = 0;
                movingBalls.remove(i);
                continue;    
            }
            var vx = ball.v * sin,
                vy = ball.v * cos;
            ball.x += vx;
            ball.y += vy;
                    
            //入袋
            if(isPocket(ball.x,ball.y)) {
                hide(ball.elem);
                
                if(ball.type == "cue") {
                        if(!hasShot) shots = 0;
                        hasShot = false;
    
                    window.setTimeout(function(){
                    
                        ball.v = 0;    
                        setBallPos(ball,170,250);
                        
                    },500);
    
                }else {
                    //移除入袋小球
                    hasShot = true;
                    ball.v = 0;    
                    for(var k = 0, l =0; k < balls.length; k++) {
                        if(balls[k] != ball) {
                            balls[l++] = balls[k];
                        }
                    }
                    balls.length -= 1;
                }
                return;
            }
            
            //边缘碰撞
            if(ball.x < R || ball.x > W - R) {
                ball.angle *= -1;
                ball.angle %= Math.PI;
                ball.v = ball.v * (1 - LOSS);
                vx = ball.v*Math.sin(ball.angle);
                vy = ball.v*Math.cos(ball.angle);
                if(ball.x < R) ball.x = R;
                if(ball.x > W - R) ball.x = W - R;
                //母球加塞
                if(ball.type == "cue")    {
                    if(ball.angle > 0) vy -= rollRight;
                    else vy += rollRight;
                    vx += rollUp;
                    rollUp *= 0.2;
                    rollRight *= 0.2;
                    ball.v = Math.sqrt(vx*vx + vy*vy);
                    ball.angle = Math.atan2(vx,vy);
                }                
            }
            if(ball.y < R || ball.y > H - R) {
                ball.angle = ball.angle > 0 ? Math.PI - ball.angle : - Math.PI - ball.angle ;
                ball.angle %= Math.PI;
                ball.v = ball.v * (1 - LOSS);
                vx = ball.v*Math.sin(ball.angle);
                vy = ball.v*Math.cos(ball.angle);
                if(ball.y < R) ball.y = R;
                if(ball.y > H - R) ball.y = H - R;    
                //母球加塞
                if(ball.type == "cue")    {
                    if(Math.abs(ball.angle) < Math.PI/2) vx += rollRight;
                    else vx -= rollRight;
                    vy += rollUp;
                    rollUp *= 0.2;
                    rollRight *= 0.2;
                    ball.v = Math.sqrt(vx*vx + vy*vy);
                    ball.angle = Math.atan2(vx,vy);
                }                    
            }
            
            //小球碰撞
            for(var j = 0; j < balls.length; j++) {
                var obj = balls[j];
                if(obj == ball) continue;
                var disX = obj.x - ball.x,
                    disY = obj.y - ball.y,
                    gap = 2 * R;
                if(disX <= gap && disY <= gap) {
                    var dis = Math.sqrt(Math.pow(disX,2)+Math.pow(disY,2));
                    if(dis <= gap) {
    
                        //如果是静止的,则添加到数组movingBalls
                        if(Math.round(obj.v) == 0)    
                        movingBalls.push(obj);
                        
                        //将坐标旋转到x轴进行碰撞计算
                        
                        // 计算角度和正余弦值 - 精确值
                        //var c = (obj.x*ball.y - obj.y*ball.x)/(2*R),
                        //    d = Math.sqrt(ball.x*ball.x + ball.y*ball.y),
                        //    angle = Math.asin(ball.y/d) - Math.asin(c/d) - ball.angle%(Math.PI/2),
                            //angle =  Math.asin(oy / (2 * R)),
                        
                        //还原两球相切状态 - 近似值
                        ball.x -= (gap - dis)*sin;
                        ball.y -= (gap - dis)*cos;
                        disX = obj.x - ball.x;
                        disY = obj.y - ball.y;
                        
                        // 计算角度和正余弦值
                        var angle = Math.atan2(disY, disX),
                            hitsin = Math.sin(angle),
                            hitcos = Math.cos(angle),
                            objVx = obj.v * Math.sin(obj.angle),
                            objVy = obj.v * Math.cos(obj.angle);
                            //trace(angle*180/Math.PI);
                            
                        // 旋转坐标
                        var x1 = 0,
                            y1 = 0,
                            x2 = disX * hitcos + disY * hitsin,
                            y2 = disY * hitcos - disX * hitsin,
                            vx1 = vx * hitcos + vy * hitsin,
                            vy1 = vy * hitcos - vx * hitsin,
                            vx2 = objVx * hitcos + objVy * hitsin,
                            vy2 = objVy * hitcos - objVx * hitsin;
                        
                        // 碰撞后的速度和位置
                        var plusVx = vx1 - vx2;
                        vx1 = vx2;
                        vx2 = plusVx + vx1;
                        
                        //母球加塞
                        if(ball.type == "cue")    {
                            vx1 += rollUp;
                            rollUp *= 0.2;
                        }                
                        
                        x1 += vx1;
                        x2 += vx2;
                        
                        // 将位置旋转回来
                        var x1Final = x1 * hitcos - y1 * hitsin,
                            y1Final = y1 * hitcos + x1 * hitsin,
                            x2Final = x2 * hitcos - y2 * hitsin,
                            y2Final = y2 * hitcos + x2 * hitsin;
                        obj.x = ball.x + x2Final;
                        obj.y = ball.y + y2Final;
                        ball.x = ball.x + x1Final;
                        ball.y = ball.y + y1Final;
                        
                        // 将速度旋转回来
                        vx = vx1 * hitcos - vy1 * hitsin;
                        vy = vy1 * hitcos + vx1 * hitsin;
                        objVx = vx2 * hitcos - vy2 * hitsin;
                        objVy = vy2 * hitcos + vx2 * hitsin; 
                        
                        //最终速度
                        ball.v = Math.sqrt(vx*vx + vy*vy) * (1 - 0);
                        obj.v = Math.sqrt(objVx*objVx + objVy*objVy) * (1 - 0);
                        
                        // 计算角度
                        ball.angle = Math.atan2(vx , vy);
                        obj.angle = Math.atan2(objVx , objVy);    
                                                                
                        //break;
                    }
                }
            }
                    
            setBallPos(ball,ball.x,ball.y);    
        }
    }
    
    function isPocket(x,y) {
        if(y < POKER) return check(0,2);
        else if (y > H - POKER) return check(3,5);
        else return false;
        
        function check(m,n) {
            for(var i=m; i<=n; i++) {
                if(x >= pokes[i][0] - POKER && x <= pokes[i][0] + POKER) {
                    var dis = Math.sqrt(Math.pow(x - pokes[i][0],2) + Math.pow(y - pokes[i][1],2));
                    if(dis <= POKER) return true;
                    else return false;
                }
            }    
        } 
        
    }
    
    function getBallPos(obj) {
        var pos = [];
        pos.push(obj.offsetLeft - THICKNESS + TOTALR);
        pos.push(obj.offsetTop - THICKNESS + TOTALR);
        return pos;
    }
    
    function setPos(obj,x,y) {
        obj.style.left = x + "px";
        obj.style.top = y + "px";
    }
    
    function setBallPos(ball,x,y) {
        if(ball.constructor == Ball) {
            ball.x = x;
            ball.y = y;
            ball = ball.elem;
        }
        setPos(ball,x + THICKNESS - TOTALR,y + THICKNESS - TOTALR);
    }
    
    function drawDot(wrap,x,y) {
        var elem = document.createElement("div");
        setStyle(elem,{
            position: "absolute",
             "1px",
            height: "1px",
            fontSize: "1px",
            background: "white"
        });
        setPos(elem,x,y);
        wrap.appendChild(elem);
    }
    
    function updateForce() {
        var obj = $("force"),
            len = 80,
            up = true;
        forceTimer = window.setInterval(update,10);
        
        function update() {
             if(up) setStyle(obj,"width",len+++"px");
             else setStyle(obj,"width",len--+"px");
             if(len > 136) up = false;
             if(len <= 0) up = true;
        }
        
    }
    
    function setStyle() {
        if(arguments.length == 2 &&  typeof arguments[1] == "object") {
            for(var key in arguments[1]) {
                arguments[0].style[key] = arguments[1][key];
            }
        } else if (arguments.length > 2) {
            arguments[0].style[arguments[1]] = arguments[2];
        }
    }
    
    function hide(obj) {
        setStyle(obj,"display","none");
    }
    
    function show(obj) {
        setStyle(obj,"display","block");
    }
    
    //输出信息
    function trace(sth,who) {
        who = who || $("tips");
        if(document.all) who.innerText = sth;
        else who.textContent = sth;
        return who;
    }
    
    function showScore(n) {
        var wrap = $("scoreBoard");
        trace(n+"连杆",wrap);
        fadeIn(wrap);
    }
    
    function fadeIn(obj){
        var fromY = 230,
            posStep = [8,14,19,23,26,28,29,29,30,30,30],
            opaStep = [0,0.05,0.1,0.15,0.2,0.25,0.3,0.4,0.5,0.6,0.8],
            fromOpa = 0,
            t = 0,
            step = posStep.length,
            inTimer = window.setInterval(showIn,20),
            outTimer;
        
        function showIn() {
            setOpacity(obj,opaStep[t]);
            obj.style.top = fromY + posStep[t] + "px";
            t++;
            if(t>=step) {
                window.clearInterval(inTimer);
                outTimer = window.setInterval(fadeOut,50);
            }    
        }
        
        function fadeOut() {
            t--;
            setOpacity(obj,opaStep[t]);
            obj.style.top = fromY + posStep[t] + "px";
            if(t <= 0) {
                window.clearInterval(outTimer);
                hide(obj);
            }
        }
        
    }
    
    function setOpacity(obj,n) {
        obj.style.cssText = "filter:alpha(opacity="+ n*100 +"); -moz-opacity:"+ n +"; opacity:"+ n;
    }
    
    function showTips() {
        var i = 0;
        tip();
        window.setInterval(tip,3000);
        
        function tip() {
            trace(TIPS[i++]);
            if(i >= TIPS.length) i = 0;
        }
    }

    图片

    这样就可以实现网页版打台球的小游戏啦,有想试试的,可以问我要图片,实现功能,加上图片,就需要这四个文件,js文件很关键。主要看js是怎么写的,如果你也感兴趣,那么来动手试试吧

  • 相关阅读:
    设置发光字
    QQ空间无导航条应对方法
    网页设计经典网站欣赏
    页面居中显示
    获取元素的绝对位置
    输入两个整数 n 和 m,从数列1,2,3.......n 中 随意取几个数, 使其和等于 m ,要求将其中所有的可能组合列出来.
    最长重复子字符串
    从头到尾彻底解析Hash 表算法
    求二叉树中节点的最大距离
    MySQL学习笔记——显示数据库信息
  • 原文地址:https://www.cnblogs.com/qishuang/p/7218014.html
Copyright © 2011-2022 走看看