Unity3D&Photon制作吃鸡游戏

https://study.163.com/course/courseMain.htm?share=1&shareId=8348227&courseId=1004507022

11 -- 程序书写规范

变量名使用Camel驼峰命名法:首字母小写,其余单词首字母大写

命名空间、类和方法名使用Pascal命名法:所有单词首字母大写

如果使用到英文单词的缩写,则全部大写:如ID

20 -- 使用Unity3D制作吃鸡手游的准备工作

https://dashboard.photonengine.com/zh-cn

为什么使用Photon服务器
  Photon服务器可以很好地实现游戏房间的匹配功能 -- 
    进入匹配房间,如果没有匹配的房间,则新建房间
    当房间人数达到一定数量,则会开始游戏

Photon插件:AssetStore下载:全名 Photon Unity Networking Classic - Free
  Import之后,会弹出一个设置向导(向导也可通过Window->PhotonUnityNeworking->PUN Wizard打开)
  点击Cloud DashBoard Login后打开网页,登录

创建Photon App:
  1. Photon Type = Photon PUN
  2. 点击创建

将创建好的App的AppID复制,在Unity->Window->PhotonUnityNetworking->PUN Wizard中点击Locate PhotonServerSettings,
  Hosting选择PhotonCloud (这里Region选择Jp,延迟比较低),粘贴AppID,Protocol选择Udp
  Client Settings的Pun Logging选择Full

通过代码与光子服务器进行连接

https://doc.photonengine.com/en-us/pun/current/getting-started/pun-intro

命名空间Photon.PunBehaviour,PhotonNetwork.ConnectUsingSettings(string gameVersion)
  参数gameVersion表示客户端版本号,用于分离版本

创建脚本Network.cs,在Awake()中写上PhotonNetwork.ConnectUsingSettings("0.0.1");
  将脚本挂载空游戏物体上,运行

与服务器连接成功

地形系统 -- Terrain

新建Terrain,发现没有所需的地形Texture

从商店导入Standard Assets素材包
人物模型https://pan.baidu.com/s/1An5Ro8pHMdjgnPAoBoRA_A,nubq

Terrain创建 -- 略

使用Standard Assets中的RigidBodyFPSController,用于控制人物,并导入人物模型(RifleAnimsetPro--Models) -- 略

21 -- 实现武器基本功能并添加特效
22 -- 完善射击功能

将枪模型RiflePlaceholder放在人物模型手上,并通过Animator实现动作

开枪功能 -- 在主角模型上挂脚本WeaponController.cs
  1. 当前弹夹中子弹数;2. 开枪动作播放;3. 开枪音效播放;4. Update()中检测是否按下鼠标左键
  5. 弹夹中子弹数不足则卡壳,播放卡壳音效

换弹夹功能 --
  1. Update()中检测是否按下R键;2. 子弹总数和当前弹夹中子弹数;3. 换弹动作播放;4. 换弹音效播放

开镜功能 -- 
  Camera的Field of View参数 即为开镜效果
  准星 -- canvas - image实现

枪口特效 --
  RifleAnimsetPro/Particles/MuzzleFlash
  放置于枪口,并在Shoot中控制播放
  private ParticleSystem m_ShootFx;
  m_ShootFx.Play();

射击功能的弹道 -- 
  暂时使用射线的方式实现射击功能,之后会优化改为真正的有弹道的子弹

// 射线模拟子弹
RaycastHit raycastHit;if (Physics.Raycast(m_MainCamera.transform.position, m_MainCamera.transform.forward, out raycastHit, m_FarestBulletReachableDistance)) {Debug.LogError(raycastHit.transform + " Shot");
}

22 -- 实现匹配功能

匹配UI -- 在net scene下制作一个按钮,实现点击加入房间的功能

加入房间相关Photon API:

让Net.cs类继承自Photon.PunBehaviour

加入房间: PhotonNetwork.JoinRandomRoom();

加入房间失败时的回调方法: OnPhotonRandomJoinFailed(object[] codeAndMsg) {}

创建房间: PhotonNetwork.CreateRoom(string roomName);

// 创建或加入房间:  PhotonNetwork.JoinOrCreateRoom(string roomName);
  没有试过该API,无需知道该名字的房间是否已经存在,加入或创建它

创建房间成功的回调方法: OnCreatedRoom() {}

加入房间成功时的回调方法: OnJoinedRoom() {}

有玩家成功连接入/加入房间的回调方法: OnPhotonPlayerConnected(PhotonPlayer newPlayer) {}

房间内所有玩家是否同步场景的属性: PhotonNetwork.automaticallySyncScene == true;
   // defines if all clients in a room should load the same level/scene as the Master client (if that used PhotonNetwork.LoadLevel())

判断当前客户端是否为主机(房主): PhotonNetwork.isMasterClient

加载场景: PhotonNetwork.LoadLevel(string sceneName); // 比如 PhotonNetwork.LoadLevel("main");

如何使用:

1. 将之前在Start()中调用的PhotonNetwork.ConnectUsingSettings("0.0.1"); 注册到一个Connect按钮上,成功连接上服务器后才启用加入房间的按钮
2. 一般来说,随机加入房间如果失败时,则自动创建一个房间
3. 一个房间中玩家数足够时,则自动开始游戏
4. 只有主机才需要加载场景,其他的客户端需要设置同步场景属性

功能扩展: 可以再加一个DropDown来控制房间玩家数(Photon好像最大支持20人同房)

24 -- 玩家位置同步

一场游戏里有很多个玩家,这些玩家的模型和位置都需要同步,因此一个场景中需要多个士兵模型

玩家脚本 -- PlayerUnit.cs

1. 如果玩家不是客户端控制的玩家,则不需要开启模型中的摄像机
2. 不是客户端控制的玩家,有一些组件是不需要开启的(包括1中的摄像机、角色控制脚本、武器脚本)
3. 有关同步的API: PhotonView

PlayerUnit脚本挂载角色身上,角色做成一个预制体,用于动态生成

用于管理生成玩家的脚本 -- PlayerGenerator.cs

在游戏场景main scene加载完成时,进行玩家的生成(PhotonNetwork.Instantiate())
-- SceneManager.sceneLoaded 注册事件

PhotonNetwork.Instantiate(string prefabName, Vector3 position, Quaternion rotation, byte group)
  -- 通过网络,实例化预制体,预制体需要位于Resources文件夹下
  -- group指的是PhotonView的组,填0即可

在需要通过Photon进行网络同步的物体(角色)上挂载脚本

PhotonView:

PhotonTransformView
  勾选需要同步的参数

需要将PhotonTransformView赋值给PhotonView的OvservedComponents属性中
  表示需要监测并同步PhotonTransformView中勾选的参数

将角色做成预制体,并在场景中删除

25 -- 同步伤害信息

玩家血量属性存在玩家信息类PlayerInfo中
  public int hp = 100;

在武器脚本中存放伤害值
  public int damage = 50;

在开火射线检测代码块判定是否打中玩家
  思路: 通过玩家tag判断
  如果是玩家,则玩家受伤,并需要将伤害同步给所有客户端

API: PhotonView.RPC(string methodName, PhotonPlayer targetPlayer, params object[] parameters)
  Call a RPC method of this GameObject on remote clients of this room( or on all, including this client)
  methodName: 调用的同步方法名 the name of the fitting method which has the RPC attribute
  targetPlayer: 需要同步给的客户端The group of targets and the way RPC gets sent
  parameters: 传入methodName方法的参数

if(raycastHit.collider.tag == "Player") {// 打到角色PhotonView pv = raycastHit.collider.GetComponent<PhotonView>();pv.RPC("GetDamage", PhotonTargets.All, m_Damage);
}

注意,在定义methodName方法时,需要写上 [PunRPC] -- 表示这是一个需要被实时同步的方法
  并继承自接口 IPunObserable的OnPhotonSerializeView(PhotonStream stream, PhotonMessageInfo info) {}
  在该方法中进行血量的同步

[PunRPC]
public void GetDamage(int damage) {m_CurrentHp -= damage;
}public void OnPhotonSerializeView(PhotonStream stream, PhotonMessageInfo info) {// 会发送给所有客户端(包括自己)if (stream.isWriting) {// 如果是写入者stream.SendNext(this.m_CurrentHp);} else {// 如果是读出者this.m_CurrentHp = (int)stream.ReceiveNext();}
}

26 -- 血条的绘制

在Player预制体下创建Canvas,用Slider制作简易血条(玩家自己的血条,位于屏幕下方)

血条的屏幕分辨率自适应
  将Canvas Scaler的UI Scale Mode设为Scale With Screen Size
  将Match调至Height处,表示以Height为基础做的自适应

在PlayerInfo中控制Slider的value值
  在同步方法中同步Slider的value值

[PunRPC]
    m_CurrentHp -= damage;if(m_CurrentHp < 0) {m_CurrentHp = 0;}slider.value = m_CurrentHp;
}public void OnPhotonSerializeView(PhotonStream stream, PhotonMessageInfo info) {// 会发送给所有客户端(包括自己)if (stream.isWriting) {// 如果是写入者stream.SendNext(this.m_CurrentHp);stream.SendNext(this.slider.value);} else {// 如果是读出者this.m_CurrentHp = (int)stream.ReceiveNext();this.slider.value = (int)stream.ReceiveNext();// 个人理解这里不必再传slider.value的值,直接在m_CurrentHp变化的地方触发更新即可
    }
}

视频教程中用的方法是:每一个PlayerUnit都配备一个Slider用于显示血条,但是在PlayerUnit的ComponentsToBeHiden的列表里加上该血条
  个人做法: 只做一个血条Slider,用PhotonView.isMine判断是否为本客户端的玩家,在PlayerManager(作为总控制(所有玩家)的脚本中)控制HpBar

27 -- IK的使用

https://docs.unity3d.com/Manual/InverseKinematics.html ---- 看一看,介绍地很详细
https://www.jianshu.com/p/7aec3699f29c -- 很详细

完善玩家视角变动(抬高压低)时,枪口跟随的功能

IK: Inverse Kinematics -- 反向动力学

一般而言,多数动画是通过旋转骨架关节的角度来实现的,这个称为 Forward Kinematics

而IK指的是从下至上的驱动
  是根据骨骼的终节点来推算其他父节点的位置的一种方法。比如通过手的位置推算手腕、胳膊肘的骨骼的位置。
  比如设置好手部位置后,角色起身时手部会保持不动,而小臂和大臂的古河会自动旋转到合适角度;
  或者在脚步踩入地面的行走动画(沼泽地)情况下,在运行时通过调整IK target来实现角色在不平坦的地面行走的效果
  仅支持配置正确的人形角色 (supported in Mecanim for any humanoid character with a correctly configured Avatar)

人形角色指的是:预制体设置的Rig->AnimationType=Humanoid

IK的使用

1. 人物模型预制体的设置Rig->AnimationType设为Humanoid

设置为Humanoid后,会自动在人物模型预制体下生成一个人物骨骼CharacterAvatar

2. 在动画控制器中的Layers Pane勾选IK

3. 在Animator组件中勾选Apply Root Motion

To set up IK for a character, you typically have objects around the scene that a character interacts with, and then set up the IK through script, in particular, Animator functions like SetIKPositionWeight, SetIKRotationWeight, SetIKPosition, SetIKRotation, SetLookAtPositionbodyPositionbodyRotation

4. Animator组件中的Avatar赋值为Humanoid自动生成的CharacterAvatar(这一步骤做了之后 播放动画的问题很大)

5. 实现IK实际功能的脚本 (即https://docs.unity3d.com/Manual/InverseKinematics.html 中的案例)

using UnityEngine;
using System;
using System.Collections;[RequireComponent(typeof(Animator))]
public class IKController : MonoBehaviour {protected Animator animator;public bool ikActive = false;public Transform rightHandObj = null;public Transform lookObj = null;void Start() {animator = GetComponent<Animator>();}//a callback for calculating IKvoid OnAnimatorIK() {if (animator) {//if the IK is active, set the position and rotation directly to the goal. if (ikActive) {// 这里只需要用到这个// Set the look target position, if one has been assignedif (lookObj != null) {// 看向某个目标点时,各个部位旋转的比重animator.SetLookAtWeight(1, 1, 1, 1);animator.SetLookAtPosition(lookObj.position);}// Set the right hand target position and rotation, if one has been assignedif (rightHandObj != null) {animator.SetIKPositionWeight(AvatarIKGoal.RightHand, 1);animator.SetIKRotationWeight(AvatarIKGoal.RightHand, 1);animator.SetIKPosition(AvatarIKGoal.RightHand, rightHandObj.position);animator.SetIKRotation(AvatarIKGoal.RightHand, rightHandObj.rotation);}}//if the IK is not active, set the position and rotation of the hand and head back to the original positionelse {animator.SetIKPositionWeight(AvatarIKGoal.RightHand, 0);animator.SetIKRotationWeight(AvatarIKGoal.RightHand, 0);animator.SetLookAtWeight(0);
}}}}

6. 在Player下的Camera下创建空物体(因为需要看向的位置是与摄像机有关的,所以作为Camera的子物体)
  将该空物体放置在Camera前的合适位置,作为枪口指向的点
  并将该空物体赋值给IKController.lookObj

28 -- 使用WheelCollider控制车辆

素材: pan.baidu.com/wap/init?surl=sA1JWo39facMXIa4M97dFQ 5n1b

导入模型,并加上四个WheelCollider
  注:使用WheelCollider的必要条件是,父物体上需要挂有RigidBody组件

转载于:https://www.cnblogs.com/FudgeBear/p/10908706.html

Unity3DPhoton制作吃鸡游戏相关推荐

  1. Unity 使用C#制作一个吃鸡游戏跑圈机制

    最近迷上吃鸡游戏,慢慢对他的跑圈机制产生了兴趣,于是就试着写了个吃鸡游戏跑圈机制出来~~~ 一.话不多少,先上跑圈效果图: 二.知识提要: 1.C# winform程序中比较简单的绘图控件就是 Pic ...

  2. 达威尔CHERRY樱桃轴 铝合金有线背光电竞吃鸡游戏机械键盘

    作为一名电脑办公的打工仔,如果你有四五年以上的工作经验,可以毫不夸张地说,你至少用过三只以上的键盘了吧?这是最少的了,有的朋友用过的键盘都有十几把了,用过的键盘牌子也有不少了.我打工几年,就用过好几个 ...

  3. mac版免费吃鸡游戏(荒野行动)

    最近吃鸡游戏非常的火爆,现为大家推出一款Mac腾讯吃鸡游戏"荒野行动 for Mac",是由网易游戏研发的一款射击求生类游戏,该游戏讲述了远洋岛事件爆发之后,小岛遭到极端分子洗劫的 ...

  4. 做了一个仿吃鸡游戏,可多人联网,算是学习总结。

    网上偶见UNITY,很有兴趣于是自学了一段时间,这是我做的一个仿吃鸡游戏DEMO,虽然只是抱着学习实践的很低要求,但从代码.模型.美工.场景都要自己做,繁杂超过了我的预估.对次时代游戏有兴趣可加我qq ...

  5. steam+linux+吃鸡游戏,steam十款免费吃鸡大逃杀游戏推荐

    今天为大家推荐十款steam免费吃鸡大逃杀游戏.虽然是免费游戏,但还是有许多因为玩法创新而被玩家热捧,如果你喜欢吃鸡游戏,又不愿意花钱买,那么今天的推荐不容错过! <瓦尔格雷夫:不朽的平原> ...

  6. 6点让吃鸡游戏成为热点

    吃鸡已经成为了当今游戏的热点词汇,各大游戏厂商纷纷效仿,拉拢人气.为什么吃鸡游戏如此火爆,游戏音效制作小编认为主要是由于背后这6点必要因素. 1.角色设计必须-- 吸引人.如果当人们首次看到角色时发现 ...

  7. 黑产盯上“吃鸡”游戏 木马盛行勒索扣费

    阿里巴巴旗下钱盾反诈实验室近日监测到,黑客利用吃鸡玩家的游戏排名以及游戏账号的预约痛点,开发了多种木马病毒,以锁屏勒索.恶意扣费.捆绑恶意代码等方式来达到感染用户手机,勒索钱财的目的. 文/鲸朔 &q ...

  8. 计算机内存不足吃鸡怎么办,Win10玩吃鸡游戏提示虚拟内存不足怎么办?

    Win10玩吃鸡游戏提示"虚拟内存不足"怎么办? 最近吃鸡游戏非常火,大家都想大吉大利晚上吃鸡!因为吃鸡游戏对电脑配置的要求非常高,所以很多用户在玩吃鸡手游时会遇到各种问题,最常见 ...

  9. MOBA类和“吃鸡”游戏为什么对网络延迟要求高?

    作者:腾讯云技术社区 链接:https://zhuanlan.zhihu.com/p/54468154 来源:知乎 著作权归作者所有.商业转载请联系作者获得授权,非商业转载请注明出处. 我们知道,不同 ...

最新文章

  1. java 实体类包含list 怎么取值_2019 最新 500 道 Java 面试题
  2. hdu 5248(二分+贪心)
  3. backbonejs mvc框架的增删查改实例
  4. Rabbtmq 消费端-幂等性保障
  5. Eclipse集成ijkplayer并实现本地和网络视频播放等
  6. JS 变量的数据类型 运算符
  7. 拓端tecdat|R语言使用Metropolis- Hasting抽样算法进行逻辑回归
  8. 浅谈网络游戏的设计——服务器端编程 (2)
  9. java web缓存技术
  10. Tkinter教程(每天半小时,3天彻底掌握Tkinter)day1
  11. 计算机报名照片 1寸,国考录用系统2021国家公务员考试报名照片尺寸是1寸还是2寸?...
  12. 终于有人把流量运营讲明白了
  13. Tushare股票数据全生命周期MACD等指标动态获取计算-前复权
  14. 超链接 与众不同的鼠标滑过超链接下划线动画效果
  15. 《大话物联网(第2版)》赠书活动名单公告
  16. 2023年全国最新二级建造师精选真题及答案59
  17. LED护眼灯真的可以护眼吗?2022专业护眼台灯品牌排行榜
  18. Web Spider 常见混淆EVAL、AA、JJ、JSFUCK
  19. Activity A 调用Activity B 里的方法探索
  20. 项目实训2021.07.02

热门文章

  1. 计算机的垃圾站是在硬盘,教你五步清理电脑垃圾,让硬盘再多20G!
  2. 前端页面最佳适配方案px转rem(野草蛮生)
  3. linux 重置bios密码忘记,Windows10专业版下重置BIOS密码的技巧
  4. 都说MES能提高企业生产效率,具体表现在哪些方面呢?
  5. [医学图像Transformer]TransUNet: Transformers Make Strong Encoders for Medical Image Segmentation
  6. ETL的过程原理及数据仓库建设
  7. Java--web.xml加载过程;文件标签详解
  8. 13个Tensorflow实践案例,教你入门到进阶
  9. 电商用户消费数据RFM分析
  10. 新概念英语第二册课文电子版_文林热点|丽江文林实验学校高二年级新概念英语课文背诵比赛圆满落幕!...