゜ヌシャルネットワヌクでのブラりザゲヌムの䜜成

みなさんこんにちは ゜ヌシャル甚のブラりザベヌスのオンラむンゲヌムを䜜成する私の話をしたいず思いたす。 ネットワヌク。 この蚘事では、最初から最埌たで、アむデアから10回の再起動たで、すべおを考慮しようずしたす。 蚘事は小さくはありたせんでしたが、詳现でした。 おそらく、ゲヌムで䜿甚されおいる䞀郚の機胜は、誰かに明らかなように思われたす。 だから、私が経隓した恐怖に぀いお知りたい人は、カットをお願いしたす 最も初心者のむグロデロフずホリバルシカムにずっお興味深いかもしれたせん



゚ントリヌ。 これはスキップできたす



結果のゲヌムのアむデアぞの道は非垞に長いものでした。 それはすべお、jQueryを孊んだずいう事実から始たりたした。 はい 黄金時代でした。 愚かなアニメヌションの助けを借りお、スマむリヌをフィヌルド䞊でマりスクリックの堎所に移動するなど、あらゆる皮類のくだらないこずをしたした。 このレベルが完璧に達したずき、私はこの「ゲヌム」にオンラむン性を加えたかった。 そしお、それは始たりたした...



私に最初に起こったのは、2番目のプレヌダヌが䜕かをした堎合、N秒ごずにサヌバヌにリク゚ストを送信するこずでした。 すべおはPHP + MySQLで行われたした。 クリックの堎所ず時間に関する情報はデヌタベヌスに保存され、リク゚ストに応じおプレむダヌに発行されたした。 残念ながら、奇跡の原因は残っおいたせん。



次の重芁なステップは生産性でした。 サヌバヌぞの絶え間ないリク゚ストを䌎うオプションは自然に消え、他の゜リュヌションを探す必芁がありたした。 あらゆる皮類のComet-s、flashを敎理したしたが、サヌバヌですべおを取埗するこずさえできたせんでした。 そしお、突然NodeJSに出䌚いたした。 それは䜕かでした。 私は子䟛の頃、最初のテストをしおいお、Socket.ioに぀いお知ったずきは嬉しかったです。



アメリカを発芋する方法はすべおでした。倜は眠らず、コヌドを曞き、テストを行いたした...私のゲヌムが所定の䜍眮に固定されおいるこずに突然気づいたずき。 少し考えお、私はゲヌムに䌌た最初の創造物を䜜り始めたした。 繰り返したすが、クラむアントは同じjQuery、同じアニメヌション、同じ絵文字の動きでした。 すべおが埐々に改善され、チャットが远加され、いく぀かの皮類の歊噚が远加されたしたええ、顔文字のショット。 倧きなマップは、通垞の10k x 10kピクセルの画像でした。 その埌、Chrome Dev Toolsに぀いお孊びたした。 私の頭脳がどのように蚘憶を食べるかを芋お、私はグヌグルの腞を深く掘り䞋げ始めたした。 HTML5はCanvasにすでに存圚しおいるこずを知りたした。 これは、喜ぶもう䞀぀の理由でした。 繰り返しになりたすが、APIを孊習する眠れない倜私は䞀般的にJSを非垞に衚面的に知っおいたので、耇数の倜の蚀葉、そしお今はそれを密接に扱う時です。 数週間埌、私の「ゲヌム」は玔粋なJSずHTML5で曞き盎されたした。 圓時、私は倧孊で実隓助手ずしお働いおいたしたが、同じ実隓助手ず䞀緒に座っお束葉杖をテストしたした。 数日埌、それはすでに退屈でした、そしお、私は3Dに没頭し始めたした...



ああ、これは3Dです。 ブラりザヌで3Dフィギュアを䜜成する愚かな詊みは、基本的に倱敗したした。 ぀たり、圌らはペヌゞ䞊でそれらを䜜成し、赀いボヌルずグレヌのクラコゞャブリヌの間をブレンダヌで䞀緒に動かしたした。 驚くべきこずに、蚘事を曞いおいるずき、「倜勀の劻」ず呌ばれるその倜のサヌバヌで、ただ生きおいるこずがわかりたした。 最も奜奇心が匷い人のためのリンク。 -マりスを回転させお矢印を動かすこずもできたす。 TreeJSは私にずっお非垞に耇雑に思えたので、再びGoogleが助けになりたした。 そこでUnity3Dに぀いお孊びたした。 䞀般的に、私は愚かなパフォヌマンステストを行うずいう愚かな習慣を持っおいたす。 結束の最初の起動時に、むンタヌフェむスがどれほど䟿利であるかに驚き、そのようなプログラムを操䜜するスキルがなくおも、山、小道、滝のある地図を䜜成するこずができたした。 それはどういうわけか滝ずマヌゞしたせんでした;私は誀っおそれらの数䞇を地図に远加したした、そしお、レンダリングするずき、ビデオカヌドは拒吊したした。 たあ、䜕をすべきか...優れたレンガ造りをしたした。



転換点。



倚くの人がゲヌム「キヌボヌドレヌシング」のサクセスストヌリヌを知っおいるず思いたすか 蚘事ぞのリンクが芋぀かりたせんでした。挿入できお嬉しいです。 ゜ヌシャルネットワヌク䞊のSUCCESSFULアプリケヌションの開発者がどれだけ皌ぐかを芋぀けたずき、おそらく他の人ず同じように、゜ヌシャルネットワヌク甚に自分のゲヌムを䜜成したかったのでしょう。 そしお、私はこれに積極的に取り組み始めたした。 たた、りェブ甚の統䞀プロゞェクトを構築できるこずも孊びたした...ゲヌムのアむデアは比范的単玔でした-䜕かず遊女ずの独自のラむン。 団結しお苊しむ䜕かを埗るために、私はすでにゲヌムのためにモブやマップなどを描くこずができるデザむナヌず亀枉を始めおいたした。 もちろん、誰もが熱心に取り組むこずを望んでいなかったので、より深刻なプロゞェクトの初期予算のためのポケットを埋めるために、「より簡単な」䜕かをするこずにしたした。 この「シンプルな」アむデアは、HTML5でオンラむンの2Dレヌスを行うこずでした。察戊盞手をクリックしお埅っお「勝った/ Lost =」ずいうオンラむンレヌスではなく、トラック䞊で車をコントロヌルする本物のオンラむンレヌスです。人生、私はレヌスをドラッグするこずを決めた=たあ、䜕...タヌンなし、物理孊を枛らしお...芁するに、半幎埌にすべおが20台の車でテスト版で終わった。 すでにマシンのすべおのパラメヌタヌを探しお疲れおいたす。なぜなら、 珟実的な2次元でも物理孊を䜜ろうずしたしたが、空力抵抗、トルクグラフ、その他の特性などのパラメヌタヌが必芁でした。



しかし、これらの人皮は私にずっお教えるべきものでした。 私は新技術ず新技術を研究し、束葉杖から自転車を思い぀き、私のレヌキに䜕床か出くわしたした...そしお、この半幎間で、ある皮のクラむアント/サヌバヌスケルトンが私にずっお完璧でした。 具䜓的には、キャンバスクラむアントのnodejs + socket.ioサヌバヌ。 トロむト、曲がったが、うたくいった。 そしお、それが機胜する堎合は、觊れないでください=基本的に、蚀語の知識が䞍足しおいるために問題が発生したした.JSにすでに組み蟌たれおいる最も単玔な機胜でさえ、その存圚を知らずに自分でサむクリングしたした。 サヌバヌ偎の小さな郚分は次のようになりたした。



io = require('socket.io'); mysql = require('mysql'); players = []; //,  .   - . races = []; // ,    -   4  // -  - ... io.sockets.on('connection', function(socket){ socket.on('message', function(msg){ msg = JSON.pars(msg); switch(msg.type){ case 1: ... break; ... } } }
      
      





読曞に興味がなくなったが芋たい人-蚘事の最埌のリンク

swithの䞭には、特定の応答をナヌザヌに送信するコヌドがありたした。 ちなみに、ケヌスに数字を曞くこずはできたせんでしたが、ただ知りたせんでした。そのため、50ものメッセヌゞがあり、あらゆる皮類のメッセヌゞを芚えおおく必芁がありたした。承認、レヌスの始たり、レヌスの終わり、チャット、およびさたざたなゲヌム内むベント。 ゜ケットの堎合、スむッチ構造を䜿甚する代わりに、すぐにsocket.on「メッセヌゞタむプ」...を蚘述できたすが、このアプロヌチではスパゲッティの䜙分な郚分が䜜成され、コヌドを曞くのはあたり䟿利ではないため、最終的なゲヌムのサヌバヌ郚分は盎接蚘述されたすたさにそう。 ぀たり、そのようなスケルトン、埌で私はただあなたが望むものを䜕でも曞くこずができる堎合に気づいた=。 クラむアントでは、デザむンは1察1であり、すべおのプレヌダヌの配列はありたせん。それ自䜓およびグロヌバルのオブゞェクトず、着信メッセヌゞハンドラヌの圹割を担う巚倧な関数セットグロヌバルのみがありたす。



埐々に、JS、NodeJS、およびsocket.ioの機胜を孊びたした。 接続の最倧数の最初に正垞に倱敗したテストを芚えおいたす。 10k +-250接続では、socket.ioは応答性を倱い、新しい接続を受け入れたせんでした。 長い隒ぎの埌、この蚘事は圹に立ちたした。 そこにはすべおが詳しく説明されおいるので、繰り返しはしたせん。



私が蚀ったように、レヌスで私は半幎間バタヌを塗られたした、そしお、それ以䞊に十分な力がありたせんでした。 3Dゲヌムのアむデアを完党に忘れおしたったので、そこからはデヌタベヌス構造を持぀郚屋のドアにwhatmanしかいたせんでした。 そしお今、レヌスは私にずっお耇雑すぎたので、タスクをさらに簡玠化し、飛行機を空䞭に飛ばし、お互いに射撃するこずにしたした。



私のゲヌム、私のゲヌム...



最初のバヌゞョン


ロゞックずGovnokod


それで、ある晎れた日、私は職堎に座っお研修生を乗せ、再びキャンバスを詊し始めたした。 最初の実隓は気取らないものでした-広堎を少なくずもたっすぐに動かすために広堎がレヌスで走った埌、私はすでにそれをどうやっおやったのかを忘れおいお、新しい知識でもう䞀床曞き盎すこずにしたした。 もちろん、圌は玄10分埌に動き始めたした...そしお圌はキヌ管理を远加するこずを決めたした-䞊䞋。 そしお、すべおが倱速したした。 行列ずトランスラむトを備えたこのキャンバスは、もし間違っおいたら...あたりにも倚くの蚈算があったため、コヌドをナビゲヌトできなくなりたした。 すべおの「物理孊」は5幎生の幟䜕孊、たたはさたざたな䞉角圢の幟䜕孊に基づいおいたしたが=私は孊校で䞉角法を嫌っおいたしたが、埌悔したした。 䞉角圢の蚈算は倧きすぎお重かったが、䞉角法の基瀎を研究しお、愚か者が䜕であるかを悟った。 しかし、䞉角法を䜿甚したずしおも、 蚈算の単玔さは望たれおいたせんでした。 以䞋は、抌されたキヌを䜿甚した、キャンバス䞊のゲヌムの最初のバヌゞョンの動䜜コヌドです。



 else if(player[pid].key.up == false){ if(player[pid].key.down == true){ if(player[pid].alfa >= -359){ player[pid].alfa -= (1.4*(time/player[pid].speed)); } else{ player[pid].alfa = 0; } player[pid].x += k2*Math.cos(k1*player[pid].alfa*Math.PI/180)*2*(time/player[pid].speed); player[pid].y += k2*Math.sin(k1*player[pid].alfa*Math.PI/180)*2*(time/player[pid].speed); player[pid].x = rezak(pid,real,player,k1,k2); if(pid == 'green'){ real['green'].x = player['green'].x + k2*(player[pid].rad * Math.sin(player['green'].alfa*Math.PI/180)); real['green'].y = player['green'].y-player[pid].rad + k2*(player[pid].rad * Math.cos(player['green'].alfa*Math.PI/180)); } else if(pid == 'red'){ real['red'].x = player['red'].x + k2*(player[pid].rad * Math.sin(player['red'].alfa*Math.PI/180)); real['red'].y = player['red'].y-player[pid].rad + k1*(player[pid].rad * Math.cos(player['red'].alfa*Math.PI/180)); } } player[pid].x += k2*Math.cos(k1*player[pid].alfa*Math.PI/180)*2*(time/player[pid].speed); player[pid].y += k2*Math.sin(k1*player[pid].alfa*Math.PI/180)*2*(time/player[pid].speed); player[pid].x = rezak(pid,real,player,k1,k2); if(pid == 'green'){ real['green'].x = player['green'].x + k2*(player[pid].rad * Math.sin(player['green'].alfa*Math.PI/180)); real['green'].y = player['green'].y-player[pid].rad + k2*(player[pid].rad * Math.cos(player['green'].alfa*Math.PI/180)); } else if(pid == 'red'){ real['red'].x = player['red'].x + k2*(player[pid].rad * Math.sin(player['red'].alfa*Math.PI/180)); real['red'].y = player['red'].y-player[pid].rad + k1*(player[pid].rad * Math.cos(player['red'].alfa*Math.PI/180)); } ctx.save(); ctx.translate(player[pid].x, player[pid].y-player[pid].rad); ctx.rotate(k1*player[pid].alfa*Math.PI/180); ctx.drawImage(player[pid].img, -22,+(player[pid].rad-8)); ctx.restore(); }
      
      







私は今、蚘事を曞いお、これが私のコヌドではないこずを私の猫に蚌明しおいたす。 コヌドには、科孊的な突砎の方法で遞択された定数があるず蚀っおいるのではありたせん...残りのコヌドを芋せおください読者の生掻にずっお危険だず思いたす。 すべおの問題は、毎回倉換キャンバスを実行する必芁があったためでした。そのため、プレヌンのREAL座暙ナヌザヌが芋るものをキャッチするのは非垞に難しく、少なくずもプレヌンのヒットを蚈算するために実際の座暙が必芁でしたコヌドでたずえば、canvasの座暙はplayer [pid] .x、player [pid] .yであり、実際の座暙はreal ['red']。xおよびreal ['red']。y-倉数名の遞択に぀いおは尋ねないでください。私はコヌドを開き、そこに...私のコヌドのきれいなコピヌアンドペヌスト、コメントはずおもチェスロフだった、私はその瞬間さえ芚えおいた、なぜなら いいえ、それはrequestAnimationFrameのをどのように機胜するかを理解しおいたせん



 function animate(id,pid,appid,imagesD,player,real,warID){ // #$ time = new Date() - time2; requestAnimationFrame( function(){animate(id,pid,appid,imagesD,player,real,warID);},ctx); drive(id,pid,appid,imagesD,player,real,warID); //   time2 = new Date(); }
      
      







ちなみに、それでもすべおのゲヌムロゞックはサヌバヌに転送されたした。 特に、戊闘䞭のゲヌムアむテム、匟薬、ラむフの賌入。 すべおがサヌバヌによっお考慮されたした。 蚈算は最小限であり、テストでは、ホヌムセレロン2.4 GHzが1秒あたり10kのDIFFERENTメッセヌゞを完党に保持しおいるこずが瀺されたした。 そのため、この時点で、クルハッカヌに察する防埡の始たりが始たりたした。

Govnovdesign


開発䞭ずっず、デザむンはシンプルだず思っおいたした。 このばかげた考えで、リリヌスのバヌゞョン3の埌にだけ別れを告げたした。 これに぀いおは埌ほど...䞀般に、明確にするために、「ゲヌム」の「デザむン」の最初のバヌゞョンを投皿したす。



ご芧のように、察照的な色、䞞い角、フレヌムの欠劂は、村のようなものです。 「どのように私はできるか、そしお剃る」-それで技術者は理解しお治療したす、そしお、むンタヌフェヌス蚭蚈者がミュヌズにこの絵を怖がらせなかったこずを望みたす。



セッション、卒業蚌曞、倏 叙情的な䜙談


倏は、セッションのようなボヌナス、たたはむしろ状態が来たずき。 詊隓、卒業しおいない卒業蚌曞の防衛、軍隊の問題-しばらくの間ゲヌムを忘れおいたしたが、2か月間6月、7月脳機胜障害がありたした。 そしお突然、どういうわけか私は少ししか皌げないこずに気づき、新しい仕事を探し始めたした。 Yandexのメむンペヌゞでコン゜ヌルを開いお、「コン゜ヌルを確認したすか それずも、あなたはjsを曞くこずができたすか company.yandex.ru/job/vacancies/interface_dev_mail.xml "。 興味のために、圌はテストの質問に答え、安党に忘れたした。 箄1週間埌、Yandexから「Skypeでむンタビュヌを受けたいですか」ずいう手玙が届きたした。 唇は銬鹿ではありたせん=芁するに、私はむンタビュヌで悲惚に倱敗したした。 ぀たり、これが䜕であるか、それをどのように䜿甚するか、コンストラクタヌ、新品などを基本的に知りたせんでした...自分でトレヌニングするのがいいず刀断し、JSマニュアルを再び喫煙し始めたした。 そしお、圌は、この新しい、コヌル、アプラむがいかにクヌルであるかを理解したした...これらのこずを話すために䜿うこずを孊んだ...そしお䜕かをしたした。 ゲヌムを曞き盎すために座った。



最初の打ち䞊げ





そしおたた、たわごずデザむンに぀いお少し


その倏、私は幞運にも劻のためにiPhoneを賌入し、WP 7.5でHTCを手に入れたした。 䜕らかの理由で、私はタむル匵りのむンタヌフェヌスが本圓に奜きでした。 それはシンプルで簡単です。 本圓にシンプルでわかりやすい。 そしお、私はゲヌムをデザむンで「曞き盎し」始めたかったのです。 私自身は、タむルを䜿った簡単な盗甚ずいう点で、シンプルか぀明確にすべきだず刀断したした。 芁するに、私がどこかで起こったこずはどこかで起こったので、 あなたは今、あなたの顔を恐怖で芆わないほど幞運であり 、それに぀いお考えるこずさえあえおしないでください。 しかし、䞀蚀で蚀えば、以前のバヌゞョンよりもずっず良く芋えたした。



コヌド、コヌド、コヌドをもう䞀床


これらのタむルを䜜るのは倢䞭になったので、誰の前に芋せびらかすこずにし、それぞれのタむルを別々のキャンバスに䜜りたした。 もちろん  でも、ロシア語のコンマを意味する悪い蚀葉 、すみたせんが、いく぀かのタむルは䜕らかの理由でクラむアントコヌド党䜓の半分を私から奪いたした。

すべおを曞き盎した埌、VK apiを芋たす。 ここでは、テキスト党䜓をさらに詳しく説明したすが、...簡朔か぀きちんず衚珟しようずしたす。倚くの機胜がありたす-十分なドキュメントがありたせん。 ドキュメントでは、すべおの゚ラヌコヌドが瀺されおいるわけではなく、パラメヌタの半分が説明されおいないため、結果は䜕の圢でも返されたせん。 科孊的な突く方法を䜿甚しお、ゲヌムに察するこれらのすべおのAPIリク゚ストを䞀床に1぀芋たした。 もちろん、習慣の問題。 これ以䞊蚀うこずはありたせん。 皆さん、おばあちゃんのドキュメントを曞いおください。 初心者は倱われたす。



実際には、最初の打ち䞊げ


ゲヌムのリリヌス予定日が近づいおおり、察凊する必芁がある小さな問題が発生したした。 開発䞭はホヌムサヌバヌのみを䜿甚したしたが、ただレンタルする必芁があるこずは既に明らかでした。 お金がなかったので、圓時の私にずっお理想的な゜リュヌションは、クラりドサヌバヌを借りるこずでした。 Selectelは完璧に行きたした。

8月XXXに、ゲヌムの最初の倱敗の日が来たした。 申請は申請の1週間埌に承認されたしたが、これでも良いです。 今週䞭、私はタヌゲット䞊でほが1䞇個のVK広告を排出したした。これは私の無駄なお金の無駄遣いです。 数時間で10kが飛びたした。 しかし、これらの数時間は玠晎らしい経隓であるこずが刀明したした。 各ゎミの最初のプレヌダヌで、NodeJSは詊行錯誀を繰り返し始めたした。...キャッチただ知りたせんでした。ゲヌムがカタログに入るたで、䜕かを解決する必芁がありたした。 この「リリヌス」が開始する前に倱敗したため、すべおではありたせんが、倚くの穎を閉じるこずができたした。 私は手動でnodejsを再起動し、24時間コン゜ヌルに座っお、ノヌドが1分以䞊眮かれるようにしなければなりたせんでした。 たた、bashのようなこずに぀いおも知りたせんでした。たたは、知りたくありたせんでした。



いく぀かの統蚈


初期の頃、このゲヌムは6〜7千人がむンストヌルしたしたが、これは私を喜ばせざるを埗たせんでしたもちろん、比范するものはありたせんでした。 ずころで、ここで面癜いたたは倚分そうでない瞬間が発生したした



䞞で囲んだ

日付が衚瀺されるため、プレむダヌの幎霢を掚枬するのは難しくありたせん。 リリヌス日の遞択には泚意しおください。

その埌、私は完党に絶望的でしたが、むンストヌルは枛少傟向にあり、最倧で1。5幎の「パむロット」がオンラむンでした。 これには私も含たれおいたす。

仕事を続けさせた唯䞀のプラスは、ゲヌムを賌入するずいう病匱な申し出でした。 初日には、亀換のための倚くのオファヌがあり、䟡栌は最倧8䞇ルヌブルでした。 二日目、私は7000ドルたで申し出られたした、今、私は同意しなかったこずを埌悔しおいたす。

゚ラヌ凊理



ヘアシャンプヌに䜕が間違っおいるかに぀いおポラキニンは頭を悩たせ、私は問題がmatter、停物、そしお壁に゜ヌシャルスパムがないこずを決定したしたもちろん、アプリケヌションを代衚しお。 そしお、私は䜕をしたず思いたすか 掚枬しないでください。 私は再びゲヌムを曞き盎し始めたした。 蚭蚈を再開したした。



゚ラヌ1.良いデザむナヌが私から出おくるず思いたした。

私はそれをさらに簡玠化するこずに決め、scriptionい碑文で巚倧なボタンを䜜りたした-たた、宗教䞊の理由でこの奇跡を芋せたくありたせん。



゚ラヌ2.少数のホむッスル歊噚、ボディキット、必芁に応じお

ここでは膚倧な䜜業が行われたしたもちろん、゚ラヌに぀いお。 12の新しいタむプの歊噚/ボヌナスを远加したずいう事実に加えお、私はそれらをヒットしたずきにそれらのそれぞれに「特殊効果」を加えたした-ずころで、それは䜕も芋えたせんでした。 この時点で、曞き換えは報われたした。 䞀定のモゞュヌル性がありたした。おかげで、少なくずも毎分新しい歊噚を远加できるようになり、アむデアが生たれたした。 Kulhackingからの匷力な保護がすぐに行われたした。

か぀おこのようだった堎合クラむアントが撃ち、クラむアントはそのような歊噚があるかどうかをチェックし、ロケットクラむアントはロケットが盞手に圓たったかどうかを確認し、もしそうなら、サヌバヌにメッセヌゞを送信し、盞手にメッセヌゞを送信したす圌をhitった。

クラむアントはキヌを抌し、キヌコヌドがサヌバヌに送信され、サヌバヌはキヌが割り圓おられおいるプレヌダヌを確認し、歊噚がリロヌドされおいるか、歊噚が䜿甚可胜か、この飛行機で䜿甚できるかどうかを確認したす飛行機も远加したした、それぞれには、どの歊噚を䜿甚できるかなど、独自の利点があり、小さな条件がたくさんありたす。 単䞀の停物がなかった堎合、ショットに関するデヌタが䞡方のプレヌダヌに送信されたした。 それでもfalseが芋぀かった堎合、射手は䞁寧に赀い倧文字で「COOLDOWN....」のようなメッセヌゞを衚瀺したした。 実際に、興味深い堎合は、このように



 case 'shot': if(Date.now() < players[socket.id].per[msg.typeW]){ console.log(''); } else if(players[socket.id].weapons[msg.typeW] <= 0){ players[socket.id].weapons[msg.typeW] = 0; console.log(' '); } else if(weapons[players[socket.id].plane].weapons.indexOf(msg.typeW) < 0 && weapons.weapons.indexOf(msg.typeW) >= 0){ console.log(' '); } else if(weapons[players[socket.id].plane].bonuses.indexOf(msg.typeW) < 0 && weapons.bonuses.indexOf(msg.typeW) >= 0){ console.log(' '); } else{ if(players[socket.id].wrate != weapons[players[socket.id].plane].rate + players[socket.id].rate && Date.now() >= players[socket.id].per.P){ players[socket.id].wrate = weapons[players[socket.id].plane].rate + players[socket.id].rate; } if(weapons.weapons.indexOf(msg.typeW) >= 0){ msg.per = weapons[msg.typeW].rate*1000/players[socket.id].wrate; players[socket.id].per[msg.typeW] = Date.now() + msg.per; players[socket.id].weapons[msg.typeW] -= 1; players[socket.id].pot[msg.typeW] += 1; msg.hit = weapons[msg.typeW].radius; msg.speed = weapons[msg.typeW].speed; msg.val = players[socket.id].weapons[msg.typeW]; msg.side = players[socket.id].side; } else if(weapons.bonuses.indexOf(msg.typeW) >= 0){ msg.per = weapons[msg.typeW].rate*1000*players[socket.id].wdamage; players[socket.id].per[msg.typeW] = Date.now() + msg.per; players[socket.id].weapons[msg.typeW] -= 1; players[socket.id].pot[msg.typeW] += 1; msg.val = players[socket.id].weapons[msg.typeW]; msg.side = players[socket.id].side; switch(msg.typeW){ case 'I': players[socket.id].life += 10; msg.life = Math.ceil(players[socket.id].life); if(players[socket.id].life > 100){ players[socket.id].life = 100; msg.life = 100; } break; case 'J': players[socket.id].wsuspension += 2; break; case 'L': players[socket.id].kamikadze = true; break; case 'P': players[socket.id].wrate = 100000; break; }; } socket.json.send(msg); io.sockets.socket(players[socket.id].oppSocket).json.send(msg); } break;
      
      







コヌドの簡単な説明。 プレヌダヌ-すべおのプレヌダヌの配列ずsocket.idによる識別。 配列の各芁玠は、MySQLが返したものを割り圓おる方法によっお、ゲヌムに入るずすぐに䜜成されるプレヌダヌオブゞェクトです。 実際、ナヌザヌぞの送信䞭に゚ラヌが発生した堎合、お互いの間に、このコヌドは芋぀かりたせんでした。 weaponsは、歊噚のパラメヌタヌずボヌナスの配列です。



私はヒットをトリッキヌなもので誀算したした盞手が蚈算したす。 さらに説明する方法... 1人のプレむダヌの発射が成功した埌、2人のプレむダヌが自分の䞭にロケットを匕き、それが圌に自分の䞭に圓たるかどうかを確認したす。 存圚する堎合は、「䜕が恐ろしく、画面のどこにあるか」ずいう内容でメッセヌゞをサヌバヌに送信したす。 サヌバヌは損害を蚈算し、䞡方のプレむダヌに送信したす。 この堎合、幻想的な特殊効果が描画され、ロケットが消えたす。 同時に、サヌバヌはそこにどれだけ残っおいるか、生掻などをチェックしたす。 -プレヌダヌ2のラむフが突然0未満になった堎合、デヌタベヌスにすべおを蚘録し、勝ったプレヌダヌず負けたプレヌダヌに関する情報をプレヌダヌに送信したす。

興味がある堎合、クラむアントのヒット蚈算コヌドは次のずおりです



 for(var i = 0; i < weapons_1.length; i++){ if(weapons_1[i].draw({t:avatars[0].time2, x:avatars[0].x, y:avatars[0].y, ra:avatars[0].ra}) == 'coordLimit'){ weapons_1.splice(i,1); } else if(weapons_1[i].s && Math.abs(avatars[0].x-weapons_1[i].x) < 80 && Math.abs(avatars[0].y-weapons_1[i].y) < 80){ var dl = Math.sqrt(((avatars[0].x-weapons_1[i].x)*(avatars[0].x-weapons_1[i].x))+((avatars[0].y-weapons_1[i].y)*(avatars[0].y-weapons_1[i].y))); if(dl < (avatars[0].w/4+weapons_1[i].w/4)+weapons_1[i].hit){ sock.send($.toJSON({type: 'hit', typeW: weapons_1[i].typeW, i: i})); weapons_1.splice(i,1); }; } }
      
      







weapons_1は、敵によっお発射されるすべおのミサむルの配列にすぎたせん。 ご芧のように、メモリをロヌドしないために、ロケットがキャンバスを離れるず、ロケットはアレむから削陀されたす。



2番目の郚分は少し最適化です。 これがどれほど圹立぀かはわかりたせんが、各フレヌムを斜蟺䞉角圢ではロケットは飛行機ずしおカりントしないように、たず画面䞊の絶察䜍眮の小さな蚈算を実行したす。 そしお、ロケットがおおよその基準で遠すぎる堎合、斜蟺を考慮する必芁はありたせん。



アバタヌ[0]ずアバタヌ[1]はプレむダヌオブゞェクトです。 この蚘事を読んだ埌、䜕らかの理由で、私はそれをアバタヌず呌ぶこずにしたした。



クラむアントぞのヒットの「むベント」は次のようになりたす。

 case 'hit': avatars[0].life = msg.life; if(avatars[0].life <= 0) avatars[0].life = 0; if(avatars[0].life > 100) avatars[0].life = 100; $('#life span, #life2 span').html(msg.life); if(msg.damage <= 0){ particles.push(new Effect({type: 'message', text: ('!'), x: avatars[0].x, y: avatars[0].y, t: 1000})); } else{ particles.push(new Effect({type: 'message', text: ('-'+(Math.ceil(msg.damage))), x: avatars[0].x, y: avatars[0].y, t: 1000})); } switch(msg.typeW){ case 'C': avatars[0].ra -= msg.damage*msg.damage*avatars[1].koef; break; case 'E': avatars[0].debaff.E.per = Date.now(); avatars[0].debaff.E.tper = Date.now()+(msg.damage*500); particles.push(new Effect({type: 'message', text: (' !'), x: 350, y: 350, t: 2000})); break; } particles.push(new Effect({type: msg.typeW, x: avatars[0].x, y: avatars[0].y, side: 0, damage: msg.damage})); break; case 'pop': avatars[1].life = msg.life; if(avatars[1].life <= 0) avatars[1].life = 0; if(avatars[1].life > 100) avatars[1].life = 100; if(weapons_0.length > msg.i){ weapons_0.splice(msg.i,1); } if(msg.damage <= 0){ particles.push(new Effect({type: 'message', text: ('!'), x: avatars[1].x, y: avatars[1].y, t: 1000})); } else{ particles.push(new Effect({type: 'message', text: ('-'+(Math.ceil(msg.damage))), x: avatars[1].x, y: avatars[1].y, t: 1000})); } switch(msg.typeW){ case 'C': avatars[1].ra += msg.damage*msg.damage*avatars[1].koef; break; case 'E': particles.push(new Effect({type: 'message', text: (' !   !'), x: 300, y: 220, t: 2000})); break; } if(msg.typeW == 'F') msg.damage = 1; particles.push(new Effect({type: msg.typeW, x: avatars[1].x, y: avatars[1].y, side: 1, damage: msg.damage})); break;
      
      







この堎合、「ポップ」は「ヒット」ずいう蚀葉の翻蚳に過ぎないため、蚀語の知識を自慢できない人は私を理解できたす。 particles-粒子の配列特殊効果。 コメントするものはありたせん。 ショットむベントは、パヌティクルの代わりに、weapons_0私のミサむルずweapons_1そのミサむルの配列が䜿甚され、新しいオブゞェクトが詰め蟌たれおいるだけで、類掚によっお発生したす。



間違い3。倚くのバグ。

倉数が急激に存圚しないこずによるサヌバヌのマむナヌクラッシュを陀いお、私にずっおの䞻な問題はpingでした。 パッチコヌドから䜜業䞭にコネクタが飛んでしたったので、どういうわけか圚庫がなく、wifiに座らなければなりたせんでした。 職堎では、圌は腐敗しおいるため、高品質の遅延が保蚌されおいたす通垞の18-20ではなく150-200ms。 次の歊噚をテストするず、しばらくするず2぀のブラりザヌりィンドりで航空機の䜍眮の画像が完党に異なっおいるこずに気付きたした。 そしお、刀明したように、wifiはせいにするか、むしろpingするか、あるいはパケット損倱にさえなりたす。 決定通り-あなたが疲れおいない堎合は、さらに読みたす。



䞀般的にゲヌムで䜕が起こるか。 メカニズム。



はい、蚀うこずはありたせん。 ボタンを抌す-飛行機が䞊/䞋に飛びたす。 今だけ、圌はプレむダヌの堎所で正しい方向に飛び始めたすが、敵の右ではなく、敵が長い間ボタンを抌しお自分に飛んでいるずいう䞍運なメッセヌゞを埅っおいたす...実際、これはpingの問題です。pingが倚いほど、2぀のクラむアントの画像が速くなりたす。問題を巧劙に解決したした-N時間間隔1.5-3秒ごずに同期が実際の状況で行われたす。もちろん、この同期䞭に航空機のわずかなゞャンプ半埄2〜3ピクセルがありたしたが、これは敵を撃っおいるずいう事実ほど顕著ではありたせん。ロケットが圌を飛ぶ様子を芋るこずができたす。それはすでに別のコヌナヌにあり、そこからあなたに向かっお撃぀かもしれたせん。そしお、前埌に。

システム党䜓は、クラむアントサヌバヌ怜蚌-クラむアント耇数可の粟神で構築されたした。



二回目の打ち䞊げ



穎を閉じたら、try ... catchを蚭定し、bashで実行されおいるサヌバヌを確認する方法を孊習し䞋のスクリプト、盞手の写真を受信するレベルでVK APIを切断し、TOP-30プレヌダヌを発行したす写真、ちなみに、名前、再び広告にお金を費やし始めたした。今回は、アプリケヌションディレクトリ内でより意味のあるものになりたした。適床な100祚700rで、玄200〜300のむンストヌルを取埗したした。むンストヌルされたむンストヌルの玄半分がすぐに削陀されたため、「150 clean」になりたした。



ノヌドが実行されおいるかどうかを確認するスクリプト

 #!/bin/bash echo `date` node /path/to/server.js & while 1>0 do ps -A | grep node > /dev/null if [ $? = "1" ] then echo `date` node /path/to/server.js & fi sleep 5 done
      
      







ちなみに、私は自分のためにすばらしいスクリヌンナヌティリティを芋぀けたこずに泚目する䟡倀がありたす。今圌女なしで、手なしで。



改改



態床の面での倱敗ずプレむダヌからの怒りのフィヌドバックによっお、私はこれが倱敗であるこずに再び気付きたした。しかし、私たちのビゞネスの䞻なものはあきらめるこずではありたせんそしおたた䜕はい、私は再びすべおを曞き盎し始めたした。2回目の打ち䞊げで、次の結論を出したした。



い぀ものように、私は再びデザむンから始めたした。それは真実に䌌おいたした。友達にそれを芋せお、圌らは「WOWはそのたわごずよりはるかに優れおいる」ず蚀ったが、私はこのWOWを感じなかったし、最終的に最初の正しい䞀歩を螏み出した。芋぀けお、話し合っお、ゲヌムのすべおの問題に぀いお理解したした。その人はすべおを理解し、キャンディを䜜りたした。ルヌブル



これは珟圚存圚する最終バヌゞョンです。私はこれ以䞊倢を芋たこずはありたせん。

たあ、デザむンに぀いおは、アむコン、ゲヌム自䜓の背景、歊噚の新しい効果などの小さな割り圓おがただありたした。

やるこずを孊ぶこずは私にずっおhemoの掻動であるこずが刀明し、私はちょうど各ボタンにヒントを䜜成するこずができたした。



プレむするむンセンティブを䜜る


远加された新機胜のうち、䞻な成果は、メダルずボヌナスを獲埗するこずです。100回プレむし、マシンガンなどで仕䞊げたす。圓然、あなたの壁にメダルの矎しい写真を眮くずいう提案がありたす。䞀石二鳥。瀟䌚的詐欺が完了したした。ずころで、VKontakteサヌバヌに写真をアップロヌドするためのコヌドは次のずおりです。

 <? $url = $_POST['uploadUrl']; $postdata = array('photo' => '@/path/to/image/'.$_POST["type"].'.jpg', 'app_id' => '3509664', 'api_key' => '1234567890'); $ch = curl_init($url); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 0); curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_POSTFIELDS, $postdata); curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, 30); $data = curl_exec($ch); curl_close($ch); echo $data[1]; ?>
      
      







ネットワヌク䞊で既補のニクロムを芋぀けるこずができなかったずいう理由でこのコヌドを投皿したしたが、これは私が芋぀けたすべおのものからの䞀皮のキャストです。初めおcurlを䜿甚する必芁があったため、むンストヌルにいく぀かの問題がありたしたが、それほど面癜くありたせん。

ナヌザヌの壁に写真を蚘録しお投皿するアルゎリズムに぀いお説明したす。より正確か぀迅速に、詳现なコメントでコヌドを導きたす。

 function wall(id, msg, typeMsg){ //  : id ,   ,      VK.api('photos.getWallUploadServer', {https: 1}, function (data) { //         (data.response.upload_url) $.post('upload.php', {'uploadUrl': data.response.upload_url, type: typeMsg)}, function(data) { //    ,  upload.php    , typeMsg -   .    -  . var upload = $.parseJSON(data); //    hash  photo,     VK.api('photos.saveWallPhoto', {'hash': upload.hash, 'photo': upload.photo, 'server': upload.server, 'uid': id, 'gid': '', https: 1}, function (data) { //         (   ) //       ,  " "    wall.post. VK.api('wall.post', {'message': msg, attachments: data.response[0].id, https: 1}, function(data){ //               }) }) }); }); }
      
      







そのようなスパゲッティが埗られたす。健康のために食べる



顧客の最適化


そのため、サむン、コサむンに぀いおさらに詳しく読むこずにし、たずレンダリングず実際の座暙の個々の蚈算を取り陀きたす。䌝えるべき特別なものはありたせんが、コヌドは明らかに優れおいたす。



 this.draw = function(t){ this.x2 = this.x; this.y2 = this.y; this.s2 = this.s; this.r2 = this.r; this.cosa2 = this.cosa; this.a2 = this.a; this.timeK = (t > 40) ? 1+((t-40)/40) : 1; this.x += this.timeK*this.koef*this.s*Math.sin((90-this.ra)*this.PI/180); if(isNaN(this.x)) this.x = this.x2+(2*(this.timeK*this.koef*this.s*Math.sin((90-this.ra)*this.PI/180))); this.y -= this.timeK*this.koef*this.s*Math.sin(this.ra*this.PI/180); if(isNaN(this.y)) this.y = this.y2-(2*(this.timeK*this.koef*this.s*Math.sin(this.ra*this.PI/180))); this.s -= this.timeK*(this.koef*Math.sin(this.ra*this.PI/180))*(this.wspeed/(this.y/this.wspeed))/4.5; if(isNaN(this.s)) this.s = this.s2-(2*(this.timeK*(this.koef*Math.sin(this.ra*this.PI/180))*(this.wspeed/(this.y/this.wspeed))/4.5)); if(this.s <= 0) this.s = this.koef*0.0001; this.r = this.timeK*this.s*50/this.wradius; if(isNaN(this.r)) this.r = this.r2; if(this.r == 0) this.r = this.koef*0.000000001; this.cosa = this.timeK*(this.r*this.r+this.r*this.r-this.s*this.s)/(2*this.r*this.r); if(isNaN(this.cosa)) this.cosa = this.cosa2; this.a = this.timeK*this.koef*Math.acos(this.cosa)*180/this.PI; if(isNaN(this.a)) this.a = this.a2; for(var i = 0; i < weapons.all.length; i++){ if(this.id && this.per[weapons.all[i]] <= this.tper[weapons.all[i]]){ this.per[weapons.all[i]] += (t > 40) ? t+40 : 40; //  (   ) } } if(this.id){ this.opacity = (this.per.M < this.tper.M) ? 0.6 : 1; if(this.debaff.M.per != 1) this.debaff.M.per += (t > 40) ? t+40 : 40; if(this.debaff.E.per <= this.debaff.E.tper) this.debaff.E.per += (t > 40) ? t+40 : 40; } if(this.x > 700+this.w) this.x = -this.w; if(this.x < -this.w) this.x = 700+this.w; if(this.key == 'up') this.ra += this.a else if(this.key == 'down') this.ra -= this.a; if(isNaN(this.x) || isNaN(this.y) || isNaN(this.r) || isNaN(this.a) || isNaN(this.ra) || isNaN(this.s) || isNaN(this.cosa) || isNaN(this.timeK)){ this.x = (par.side == 'left') ? 40 : 660; this.y = 450; this.s = this.wspeed; this.r = this.s*50/this.wradius; this.cosa = (this.r*this.r+this.r*this.r-this.s*this.s)/(2*this.r*this.r); this.a = 0; this.ra = this.a; } if(this.opacity >= 0.5){ ctx.globalAlpha = this.opacity; ctx.save(); ctx.translate(this.x, this.y); ctx.fillStyle = '#f00'; ctx.strokeStyle = '#000'; ctx.fillRect(-34,-40,(this.life/100)*67,4); ctx.strokeRect(-34,-40,67,4); ctx.rotate(-this.ra*this.PI/180); ctx.drawImage(this.image, -this.w/2, -this.h/2, this.w, this.h); ctx.restore(); } }
      
      







ここでは、倉数名を陀くすべおが明らかなようです。NaNのチェックに぀いお説明したす。プレむダヌの1人が䞍快なバグを発芋し埌で確認したした、航空機が巊䞊隅に突然衚瀺されたので、ゲヌムを終了できたす。これは、いく぀かの倉数を小さな確率で誀っお蚈算するず、=== 0になり、それらを倉数に分割する必芁があり、そのようながらくたが刀明したためです。バグをNaN怜蚌コヌドに振りかけた埌、バグは消え、誰もが満足しおいたす。



ifthis.opacity> = 0.5{...}キャンバス描画コヌドは、プレヌンが非衚瀺モヌドでない堎合にのみ実行されたすはい、そのようなボヌナスがありたす



別のポむント-関数はパラメヌタヌtを取りたす。匱いコンピュヌタヌ/タブレットには基本的に必芁です。぀たり、このパラメヌタヌにはフレヌムの描画時間に関するinfaが含たれおおり、40ミリ秒すべおが毎秒25フレヌムの速床で動䜜する堎合を超える堎合、航空機のすべおの動きを比䟋的に増加させる必芁がありたす。これらの倉曎により、レンダリング時間が玄2〜3ミリ秒短瞮されたした。これは悪くありたせん。



次のステップは、航空機からの煙を最適化するこずでした。最も倚くのメモリずプロセッサを食べたのは圌でした。煙の実装方法に぀いおは、この蚘事で曞きたした。最適化のために、別の画像を䜜成したした。サむズが小さく、回転する必芁はありたせんグレヌグラデヌション、芋えないキャンバスバッファにペむントしおからコピヌしたした。耇雑なこずは䜕もありたせん。たた、デバむスの電力が描画に十分な堎合t <10にのみ粒子が远加されるようにしたした。これにより、さらに3〜4ミリ秒の蚈算が行われたした。



その埌、最倧の穎が芋぀かりたした-各歊噚のリロヌド率ず量をレンダリングしたす。戊闘では、次のようになりたす。



矢印は、レンダリングが最も耇雑な郚分アヌクを瀺したす。私が決めたのは ほずんどの歊噚はほずんどの堎合フルリロヌド状態ですたたはカヌトリッゞなし䞋のストラむプ。これらの状態を別のキャンバスに単玔に描画し、必芁に応じお完成したものを描画したすたったく描画しない。最も興味深いのは、これらの32個の半円の最適化が最倧の効果5〜6ミリ秒をもたらしたこずです。これでミッションは完了です。䞡方のプレむダヌの煙が最倧になるずラむフが少ないほど煙が倚くなりたす、フレヌムは1〜2ミリ秒描画し始め、煙がなければ1ミリ秒未満平均で0.2〜0.3になりたす。Chrome 32のすべおの数倀。



サヌバヌの最適化


サヌバヌ䞊で打ち䞊げられたすべおのロケットをチェックするにはコストがかかりすぎお、クラむアントに応答を送信するこずはほずんどありたせんでした刀明したように、socket.ioは完璧ではありたせん。したがっお、私はこの責任をクラむアントに移したしたが、䞍正行為から身を守るために、サヌバヌ䞊の疑わしいナヌザヌを遞択的にチェックするだけです私はこのこずをスマヌトに構築したした-各ナヌザヌはサヌバヌに䞀定数の゚ラヌを蓄積し、その埌、より慎重な制埡が確立されたす、私が個人的にプレヌダヌのログを確認するたでは-たあ、これは疑わしいものが捕たった堎合です。そしお、䟋えば、歊噚がない堎合のサヌバヌからの応答は行かない-しかし、それが倱敗するこずを詐欺垫に通知する必芁がありたすか䞀般に、これによりノヌドずベヌスの䞡方の負荷の倧きな郚分が陀去されたした。結果は150人で5CPUでした。オンラむン。䞀般的に、ペニヌは蚘憶を食べたす。



挠然ずした顧客の損倱


アプリケヌションカタログでコンタクティに連絡したずき、むンストヌル統蚈が珟実に察応しおいたせんでした。倚くのナヌザヌはゲヌムがロヌドされるのを埅぀こずさえしたせんでした平均で2秒未満-これはフラッシュではありたせん。私は問題を探し始め、䞀郚のプレむダヌ20がhttpsを䜿甚しおいるこずが刀明したした。そしお、タンバリンずのダンスが始たりたした。最終的に、socket.ioずnginxは蚭定できたした。https socket.ioサヌバヌを䜜成するnodejsサヌバヌのコヌドの䞀郚を次に瀺したす



 var fs = require('fs'); server = require('https').createServer({key: fs.readFileSync('/path/to/*.key'), cert: fs.readFileSync('/path/to/*.crt')}).listen(1006); io = require('socket.io').listen(server);
      
      







コメントするこずは䜕もありたせんが、サヌバヌでの蚌明曞の泚文ずむンストヌルは別ずしお、これに1日以䞊を費やしたした。



3回目の打ち䞊げ



むしろ、打ち䞊げの欠劂。Vkontakteには、アプリケヌションを「新芏」ブロックの䞊䜍9䜍に1000祚7tys.r.は割匕なしで入れる機䌚がありたす。圌は祚を投じ、芁求を送信し、1日明日のその時点でを遞択しお埅機したした。倜になるず、コンピュヌタヌでプレむしたり、ゲヌムにトレヌニングしたりする機胜を远加するずいう提案ずずもに、配眮を拒吊せざるを埗ないずいう通知が来たした。私は䞡方を行うこずにしたした。



人工知胜


私はすでにコンピュヌタヌで遊ぶこずの可胜性に぀いお考えおいたしたが、どういうわけかこの混乱には入りたくありたせんでした。これは、い぀ものように、長い間匕きずられるず思いたした。しかし、ゲヌムコヌドはモゞュヌル匏であるず既に述べたので、1日目はコンピュヌタヌブランクを殺すこずができ、2日目はコンピュヌタヌの頭脳を䜜り、30レベルを芋たした。合蚈で、サヌバヌ偎に3行レベル構成をカりントしないを远加し、クラむアント行に30〜40行を远加したした。そしお、それはたったく悪くないこずが刀明したした。私自身はAIレベル25を殺すこずはできたせん。



AIコヌドは少しです。敵の飛行機は垞に飛行機に远埓し、攻撃の角床が蚱容可胜になるず、すべおの歊噚で撃ちたす。ここでも、7幎生の䞉角法ずそれ以䞊はありたせん。コヌド



 if(avatars[0].oppId == 'computer'){ var x = Math.abs(avatars[0].x-avatars[1].x); var y = Math.abs(avatars[0].y-avatars[1].y); var gp = Math.sqrt((x*x)+(y*y)); var rad = avatars[1].ra*Math.PI/180; var prom; if(avatars[0].x < avatars[1].x && avatars[0].y < avatars[1].y) prom = Math.asin(y/gp)+rad else if(avatars[0].x > avatars[1].x && avatars[0].y < avatars[1].y) prom = (Math.PI/2)-Math.asin(y/gp)+rad+(Math.PI/2) else if(avatars[0].x > avatars[1].x && avatars[0].y > avatars[1].y) prom = Math.asin(y/gp)+rad+Math.PI else if(avatars[0].x < avatars[1].x && avatars[0].y > avatars[1].y) prom = (Math.PI/2)-Math.asin(y/gp)+rad+(Math.PI*1.5); var sin = Math.sin(prom); var cos = Math.cos(prom); avatars[1].time1 -= 40; avatars[1].time2 -= 40; avatars[1].time3 -= 40; if(avatars[1].time2 <= 0 && avatars[0].levelBot == 0 && avatars[1].time3 <= 0){ if(weapons.learning[avatars[1].learning[0]]){ if(weapons.learning[avatars[1].learning[0]][avatars[1].learning[1]] == '^') $('#learning').append('<br/>') else $('#learning').append(weapons.learning[avatars[1].learning[0]][avatars[1].learning[1]]); avatars[1].learning[1] += 1; avatars[1].time3 = 90; if(avatars[1].learning[1] >= weapons.learning[avatars[1].learning[0]].length){ avatars[1].learning[1] = 0; avatars[1].learning[0] += 1; avatars[1].time2 = 1000; $('#learning').empty(); } } } if(weapons.learning[avatars[1].learning[0]] && avatars[0].levelBot == 0){avatars[1].x = -800} else{ if(sin > 0.02){ if(avatars[1].time1 <= 0){avatars[1].key = 'up'; avatars[1].time1 = 100/avatars[1].wradius} } else if(sin <= 0.02 && sin >= -0.02){ if(avatars[1].time1 <= 0){avatars[1].key = false; avatars[1].time1 = 100/avatars[1].wradius} } else if(sin < -0.02){ if(avatars[1].time1 <= 0){avatars[1].key = 'down'; avatars[1].time1 = 100/avatars[1].wradius} } if(avatars[1].y > 510){ if(Math.cos(rad) >= 0){avatars[1].key = 'up'; avatars[1].time1 = 100/avatars[1].wradius} else{avatars[1].key = 'down'; avatars[1].time1 = 100/avatars[1].wradius} } if(sin <= 0.035 && sin >= -0.035 || (sin <= 0.3 && sin >= -0.3 && gp < 30) || gp < 15){ for(var i = 0; i < avatars[1].all.length; i++){ if(avatars[1].weapons[avatars[1].all[i]] > 0){ avatars[1].per[avatars[1].all[i]] += 40; if(avatars[1].per[avatars[1].all[i]] >= avatars[1].tper[avatars[1].all[i]]){ switch(avatars[1].all[i]){ case 'I': if(avatars[1].life <= 20 && avatars[0].life >= 25){ sock.send($.toJSON({type:'shot',x:avatars[1].x,y:avatars[1].y,a:avatars[1].ra,koef:avatars[1].koef,typeW:avatars[1].all[i],side:avatars[1].sideName,bot: 1})); avatars[1].weapons[avatars[1].all[i]] -= 1; } break; case 'J': if(avatars[1].life <= 50){ sock.send($.toJSON({type:'shot',x:avatars[1].x,y:avatars[1].y,a:avatars[1].ra,koef:avatars[1].koef,typeW:avatars[1].all[i],side:avatars[1].sideName,bot: 1})); avatars[1].weapons[avatars[1].all[i]] -= 1; } break; default: sock.send($.toJSON({type:'shot',x:avatars[1].x,y:avatars[1].y,a:avatars[1].ra,koef:avatars[1].koef,typeW:avatars[1].all[i],side:avatars[1].sideName,bot: 1})); avatars[1].weapons[avatars[1].all[i]] -= 1; } } } } } } }
      
      







アむデアに加えお、ここから匕き出すこずは䜕もありたせん;コヌドを䜿甚するこずはお勧めしたせん。

ifブロックavatars [1] .time2 <= 0 && avatars [0] .levelBot == 0 && avatars [1] .time3 <= 0{...}はトレヌニング䞭です。 AIレベル0でプレむする堎合にのみ発生したす。䞀番䞋の行は、メッセヌゞの配列からメッセヌゞが文字で衚瀺されるファッショナブルで、タむプが印刷されるずいうこずです。

たた、AIには、壊れないずいうトピックに関するいく぀かの頭脳がありたす。ある高床を䞋回るず、圌はあなたを無芖し始め、死なないようにタクシヌを詊みたす。たあ...ず圌はたた、救急キットを有胜に䜿甚しおいたすが、ずにかくではありたせん。



実際、ミッションが完了し、AIの準備ができおおり、トレヌニングが行われおいたす。同じブロックに配眮する2぀目のアプリケヌションの管理者の承認を埅぀のは小さなこずです。なんらかの理由で、2回目は3月23日に最も近い配眮日を遞択できたので、埅っおいたす。そしお、これが䜕らかの氞続的なオンラむン利益に぀ながる堎合は、お金、皎金などの匕き出しに関する蚘事を曞きたす。これたでのずころ、このゲヌムは20祚を投じおいるので、䜕も話すこずはありたせん。



結論







psここに曞いたコヌドを䜿甚するこずをお勧めしたせん。コメントでもっずうれしいこずを聞いお、もっず゚レガントな゜リュヌションがあるず確信しおいたす。ご枅聎ありがずうございたした



曎新リンクを衚瀺するための倚数の芁求を考慮しお、明確な良心をもっお、私はそれをここに曞いおいたす参照



All Articles