国产xxxx99真实实拍_久久不雅视频_高清韩国a级特黄毛片_嗯老师别我我受不了了小说

資訊專欄INFORMATION COLUMN

電影《動物世界》對戰(zhàn)系統(tǒng)(Javascript)

娣辯孩 / 2226人閱讀

摘要:最近刷了一部電影動物世界,感概原來簡單的剪刀石頭布游戲還可以這么燒腦,強大的數(shù)據(jù)分析能力對人性心理的靈敏嗅覺等。看完之后饒有興致,于是便利用技術,實現(xiàn)了一個動物世界多人對戰(zhàn)系統(tǒng)。

最近刷了一部電影《動物世界》,感概原來簡單的“剪刀石頭布”游戲還可以這么燒腦,強大的數(shù)據(jù)分析能力、對人性心理的靈敏嗅覺等。看完之后饒有興致,于是便利用socket技術,實現(xiàn)了一個“動物世界”多人對戰(zhàn)系統(tǒng)。

游戲背景

故事講述的是男主被發(fā)小欺騙,欠下了一屁股債,為了償還債務被迫上了一艘賊船,同時上船的還有一批人,大伙兒的狀況都差不多。上船的好處是有機會還清債務并且還可能獲得一筆巨大的財富,這對于在現(xiàn)實世界中已經(jīng)生活不能自理的人來說,無疑是一次改變?nèi)松臋C會,而一旦失敗的話,就要被拉去做人體實驗(恐怖如斯)。

上船的人會進行一場賭博,就是我們小時候常玩的“石頭剪刀布”,每人初始時擁有12張卡牌,石頭、剪刀、布各4張,并且擁有3顆星,大家可以找任何一個人作為對手,每人各出一張卡牌,獲勝者將從失敗方拿走一顆星。游戲獲勝條件是手里卡牌全部消耗完并且擁有的星星不少于3顆,反之,若卡牌消耗完且星星少于3顆、或還有卡牌但星星為0,都視為失敗。

后端邏輯

我們將利用koa來搭建一個socket服務器,來管理客戶端的消息接受和分發(fā)。

主要邏輯:

const io = SocketIO(server) // 建立socket連接
const users = {} // 緩存當前鏈接的用戶
const challengeData = {} // 緩存用戶發(fā)起的對戰(zhàn)信息

io.on("connection", socket => { // 客戶端連接后
  const id = socket.id // 當前連接的unique標識

  socket.emit("connected") // 告訴客戶端已經(jīng)連接成功

  // 接收客戶端的open事件
  socket.on("open", name => {
    // 初始化數(shù)據(jù)
    users[id] = {
      id,
      name, // 用戶昵稱
      star: 3, // 用戶擁有的星星
      stone: 4, // 用戶擁有的“石頭”卡牌數(shù)量
      scissors: 4, // 用戶擁有的“剪刀”卡牌數(shù)量
      paper: 4 // 用戶擁有的“布”卡牌數(shù)量
    }

    // 通知所有人,當前所有用戶的信息
    io.emit("update_users", users)
  })

  // 用戶發(fā)起挑戰(zhàn)
  socket.on("challenge", data => {
    // data包括fromCard(發(fā)起者出示的卡牌)、toId(被挑戰(zhàn)者的id)
    data.fromId = id
    challengeData[id] = data
    io.to(data.toId).emit("accept_challenge", users[id]) // 告訴對方有人要和你對戰(zhàn)
  })

  // 發(fā)起者取消了挑戰(zhàn)
  socket.on("cancel_challenge", () => {
    io.to(challengeData[id].toId).emit("cancel_challenge") // 告訴對方挑戰(zhàn)已取消
    delete challengeData[id] // 刪除緩存的數(shù)據(jù)
  })

  // 對方接受挑戰(zhàn)的信息
  socket.on("respond_challenge", data => {
    if (data.accept) { // 接受
      let cd = challengeData[data.fromId]
      cd.toCard = data.toCard // 被挑戰(zhàn)者出示的卡牌

        // 雙方卡牌各減少1
      users[cd.fromId][cd.fromCard]--
      users[cd.toId][cd.toCard]--

      let result = getChallengeResult(cd.fromCard, cd.toCard) // 獲得挑戰(zhàn)結(jié)果

        // 比賽后的星星變更
      if (result === 1) {
        users[cd.fromId].star++
        users[cd.toId].star--
      } else if (result === -1) {
        users[cd.fromId].star--
        users[cd.toId].star++
      }

        // 告訴挑戰(zhàn)者和被挑戰(zhàn)者,比賽的結(jié)果
      io.to(cd.fromId).emit("result_challenge", result, users)
      io.to(cd.toId).emit("result_challenge", -result, users)
    } else { // 拒絕
      io.to(data.fromId).emit("cancel_challenge") // 告訴發(fā)起者對方不接受挑戰(zhàn)
    }

    delete challengeData[data.fromId]
  })

  // 比賽勝利
  socket.on("success_challenge", () => {
    // 告訴所有人,有人獲得了勝利
    socket.broadcast.emit("success_challenge", users[id])
  })

  // 斷開連接
  socket.on("disconnect", () => {
    delete users[id]
    // 廣播用戶已退出
    socket.broadcast.emit("update_users", users)
  })
})
前端邏輯

前端使用Vue來進行頁面渲染。

import request from "@/common/request"
import tips from "@axe/tips"
import modal from "@axe/modal"

import Loading from "./components/Loading.vue"

/* eslint-disable no-alert */
export default {
  name: "App",
  components: {
    Loading
  },
  data () {
    return {
      isConnected: false,
      id: "",
      selectedUserId: "",
      selectedCard: "",
      users: {},
      acceptChallenge: false
    };
  },
  computed: {
    userInfo () {
      let user = this.users[this.id] || {}

      return {
        star: user.star || 0,
        stone: user.stone || 0,
        scissors: user.scissors || 0,
        paper: user.paper || 0
      }
    },
    totalInfo () {
      let info = {
        stone: 0,
        scissors: 0,
        paper: 0
      }

      for (let id in this.users) {
        let user = this.users[id]

        info.stone += user.stone || 0
        info.scissors += user.scissors || 0
        info.paper += user.paper || 0
      }

      return info
    }
  },
  methods: {
    handleSelectCard (type) {
      this.selectedCard = type
    },
    handleSelectUser (id) {
      if (this.id === id) {
        tips.show({
          content: "不可以挑戰(zhàn)自己哦"
        })
        return
      }

      this.selectedUserId = id
    },
    handleChallenge () {
      if (this.gameover) {
        tips.show({
          content: "游戲已結(jié)束,請重新開始"
        })
        return
      }

      if (!this.selectedCard) {
        tips.show({
          content: "請?zhí)暨x卡牌"
        })
        return
      }

      if (this.users[this.id][this.selectedCard] <= 0) {
        tips.show({
          content: "這類卡牌已耗盡"
        })
        return
      }

      let user = this.users[this.selectedUserId]

      if (!user) {
        tips.show({
          content: "請?zhí)暨x對手"
        })
        return
      }

      if (user.star <= 0 || (user.stone + user.scissors + user.paper) <= 0) {
        tips.show({
          content: "該用戶已不具備對戰(zhàn)能力了"
        })
        return
      }

      if (!this.acceptChallenge) {
        this.socket.emit("challenge", {
          fromCard: this.selectedCard,
          toId: this.selectedUserId
        })

        modal.show({
          title: "發(fā)起挑戰(zhàn)",
          content: "等待對方接受中...",
          confirmText: "取消挑戰(zhàn)"
        }, t => {
          if (t === "confirm") {
            this.socket.emit("cancel_challenge")
          }
        })
      } else {
        this.socket.emit("respond_challenge", {
          accept: true,
          fromId: this.challengeFromUser.id,
          toCard: this.selectedCard
        })

        // 重置記錄
        this.acceptChallenge = false
      }
    }
  },
  mounted () {
    request({
      url: "/api/info"
    }).then(data => {
      // 使用ip建立連接,局域網(wǎng)內(nèi)其他設備也可以訪問
      this.socket = window.io.connect("http://" + data.ip + ":" + data.port)

      this.socket.on("connected", () => {
        let name = window.prompt("請輸入您優(yōu)雅高貴的稱呼")

        if (!name || !name.trim()) {
          name = this.socket.id
        }

            // 告訴服務器,有人進來了
        this.socket.emit("open", name)

        // 已連接
        this.id = this.socket.id
        this.isConnected = true
      })

      this.socket.on("update_users", users => {
        this.users = users
      })

      // 是否接受挑戰(zhàn)
      this.socket.on("accept_challenge", fromUser => {
        modal.show({
          title: "接受挑戰(zhàn)",
          content: "是否接受來自【" + fromUser.name + "】的挑戰(zhàn)?",
          confirmText: "接受",
          cancelText: "拒絕"
        }, t => {
          if (t === "confirm") {
            // 緩存挑戰(zhàn)信息,等待用戶選擇出示的卡牌
            this.selectedUserId = fromUser.id
            this.acceptChallenge = true
            this.challengeFromUser = fromUser
          } else {
            this.socket.emit("respond_challenge", {
              accept: false,
              fromId: fromUser.id
            })
          }
        })
      })

      this.socket.on("cancel_challenge", () => {
        this.acceptChallenge = false

        modal.hide()
        tips.show({
          content: "對方取消了挑戰(zhàn)"
        })
      })

      // 監(jiān)聽對戰(zhàn)結(jié)果
      this.socket.on("result_challenge", (result, users) => {
        this.users = users

        modal.hide()
        tips.show({
          content: result === 0 ? "平局" : (result === 1 ? "你贏了" : "你輸了")
        }, () => {
          // 檢測游戲勝利和失敗條件
          let user = users[this.id]
          let cardCount = user.stone + user.scissors + user.paper

          if (user.star >= 3 && cardCount <= 0) {
            this.socket.emit("success_challenge")

            modal.show({
              title: "游戲勝利",
              content: "恭喜你獲得了勝利!",
              confirmText: "再來一局"
            }, t => {
              if (t === "confirm") {
                window.location.reload()
              }
            })
          } else if (user.star <= 0 || cardCount <= 0) {
            this.gameover = true

            modal.show({
              title: "游戲結(jié)束",
              content: user.star <= 0 ? "你已經(jīng)沒有星星了" : "你已經(jīng)沒有卡牌了",
              confirmText: "重新開始"
            }, t => {
              if (t === "confirm") {
                window.location.reload()
              }
            })
          }
        })
      })

      // 接收系統(tǒng)廣播,有人挑戰(zhàn)成功的信息
      this.socket.on("success_challenge", user => {
        window.alert(`恭喜【${user.name}】挑戰(zhàn)成功,戰(zhàn)績(${user.star})顆星`)
      })
    })
  }
}
補充說明

游戲預覽

源碼地址:https://github.com/ansenhuang/node-socket

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://specialneedsforspecialkids.com/yun/98887.html

相關文章

  • 《機器學習》作者Peter Flach:好萊塢也借AI上頭條

    摘要:在高度結(jié)構(gòu)化的數(shù)據(jù)挖掘以及通過分析來評估和改進機器學習模型方面,是國際領先的研究人員。在機器學習里,我并沒有涉及強化學習的內(nèi)容。這些準備讓讀者了解機器學習能做什么,然后我的書能幫助他們了解機器學習怎么工作。 非商業(yè)轉(zhuǎn)載請注明作譯者、出處,并保留本文的原始鏈接:http://www.ituring.com.cn/art... 訪談對象: Peter Flach,布里斯托大學人工智能教授,...

    MartinHan 評論0 收藏0
  • 《機器學習》作者Peter Flach:好萊塢也借AI上頭條

    摘要:在高度結(jié)構(gòu)化的數(shù)據(jù)挖掘以及通過分析來評估和改進機器學習模型方面,是國際領先的研究人員。在機器學習里,我并沒有涉及強化學習的內(nèi)容。這些準備讓讀者了解機器學習能做什么,然后我的書能幫助他們了解機器學習怎么工作。 非商業(yè)轉(zhuǎn)載請注明作譯者、出處,并保留本文的原始鏈接:http://www.ituring.com.cn/art... 訪談對象: Peter Flach,布里斯托大學人工智能教授,...

    haobowd 評論0 收藏0
  • 復雜的中國駕駛場景,正是深度學習的優(yōu)勢

    摘要:如果這個場景足夠簡單的話,深度學習并不能表現(xiàn)出相對于其它基于傳統(tǒng)模式識別方法的優(yōu)勢。這是深度學習目前受到關注的一個非常重要的原因。通過積累大量的數(shù)據(jù)進行足夠的訓練,基于深度學習的系統(tǒng)可以給出最優(yōu)規(guī)劃。 谷歌和李世石的人機大戰(zhàn)引爆了公眾對于人工智能的關注,也讓基于深度學習的人工智能成為汽車業(yè)界關注的重點,那么深度學習在智能駕駛的應用場景下有什么幫助呢?自動駕駛最先出現(xiàn)在美國,而不是歐洲或者日本...

    tracymac7 評論0 收藏0
  • 框架的游戲:2019 年 JavaScript 流行趨勢

    摘要:年新星調(diào)查中顯示,越來越流行,其熱度已經(jīng)逐漸超過了。及其框架位于全球最受歡迎使用最廣泛的技術榜榜首。本文轉(zhuǎn)載自框架的游戲年流行趨勢英文原文JavaScript 生態(tài)系統(tǒng)復雜多變,各種框架讓人眼花繚亂。究竟孰優(yōu)孰劣,如今的發(fā)展趨勢是怎樣的,用人單位又需要怎樣的人才?本文站在一個中立者的角度,客觀分析了當前這場框架的游戲中,JavaScript 的流行趨勢。 Javascript 的生態(tài)環(huán)境讓我...

    mrcode 評論0 收藏0

發(fā)表評論

0條評論

最新活動
閱讀需要支付1元查看
<