Points de base
J'ai commencé à y penser à partir du moment où j'ai décidé d'essayer de construire un jeu avec PHP et React. "Je veux faire un jeu économique multijoueur, similaire à Stardew Valley, mais sans sortir avec du contenu et avoir un système économique axé sur les joueurs." Le système est ignorant.
Je ne suis même pas sûr de connaître suffisamment de connaissances React pour justifier l'utilisation. Je veux dire, mon interface initiale - j'étais très concentré sur l'économie des serveurs et des jeux - est parfait pour React. Mais que lorsque je commence à faire l'agriculture / l'aspect interactif des choses? J'aime l'idée de construire des interfaces isométriques autour des systèmes économiques.
J'ai regardé un discours de Dead_lugosi, qui a décrit le processus de construction d'un jeu médiéval avec PHP. Margaret m'a inspiré, et ce discours a été l'une des raisons pour lesquelles j'ai écrit un livre sur le développement du jeu JS. Je suis déterminé à écrire mon expérience. Peut-être que d'autres peuvent aussi apprendre de mes erreurs.
(Le code de cette partie peut être trouvé sur: github.com/assertchris-tutorials/sitepoint-making-games/tree/part-1. Je l'ai assorti en php 7.1 et la dernière version de Google Chrome il a été testé.
J'ai d'abord recherché des conseils sur la construction d'un système économique multi-personnes. J'ai trouvé un excellent poste de débordement de pile où les gens expliquent diverses choses à considérer. J'ai été à mi-chemin avant de réaliser que je pourrais avoir commencé au mauvais endroit. "Premièrement: j'ai besoin d'un serveur PHP. J'aurai un tas de clients React, donc je veux quelque chose qui peut gérer une concurrence élevée (et peut-être même des coqueurs Web). Il doit être persistant: les choses doivent être même si le joueur est pas en ligne.
J'ai commencé à configurer un serveur PHP asynchrone - pour gérer une concurrence élevée et prendre en charge les Websockets. J'ai ajouté mes travaux récents avec PHP PRÉPROCESSEUR pour rendre les choses plus claires et créé les premiers points de terminaison.de
:
$host = new Aerys\Host(); $host->expose("*", 8080); $host->use($router = Aerys\router()); $host->use($root = Aerys\root(.."/public")); $web = process .."/routes/web.pre"; $web($router); $api = process .."/routes/api.pre"; $api($router);
J'ai décidé d'utiliser Aerys pour les parties HTTP et WebSocket de l'application. Ce code semble très différent de la documentation AERYS, mais c'est parce que j'ai une bonne compréhension de ce dont j'ai besoin.
Le processus habituel d'exécution d'une application Aerys consiste à utiliser une commande comme celle-ci:
vendor/bin/aerys -d -c config.php
Il y a beaucoup de code à répéter, et il ne gére pas le fait que je veux prétraiter en utilisant PHP. J'ai créé un fichier de chargeur.
de loader.php
:
return Pre\processAndRequire(__DIR__ . "/config.pre");
Ensuite, j'ai installé mes dépendances. Ceci est de composer.json
:
"require": { "amphp/aerys": "dev-amp_v2", "amphp/parallel": "dev-master", "league/container": "^2.2", "league/plates": "^3.3", "pre/short-closures": "^0.4.0" }, "require-dev": { "phpunit/phpunit": "^6.0" },
Je souhaite utiliser amphp/parallel
pour déplacer le code de blocage du serveur asynchrone, mais il ne peut pas être installé avec la balise stable de amphp/aerys
. C'est pourquoi j'utilise la branche dev-amp_v2
.
Je pense que c'est une bonne idée d'inclure une sorte de moteur de modèle et de localisateur de service. J'ai choisi chaque version de PHP League. Enfin, j'ai ajouté pre/short-closures
, qui est utilisé à la fois pour gérer la syntaxe personnalisée dans config.pre
, et aussi aux fermes courtes que je prévois d'utiliser plus tard ...
Ensuite, j'ai commencé à créer le fichier de routage. De routes/web.pre
:
use Aerys\Router; use App\Action\HomeAction; return (Router $router) => { $router->route( "GET", "/", new HomeAction ); };
et de routes/api.pre
:
use Aerys\Router; use App\Action\Api\HomeAction; return (Router $router) => { $router->route( "GET", "/api", new HomeAction ); };
Bien qu'il s'agisse d'un itinéraire simple, cela m'aide à tester le code dans config.pre
. J'ai décidé de faire revenir ces fichiers de routage aux fermetures afin que je puisse leur transmettre un $router
dactylographié à laquelle ils peuvent ajouter leurs propres itinéraires. Enfin, j'ai créé deux opérations (similaires).
de app/Actions/HomeAction.pre
:
namespace App\Action; use Aerys\Request; use Aerys\Response; class HomeAction { public function __invoke(Request $request, Response $response) { $response->end("hello world"); } }
La touche finale consiste à ajouter des scripts de raccourci pour démarrer la version de développement et de production du serveur Aerys.
de composer.json
:
"scripts": { "dev": "vendor/bin/aerys -d -c loader.php", "prod": "vendor/bin/aerys -c loader.php" }, "config": { "process-timeout": 0 },
Après tout cela, je peux démarrer un nouveau serveur et accéder à http://127.0.0.1:8080 en tapant la commande suivante:
composer dev
Paramètres frontaux
"D'accord, maintenant que j'ai rendu les choses relativement stables du côté PHP; comment puis-je construire un fichier ReactJS? Peut-être que je peux utiliser Laravel Mix…?"
Je ne veux pas vraiment créer une toute nouvelle chaîne de construction, et Mix a également été reconstruit pour bien fonctionner dans des projets non-laravels. Bien que la configuration et les extensions soient relativement faciles, il est plus orienté VueJS par défaut.
La première chose que je dois faire est d'installer certaines dépendances NPM. De package.json
:
"devDependencies": { "babel-preset-react": "^6.23.0", "bootstrap-sass": "^3.3.7", "jquery": "^3.1.1", "laravel-mix": "^0.7.5", "react": "^15.4.2", "react-dom": "^15.4.2", "webpack": "^2.2.1" },
mix utilise WebPack pour prétraiter et regrouper les fichiers JS et CSS. J'ai également besoin d'installer React et des bibliothèques Babel connexes pour créer des fichiers JSX. Enfin, j'ai ajouté le fichier bootstrap pour obtenir des styles par défaut.
Mélanger Charge automatiquement des fichiers de configuration personnalisés, j'ai donc ajouté ce qui suit. De webpack.mix.js
:
let mix = require("laravel-mix") // load babel presets for jsx files mix.webpackConfig({ "module": { "rules": [ { "test": /jsx$/, "exclude": /(node_modules)/, "loader": "babel-loader" + mix.config.babelConfig(), "query": { "presets": [ "react", "es2015", ], }, }, ], }, }) // set up front-end assets mix.setPublicPath("public") mix.js("assets/js/app.jsx", "public/js/app.js") mix.sass("assets/scss/app.scss", "public/css/app.css") mix.version()
J'ai besoin de dire à mix comment gérer les fichiers JSX, j'ai donc ajouté la même configuration que celles qui sont généralement placées dans .babelrc
. J'ai l'intention d'obtenir un seul point d'entrée JS et CSS dans différentes parties de l'application.
Remarque: Les versions futures de Mix auront une prise en charge intégrée pour la construction d'actifs ReactJS. À ce moment-là, le code mix.webpackConfig
peut être supprimé.
Encore une fois, j'ai créé des scripts de raccourci pour économiser beaucoup de travail. De package.json
:
$host = new Aerys\Host(); $host->expose("*", 8080); $host->use($router = Aerys\router()); $host->use($root = Aerys\root(.."/public")); $web = process .."/routes/web.pre"; $web($router); $api = process .."/routes/api.pre"; $api($router);
Les trois scripts utilisent des commandes de variables WebPack, mais elles diffèrent dans leurs opérations autres que cela. dev
Créer des versions de débogage des fichiers JS et CSS. Le commutateur -w
démarre le moniteur WebPack (afin que le bundle puisse être partiellement reconstruit). Le commutateur -p
permet une version de production rationalisée du bundle.
Puisque j'utilise le contrôle de version groupée, j'ai besoin d'un moyen de faire référence à un fichier comme /js/app.60795d5b3951178abba1.js
sans connaître la valeur de hachage. J'ai remarqué que Mix aime créer des fichiers manifestes, j'ai donc fait une fonction d'assistance pour l'interroger. De helpers.pre
:
vendor/bin/aerys -d -c config.php
Aerys sait comment gérer les promesses lorsqu'ils apparaissent sous la forme de $val = yield $promise
, j'ai donc utilisé la mise en œuvre des promesses d'AMP. Après avoir lu et décodé le fichier, je peux trouver le chemin d'accès à fichier correspondant. J'ai ajusté HomeAction
. De app/Actions/HomeAction.pre
:
return Pre\processAndRequire(__DIR__ . "/config.pre");
J'ai réalisé que je pouvais continuer à créer des fonctions qui renvoient les promesses et les utilisent de cette manière pour garder le code asynchrone. Ceci est mon code JS de assets/js/component.jsx
:
"require": { "amphp/aerys": "dev-amp_v2", "amphp/parallel": "dev-master", "league/container": "^2.2", "league/plates": "^3.3", "pre/short-closures": "^0.4.0" }, "require-dev": { "phpunit/phpunit": "^6.0" },
… et de assets/js/app.jsx
:
use Aerys\Router; use App\Action\HomeAction; return (Router $router) => { $router->route( "GET", "/", new HomeAction ); };
Après tout, je veux juste voir si Mix compilera mes fichiers JSX et si je peux les retrouver en utilisant la fonction Async mix
. Cela fonctionne!
Remarque: L'utilisation de la fonction mix
à chaque fois est coûteuse, surtout si nous chargeons le même fichier. Au lieu de cela, nous pouvons charger tous les modèles pendant la phase de démarrage du serveur et les référer à l'intérieur de l'opération si nécessaire. Le fichier de configuration que nous commençons Aerys peut renvoyer une promesse (comme celle qui nous est donnée par Amp\all
), afin que nous puissions analyser tous les modèles avant le début du serveur.
Connectez-vous à l'aide de WebSockets
Je l'ai presque configuré. La dernière chose à faire est de connecter le backend et le frontend via WebSockets. J'ai trouvé cela relativement simple, en utilisant une nouvelle classe. De app/Socket/GameSocket.pre
:
use Aerys\Router; use App\Action\Api\HomeAction; return (Router $router) => { $router->route( "GET", "/api", new HomeAction ); };
… et des modifications mineures pour le routage Web (à partir de routes/web.pre
):
namespace App\Action; use Aerys\Request; use Aerys\Response; class HomeAction { public function __invoke(Request $request, Response $response) { $response->end("hello world"); } }
Maintenant, je peux changer le JS pour me connecter à ce WebSocket et envoyer le message à tous ceux qui y sont connectés. De assets/js/component.jsx
:
"scripts": { "dev": "vendor/bin/aerys -d -c loader.php", "prod": "vendor/bin/aerys -c loader.php" }, "config": { "process-timeout": 0 },
Lorsque je crée un nouvel objet Component
, il se connecte au serveur WebSocket et ajoute un écouteur d'événements pour le nouveau message. J'ai ajouté du code de débogage - pour m'assurer qu'il se connecte correctement et envoie de nouveaux messages.
Nous allons aller plus en détail sur PHP et les webockets plus tard, ne vous inquiétez pas.
Résumé
Dans cette section, nous avons examiné comment configurer un serveur Web PHP asynchrone simple, comment utiliser Laravel Mix dans des projets non-laravel, et même comment connecter le backend et le frontage ensemble à l'aide de WebSockets.
wow! Il couvre beaucoup de contenu et nous n'avons pas encore écrit une ligne de code de jeu. Rejoignez-moi dans la deuxième partie et nous commencerons à construire la logique du jeu et à réagir l'interface.
(Cet article a été évalué par des pairs par Niklas Keller. Merci à tous les pairs examinateurs de SitePoint pour amener le contenu de SitePoint à son meilleur!)
FAQ pour le développement de jeux avec ReactJS et Php
ReactJS et PHP sont très compatibles dans le développement du jeu. ReactJS est une bibliothèque JavaScript qui est idéale pour la construction d'interfaces utilisateur, en particulier pour les applications à une seule page. Il permet une conception Web rapide et réactive. D'un autre côté, PHP est un langage de script côté serveur qui est très adapté au développement back-end. Il peut gérer la base de données, l'authentification des utilisateurs et la logique côté serveur. Lorsqu'elles sont utilisées ensemble, ReactJS peut gérer le frontal, créer des interfaces utilisateur dynamiques et interactives, tandis que PHP gère le back-end.
Oui, vous pouvez utiliser PHP pour la logique de jeu dans les jeux ReactJS. Bien que ReactJS gère l'interface utilisateur, PHP peut gérer la logique de jeu du côté du serveur. Cela comprend le traitement des données, la gestion des séances des utilisateurs et le contrôle des règles de jeu. Cette séparation des préoccupations permet un processus de développement plus ordonné et efficace.
ReactJS offre de nombreux avantages pour le développement du jeu. Son Dom virtuel permet des mises à jour et un rendu efficaces, ce qui rend le jeu plus fluide. Il prend également en charge les composants réutilisables, ce qui peut considérablement accélérer le temps de développement. De plus, ReactJS a une énorme communauté et des ressources riches pour faciliter la recherche de solutions aux problèmes ou apprendre de nouvelles technologies.
PHP présente de nombreux avantages dans le développement du jeu. Il s'agit d'un langage côté serveur, ce qui signifie qu'il peut gérer la gestion des données, l'authentification des utilisateurs et la logique du jeu côté serveur. PHP est également facile à apprendre, a une syntaxe simple et a une énorme communauté de développeurs. Il est également très évolutif, ce qui le rend adapté aux jeux qui peuvent nécessiter une gestion d'un grand nombre d'utilisateurs.
Pour commencer à développer des jeux avec ReactJS et PHP, vous devez d'abord apprendre les bases des deux langues. Il existe de nombreuses ressources en ligne et tutoriels disponibles. Une fois que vous êtes familier avec ces langues, vous pouvez commencer par construire un jeu simple. Cela peut être un jeu de texte de base ou un simple jeu de puzzle. Au fur et à mesure que vous gagnez plus d'expérience, vous pouvez commencer à construire des jeux plus complexes.
Oui, il existe plusieurs ressources et bibliothèques qui peuvent aider au développement de jeux à l'aide de ReactJS et PHP. Pour ReactJS, des bibliothèques comme React Game Kit et React Game Engine sont très utiles. Pour PHP, vous pouvez trouver des bibliothèques comme PHP-SDL ou Wyvern utile. De plus, il existe de nombreux tutoriels, guides et forums en ligne où vous pouvez en savoir plus et obtenir de l'aide.
Oui, vous pouvez créer des jeux multijoueurs à l'aide de ReactJS et PHP. ReactJS peut gérer les interfaces utilisateur, tandis que PHP peut gérer la logique côté serveur, y compris la gestion des sessions de joueurs et la synchronisation de l'état de jeu sur plusieurs clients.
Avec ReactJS et PHP, vous pouvez construire une grande variété de jeux. Cela comprend des jeux de texte simples, des jeux de puzzle, des jeux de plate-forme, des jeux de rôle et même des jeux en ligne multijoueurs. Les possibilités sont énormes et la limite est en fait votre imagination et votre niveau de compétence.
Dans un jeu développé à l'aide de ReactJS et PHP, PHP côté serveur peut être utilisé pour traiter les données. Cela peut inclure les données des joueurs, l'état du jeu, les scores, etc. Ces données peuvent être stockées dans une base de données et peuvent être interagies avec cette base de données à l'aide de PHP pour récupérer et mettre à jour les données selon les besoins.
Dans un jeu développé à l'aide de ReactJS, l'entrée de l'utilisateur peut être traitée à l'aide du système de traitement d'événements de React. Cela peut inclure des clics de souris, des touches de clavier et des événements tactiles. Le système de traitement des événements de React est puissant et flexible, vous permettant de contrôler facilement la façon dont le jeu réagit à la saisie des utilisateurs.
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!