日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Cocos Creator实现FPS经典瞄准镜+监视器

發布時間:2023/12/18 编程问答 30 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Cocos Creator实现FPS经典瞄准镜+监视器 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

引言:前兩周,「Cocos Star Writer」Nowpaper 在《籠中窺夢》視錯覺效果的實現中使用了 RenderToTexture 技術,本次 Nowpaper 將繼續拓展 RenderToTexture 的使用法。

RenderToTexture 是個非常有趣的技術,它能夠將一個攝像機畫面渲染成紋理,然后和材質結合,讓某一個 Mesh 顯示成指定的畫面。在游戲開發中,它被廣泛用于實現鏡子、監視器畫面、瞄準鏡、傳送門,甚至用戶界面顯示、動態紋理噴涂等。

在 Cocos Creator 3.4 以后的版本中,RenderToTexture 技術已經相對完善,使用起來也更加方便。在我之前的傳送門分享中,傳送門里的畫面就使用了這個技術來實現,當時還得寫一些代碼,而現在只需要在編輯器中編輯,就可以輕松實現可渲染紋理了。

今天我們將繼續拓展一下,使用 RenderToTexture 做一個瞄準鏡以及顯示指定攝像機的畫面監視器。

PS.源碼和視頻教程見文末。本次使用的是 v3.5。

準備

首先新建一個項目并搭建游戲場景。我這里就搭建一個簡單的街道,包含一些物體,讓場景看起來稍微不那么單調。

瞄準鏡

一般來說當角色瞄準的時候,我們可以看到在鏡頭中,顯示的畫面被放大,視覺更加前向。

這個效果的原理其實就是:在槍械的瞄準位置增加一個攝像機,然后將攝像機的畫面渲染到一個紋理上。

這樣的話事情就簡單了。我準備了一個槍械,它帶有瞄準動畫,現在為他增加一個第一人稱攝像機,通過調整讓它看起來比較合適。

現在新建一個可渲染紋理:

圖像寬高數值默認都是1,這個需要我們依據自己的情況作修改,通常是按照視口的大小比例來調整。如果要想完美適配的話,最好是代碼中作一些控制,在這里我們就直接使用 512x512:

現在再創建一個材質:

著色器選擇為內置-unlit:

開啟 UseTexture,勾選 RTTexture 選項,將剛剛新建的可渲染紋理拖動進下面的引用中:

現在為瞄準鏡建立一個圓形面片。一般來說建模師會提供一個,在這里我們就直接自己放個圓柱形,通過節點調整到對應的 Node 中:

現在選擇槍械的動畫,去掉動畫預烘培:

關于動畫控制腳本,在這里就不提供了,播放 Animation 的指定動畫即可:

選擇這個圓柱,將它的材質更換為剛剛創建的瞄準鏡材質:

接下來在瞄準組件中添加一個攝像機,并且調整好位置,拍攝倍率直接修改 Fov 數值即可:

根據攝像機預覽畫面,調整好數值以后,往下拉到最下面,在 RenderToTexture 中,將之前建立的名為「瞄準鏡」的可渲染紋理,拖進其中:

如果一切順利,我們可能直接就在編輯器中看到效果。現在運行一下(我這里使用了自定義腳本,讓瞄準的動作看起來更加準確),你可以看到在瞄準鏡中已經有了放大的畫面,我們再走動一下瞄準不同的地方試試:

到此為止,瞄準鏡的實現就已經搞定了,是不是很簡單呢,下面我們試一下監視器效果。

監視器

在很多游戲中,玩家可以通過監視器屏幕看到攝像頭傳來的數據,這類效果同樣也是使用 RenderToTexture 實現。本次我們將做一個無人機控制板+一個街頭的攝像機。

同樣也是使用前面搭建的街景,在這個房間場景中,我們用一個框框來表示無人機控制板;而監視器的畫面則直接投射到電視中。完成了這兩個后,將空間中的面片放置到準確位置,并且放置一個攝像機觀察場景:

新建一個可渲染紋理,命名為「無人機」,同樣建立一個材質,著色器選內置-unlit,然后選擇 UseTexture,勾選 RT,下面選擇對應的可渲染紋理。這里我們就不新建監視器的渲染紋理和材質了,直接使用之前瞄準鏡的即可:

現在分別建立兩個攝像機,為方便觀察將無人機簡單做成一個小飛機的樣子:

然后將街頭攝像機擺好俯視即可,適當地作一些腳本完成控制,這些腳本如下:

first-person-camera.ts 來自官方例子工程:

import?{?_decorator,?Component,?math,?systemEvent,?SystemEvent,?KeyCode,?game,?cclegacy,?Touch,?EventKeyboard,?EventMouse?}?from?"cc"; const?{?ccclass,?property,?menu?}?=?_decorator; const?v2_1?=?new?math.Vec2(); const?v2_2?=?new?math.Vec2(); const?v3_1?=?new?math.Vec3(); const?qt_1?=?new?math.Quat(); const?id_forward?=?new?math.Vec3(0,?0,?1); const?KEYCODE?=?{W:?'W'.charCodeAt(0),S:?'S'.charCodeAt(0),A:?'A'.charCodeAt(0),D:?'D'.charCodeAt(0),Q:?'Q'.charCodeAt(0),E:?'E'.charCodeAt(0),w:?'w'.charCodeAt(0),s:?'s'.charCodeAt(0),a:?'a'.charCodeAt(0),d:?'d'.charCodeAt(0),q:?'q'.charCodeAt(0),e:?'e'.charCodeAt(0),SHIFT:?KeyCode.SHIFT_LEFT?, };@ccclass("COMMON.FirstPersonCamera") @menu("common/FirstPersonCamera") export?class?FirstPersonCamera?extends?Component?{@propertymoveSpeed?=?1;@propertymoveSpeedShiftScale?=?5;@property({?slide:?true,?range:?[0.05,?0.5,?0.01]?})damp?=?0.2;@propertyrotateSpeed?=?1;_euler?=?new?math.Vec3();_velocity?=?new?math.Vec3();_position?=?new?math.Vec3();_speedScale?=?1;onLoad()?{math.Vec3.copy(this._euler,?this.node.eulerAngles);math.Vec3.copy(this._position,?this.node.position);}onDestroy()?{this._removeEvents();}onEnable()?{this._addEvents();}onDisable()?{this._removeEvents();}update(dt:?number)?{//?positionmath.Vec3.transformQuat(v3_1,?this._velocity,?this.node.rotation);math.Vec3.scaleAndAdd(this._position,?this._position,?v3_1,?this.moveSpeed?*?this._speedScale);math.Vec3.lerp(v3_1,?this.node.position,?this._position,?dt?/?this.damp);this.node.setPosition(v3_1);//?rotationmath.Quat.fromEuler(qt_1,?this._euler.x,?this._euler.y,?this._euler.z);math.Quat.slerp(qt_1,?this.node.rotation,?qt_1,?dt?/?this.damp);this.node.setRotation(qt_1);}private?_addEvents()?{systemEvent.on(SystemEvent.EventType.MOUSE_WHEEL,?this.onMouseWheel,?this);systemEvent.on(SystemEvent.EventType.KEY_DOWN,?this.onKeyDown,?this);systemEvent.on(SystemEvent.EventType.KEY_UP,?this.onKeyUp,?this);systemEvent.on(SystemEvent.EventType.TOUCH_MOVE,?this.onTouchMove,?this);systemEvent.on(SystemEvent.EventType.TOUCH_END,?this.onTouchEnd,?this);}private?_removeEvents()?{systemEvent.off(SystemEvent.EventType.MOUSE_WHEEL,?this.onMouseWheel,?this);systemEvent.off(SystemEvent.EventType.KEY_DOWN,?this.onKeyDown,?this);systemEvent.off(SystemEvent.EventType.KEY_UP,?this.onKeyUp,?this);systemEvent.off(SystemEvent.EventType.TOUCH_MOVE,?this.onTouchMove,?this);systemEvent.off(SystemEvent.EventType.TOUCH_END,?this.onTouchEnd,?this);}onMouseWheel(e:?EventMouse)?{const?delta?=?-e.getScrollY()?*?this.moveSpeed?/?24;?//?delta?is?positive?when?scroll?downmath.Vec3.transformQuat(v3_1,?id_forward,?this.node.rotation);math.Vec3.scaleAndAdd(v3_1,?this.node.position,?v3_1,?delta);this.node.setPosition(v3_1);}onKeyDown(e:?EventKeyboard)?{const?v?=?this._velocity;if?(e.keyCode?===?KEYCODE.SHIFT)?{?this._speedScale?=?this.moveSpeedShiftScale;?}else?if?(e.keyCode?===?KEYCODE.W?||?e.keyCode?===?KEYCODE.w)?{?if?(v.z?===?0)?{?v.z?=?-1;?}?}else?if?(e.keyCode?===?KEYCODE.S?||?e.keyCode?===?KEYCODE.s)?{?if?(v.z?===?0)?{?v.z?=?1;?}?}else?if?(e.keyCode?===?KEYCODE.A?||?e.keyCode?===?KEYCODE.a)?{?if?(v.x?===?0)?{?v.x?=?-1;?}?}else?if?(e.keyCode?===?KEYCODE.D?||?e.keyCode?===?KEYCODE.d)?{?if?(v.x?===?0)?{?v.x?=?1;?}?}else?if?(e.keyCode?===?KEYCODE.Q?||?e.keyCode?===?KEYCODE.q)?{?if?(v.y?===?0)?{?v.y?=?-1;?}?}else?if?(e.keyCode?===?KEYCODE.E?||?e.keyCode?===?KEYCODE.e)?{?if?(v.y?===?0)?{?v.y?=?1;?}?}}onKeyUp(e:?EventKeyboard)?{const?v?=?this._velocity;if?(e.keyCode?===?KEYCODE.SHIFT)?{?this._speedScale?=?1;?}else?if?(e.keyCode?===?KEYCODE.W?||?e.keyCode?===?KEYCODE.w)?{?if?(v.z?<?0)?{?v.z?=?0;?}?}else?if?(e.keyCode?===?KEYCODE.S?||?e.keyCode?===?KEYCODE.s)?{?if?(v.z?>?0)?{?v.z?=?0;?}?}else?if?(e.keyCode?===?KEYCODE.A?||?e.keyCode?===?KEYCODE.a)?{?if?(v.x?<?0)?{?v.x?=?0;?}?}else?if?(e.keyCode?===?KEYCODE.D?||?e.keyCode?===?KEYCODE.d)?{?if?(v.x?>?0)?{?v.x?=?0;?}?}else?if?(e.keyCode?===?KEYCODE.Q?||?e.keyCode?===?KEYCODE.q)?{?if?(v.y?<?0)?{?v.y?=?0;?}?}else?if?(e.keyCode?===?KEYCODE.E?||?e.keyCode?===?KEYCODE.e)?{?if?(v.y?>?0)?{?v.y?=?0;?}?}}onTouchMove(e:?Touch)?{e.getStartLocation(v2_1);if?(v2_1.x?>?cclegacy.winSize.width?*?0.4)?{?//?rotatione.getDelta(v2_2);this._euler.y?-=?v2_2.x?*?0.5;this._euler.x?+=?v2_2.y?*?0.5;}?else?{?//?positione.getLocation(v2_2);math.Vec2.subtract(v2_2,?v2_2,?v2_1);this._velocity.x?=?v2_2.x?*?0.01;this._velocity.z?=?-v2_2.y?*?0.01;}}onTouchEnd(e:?Touch)?{e.getStartLocation(v2_1);if?(v2_1.x?<?cclegacy.winSize.width?*?0.4)?{?//?positionthis._velocity.x?=?0;this._velocity.z?=?0;}}changeEnable()?{this.enabled?=?!this.enabled;} }

PlayerController.ts:

import?{?_decorator,?Component,?Node,?KeyCode,?EventKeyboard,?RigidBody,?Vec3,?v3,?input,?Input?}?from?'cc'; const?{?ccclass,?property?}?=?_decorator;@ccclass('PlayerController') export?class?PlayerController?extends?Component?{@propertymoveSpeed?=?10;@propertyrotSpeed?=?90;private?keyMap?=?{};start()?{input.on(Input.EventType.KEY_DOWN,this.onKeyDown,this);input.on(Input.EventType.KEY_UP,this.onKeyUp,this);}setRotSpeed(value){this.rotSpeed?=?value;}private?onKeyDown(e:?EventKeyboard)?{this.keyMap[e.keyCode]?=?true;}private?onKeyUp(e:?EventKeyboard)?{this.keyMap[e.keyCode]?=?false;}private?vec3:Vec3?=?v3();update(deltaTime:?number)?{????????if?(this.keyMap[KeyCode.KEY_W])?{Vec3.add(this.vec3,this.node.position,this.node.forward.clone().multiplyScalar(-this.moveSpeed?*?deltaTime));this.node.position?=?this.vec3;?}?else?if?(this.keyMap[KeyCode.KEY_S])?{Vec3.add(this.vec3,this.node.position,this.node.forward.clone().multiplyScalar(this.moveSpeed?*?deltaTime));this.node.position?=?this.vec3;?}else?{}if?(this.keyMap[KeyCode.KEY_A])?{this.node.setRotationFromEuler(0,this.node.eulerAngles.y?+?deltaTime?*?this.rotSpeed,0);}else?if?(this.keyMap[KeyCode.KEY_D])?{this.node.setRotationFromEuler(0,this.node.eulerAngles.y?+?deltaTime?*?-this.rotSpeed,0);}} }

FirstPersonGunCamreSc.ts:

import?{?_decorator,?Component,?Node,?CCObject,?Vec3,?Quat,?tween,?Camera?}?from?'cc'; const?{?ccclass,?property?}?=?_decorator;@ccclass('FirstPersonGunCamreSc') export?class?FirstPersonGunCamreSc?extends?Component?{private?original_position:Vec3;@property(Camera)aniCamera:Camera?=?null;start()?{this.original_position?=?this.node.position.clone();}aim(){tween(this.node).to(0.3,{position:this.aniCamera.node.position}).start();tween(this.getComponent(Camera)).to(0.3,{fov:this.aniCamera.fov}).start();}unAim(){tween(this.node).to(0.3,{position:this.original_position}).start();tween(this.getComponent(Camera)).to(0.3,{fov:45}).start();}update(deltaTime:?number)?{} }

GunSc.ts:

import?{?_decorator,?Component,?Node,?SkeletalAnimation,?input,?Input,?EventKeyboard,?misc,?KeyCode?}?from?'cc'; import?{?FirstPersonGunCamreSc?}?from?'./FirstPersonGunCamreSc'; import?{?PlayerController?}?from?'./PlayerController'; const?{?ccclass,?property?}?=?_decorator;@ccclass('GunSc') export?class?GunSc?extends?Component?{@property(SkeletalAnimation)gunSA:SkeletalAnimation?=?null;@property(FirstPersonGunCamreSc)FirstPersonGunCam:FirstPersonGunCamreSc?=?null;start()?{this.playIndex(5);input.on(Input.EventType.KEY_DOWN,this.onKeyDown,this);}private?_isaim?=?false;private?onKeyDown(e:EventKeyboard){if(e.keyCode?==?KeyCode.SPACE){this._isaim?=?!this._isaim;if(this._isaim){this.aim();}else{this.unAim();}}}update(deltaTime:?number)?{}private?playIndex(index)?{const?animatname?=?this.gunSA.clips[index].name;this.gunSA.play(animatname);this.gunSA.crossFade(animatname);}aim(){this.FirstPersonGunCam.aim();this.playIndex(1);this.getComponent(PlayerController)?.setRotSpeed(30);}unAim(){this.playIndex(5);this.FirstPersonGunCam.unAim();this.getComponent(PlayerController)?.setRotSpeed(90);} }

現在給攝像機上添加渲染紋理,為監視器添加對應的材質。如此一來,我們在電視上看到了街頭監視器畫面,而屏幕左邊則投射了無人機畫面。由于有控制腳本,我們可以控制它到處飛行一下,看看效果:

資源鏈接

  • 源碼下載丨Cocos Store

https://store.cocos.com/app/detail/3803

  • 視頻教程(UP 主:Nowpaper)

https://www.bilibili.com/video/BV1S34y1j7Ha

  • 論壇討論帖:

https://forum.cocos.org/t/topic/136021

今天的文章就到這里,我是 Nowpaper,一個混跡游戲行業的老爸,如果您喜歡我的分享,不妨多多點贊留言,也歡迎關注我的 B 站,您的支持是我更新的動力,下次再見!

Nowpaper 往期分享

《籠中窺夢》多維空間視錯覺效果

《守望先鋒》同級的槍彈射擊體驗

《時空幻境》時間倒放玩法

《饑荒》同款視覺表現

用 RenderTexture 實現小地圖與傳送門

Cocos Store 正在舉辦618大促活動,超低優惠

還有Cocos周邊實物禮品贈送!

總結

以上是生活随笔為你收集整理的Cocos Creator实现FPS经典瞄准镜+监视器的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

主站蜘蛛池模板: 操丰满女人 | 欧美美女爱爱视频 | 精品国产高清在线观看 | 阿v视频免费在线观看 | 西西午夜视频 | 日韩av中文字幕在线 | 超碰夫妻| 成人欧美在线观看 | 在线观看成年人网站 | 严厉高冷老师动漫播放 | 狠狠艹视频 | 熟女少妇精品一区二区 | 在线免费av网 | 少妇色欲网 | 天天天天天操 | 日本大尺度吃奶做爰久久久绯色 | 极品色影视 | 综合性色 | 91爽爽| 少妇精品一区二区 | 亚洲乱色熟女一区二区三区 | 国产又粗又猛又爽又黄视频 | 婷婷激情社区 | 粉嫩视频在线观看 | 日日碰狠狠躁久久躁蜜桃 | 欧美在线视频网站 | 日日摸夜夜添狠狠添欧美 | 人人澡人人射 | 少妇被躁爽到高潮无码文 | 超碰最新在线 | 9l视频自拍蝌蚪9l视频成人 | 天天做天天爱天天做 | 精品自拍偷拍 | 在线观看的黄网 | 国产麻豆剧传媒精品国产av | av网站一区二区 | 国产高清露脸 | 亚洲一区欧美一区 | 国内露脸中年夫妇交换 | 一本色道久久hezyo无码 | 轻点好疼好大好爽视频 | 国产在线观看精品 | 精品自拍一区 | 日本伊人色 | 国产精品免费无遮挡无码永久视频 | 日批免费在线观看 | 久热国产视频 | 后入内射欧美99二区视频 | 麻豆亚洲 | 日韩成年视频 | 色在线看 | 亚洲 欧美 另类 综合 偷拍 | 国产高清一二三区 | 麻豆md0077饥渴少妇 | 男人添女人囗交视频 | 成人午夜在线免费观看 | 欧美第一视频 | 91天堂网| 91精品国产日韩91久久久久久 | 精品福利在线 | 69精品丰满人妻无码视频a片 | jizz日韩| 全黄性性激高免费视频 | 一级a性色生活片久久无 | 51人人看 | 婷婷中文| 欧美无马 | 天天看夜夜 | 狠狠狠狠狠狠干 | 精品国产乱码久久久久夜深人妻 | 久久成人福利 | 在线观看免费福利 | 日批免费在线观看 | 中文字幕少妇在线三级hd | 国产欧美一区二区精品性色超碰 | 亚洲高清在线观看视频 | 农村妇女精品一区二区 | 我要色综合天天 | 国产精品婷婷午夜在线观看 | 越南性xxxx精品hd | 精品伦一区二区三区 | 爱情岛论坛成人 | 人人妻人人藻人人爽欧美一区 | 在线免费看av的网站 | 色黄网站在线观看 | 精品日韩av | 久久视频这里只有精品 | 国产偷人爽久久久久久老妇app | 黄色免费网站视频 | 人妻熟人中文字幕一区二区 | 国产乱人对白 | 精品免费国产一区二区三区 | 中文在线字幕免费观 | 青青在线视频观看 | 九九视频免费看 | 97人人视频 | 国产女人在线视频 | 欧美亚洲日本一区 | 日本全黄裸体片 |