canvas模拟细菌粒子点击繁殖碰撞效果代码
代码语言:html
所属分类:粒子
代码描述:canvas模拟细菌粒子点击繁殖碰撞效果代码,点击左键可新增繁殖细菌,可设置重力、深度等开关。
下面为部分代码预览,完整代码请点击下载或在bfwstudio webide中打开
<!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8"> <style type="text/css"> html{color:#000;background:#222222;} a{cursor:pointer;} html,body,div,dl,dt,dd,ul,ol,li,h1,h2,h3,h4,h5,h6,pre,code,form,fieldset,legend,input,textarea,p,blockquote,th,td{margin:0;padding:0;} table{border-collapse:collapse;border-spacing:0;} fieldset,img{border:0;} address,caption,cite,code,dfn,em,strong,th,var{font-style:normal;font-weight:normal;} li{list-style:none;} caption,th{text-align:left;} /* h1,h2,h3,h4,h5,h6{font-size:100%;} */ q:before,q:after{content:'';} abbr,acronym {border:0;font-variant:normal;} sup {vertical-align:text-top;} sub {vertical-align:text-bottom;} input,textarea,select{font-family:inherit;font-size:inherit;font-weight:inherit;outline-style:none;outline-width:0pt;} legend{color:#000;} a:focus,object,h1,h2,h3,h4,h5,h6{-moz-outline-style: none; border:0px;} strong {font-weight: bold;} body, html { background-color: #111; } #world { background: #000; border: 6px solid #222222; border-radius: 2px; box-shadow: 0 0 2px #000; -o-box-shadow: 0 0 2px #000; -moz-box-shadow: 0 0 2px #000; -webkit-box-shadow: 0 0 2px #000; } #instructions { font-family: Helvetica, Arial, sans-serif; font-size: 11px; color: #999; display: none; text-align: center; background: rgba(20,20,20,0.6); letter-spacing: 0.09em; width: 912px; padding: 10px 0; z-index: 6; } #instructions strong { color: #ddd; font-weight: normal; } #options { color: #fff; position: absolute; display: none; } #options .switch { cursor: pointer; color: #999; background: #222; height: 12px; display: block; float: left; margin: 2px 10px 2px 2px; padding: 5px; font-family: Helvetica, Arial, sans-serif; font-size: 11px; text-decoration: none; text-transform: uppercase; text-shadow: 0 0 1px #333; border-radius: 2px; transition: all .11s ease-out; -o-transition: all .11s ease-out; -moz-transition: all .11s ease-out; -webkit-transition: all .11s ease-out; box-shadow: 0 0 2px #000; -o-box-shadow: 0 0 2px #000; -moz-box-shadow: 0 0 2px #000; -webkit-box-shadow: 0 0 2px #000; } #options .switch.on { background: #761d36; color: #ddd; } #options .switch:hover { background: #9f123a; color: #eee; } #options .switch span { text-align: center; font-weight: bold; padding: 3px 0 3px 0; } </style> </head> <body> <div id="panel"> <p><strong>Mouse down</strong> to create bacteria.<br/><strong>Mouse down</strong> + <strong>Space</strong> to create turbines.</p> </div> <div id="options"><a id="gravity-switch" class="switch" title="Toggles gravity ON/OFF in the physics world." href="#">Gravity <span>OFF</span></a><a id="depth-switch" class="switch" title="Toggles depth trails ON/OFF. Performance killer." href="#">Depth <span>OFF</span></a><a id="turbines-switch" class="switch" title="Toggles turbine sucture ON/OFF." href="#">Turbines <span>OFF</span></a><a id="infection-switch" class="switch" title="When ON this causes bacteria to become infected by turbines and carry that infection to their siblings." href="#">Infection <span>OFF</span></a><a id="reset-button" class="switch" title="Removes all bacteria and turbines." href="#">Reset</a></div><div id="instructions"><strong>Mouse Down</strong> to create bacteria. <strong>Mouse Down + Space</strong> to create turbines.</div> <canvas id="world"><p class="noCanvas">You need a <a href="https://www.google.com/chrome">modern browser</a> to view this.</p></canvas> <script > /** * */ var UserProfile = { /** */ UA_ANDROID: 'android', UA_IPHONE: 'iphone', UA_IPAD: 'ipad', isOnline: navigator.onLine, isAuthenticated: false, /** * */ isTouchDevice: function() { if (navigator.userAgent.toLowerCase().indexOf(this.UA_ANDROID) != -1 || navigator.userAgent.toLowerCase().indexOf(this.UA_IPHONE) != -1 || navigator.userAgent.toLowerCase().indexOf(this.UA_IPAD) != -1 ) { return true; } else { return false; } }, /** * */ supportsAudio: function() { return !this.isTouchDevice(); }, /** * */ supportsAjax: function() { return window.XMLHttpRequest != null && this.isOnline; }, /** * */ suportsLocalStorage: function() { return ('localStorage' in window) && window['localStorage'] !== null; } }; /** * Holds generic AJAX communication functions. */ AJAX = { /** * Triggers an AJAX call using the POST method. * * @param {String} url The URL to invoke * @param {String} parameters Variables to send to the URL * @param {Function} success Called if the call succeeds * @param {Function} error Called if the call fails */ post: function( url, parameters, success, error ) { this.post( url, parameters, success, error, 'POST' ); }, /** * Triggers an AJAX call using the GET method. * * @param {String} url The URL to invoke * @param {String} parameters Variables to send to the URL * @param {Function} success Called if the call succeeds * @param {Function} error Called if the call fails */ get: function( url, parameters, success, error ) { this.post( url, parameters, success, error, 'GET' ); }, /** * Triggers an AJAX call using the supplied arguments. * * @param {String} url The URL to invoke * @param {String} parameters Variables to send to the URL * @param {Function} success Called if the call succeeds * @param {Function} error Called if the call fails * @param {String} method Called if the call fails */ send: function( url, parameters, success, error, method ) { var request = new XMLHttpRequest(); request.open(method, url, true); request.setRequestHeader("Content-type", "application/x-www-form-urlencoded"); if( request ) { request.onreadystatechange = function() { if (request.readyState == 4) { if (request.status == 200) { success( request.responseText ); } else { error( request.responseText ); } } }; request.send(parameters); } } }; /** * Defines a 2D position. */ function Point( x, y ) { this.position = { x: x || 0, y: y || 0 }; } Point.prototype.distanceTo = function(p) { var dx = p.x-this.position.x; var dy = p.y-this.position.y; return Math.sqrt(dx*dx + dy*dy); }; Point.prototype.clonePosition = function() { return { x: this.position.x, y: this.position.y }; }; /** * Defines of a rectangular region. */ function Region() { this.left = 999999; this.top = 999999; this.right = 0; this.bottom = 0; } Region.prototype.reset = function() { this.left = 999999; this.top = 999999; this.right = 0; this.bottom = 0; }; Region.prototype.inflate = function( x, y ) { this.left = Math.min(this.left, x); this.top = Math.min(this.top, y); this.right = Math.max(this.right, x); this.bottom = Math.max(this.bottom, y); }; Region.prototype.contains = function( x, y ) { return x > this.left && x < this.right && y > this.top && y < this.bottom; }; var p = new Point(); </script> <script> /** * */ var BacteriumWorld = new function() { // The size that the game will render at on a desktop browser var DEFAULT_WIDTH = 900; var DEFAULT_HEIGHT = 500; // The number of times the game will be redrawn per second var FRAMERATE = 60; var MAX_TURBINE_RADIUS = 100; // The world dimensions, defaults to full screen for touch devices var world = { x: 0, y: 0, width: UserProfile.isTouchDevice() ? window.innerWidth : DEFAULT_WIDTH, height: UserProfile.isTouchDevice() ? window.innerHeight : DEFAULT_HEIGHT }; var gravity = { x: 0, y: 2 }; // The canvas and its 2D context var canvas; var context; // The current state of the mouse var mouse = { x: 0, y: 2, down: false }; // The current state of the keyboard var key = { spaceDown: false }; // Contains settings that are saved and restored between sessions var settings = { gravityEnabled: false, depthEnabled: false, turbinesEnabled: false, infectionEnabled: true }; // Holds all of out Foam and Turbine instances var bacteriaPool = []; var turbinePool = []; var ui = { instructions: null, options: null, gravitySwitch: null, gravitySwitchState: null, depthSwitch: null, depthSwitchState: null, turbinesSwitch: null, turbinesSwitchState: null, infectionSwitch: null, infectionSwitchState: null }; /** * Initializes the game world and rendering. */ this.initialize = function(){ // Collect references to all DOM elements being used canvas = document.getElementById('world'); ui.instructions = document.getElementById('instructions'); ui.options = document.getElementById('options'); ui.resetButton = document.getElementById('reset-button'); ui.gravitySwitch = document.getElementById('gravity-switch'); ui.gravitySwitchState = ui.gravitySwitch.getElementsByTagName( 'span' )[0]; ui.depthSwitch = document.getElementById('depth-switch'); ui.depthSwitchState = ui.depthSwitch.getElementsByTagName( 'span' )[0]; ui.turbinesSwitch = document.getElementById('turbines-switch'); ui.turbinesSwitchState = ui.turbinesSwitch.getElementsByTagName( 'span' )[0]; ui.infectionSwitch = document.getElementById('infection-switch'); ui.infectionSwitchState = ui.infectionSwitch.getElementsByTagName( 'span' )[0]; // Make sure that the Canvas element is available before continuing if (canvas && canvas.getContext) { context = canvas.getContext('2d'); // Register event listeners document.addEventListener('mousemove', documentMouseMoveHandler, false); canvas.addEventListener('mousedown', documentMouseDownHandler, false); document.addEventListener('mouseup', documentMouseUpHandler, false); canvas.addEventListener('touchstart', documentTouchStartHandler, false); document.addEventListener('touchmove', documentTouchMoveHandler, false); document.addEventListener('touchend', documentTouchEndHandler, false); document.addEventListener('keydown', documentKeyDownHandler, false); document.addEventListener('keyup', documentKeyUpHandler, false); window.addEventListener('resize', windowResizeHandler, false); ui.resetButton.addEventListener('click', resetButtonClickedHandler, false); ui.gravitySwitch.addEventListener('click', gravitySwitchClickedHandler, false); ui.depthSwitch.addEventListener('click', depthSwitchClickedHandler, false); ui.turbinesSwitch.addEventListener('click', turbinesSwitchClickedHandler, false); ui.infectionSwitch.addEventListener('click', infectionSwitchClickedHandler, false); // Attempts to restore settings from saved data if there is any restoreSettings(); updateUI(); // Force an initial resize to make sure the UI is sized correctly windowResizeHandler(); ui.instructions.style.display = 'block'; ui.options.style.display = 'block'; // If we are on a touch device, certain elements need to be configured differently if( UserProfile.isTouchDevice() ) { // TODO: Hide excess UI that does not work on small screens } // Initiate the main render loop of the game setInterval( loop, 1000 / FRAMERATE ); } }; /** * Restores settings from local storage if there are * any historical records. */ function restoreSettings() { if( UserProfile.suportsLocalStorage() ) { var gravityEnabled = localStorage[ 'gravityEnabled' ]; var depthEnabled = localStorage[ 'depthEnabled' ]; var turbinesEnabled = localStorage[ 'turbinesEnabled' ]; var infectionEnabled = localStorage[ 'infectionEnabled' ]; if( gravityEnabled ) { settings.gravityEnabled = gravityEnabled == 'true'; } if( depthEnabled ) { settings.depthEnabled = depthEnabled == 'true'; } if( turbinesEnabled ) { settings.turbinesEnabled = turbinesEnabled == 'true'; } if( infectio.........完整代码请登录后点击上方下载按钮下载查看
网友评论0