|- libs // 第三方庫
|
|- configs // 場景中物體的配置
|
|- public // 公共資源
|
|- src // 源碼
|
|- game.js // 小遊戲入口
|
|- game.json // 小遊戲配置
|
|- project.config.json // 項目配置
|
|- README.md // 項目說明
複製代碼
game.js,game.json,project.config.json 這三個文件經過微信開發者工具會自動建立,只須要把game.js中原有的內容清空便可。html
引入Three.js的源碼和微信提供的Adaptergit
地址:github
如今目錄看起來應該是這樣json
在game.js中:canvas
import './libs/weapp-adapter'
import * as THREE from './libs/three'
GameGlobal.THREE = THREE
複製代碼
GameGlobal是小遊戲的全局對象,相似於瀏覽器的window,這樣就不用在用到three.js的時候再去引用了,引入weapp-adapte也會有一個canvas對象,全部的繪製都會在這個canvas上進行。api
該目錄用於存放Three.js渲染的相關的代碼瀏覽器
scene.jsbash
const scene = () => {
const sceneInstance = new THREE.Scene()
const axesHelper = new THREE.AxesHelper(100)
sceneInstance.add(axesHelper)
return sceneInstance
}
export default scene
複製代碼
new THREE.AxesHelper(AxesHelper)是座標系的輔助函數,將它添加到場景中就能夠看到座標軸了,文檔:AxesHelper微信
camera.js微信開發
const camera = () => {
const ratio = window.innerHeight / window.innerWidth
const size = 30
// 設置相機可看到範圍
const cameraInstance = new THREE.OrthographicCamera(
-size, size, size * ratio, -size * ratio, -100, 85
)
cameraInstance.position.set(0, 0, 0) // 設置相機位置
cameraInstance.lookAt(new THREE.Vector3(0, 0, 0)) // 設置相機位置從0, 0, 0望向0, 0, 0
return cameraInstance
}
export default camera
複製代碼
new THREE.OrthographicCamera
是正交相機,關於它的參數上一篇有說過,這裏就不說了,說一下它的幾個參數的是怎麼計算的:相機可視寬度是我指定的,根據上圖,如今的相機可視寬度是60,若是想要相機看到場景中的物體不變形,那麼相機可視範圍的尺寸就要和整個canvas(畫布)的尺寸成正比:
畫布高 / 畫布寬 = 相機可視高 / 相機可視寬
相機可視高 = 相機可視高 * 畫布高 / 畫布寬
複製代碼
相機近平面這裏給了負值,目的是渲染相機後面的場景,可理解爲讓相機更接近物體
import camera from './camera'
import scene from './scene'
class Renderer {
constructor () {
this.camera = null
this.scene = null
}
init () {
this.camera = camera()
this.scene = scene()
this.instance = new THREE.WebGLRenderer({
canvas,
antialias: true // 開啓抗鋸齒
})
}
render () {
this.instance.render(this.scene, this.camera)
}
}
export default new Renderer()
複製代碼
修改game.js
import './libs/weapp-adapter'
import * as THREE from './libs/three'
import renderer from './src/renderer/index'
GameGlobal.THREE = THREE
renderer.init()
renderer.render()
複製代碼
這時候在開發者工具中就能夠看到座標系了:
根據文檔:紅色表明 X 軸. 綠色表明 Y 軸. 藍色表明 Z 軸.
目前並不能看到z軸,只須要改一下相機位置便可:
在camera.js修改:
cameraInstance.position.set(-10, 10, 10) // 以前是0,0,0
複製代碼
新建如下文件
block_config.js文件是立方體的基本配置
game 目錄存放整個遊戲不一樣層之間的控制文件
objects 目錄存放遊戲場景中的物體
pages 遊戲頁面,叫頁面可能不太合適,就理解爲遊戲的不一樣狀態,好比遊戲開始,結束等
編寫塊的相關代碼:
block_config.js
export default {
width: 16,
height: 10
}
複製代碼
base.js
import blockConfig from '../../../configs/block_config'
export default class BaseBlock {
constructor (type) {
this.type = type
this.height = blockConfig.height
this.width = blockConfig.width
}
}
複製代碼
box.js
import Base from './base'
class Box extends Base {
constructor (x, y, z) {
super('box')
this.instance = null
this.x = x
this.y = y
this.z = z
this.create()
}
create () {
const geometry = new THREE.BoxGeometry(this.width, this.height, this.width)
const material = new THREE.MeshBasicMaterial({
color: 0xffffff
})
this.instance = new THREE.Mesh(geometry, material)
this.instance.position.set(this.x, this.y, this.z)
}
}
export default Box
複製代碼
new THREE.BoxGeometry
是three.js提供的渲染立方體的方法,這裏的三個參數分別爲:
game_page.js
import renderer from '../renderer/index'
import Box from '../objects/block/box'
export default class GamePage {
constructor () {
this.renderer = renderer
}
init () {
this.renderer.init()
this.addBlock()
this.render()
}
addBlock () {
const box = new Box(-15, 0, 0)
this.renderer.scene.add(box.instance)
}
render () {
this.renderer.render()
requestAnimationFrame(() => { this.render() })
}
}
複製代碼
完善controller.js 和 view.js的邏輯
view.js
import GamePage from '../pages/game_page'
class GameView {
constructor () {
this.gamePage = null
}
initGamePage () {
this.gamePage = new GamePage()
this.gamePage.init()
}
}
export default new GameView()
複製代碼
controller.js
import gameView from './view'
class GameController {
constructor () {
this.gameView = gameView
}
initPages () {
this.gameView.initGamePage()
}
}
export default new GameController()
複製代碼
修改game.js
import './libs/weapp-adapter'
import * as THREE from './libs/three'
import controller from './src/game/controller'
GameGlobal.THREE = THREE
controller.initPages()
複製代碼
這時候去看開發者工具,應該會渲染出一個白色的立方體
可是仔細看圖中紅框部位鋸齒仍是挺明顯的,去官方論壇搜索了一下,找到了解決方案,要手動的設置一下canvas的寬高:
修改renderer -> index.js文件
/* 省略以前的代碼 */
init () {
this.camera = camera()
this.scene = scene()
/* 新增代碼 */
const { width, height } = canvas
if (window.devicePixelRatio) {
canvas.height = height * window.devicePixelRatio
canvas.width = width * window.devicePixelRatio
}
/* 新增代碼結束 */
this.instance = new THREE.WebGLRenderer({
canvas,
antialias: true
})
}
複製代碼
這時候再去看,鋸齒就消失了
新建 cylinder.js
import Base from './base'
export default class Cylinder extends Base {
constructor (x, y, z) {
super('cylinder')
this.x = x
this.y = y
this.z = z
this.create()
}
create () {
const geometry = new THREE.CylinderGeometry(
this.width / 2, this.width / 2, this.height, 120
)
const material = new THREE.MeshBasicMaterial({
color: 0xffffff
})
this.instance = new THREE.Mesh(geometry, material)
this.instance.position.set(this.x, this.y, this.z)
}
}
複製代碼
new THREE.CylinderGeometry
是three.js提供繪製圓柱體的方法,這裏的三個參數分別是:
修改game_page.js
import Cylinder from '../objects/block/cylinder' // 新增
/* 省略以前代碼 */
addBlock () {
const box = new Box(-15, 0, 0)
const cylinder = new Cylinder(20, 0, 0) // 新增
this.renderer.scene.add(box.instance)
this.renderer.scene.add(cylinder.instance) // 新增
}
複製代碼
修改完以後再去看看開發者工具
這樣一個基本的場景就行了,可是還缺燈光,陰影,背景,下一篇在寫。。
完整的代碼在這裏GitHub