├── Client └── WarCardJS │ ├── .cocos-project.json │ ├── CMakeLists.txt │ ├── index.html │ ├── main.js │ ├── manifest.webapp │ ├── project.json │ ├── res │ ├── HelloWorld.png │ ├── card.txt │ ├── grossini.plist │ ├── grossini.png │ ├── loading.js │ ├── sprites.plist │ └── sprites.png │ └── src │ ├── GameConfig.js │ ├── GameScene.js │ ├── Player.js │ ├── app.js │ ├── cards.js │ └── resource.js ├── README.md └── Server └── CardWarNettyServer ├── .classpath ├── .project ├── .settings └── org.eclipse.jdt.core.prefs ├── bin └── com │ ├── json │ ├── JSONArray.class │ ├── JSONException.class │ ├── JSONObject$Null.class │ ├── JSONObject.class │ ├── JSONString.class │ ├── JSONStringer.class │ ├── JSONTokener.class │ └── JSONWriter.class │ └── server │ ├── Config.class │ ├── GameEventHandler.class │ ├── GameManager.class │ ├── GameResponseDispatcher.class │ ├── GameServerInitializer.class │ ├── GameServerMain.class │ ├── HttpRequestHandler.class │ ├── LoggerManager.class │ ├── Player.class │ ├── TextWebSocketFrameHandler.class │ └── WebSocketServer.class ├── conf ├── configuration.properties └── logger.properties ├── lib ├── netty-all-4.0.33.Final-sources.jar └── netty-all-4.0.33.Final.jar └── src └── com ├── json ├── JSONArray.java ├── JSONException.java ├── JSONObject.java ├── JSONString.java ├── JSONStringer.java ├── JSONTokener.java └── JSONWriter.java └── server ├── Config.java ├── GameEventHandler.java ├── GameManager.java ├── GameResponseDispatcher.java ├── GameServerInitializer.java ├── GameServerMain.java ├── HttpRequestHandler.java ├── LoggerManager.java ├── Player.java ├── TextWebSocketFrameHandler.java └── WebSocketServer.java /Client/WarCardJS/.cocos-project.json: -------------------------------------------------------------------------------- 1 | { 2 | "engine_version": "cocos2d-x-3.9", 3 | "has_native": true, 4 | "project_type": "js" 5 | } -------------------------------------------------------------------------------- /Client/WarCardJS/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | #/**************************************************************************** 2 | # Copyright (c) 2014 Chukong Technologies Inc. 3 | # 4 | # http://www.cocos2d-x.org 5 | # 6 | # Permission is hereby granted, free of charge, to any person obtaining a copy 7 | # of this software and associated documentation files (the "Software"), to deal 8 | # in the Software without restriction, including without limitation the rights 9 | # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | # copies of the Software, and to permit persons to whom the Software is 11 | # furnished to do so, subject to the following conditions: 12 | 13 | # The above copyright notice and this permission notice shall be included in 14 | # all copies or substantial portions of the Software. 15 | 16 | # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | # THE SOFTWARE. 23 | # ****************************************************************************/ 24 | 25 | cmake_minimum_required(VERSION 2.8) 26 | 27 | set(APP_NAME MyGame) 28 | project (${APP_NAME}) 29 | 30 | set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cmake/Modules/") 31 | include(CocosBuildHelpers) 32 | 33 | option(USE_CHIPMUNK "Use chipmunk for physics library" ON) 34 | option(DEBUG_MODE "Debug or release?" ON) 35 | option(BUILD_EXTENSIONS "Build extension library" ON) 36 | option(BUILD_EDITOR_SPINE "Build editor support for spine" ON) 37 | option(BUILD_EDITOR_COCOSTUDIO "Build editor support for cocostudio" ON) 38 | option(BUILD_EDITOR_COCOSBUILDER "Build editor support for cocosbuilder" ON) 39 | option(USE_BULLET "Use bullet for physics3d library" ON) 40 | option(USE_PREBUILT_LIBS "Use prebuilt libraries in external directory" ON) 41 | 42 | 43 | if(DEBUG_MODE) 44 | set(CMAKE_BUILD_TYPE DEBUG) 45 | else(DEBUG_MODE) 46 | set(CMAKE_BUILD_TYPE RELEASE) 47 | endif(DEBUG_MODE) 48 | 49 | if(USE_BULLET) 50 | add_definitions(-DCC_ENABLE_BULLET_INTEGRATION=1) 51 | add_definitions(-DCC_USE_PHYSICS=1) 52 | endif(USE_BULLET) 53 | 54 | set(CMAKE_C_FLAGS_DEBUG "-DCOCOS2D_DEBUG=1") 55 | set(CMAKE_CXX_FLAGS_DEBUG ${CMAKE_C_FLAGS_DEBUG}) 56 | 57 | if(WIN32) 58 | ADD_DEFINITIONS (-D_USRDLL -DCOCOS2DXWIN32_EXPORTS -D_WINDOWS -DWIN32) 59 | 60 | if(MSVC) 61 | ADD_DEFINITIONS(-D_CRT_SECURE_NO_WARNINGS 62 | -D_SCL_SECURE_NO_WARNINGS 63 | -wd4251 -wd4244 -wd4334 64 | -wd4005 -wd4820 -wd4710 65 | -wd4514 -wd4056 -wd4996 -wd4099) 66 | else(MSVC)#MINGW 67 | 68 | endif(MSVC) 69 | elseif(APPLE) 70 | 71 | 72 | else()#Linux 73 | ADD_DEFINITIONS(-DLINUX -DCC_RESOURCE_FOLDER_LINUX="/") 74 | endif() 75 | 76 | 77 | if(NOT MSVC)# all gcc 78 | set(CMAKE_C_FLAGS_DEBUG "-g -Wall -DCOCOS2D_DEBUG=1") 79 | set(CMAKE_CXX_FLAGS_DEBUG ${CMAKE_C_FLAGS_DEBUG}) 80 | set(CMAKE_C_FLAGS ${CMAKE_C_FLAGS} "-std=c99") 81 | set(CMAKE_CXX_FLAGS ${CMAKE_CXX_FLAGS} "-std=c++11") 82 | endif() 83 | 84 | if(MINGW) 85 | add_definitions(-DGLEW_STATIC) 86 | endif() 87 | 88 | 89 | if(USE_CHIPMUNK) 90 | message("Using chipmunk ...") 91 | add_definitions(-DCC_ENABLE_CHIPMUNK_INTEGRATION=1) 92 | elseif(USE_BOX2D) 93 | message("Using box2d ...") 94 | add_definitions(-DCC_ENABLE_BOX2D_INTEGRATION=1) 95 | else(USE_CHIPMUNK) 96 | message(FATAL_ERROR "Must choose a physics library.") 97 | endif(USE_CHIPMUNK) 98 | 99 | # architecture 100 | if ( CMAKE_SIZEOF_VOID_P EQUAL 8 ) 101 | set(ARCH_DIR "64-bit") 102 | else() 103 | set(ARCH_DIR "32-bit") 104 | endif() 105 | 106 | if(WIN32) # Win32 107 | set(PLATFORM_FOLDER win32) 108 | elseif(APPLE)# osx or ios 109 | set(PLATFORM_FOLDER mac) 110 | else() # Assume Linux 111 | set(PLATFORM_FOLDER linux) 112 | endif() 113 | 114 | set(COCOS_EXTERNAL_DIR ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/external) 115 | 116 | 117 | include_directories( 118 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/ 119 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos 120 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/base 121 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/2d 122 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/ui 123 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/audio/include 124 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/storage 125 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/network 126 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/platform 127 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/editor-support 128 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/editor-support/spine 129 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/editor-support/cocosbuilder 130 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/editor-support/cocostudio 131 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/deprecated 132 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/platform 133 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/extensions 134 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/external 135 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/external/chipmunk/include/chipmunk 136 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/external/spidermonkey/include/${PLATFORM_FOLDER} 137 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/scripting/js-bindings/auto 138 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/scripting/js-bindings/manual 139 | ) 140 | 141 | link_directories( 142 | ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/external/spidermonkey/prebuilt/${PLATFORM_FOLDER}/${ARCH_DIR} 143 | ) 144 | 145 | 146 | if(USE_PREBUILT_LIBS) 147 | include(CocosUsePrebuiltLibs) 148 | endif() 149 | 150 | # GLFW3 used on Mac, Windows and Linux desktop platforms 151 | if(LINUX OR MACOSX OR WINDOWS) 152 | cocos_find_package(OpenGL OPENGL REQUIRED) 153 | 154 | if(LINUX OR WINDOWS) 155 | cocos_find_package(GLEW GLEW REQUIRED) 156 | endif() 157 | 158 | cocos_find_package(GLFW3 GLFW3 REQUIRED) 159 | include_directories(${GLFW3_INCLUDE_DIRS}) 160 | 161 | if(LINUX) 162 | set(CMAKE_THREAD_PREFER_PTHREAD TRUE) 163 | find_package(Threads REQUIRED) 164 | set(THREADS_LIBRARIES ${CMAKE_THREAD_LIBS_INIT}) 165 | 166 | #cocos_find_package(FMODEX FMODEX REQUIRED) 167 | cocos_find_package(Fontconfig FONTCONFIG REQUIRED) 168 | cocos_find_package(GTK3 GTK3 REQUIRED) 169 | endif() 170 | 171 | if(WINDOWS) 172 | cocos_find_package(Vorbis VORBIS REQUIRED) 173 | cocos_find_package(MPG123 MPG123 REQUIRED) 174 | cocos_find_package(OpenAL OPENAL REQUIRED) 175 | # because FindOpenAL.cmake set include dir for '#include ' for portability (not for '#include ' 176 | set(OPENAL_DEFINITIONS "-DOPENAL_PLAIN_INCLUDES") 177 | endif() 178 | endif(LINUX OR MACOSX OR WINDOWS) 179 | 180 | # Freetype required on all platforms 181 | cocos_find_package(Freetype FREETYPE REQUIRED) 182 | 183 | # WebP required if used 184 | if(USE_WEBP) 185 | cocos_find_package(WebP WEBP REQUIRED) 186 | endif(USE_WEBP) 187 | 188 | # Chipmunk 189 | if(USE_CHIPMUNK) 190 | cocos_find_package(Chipmunk CHIPMUNK REQUIRED) 191 | add_definitions(-DCC_ENABLE_CHIPMUNK_INTEGRATION=1) 192 | if(IOS OR MACOSX) 193 | # without this chipmunk will try to use apple defined geometry types, that conflicts with cocos 194 | add_definitions(-DCP_USE_CGPOINTS=0) 195 | endif() 196 | else(USE_CHIPMUNK) 197 | add_definitions(-DCC_USE_PHYSICS=0) 198 | endif(USE_CHIPMUNK) 199 | 200 | # Box2d (not prebuilded, exists as source) 201 | if(USE_BOX2D) 202 | if(USE_PREBUILT_LIBS) 203 | add_subdirectory(frameworks/cocos2d-x/external/Box2D) 204 | set(Box2D_INCLUDE_DIRS ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/js-bindings/cocos2d-x/external/box2d/include) 205 | set(Box2D_LIBRARIES box2d) 206 | else() 207 | find_package(Box2D REQUIRED CONFIG) 208 | # actually Box2D in next line is not a library, it is target exported from Box2DConfig.cmake 209 | set(Box2D_LIBRARIES Box2D) 210 | endif() 211 | message(STATUS "Box2D include dirs: ${Box2D_INCLUDE_DIRS}") 212 | add_definitions(-DCC_ENABLE_BOX2D_INTEGRATION=1) 213 | else() 214 | add_definitions(-DCC_ENABLE_BOX2D_INTEGRATION=0) 215 | endif(USE_BOX2D) 216 | 217 | # Tinyxml2 (not prebuilded, exists as source) 218 | if(USE_PREBUILT_LIBS) 219 | add_subdirectory(frameworks/cocos2d-x/external/tinyxml2) 220 | set(TinyXML2_INCLUDE_DIRS ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/external/tinyxml2) 221 | set(TinyXML2_LIBRARIES tinyxml2) 222 | else() 223 | cocos_find_package(TinyXML2 TinyXML2 REQUIRED) 224 | endif() 225 | message(STATUS "TinyXML2 include dirs: ${TinyXML2_INCLUDE_DIRS}") 226 | 227 | # libjpeg 228 | cocos_find_package(JPEG JPEG REQUIRED) 229 | cocos_find_package(ZLIB ZLIB REQUIRED) 230 | 231 | # minizip (we try to migrate to minizip from https://github.com/nmoinvaz/minizip) 232 | # only msys2 currently provides package for this variant, all other 233 | # dists have packages from zlib, thats very old for us. 234 | # moreover our embedded version modified to quick provide 235 | # functionality needed by cocos. 236 | if(USE_PREBUILT_LIBS OR NOT MINGW) 237 | add_subdirectory(frameworks/cocos2d-x/external/unzip) 238 | set(MINIZIP_INCLUDE_DIRS ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/external/unzip) 239 | set(MINIZIP_LIBRARIES unzip) 240 | message(STATUS "MINIZIP include dirs: ${MINIZIP_INCLUDE_DIRS}") 241 | else() 242 | cocos_find_package(MINIZIP MINIZIP REQUIRED) 243 | # double check that we have needed functions 244 | include(CheckLibraryExists) 245 | check_library_exists(${MINIZIP_LIBRARIES} "unzGoToFirstFile2" "" MINIZIP_HAS_GOTOFIRSTFILE2) 246 | if(NOT MINIZIP_HAS_GOTOFIRSTFILE2) 247 | message(FATAL_ERROR "Minizip library on you system very old. Please use recent version from https://github.com/nmoinvaz/minizip or enable USE_PREBUILT_LIBS") 248 | endif() 249 | add_definitions(-DMINIZIP_FROM_SYSTEM) 250 | endif() 251 | 252 | cocos_find_package(PNG PNG REQUIRED) 253 | cocos_find_package(TIFF TIFF REQUIRED) 254 | cocos_find_package(WEBSOCKETS WEBSOCKETS REQUIRED) 255 | cocos_find_package(CURL CURL REQUIRED) 256 | 257 | 258 | add_subdirectory(frameworks/cocos2d-x/external/flatbuffers) 259 | set(FLATBUFFERS_INCLUDE_DIRS frameworks/cocos2d-x/external) 260 | message(STATUS "Flatbuffers include dirs: ${FLATBUFFERS_INCLUDE_DIRS}") 261 | 262 | 263 | # build xxhash 264 | add_subdirectory(frameworks/cocos2d-x/external/xxhash) 265 | include_directories(frameworks/cocos2d-x/external/xxhash) 266 | 267 | #buid recast 268 | add_subdirectory(frameworks/cocos2d-x/external/recast) 269 | 270 | set(GAME_SRC 271 | frameworks/runtime-src/proj.linux/main.cpp 272 | frameworks/runtime-src/Classes/AppDelegate.cpp 273 | ) 274 | 275 | # cocos2d 276 | add_subdirectory(frameworks/cocos2d-x/cocos) 277 | 278 | #jsbindings library 279 | add_subdirectory(frameworks/cocos2d-x/cocos/scripting/js-bindings) 280 | 281 | # add the executable 282 | add_executable(${APP_NAME} 283 | ${GAME_SRC} 284 | ) 285 | 286 | target_link_libraries(${APP_NAME} 287 | jscocos2d 288 | cocos2d 289 | recast 290 | ) 291 | 292 | if(USE_BULLET) 293 | add_subdirectory(frameworks/cocos2d-x/external/bullet) 294 | target_link_libraries(${APP_NAME} bullet) 295 | endif() 296 | 297 | set(APP_BIN_DIR "${CMAKE_BINARY_DIR}/bin") 298 | 299 | set_target_properties(${APP_NAME} PROPERTIES 300 | RUNTIME_OUTPUT_DIRECTORY "${APP_BIN_DIR}") 301 | 302 | pre_build(${APP_NAME} 303 | COMMAND ${CMAKE_COMMAND} -E remove_directory ${APP_BIN_DIR}/script 304 | COMMAND ${CMAKE_COMMAND} -E remove_directory ${APP_BIN_DIR}/res 305 | COMMAND ${CMAKE_COMMAND} -E remove_directory ${APP_BIN_DIR}/src 306 | COMMAND ${CMAKE_COMMAND} -E remove ${APP_BIN_DIR}/*.js 307 | COMMAND ${CMAKE_COMMAND} -E remove ${APP_BIN_DIR}/*.json 308 | COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_CURRENT_SOURCE_DIR}/res ${APP_BIN_DIR}/res 309 | COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_CURRENT_SOURCE_DIR}/src ${APP_BIN_DIR}/src 310 | COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_CURRENT_SOURCE_DIR}/frameworks/cocos2d-x/cocos/scripting/js-bindings/script ${APP_BIN_DIR}/script 311 | COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_CURRENT_SOURCE_DIR}/main.js ${APP_BIN_DIR}/main.js 312 | COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_CURRENT_SOURCE_DIR}/project.json ${APP_BIN_DIR}/project.json 313 | ) 314 | 315 | -------------------------------------------------------------------------------- /Client/WarCardJS/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | Cocos2d-html5 Hello World test 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /Client/WarCardJS/main.js: -------------------------------------------------------------------------------- 1 | /** 2 | * A brief explanation for "project.json": 3 | * Here is the content of project.json file, this is the global configuration for your game, you can modify it to customize some behavior. 4 | * The detail of each field is under it. 5 | { 6 | "project_type": "javascript", 7 | // "project_type" indicate the program language of your project, you can ignore this field 8 | 9 | "debugMode" : 1, 10 | // "debugMode" possible values : 11 | // 0 - No message will be printed. 12 | // 1 - cc.error, cc.assert, cc.warn, cc.log will print in console. 13 | // 2 - cc.error, cc.assert, cc.warn will print in console. 14 | // 3 - cc.error, cc.assert will print in console. 15 | // 4 - cc.error, cc.assert, cc.warn, cc.log will print on canvas, available only on web. 16 | // 5 - cc.error, cc.assert, cc.warn will print on canvas, available only on web. 17 | // 6 - cc.error, cc.assert will print on canvas, available only on web. 18 | 19 | "showFPS" : true, 20 | // Left bottom corner fps information will show when "showFPS" equals true, otherwise it will be hide. 21 | 22 | "frameRate" : 60, 23 | // "frameRate" set the wanted frame rate for your game, but the real fps depends on your game implementation and the running environment. 24 | 25 | "noCache" : false, 26 | // Set "noCache" to true can make the loader ignoring the html page cache while loading your resources, 27 | // especially useful in Android web browsers. 28 | 29 | "id" : "gameCanvas", 30 | // "gameCanvas" sets the id of your canvas element on the web page, it's useful only on web. 31 | 32 | "renderMode" : 0, 33 | // "renderMode" sets the renderer type, only useful on web : 34 | // 0 - Automatically chosen by engine 35 | // 1 - Forced to use canvas renderer 36 | // 2 - Forced to use WebGL renderer, but this will be ignored on mobile browsers 37 | 38 | "engineDir" : "frameworks/cocos2d-html5/", 39 | // In debug mode, if you use the whole engine to develop your game, you should specify its relative path with "engineDir", 40 | // but if you are using a single engine file, you can ignore it. 41 | 42 | "modules" : ["cocos2d"], 43 | // "modules" defines which modules you will need in your game, it's useful only on web, 44 | // using this can greatly reduce your game's resource size, and the cocos console tool can package your game with only the modules you set. 45 | // For details about modules definitions, you can refer to "../../frameworks/cocos2d-html5/modulesConfig.json". 46 | 47 | "jsList" : [ 48 | ] 49 | // "jsList" sets the list of js files in your game. 50 | } 51 | * 52 | */ 53 | 54 | cc.game.onStart = function(){ 55 | if(!cc.sys.isNative && document.getElementById("cocosLoading")) //If referenced loading.js, please remove it 56 | document.body.removeChild(document.getElementById("cocosLoading")); 57 | 58 | // Pass true to enable retina display, on Android disabled by default to improve performance 59 | cc.view.enableRetina(cc.sys.os === cc.sys.OS_IOS ? true : false); 60 | // Adjust viewport meta 61 | cc.view.adjustViewPort(true); 62 | // Setup the resolution policy and design resolution size 63 | cc.view.setDesignResolutionSize(450, 800, cc.ResolutionPolicy.SHOW_ALL); 64 | // Instead of set design resolution, you can also set the real pixel resolution size 65 | // Uncomment the following line and delete the previous line. 66 | // cc.view.setRealPixelResolution(960, 640, cc.ResolutionPolicy.SHOW_ALL); 67 | // The game will be resized when browser size change 68 | cc.view.resizeWithBrowserSize(true); 69 | //load resources 70 | cc.LoaderScene.preload(g_resources, function () { 71 | cc.director.runScene(new LoginScene()); 72 | }, this); 73 | }; 74 | cc.game.run(); -------------------------------------------------------------------------------- /Client/WarCardJS/manifest.webapp: -------------------------------------------------------------------------------- 1 | { 2 | "version": "1.0", 3 | "name": "WarCardJS", 4 | "description": "WarCardJS", 5 | "launch_path": "/index.html", 6 | "icons": { 7 | "128": "/res/icon.png" 8 | }, 9 | "developer": { 10 | "name": "Cocos2d-html5", 11 | "url": "http://cocos2d-x.org/" 12 | }, 13 | "default_locale": "en", 14 | "installs_allowed_from": [ 15 | "*" 16 | ], 17 | "orientation": "portrait-primary", 18 | "fullscreen": "true" 19 | } 20 | -------------------------------------------------------------------------------- /Client/WarCardJS/project.json: -------------------------------------------------------------------------------- 1 | { 2 | "project_type": "javascript", 3 | 4 | "debugMode" : 1, 5 | "showFPS" : true, 6 | "frameRate" : 60, 7 | "noCache" : false, 8 | "id" : "gameCanvas", 9 | "renderMode" : 0, 10 | "engineDir":"frameworks/cocos2d-html5", 11 | 12 | "modules" : ["cocos2d","extensions"], 13 | 14 | "jsList" : [ 15 | "src/GameConfig.js", 16 | "src/GameScene.js", 17 | "src/resource.js", 18 | "src/app.js", 19 | "src/Player.js" 20 | ] 21 | } 22 | -------------------------------------------------------------------------------- /Client/WarCardJS/res/HelloWorld.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Client/WarCardJS/res/HelloWorld.png -------------------------------------------------------------------------------- /Client/WarCardJS/res/card.txt: -------------------------------------------------------------------------------- 1 | cardBack_blue1.png 2 | cardBack_blue2.png 3 | cardBack_blue3.png 4 | cardBack_blue4.png 5 | cardBack_blue5.png 6 | cardBack_green1.png 7 | cardBack_green2.png 8 | cardBack_green3.png 9 | cardBack_green4.png 10 | cardBack_green5.png 11 | cardBack_red1.png 12 | cardBack_red2.png 13 | cardBack_red3.png 14 | cardBack_red4.png 15 | cardBack_red5.png 16 | cardClubs10.png 17 | cardClubs2.png 18 | cardClubs3.png 19 | cardClubs4.png 20 | cardClubs5.png 21 | cardClubs6.png 22 | cardClubs7.png 23 | cardClubs8.png 24 | cardClubs9.png 25 | cardClubsA.png 26 | cardClubsJ.png 27 | cardClubsK.png 28 | cardClubsQ.png 29 | cardDiamonds10.png 30 | cardDiamonds2.png 31 | cardDiamonds3.png 32 | cardDiamonds4.png 33 | cardDiamonds5.png 34 | cardDiamonds6.png 35 | cardDiamonds7.png 36 | cardDiamonds8.png 37 | cardDiamonds9.png 38 | cardDiamondsA.png 39 | cardDiamondsJ.png 40 | cardDiamondsK.png 41 | cardDiamondsQ.png 42 | cardHearts10.png 43 | cardHearts2.png 44 | cardHearts3.png 45 | cardHearts4.png 46 | cardHearts5.png 47 | cardHearts6.png 48 | cardHearts7.png 49 | cardHearts8.png 50 | cardHearts9.png 51 | cardHeartsA.png 52 | cardHeartsJ.png 53 | cardHeartsK.png 54 | cardHeartsQ.png 55 | cardJoker.png 56 | cardSpades10.png 57 | cardSpades2.png 58 | cardSpades3.png 59 | cardSpades4.png 60 | cardSpades5.png 61 | cardSpades6.png 62 | cardSpades7.png 63 | cardSpades8.png 64 | cardSpades9.png 65 | cardSpadesA.png 66 | cardSpadesJ.png 67 | cardSpadesK.png 68 | cardSpadesQ.png 69 | -------------------------------------------------------------------------------- /Client/WarCardJS/res/grossini.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | texture 6 | 7 | width 8 | 512 9 | height 10 | 256 11 | 12 | frames 13 | 14 | grossini_dance_01.png 15 | 16 | x 17 | 347 18 | y 19 | 1 20 | width 21 | 51 22 | height 23 | 109 24 | offsetX 25 | 0 26 | offsetY 27 | -1 28 | originalWidth 29 | 85 30 | originalHeight 31 | -121 32 | 33 | grossini_dance_02.png 34 | 35 | x 36 | 215 37 | y 38 | 111 39 | width 40 | 63 41 | height 42 | 109 43 | offsetX 44 | -6 45 | offsetY 46 | -1 47 | originalWidth 48 | 85 49 | originalHeight 50 | -121 51 | 52 | grossini_dance_03.png 53 | 54 | x 55 | 151 56 | y 57 | 111 58 | width 59 | 63 60 | height 61 | 109 62 | offsetX 63 | -6 64 | offsetY 65 | -1 66 | originalWidth 67 | 85 68 | originalHeight 69 | -121 70 | 71 | grossini_dance_04.png 72 | 73 | x 74 | 1 75 | y 76 | 111 77 | width 78 | 74 79 | height 80 | 109 81 | offsetX 82 | -0.5 83 | offsetY 84 | -1 85 | originalWidth 86 | 85 87 | originalHeight 88 | -121 89 | 90 | grossini_dance_05.png 91 | 92 | x 93 | 76 94 | y 95 | 111 96 | width 97 | 74 98 | height 99 | 109 100 | offsetX 101 | -0.5 102 | offsetY 103 | -1 104 | originalWidth 105 | 85 106 | originalHeight 107 | -121 108 | 109 | grossini_dance_06.png 110 | 111 | x 112 | 399 113 | y 114 | 1 115 | width 116 | 63 117 | height 118 | 109 119 | offsetX 120 | -6 121 | offsetY 122 | -1 123 | originalWidth 124 | 85 125 | originalHeight 126 | -121 127 | 128 | grossini_dance_07.png 129 | 130 | x 131 | 105 132 | y 133 | 1 134 | width 135 | 63 136 | height 137 | 109 138 | offsetX 139 | -6 140 | offsetY 141 | -1 142 | originalWidth 143 | 85 144 | originalHeight 145 | -121 146 | 147 | grossini_dance_08.png 148 | 149 | x 150 | 1 151 | y 152 | 1 153 | width 154 | 51 155 | height 156 | 109 157 | offsetX 158 | 0 159 | offsetY 160 | -1 161 | originalWidth 162 | 85 163 | originalHeight 164 | -121 165 | 166 | grossini_dance_09.png 167 | 168 | x 169 | 295 170 | y 171 | 1 172 | width 173 | 51 174 | height 175 | 109 176 | offsetX 177 | 0 178 | offsetY 179 | -1 180 | originalWidth 181 | 85 182 | originalHeight 183 | -121 184 | 185 | grossini_dance_10.png 186 | 187 | x 188 | 232 189 | y 190 | 1 191 | width 192 | 62 193 | height 194 | 109 195 | offsetX 196 | 5.5 197 | offsetY 198 | -1 199 | originalWidth 200 | 85 201 | originalHeight 202 | -121 203 | 204 | grossini_dance_11.png 205 | 206 | x 207 | 169 208 | y 209 | 1 210 | width 211 | 62 212 | height 213 | 109 214 | offsetX 215 | 5.5 216 | offsetY 217 | -1 218 | originalWidth 219 | 85 220 | originalHeight 221 | -121 222 | 223 | grossini_dance_12.png 224 | 225 | x 226 | 279 227 | y 228 | 111 229 | width 230 | 51 231 | height 232 | 106 233 | offsetX 234 | 0 235 | offsetY 236 | -2.5 237 | originalWidth 238 | 85 239 | originalHeight 240 | -121 241 | 242 | grossini_dance_13.png 243 | 244 | x 245 | 53 246 | y 247 | 1 248 | width 249 | 51 250 | height 251 | 109 252 | offsetX 253 | 0 254 | offsetY 255 | -1 256 | originalWidth 257 | 85 258 | originalHeight 259 | -121 260 | 261 | grossini_dance_14.png 262 | 263 | x 264 | 331 265 | y 266 | 111 267 | width 268 | 51 269 | height 270 | 106 271 | offsetX 272 | 0 273 | offsetY 274 | -2.5 275 | originalWidth 276 | 85 277 | originalHeight 278 | -121 279 | 280 | 281 | 282 | 283 | -------------------------------------------------------------------------------- /Client/WarCardJS/res/grossini.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Client/WarCardJS/res/grossini.png -------------------------------------------------------------------------------- /Client/WarCardJS/res/loading.js: -------------------------------------------------------------------------------- 1 | (function(){var createStyle=function(){return".cocosLoading{position:absolute;margin:-30px -60px;padding:0;top:50%;left:50%}"+".cocosLoading ul{margin:0;padding:0;}"+".cocosLoading span{color:#FFF;text-align:center;display:block;}"+".cocosLoading li{list-style:none;float:left;border-radius:15px;width:15px;height:15px;background:#FFF;margin:5px 0 0 10px}"+".cocosLoading li .ball,.cocosLoading li .unball{background-color:#2187e7;background-image:-moz-linear-gradient(90deg,#2187e7 25%,#a0eaff);background-image:-webkit-linear-gradient(90deg,#2187e7 25%,#a0eaff);width:15px;height:15px;border-radius:50px}"+".cocosLoading li .ball{transform:scale(0);-moz-transform:scale(0);-webkit-transform:scale(0);animation:showDot 1s linear forwards;-moz-animation:showDot 1s linear forwards;-webkit-animation:showDot 1s linear forwards}"+".cocosLoading li .unball{transform:scale(1);-moz-transform:scale(1);-webkit-transform:scale(1);animation:hideDot 1s linear forwards;-moz-animation:hideDot 1s linear forwards;-webkit-animation:hideDot 1s linear forwards}"+"@keyframes showDot{0%{transform:scale(0,0)}100%{transform:scale(1,1)}}"+"@-moz-keyframes showDot{0%{-moz-transform:scale(0,0)}100%{-moz-transform:scale(1,1)}}"+"@-webkit-keyframes showDot{0%{-webkit-transform:scale(0,0)}100%{-webkit-transform:scale(1,1)}}"+"@keyframes hideDot{0%{transform:scale(1,1)}100%{transform:scale(0,0)}}"+"@-moz-keyframes hideDot{0%{-moz-transform:scale(1,1)}100%{-moz-transform:scale(0,0)}}"+"@-webkit-keyframes hideDot{0%{-webkit-transform:scale(1,1)}100%{-webkit-transform:scale(0,0)}}"};var createDom=function(id,num){id=id||"cocosLoading";num=num||5;var i,item;var div=document.createElement("div");div.className="cocosLoading";div.id=id;var bar=document.createElement("ul");var list=[];for(i=0;i=list.length){direction=!direction;index=0;time=1000}else{time=300}animation()},time)};animation()};(function(){var bgColor=document.body.style.background;document.body.style.background="#000";var style=document.createElement("style");style.type="text/css";style.innerHTML=createStyle();document.head.appendChild(style);var list=createDom();startAnimation(list,function(){var div=document.getElementById("cocosLoading");if(!div){document.body.style.background=bgColor}return !!div})})()})(); -------------------------------------------------------------------------------- /Client/WarCardJS/res/sprites.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | frames 6 | 7 | cardBack_blue1.png 8 | 9 | frame 10 | {{0,263},{70,95}} 11 | offset 12 | {0,0} 13 | rotated 14 | 15 | sourceColorRect 16 | {{0,0},{70,95}} 17 | sourceSize 18 | {70,95} 19 | 20 | 21 | cardBack_blue2.png 22 | 23 | frame 24 | {{0,359},{70,95}} 25 | offset 26 | {0,0} 27 | rotated 28 | 29 | sourceColorRect 30 | {{0,0},{70,95}} 31 | sourceSize 32 | {70,95} 33 | 34 | 35 | cardBack_blue3.png 36 | 37 | frame 38 | {{0,167},{70,95}} 39 | offset 40 | {0,0} 41 | rotated 42 | 43 | sourceColorRect 44 | {{0,0},{70,95}} 45 | sourceSize 46 | {70,95} 47 | 48 | 49 | cardBack_blue4.png 50 | 51 | frame 52 | {{0,71},{70,95}} 53 | offset 54 | {0,0} 55 | rotated 56 | 57 | sourceColorRect 58 | {{0,0},{70,95}} 59 | sourceSize 60 | {70,95} 61 | 62 | 63 | cardBack_blue5.png 64 | 65 | frame 66 | {{213,480},{70,95}} 67 | offset 68 | {0,0} 69 | rotated 70 | 71 | sourceColorRect 72 | {{0,0},{70,95}} 73 | sourceSize 74 | {70,95} 75 | 76 | 77 | cardBack_green1.png 78 | 79 | frame 80 | {{426,768},{70,95}} 81 | offset 82 | {0,0} 83 | rotated 84 | 85 | sourceColorRect 86 | {{0,0},{70,95}} 87 | sourceSize 88 | {70,95} 89 | 90 | 91 | cardBack_green2.png 92 | 93 | frame 94 | {{426,672},{70,95}} 95 | offset 96 | {0,0} 97 | rotated 98 | 99 | sourceColorRect 100 | {{0,0},{70,95}} 101 | sourceSize 102 | {70,95} 103 | 104 | 105 | cardBack_green3.png 106 | 107 | frame 108 | {{426,576},{70,95}} 109 | offset 110 | {0,0} 111 | rotated 112 | 113 | sourceColorRect 114 | {{0,0},{70,95}} 115 | sourceSize 116 | {70,95} 117 | 118 | 119 | cardBack_green4.png 120 | 121 | frame 122 | {{426,480},{70,95}} 123 | offset 124 | {0,0} 125 | rotated 126 | 127 | sourceColorRect 128 | {{0,0},{70,95}} 129 | sourceSize 130 | {70,95} 131 | 132 | 133 | cardBack_green5.png 134 | 135 | frame 136 | {{426,384},{70,95}} 137 | offset 138 | {0,0} 139 | rotated 140 | 141 | sourceColorRect 142 | {{0,0},{70,95}} 143 | sourceSize 144 | {70,95} 145 | 146 | 147 | cardBack_red1.png 148 | 149 | frame 150 | {{426,288},{70,95}} 151 | offset 152 | {0,0} 153 | rotated 154 | 155 | sourceColorRect 156 | {{0,0},{70,95}} 157 | sourceSize 158 | {70,95} 159 | 160 | 161 | cardBack_red2.png 162 | 163 | frame 164 | {{426,192},{70,95}} 165 | offset 166 | {0,0} 167 | rotated 168 | 169 | sourceColorRect 170 | {{0,0},{70,95}} 171 | sourceSize 172 | {70,95} 173 | 174 | 175 | cardBack_red3.png 176 | 177 | frame 178 | {{426,96},{70,95}} 179 | offset 180 | {0,0} 181 | rotated 182 | 183 | sourceColorRect 184 | {{0,0},{70,95}} 185 | sourceSize 186 | {70,95} 187 | 188 | 189 | cardBack_red4.png 190 | 191 | frame 192 | {{426,0},{70,95}} 193 | offset 194 | {0,0} 195 | rotated 196 | 197 | sourceColorRect 198 | {{0,0},{70,95}} 199 | sourceSize 200 | {70,95} 201 | 202 | 203 | cardBack_red5.png 204 | 205 | frame 206 | {{355,864},{70,95}} 207 | offset 208 | {0,0} 209 | rotated 210 | 211 | sourceColorRect 212 | {{0,0},{70,95}} 213 | sourceSize 214 | {70,95} 215 | 216 | 217 | cardClubs10.png 218 | 219 | frame 220 | {{355,0},{70,95}} 221 | offset 222 | {0,0} 223 | rotated 224 | 225 | sourceColorRect 226 | {{0,0},{70,95}} 227 | sourceSize 228 | {70,95} 229 | 230 | 231 | cardClubs2.png 232 | 233 | frame 234 | {{355,768},{70,95}} 235 | offset 236 | {0,0} 237 | rotated 238 | 239 | sourceColorRect 240 | {{0,0},{70,95}} 241 | sourceSize 242 | {70,95} 243 | 244 | 245 | cardClubs3.png 246 | 247 | frame 248 | {{355,672},{70,95}} 249 | offset 250 | {0,0} 251 | rotated 252 | 253 | sourceColorRect 254 | {{0,0},{70,95}} 255 | sourceSize 256 | {70,95} 257 | 258 | 259 | cardClubs4.png 260 | 261 | frame 262 | {{355,576},{70,95}} 263 | offset 264 | {0,0} 265 | rotated 266 | 267 | sourceColorRect 268 | {{0,0},{70,95}} 269 | sourceSize 270 | {70,95} 271 | 272 | 273 | cardClubs5.png 274 | 275 | frame 276 | {{355,480},{70,95}} 277 | offset 278 | {0,0} 279 | rotated 280 | 281 | sourceColorRect 282 | {{0,0},{70,95}} 283 | sourceSize 284 | {70,95} 285 | 286 | 287 | cardClubs6.png 288 | 289 | frame 290 | {{355,384},{70,95}} 291 | offset 292 | {0,0} 293 | rotated 294 | 295 | sourceColorRect 296 | {{0,0},{70,95}} 297 | sourceSize 298 | {70,95} 299 | 300 | 301 | cardClubs7.png 302 | 303 | frame 304 | {{355,288},{70,95}} 305 | offset 306 | {0,0} 307 | rotated 308 | 309 | sourceColorRect 310 | {{0,0},{70,95}} 311 | sourceSize 312 | {70,95} 313 | 314 | 315 | cardClubs8.png 316 | 317 | frame 318 | {{355,192},{70,95}} 319 | offset 320 | {0,0} 321 | rotated 322 | 323 | sourceColorRect 324 | {{0,0},{70,95}} 325 | sourceSize 326 | {70,95} 327 | 328 | 329 | cardClubs9.png 330 | 331 | frame 332 | {{355,96},{70,95}} 333 | offset 334 | {0,0} 335 | rotated 336 | 337 | sourceColorRect 338 | {{0,0},{70,95}} 339 | sourceSize 340 | {70,95} 341 | 342 | 343 | cardClubsA.png 344 | 345 | frame 346 | {{284,864},{70,95}} 347 | offset 348 | {0,0} 349 | rotated 350 | 351 | sourceColorRect 352 | {{0,0},{70,95}} 353 | sourceSize 354 | {70,95} 355 | 356 | 357 | cardClubsJ.png 358 | 359 | frame 360 | {{284,768},{70,95}} 361 | offset 362 | {0,0} 363 | rotated 364 | 365 | sourceColorRect 366 | {{0,0},{70,95}} 367 | sourceSize 368 | {70,95} 369 | 370 | 371 | cardClubsK.png 372 | 373 | frame 374 | {{284,672},{70,95}} 375 | offset 376 | {0,0} 377 | rotated 378 | 379 | sourceColorRect 380 | {{0,0},{70,95}} 381 | sourceSize 382 | {70,95} 383 | 384 | 385 | cardClubsQ.png 386 | 387 | frame 388 | {{284,576},{70,95}} 389 | offset 390 | {0,0} 391 | rotated 392 | 393 | sourceColorRect 394 | {{0,0},{70,95}} 395 | sourceSize 396 | {70,95} 397 | 398 | 399 | cardDiamonds10.png 400 | 401 | frame 402 | {{213,672},{70,95}} 403 | offset 404 | {0,0} 405 | rotated 406 | 407 | sourceColorRect 408 | {{0,0},{70,95}} 409 | sourceSize 410 | {70,95} 411 | 412 | 413 | cardDiamonds2.png 414 | 415 | frame 416 | {{284,480},{70,95}} 417 | offset 418 | {0,0} 419 | rotated 420 | 421 | sourceColorRect 422 | {{0,0},{70,95}} 423 | sourceSize 424 | {70,95} 425 | 426 | 427 | cardDiamonds3.png 428 | 429 | frame 430 | {{284,384},{70,95}} 431 | offset 432 | {0,0} 433 | rotated 434 | 435 | sourceColorRect 436 | {{0,0},{70,95}} 437 | sourceSize 438 | {70,95} 439 | 440 | 441 | cardDiamonds4.png 442 | 443 | frame 444 | {{284,288},{70,95}} 445 | offset 446 | {0,0} 447 | rotated 448 | 449 | sourceColorRect 450 | {{0,0},{70,95}} 451 | sourceSize 452 | {70,95} 453 | 454 | 455 | cardDiamonds5.png 456 | 457 | frame 458 | {{284,192},{70,95}} 459 | offset 460 | {0,0} 461 | rotated 462 | 463 | sourceColorRect 464 | {{0,0},{70,95}} 465 | sourceSize 466 | {70,95} 467 | 468 | 469 | cardDiamonds6.png 470 | 471 | frame 472 | {{284,96},{70,95}} 473 | offset 474 | {0,0} 475 | rotated 476 | 477 | sourceColorRect 478 | {{0,0},{70,95}} 479 | sourceSize 480 | {70,95} 481 | 482 | 483 | cardDiamonds7.png 484 | 485 | frame 486 | {{284,0},{70,95}} 487 | offset 488 | {0,0} 489 | rotated 490 | 491 | sourceColorRect 492 | {{0,0},{70,95}} 493 | sourceSize 494 | {70,95} 495 | 496 | 497 | cardDiamonds8.png 498 | 499 | frame 500 | {{213,864},{70,95}} 501 | offset 502 | {0,0} 503 | rotated 504 | 505 | sourceColorRect 506 | {{0,0},{70,95}} 507 | sourceSize 508 | {70,95} 509 | 510 | 511 | cardDiamonds9.png 512 | 513 | frame 514 | {{213,768},{70,95}} 515 | offset 516 | {0,0} 517 | rotated 518 | 519 | sourceColorRect 520 | {{0,0},{70,95}} 521 | sourceSize 522 | {70,95} 523 | 524 | 525 | cardDiamondsA.png 526 | 527 | frame 528 | {{213,576},{70,95}} 529 | offset 530 | {0,0} 531 | rotated 532 | 533 | sourceColorRect 534 | {{0,0},{70,95}} 535 | sourceSize 536 | {70,95} 537 | 538 | 539 | cardDiamondsJ.png 540 | 541 | frame 542 | {{426,864},{70,95}} 543 | offset 544 | {0,0} 545 | rotated 546 | 547 | sourceColorRect 548 | {{0,0},{70,95}} 549 | sourceSize 550 | {70,95} 551 | 552 | 553 | cardDiamondsK.png 554 | 555 | frame 556 | {{213,384},{70,95}} 557 | offset 558 | {0,0} 559 | rotated 560 | 561 | sourceColorRect 562 | {{0,0},{70,95}} 563 | sourceSize 564 | {70,95} 565 | 566 | 567 | cardDiamondsQ.png 568 | 569 | frame 570 | {{213,288},{70,95}} 571 | offset 572 | {0,0} 573 | rotated 574 | 575 | sourceColorRect 576 | {{0,0},{70,95}} 577 | sourceSize 578 | {70,95} 579 | 580 | 581 | cardHearts10.png 582 | 583 | frame 584 | {{142,384},{70,95}} 585 | offset 586 | {0,0} 587 | rotated 588 | 589 | sourceColorRect 590 | {{0,0},{70,95}} 591 | sourceSize 592 | {70,95} 593 | 594 | 595 | cardHearts2.png 596 | 597 | frame 598 | {{213,192},{70,95}} 599 | offset 600 | {0,0} 601 | rotated 602 | 603 | sourceColorRect 604 | {{0,0},{70,95}} 605 | sourceSize 606 | {70,95} 607 | 608 | 609 | cardHearts3.png 610 | 611 | frame 612 | {{213,96},{70,95}} 613 | offset 614 | {0,0} 615 | rotated 616 | 617 | sourceColorRect 618 | {{0,0},{70,95}} 619 | sourceSize 620 | {70,95} 621 | 622 | 623 | cardHearts4.png 624 | 625 | frame 626 | {{213,0},{70,95}} 627 | offset 628 | {0,0} 629 | rotated 630 | 631 | sourceColorRect 632 | {{0,0},{70,95}} 633 | sourceSize 634 | {70,95} 635 | 636 | 637 | cardHearts5.png 638 | 639 | frame 640 | {{142,864},{70,95}} 641 | offset 642 | {0,0} 643 | rotated 644 | 645 | sourceColorRect 646 | {{0,0},{70,95}} 647 | sourceSize 648 | {70,95} 649 | 650 | 651 | cardHearts6.png 652 | 653 | frame 654 | {{142,768},{70,95}} 655 | offset 656 | {0,0} 657 | rotated 658 | 659 | sourceColorRect 660 | {{0,0},{70,95}} 661 | sourceSize 662 | {70,95} 663 | 664 | 665 | cardHearts7.png 666 | 667 | frame 668 | {{142,672},{70,95}} 669 | offset 670 | {0,0} 671 | rotated 672 | 673 | sourceColorRect 674 | {{0,0},{70,95}} 675 | sourceSize 676 | {70,95} 677 | 678 | 679 | cardHearts8.png 680 | 681 | frame 682 | {{142,576},{70,95}} 683 | offset 684 | {0,0} 685 | rotated 686 | 687 | sourceColorRect 688 | {{0,0},{70,95}} 689 | sourceSize 690 | {70,95} 691 | 692 | 693 | cardHearts9.png 694 | 695 | frame 696 | {{142,480},{70,95}} 697 | offset 698 | {0,0} 699 | rotated 700 | 701 | sourceColorRect 702 | {{0,0},{70,95}} 703 | sourceSize 704 | {70,95} 705 | 706 | 707 | cardHeartsA.png 708 | 709 | frame 710 | {{142,288},{70,95}} 711 | offset 712 | {0,0} 713 | rotated 714 | 715 | sourceColorRect 716 | {{0,0},{70,95}} 717 | sourceSize 718 | {70,95} 719 | 720 | 721 | cardHeartsJ.png 722 | 723 | frame 724 | {{142,192},{70,95}} 725 | offset 726 | {0,0} 727 | rotated 728 | 729 | sourceColorRect 730 | {{0,0},{70,95}} 731 | sourceSize 732 | {70,95} 733 | 734 | 735 | cardHeartsK.png 736 | 737 | frame 738 | {{142,96},{70,95}} 739 | offset 740 | {0,0} 741 | rotated 742 | 743 | sourceColorRect 744 | {{0,0},{70,95}} 745 | sourceSize 746 | {70,95} 747 | 748 | 749 | cardHeartsQ.png 750 | 751 | frame 752 | {{142,0},{70,95}} 753 | offset 754 | {0,0} 755 | rotated 756 | 757 | sourceColorRect 758 | {{0,0},{70,95}} 759 | sourceSize 760 | {70,95} 761 | 762 | 763 | cardJoker.png 764 | 765 | frame 766 | {{71,839},{70,95}} 767 | offset 768 | {0,0} 769 | rotated 770 | 771 | sourceColorRect 772 | {{0,0},{70,95}} 773 | sourceSize 774 | {70,95} 775 | 776 | 777 | cardSpades10.png 778 | 779 | frame 780 | {{0,839},{70,95}} 781 | offset 782 | {0,0} 783 | rotated 784 | 785 | sourceColorRect 786 | {{0,0},{70,95}} 787 | sourceSize 788 | {70,95} 789 | 790 | 791 | cardSpades2.png 792 | 793 | frame 794 | {{71,743},{70,95}} 795 | offset 796 | {0,0} 797 | rotated 798 | 799 | sourceColorRect 800 | {{0,0},{70,95}} 801 | sourceSize 802 | {70,95} 803 | 804 | 805 | cardSpades3.png 806 | 807 | frame 808 | {{71,647},{70,95}} 809 | offset 810 | {0,0} 811 | rotated 812 | 813 | sourceColorRect 814 | {{0,0},{70,95}} 815 | sourceSize 816 | {70,95} 817 | 818 | 819 | cardSpades4.png 820 | 821 | frame 822 | {{71,551},{70,95}} 823 | offset 824 | {0,0} 825 | rotated 826 | 827 | sourceColorRect 828 | {{0,0},{70,95}} 829 | sourceSize 830 | {70,95} 831 | 832 | 833 | cardSpades5.png 834 | 835 | frame 836 | {{71,455},{70,95}} 837 | offset 838 | {0,0} 839 | rotated 840 | 841 | sourceColorRect 842 | {{0,0},{70,95}} 843 | sourceSize 844 | {70,95} 845 | 846 | 847 | cardSpades6.png 848 | 849 | frame 850 | {{71,359},{70,95}} 851 | offset 852 | {0,0} 853 | rotated 854 | 855 | sourceColorRect 856 | {{0,0},{70,95}} 857 | sourceSize 858 | {70,95} 859 | 860 | 861 | cardSpades7.png 862 | 863 | frame 864 | {{71,263},{70,95}} 865 | offset 866 | {0,0} 867 | rotated 868 | 869 | sourceColorRect 870 | {{0,0},{70,95}} 871 | sourceSize 872 | {70,95} 873 | 874 | 875 | cardSpades8.png 876 | 877 | frame 878 | {{71,167},{70,95}} 879 | offset 880 | {0,0} 881 | rotated 882 | 883 | sourceColorRect 884 | {{0,0},{70,95}} 885 | sourceSize 886 | {70,95} 887 | 888 | 889 | cardSpades9.png 890 | 891 | frame 892 | {{71,71},{70,95}} 893 | offset 894 | {0,0} 895 | rotated 896 | 897 | sourceColorRect 898 | {{0,0},{70,95}} 899 | sourceSize 900 | {70,95} 901 | 902 | 903 | cardSpadesA.png 904 | 905 | frame 906 | {{0,743},{70,95}} 907 | offset 908 | {0,0} 909 | rotated 910 | 911 | sourceColorRect 912 | {{0,0},{70,95}} 913 | sourceSize 914 | {70,95} 915 | 916 | 917 | cardSpadesJ.png 918 | 919 | frame 920 | {{0,647},{70,95}} 921 | offset 922 | {0,0} 923 | rotated 924 | 925 | sourceColorRect 926 | {{0,0},{70,95}} 927 | sourceSize 928 | {70,95} 929 | 930 | 931 | cardSpadesK.png 932 | 933 | frame 934 | {{0,551},{70,95}} 935 | offset 936 | {0,0} 937 | rotated 938 | 939 | sourceColorRect 940 | {{0,0},{70,95}} 941 | sourceSize 942 | {70,95} 943 | 944 | 945 | cardSpadesQ.png 946 | 947 | frame 948 | {{0,455},{70,95}} 949 | offset 950 | {0,0} 951 | rotated 952 | 953 | sourceColorRect 954 | {{0,0},{70,95}} 955 | sourceSize 956 | {70,95} 957 | 958 | 959 | sprites.png 960 | 961 | frame 962 | {{0,0},{140,70}} 963 | offset 964 | {0,0} 965 | rotated 966 | 967 | sourceColorRect 968 | {{0,0},{140,70}} 969 | sourceSize 970 | {140,70} 971 | 972 | 973 | 974 | 975 | metadata 976 | 977 | format 978 | 2 979 | size 980 | {512,1024} 981 | textureFileName 982 | sprites.png 983 | 984 | 985 | -------------------------------------------------------------------------------- /Client/WarCardJS/res/sprites.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Client/WarCardJS/res/sprites.png -------------------------------------------------------------------------------- /Client/WarCardJS/src/GameConfig.js: -------------------------------------------------------------------------------- 1 | var WebSocket = WebSocket || window.WebSocket || window.MozWebSocket; 2 | var ws = null; 3 | 4 | var cards = { 5 | c1:"cardClubsA.png", 6 | c2:"cardClubsJ.png", 7 | c3:"cardClubsK.png", 8 | c4:"cardClubsQ.png", 9 | c5:"cardDiamonds10.png", 10 | c6:"cardDiamonds2.png", 11 | c7:"cardDiamonds3.png", 12 | c8:"cardDiamonds4.png", 13 | c9:"cardDiamonds5.png", 14 | c10:"cardDiamonds6.png", 15 | c11:"cardDiamonds7.png", 16 | c12:"cardDiamonds8.png", 17 | c13:"cardDiamonds9.png", 18 | c14:"cardDiamondsA.png", 19 | c15:"cardDiamondsJ.png", 20 | c16:"cardDiamondsK.png", 21 | c17:"cardDiamondsQ.png", 22 | c18:"cardHearts10.png", 23 | c19:"cardHearts2.png", 24 | c20:"cardHearts3.png", 25 | c21:"cardHearts4.png", 26 | c22:"cardHearts5.png", 27 | c23:"cardHearts6.png", 28 | c24:"cardHearts7.png", 29 | c25:"cardHearts8.png", 30 | c26:"cardHearts9.png", 31 | c27:"cardHeartsA.png", 32 | c28:"cardHeartsJ.png", 33 | c29:"cardHeartsK.png", 34 | c30:"cardHeartsQ.png", 35 | c31:"cardJoker.png", 36 | c32:"cardSpades10.png", 37 | c33:"cardSpades2.png", 38 | c34:"cardSpades3.png", 39 | c35:"cardSpades4.png", 40 | c36:"cardSpades5.png", 41 | c37:"cardSpades6.png", 42 | c38:"cardSpades7.png", 43 | c39:"cardSpades8.png", 44 | c40:"cardSpades9.png", 45 | c41:"cardSpadesA.png", 46 | c42:"cardSpadesJ.png", 47 | c43:"cardSpadesK.png", 48 | c44:"cardSpadesQ.png", 49 | c45:"cardClubs10.png", 50 | c46:"cardClubs2.png", 51 | c47:"cardClubs3.png", 52 | c48:"cardClubs4.png", 53 | c49:"cardClubs5.png", 54 | c50:"cardClubs6.png", 55 | c51:"cardClubs7.png", 56 | c52:"cardClubs8.png", 57 | c53:"cardClubs9.png", 58 | }; 59 | 60 | Events = { 61 | HANDSHAKE_COMPLETE_SUCCESS:1, 62 | LOGIN:2, 63 | LOGIN_DONE:3, 64 | NEW_USER_LOGIN_DONE:4, 65 | PLAY:5, 66 | PLAY_DONE:6, 67 | }; 68 | 69 | 70 | var Encode = function(obj) { 71 | return JSON.stringify(obj); 72 | }; 73 | var Decode = function(obj) { 74 | return JSON.parse(obj); 75 | }; -------------------------------------------------------------------------------- /Client/WarCardJS/src/GameScene.js: -------------------------------------------------------------------------------- 1 | var spriteFrameCache = cc.spriteFrameCache; 2 | var size = null; 3 | var MENU_TAG = 1; 4 | var CENTER_DECK = 2; 5 | var CARD = 3; 6 | var TEXT_INPUT_FONT_SIZE_PLAYER = 20; 7 | 8 | var GameLayer = cc.Layer.extend({ 9 | cardDeckSprite:null, 10 | sprite:null, 11 | listener1:null, 12 | jsonData:null, 13 | textFieldUserNameCapton:null, 14 | currentPlayer:null, 15 | otherPlayers:[], 16 | ctor:function (_jsondata) { 17 | this.jsonData = _jsondata; 18 | //after succesful login we want to take control on massages coming from server 19 | //so we attache this new callback function to the websocket onmessage 20 | ws.onmessage = this.ongamestatus.bind(this); 21 | ws.onclose = this.onclose.bind(this); 22 | ws.onerror = this.onerror.bind(this); 23 | 24 | this._super(); 25 | size = cc.winSize; 26 | return true; 27 | }, 28 | 29 | onEnter:function () { 30 | 31 | this._super(); 32 | // Make sprite1 touchable 33 | this.listener1 = cc.EventListener.create({ 34 | event: cc.EventListener.TOUCH_ONE_BY_ONE, 35 | swallowTouches: true, 36 | onTouchBegan: function (touch, event) { 37 | event.getCurrentTarget().invokeTurn(); 38 | return true; 39 | }, 40 | onTouchEnded: function (touch, event) { 41 | 42 | } 43 | }); 44 | this.setUserObject(this.listener1); 45 | cc.eventManager.addListener(this.listener1, this); 46 | spriteFrameCache.addSpriteFrames(res.sprites_plist, res.sprites_png); 47 | 48 | var userName = this.jsonData.username; 49 | this.textFieldUserNameCapton = new cc.TextFieldTTF("Hello "+userName, 50 | TEXT_INPUT_FONT_NAME, 51 | TEXT_INPUT_FONT_SIZE_PLAYER); 52 | this.textFieldUserNameCapton.setTextColor(cc.color.RED); 53 | this.textFieldUserNameCapton.x = size.width / 2; 54 | this.textFieldUserNameCapton.y = size.height-(TEXT_INPUT_FONT_SIZE_PLAYER+100); 55 | this.addChild(this.textFieldUserNameCapton,10); 56 | 57 | this.eventHandler(this.jsonData.event); 58 | 59 | }, 60 | onExit:function () { 61 | 62 | this._super(); 63 | spriteFrameCache.removeSpriteFramesFromFile(res.sprites_plist); 64 | spriteFrameCache.removeSpriteFramesFromFile(res.sprites_png); 65 | cc.eventManager.removeListener(this.listener1); 66 | }, 67 | eventHandler:function(event) 68 | { 69 | 70 | 71 | switch (event) { 72 | case Events.LOGIN_DONE: 73 | { 74 | this.setupCurrentPlayer(); 75 | break; 76 | } 77 | case Events.NEW_USER_LOGIN_DONE: 78 | { 79 | this.setupOtherPlayerS(); 80 | break; 81 | 82 | } 83 | case Events.PLAY_DONE: 84 | { 85 | this.setPlayState(); 86 | break; 87 | 88 | } 89 | } 90 | this.setTurnMassage(); 91 | }, 92 | setTurnMassage:function() 93 | { 94 | var userName = this.jsonData.username; 95 | var activePlayerId = this.jsonData.activeplayerid; 96 | if(activePlayerId === this.currentPlayer.id) 97 | { 98 | this.textFieldUserNameCapton.setString("Hello "+userName+" Its your turn"); 99 | } 100 | else 101 | { 102 | this.textFieldUserNameCapton.setString("Hello "+userName); 103 | } 104 | 105 | }, 106 | onCallbackMoveTo:function (nodeExecutingAction,player) { 107 | //console.log("nodeExecutingAction id:"+nodeExecutingAction.playerid+" :nodeExecutingAction.x:"+nodeExecutingAction.x+" nodeExecutingAction.y:"+nodeExecutingAction.y); 108 | //var activePlayerId = this.jsonData.activeplayerid; 109 | //if(activePlayerId !== this.currentPlayer.id) 110 | //{ 111 | this.currentPlayer.updatePlayerNumberOfCardsCaption(this.jsonData.numcardsleft); 112 | this.otherPlayers[0].updatePlayerNumberOfCardsCaption(this.jsonData.players[0].numcardsleft); 113 | //} 114 | //else 115 | //{ 116 | //TODO this fix this hard coded position getter 117 | //this.otherPlayers[0].updatePlayerNumberOfCardsCaption(this.jsonData.players[0].numcardsleft); 118 | //this.currentPlayer.updatePlayerNumberOfCardsCaption(this.jsonData.numcardsleft); 119 | //} 120 | 121 | }, 122 | setPlayState:function() 123 | { 124 | 125 | this.currentPlayer.setNewCardById(this.jsonData.activecardid); 126 | this.updatePlayer(this.currentPlayer,this.jsonData); 127 | if(this.jsonData.players.length>0) 128 | { 129 | for(var i=0;iinvokeTurn() not its turn:"+this.currentPlayer.id); 185 | } 186 | }, 187 | setupCurrentPlayer:function() 188 | { 189 | this.currentPlayer = new Player(this.jsonData.id,this.jsonData.username, 190 | this.jsonData.activecardid); 191 | this.updatePlayer(this.currentPlayer,this.jsonData); 192 | 193 | this.addChild(this.currentPlayer,1); 194 | this.positionPlayer(this.currentPlayer); 195 | if(this.jsonData.players.length>0) 196 | { 197 | for(var i=0;i0) 209 | { 210 | for(var i=0;i.ws.onmessage():"+e.data); 264 | if(e.data!==null || e.data !== 'undefined') 265 | { 266 | this.jsonData = Decode(e.data); 267 | this.eventHandler(this.jsonData.event); 268 | 269 | } 270 | } 271 | , 272 | 273 | onclose:function (e) { 274 | 275 | }, 276 | onerror:function (e) { 277 | 278 | } 279 | 280 | }); 281 | 282 | 283 | var EnterWorldScene = cc.Scene.extend({ 284 | session:null, 285 | ctor:function (_session) { 286 | this.session = _session; 287 | this._super(); 288 | size = cc.winSize; 289 | return true; 290 | }, 291 | onEnter:function () { 292 | this._super(); 293 | var layer = new GameLayer(this.session); 294 | this.addChild(layer); 295 | } 296 | 297 | }); -------------------------------------------------------------------------------- /Client/WarCardJS/src/Player.js: -------------------------------------------------------------------------------- 1 | var TEXT_INPUT_FONT_NAME = "Thonburi"; 2 | var TEXT_INPUT_FONT_SIZE = 36; 3 | var TEXT_INPUT_FONT_SIZE_PLAYER = 20; 4 | 5 | var Player = cc.Sprite.extend({ 6 | 7 | id:null, 8 | username:null, 9 | event:null, 10 | activecardid:null, 11 | activeplayerid:null, 12 | registertionnum:null, 13 | winner:null, 14 | winnercards:"", 15 | numcardsleft:null, 16 | spriteSize:null, 17 | textFieldUserName:null, 18 | ctor: function(_id,_username,_activecardid){ 19 | this.id = _id; 20 | this.username = _username; 21 | this.activecardid = _activecardid; 22 | var cardName = this.getPlayerCardById(this.activecardid); 23 | this._super("#"+cardName); 24 | 25 | }, 26 | onEnter:function () { 27 | 28 | this._super(); 29 | this.spriteSize = this.getContentSize(); 30 | this.setPlayerNameCaption(this.username); 31 | this.setPlayerNumberOfCardsCaption(this.numcardsleft); 32 | 33 | }, 34 | onExit:function () { 35 | this._super(); 36 | }, 37 | getPlayerCardById:function(_cardId) 38 | { 39 | var cardName = cards[_cardId]; 40 | return cardName; 41 | }, 42 | setPlayerNameCaption:function(_name) 43 | { 44 | this.textFieldUserName = new cc.TextFieldTTF(_name, 45 | TEXT_INPUT_FONT_NAME, 46 | TEXT_INPUT_FONT_SIZE_PLAYER); 47 | this.textFieldUserName.setTextColor(cc.color.RED); 48 | this.textFieldUserName.x = this.spriteSize.width / 2; 49 | this.textFieldUserName.y = 0-TEXT_INPUT_FONT_SIZE_PLAYER; 50 | this.addChild(this.textFieldUserName,2); 51 | }, 52 | updatePlayerNumberOfCardsCaption:function(_numberOfCards) 53 | { 54 | this.numcardsleft = _numberOfCards 55 | this.textFieldNumberOfCards.setString("Cards:"+this.numcardsleft); 56 | }, 57 | setPlayerNumberOfCardsCaption:function(_numberOfCards) 58 | { 59 | this.textFieldNumberOfCards = new cc.TextFieldTTF("Cards:"+_numberOfCards, 60 | TEXT_INPUT_FONT_NAME, 61 | TEXT_INPUT_FONT_SIZE_PLAYER); 62 | this.textFieldNumberOfCards.setTextColor(cc.color.RED); 63 | this.textFieldNumberOfCards.x = this.spriteSize.width / 2; 64 | this.textFieldNumberOfCards.y = 0-(TEXT_INPUT_FONT_SIZE_PLAYER+TEXT_INPUT_FONT_SIZE_PLAYER); 65 | this.addChild(this.textFieldNumberOfCards,2); 66 | }, 67 | setNewCardById:function (_cardid) 68 | { 69 | //get the right card from the cards hash 70 | var cardName = cards[_cardid]; 71 | this.activecardid = cardName; 72 | //this._super(this.playerSpriteFrameName); 73 | this.setSpriteFrame(cardName); 74 | }, 75 | 76 | 77 | }); 78 | 79 | 80 | 81 | -------------------------------------------------------------------------------- /Client/WarCardJS/src/app.js: -------------------------------------------------------------------------------- 1 | var TEXT_INPUT_FONT_NAME = "Thonburi"; 2 | var TEXT_INPUT_FONT_SIZE = 36; 3 | var sceneIdx = -1; 4 | var TEXT_FIELD_ERR = 1; 5 | 6 | //--------------------------------------------------------------\ 7 | 8 | var LoginLayer = cc.Layer.extend({ 9 | sprite:null, 10 | size:null, 11 | textFieldUserName:null, 12 | textErorrConnectedField:null, 13 | enterWorldScene:null, 14 | textField:null, 15 | ctor:function () { 16 | ////////////////////////////// 17 | // 1. super init first 18 | this._super(); 19 | this.size = cc.winSize; 20 | return true; 21 | }, 22 | onEnter:function () { 23 | //----start2----onEnter 24 | this._super(); 25 | var winSize = cc.director.getWinSize(); 26 | 27 | 28 | // Create the textfield 29 | this.textField = new ccui.TextField(); 30 | this.textField.setMaxLengthEnabled(true); 31 | this.textField.setMaxLength(30); 32 | this.textField.setTouchEnabled(true); 33 | this.textField.fontName = TEXT_INPUT_FONT_NAME; 34 | this.textField.fontSize = 30; 35 | this.textField.placeHolder = "[click here for user name]"; 36 | this.textField.x = winSize.width / 2.0; 37 | this.textField.y = winSize.height / 2.0; 38 | this.textField.addEventListener(this.textFieldEvent, this); 39 | this.addChild(this.textField); 40 | 41 | 42 | cc.MenuItemFont.setFontSize(35); 43 | var menu = new cc.Menu( 44 | new cc.MenuItemFont("Login Game", this.loginGame, this) 45 | ); 46 | menu.alignItemsVerticallyWithPadding(4); 47 | menu.x = this.size.width / 2; 48 | menu.y = this.size.height / 2 - 50; 49 | this.addChild(menu,5); 50 | }, 51 | onExit:function () { 52 | this._super(); 53 | }, 54 | createErrorMsg:function () { 55 | this.textErorrConnectedField = new cc.TextFieldTTF("Error Connecting Server try again", 56 | TEXT_INPUT_FONT_NAME, 57 | TEXT_INPUT_FONT_SIZE+20); 58 | this.textErorrConnectedField.setTag(TEXT_FIELD_ERR); 59 | this.textErorrConnectedField.x = cc.winSize.width / 2; 60 | this.textErorrConnectedField.y = cc.winSize.height / 2 +50; 61 | this.addChild(this.textErorrConnectedField,2); 62 | }, 63 | 64 | loginGame:function (sender) { 65 | //remove error msg if any 66 | if(this.getChildByTag(TEXT_FIELD_ERR)!==null) 67 | { 68 | this.removeChildByTag(TEXT_FIELD_ERR); 69 | } 70 | 71 | //check login in the server 72 | var txtUserName = this.textField.getString(); 73 | var config = { 74 | event:Events.LOGIN, 75 | username:txtUserName 76 | }; 77 | var message = Encode(config); 78 | try { 79 | ws = new WebSocket("ws://localhost:8888/ws"); 80 | ws.onopen = function() { 81 | 82 | ws.send(message); 83 | 84 | }; 85 | ws.onmessage = function (e) { 86 | console.log("app->srv.ws.onmessage():"+e.data); 87 | if(e.data!==null || e.data !== 'undefined') 88 | { 89 | var jsonFromClient = Decode(e.data); 90 | if(jsonFromClient.event === Events.LOGIN_DONE) 91 | { 92 | enterWorldScene = new EnterWorldScene(jsonFromClient); 93 | cc.director.runScene(enterWorldScene); 94 | } 95 | } 96 | }; 97 | ws.onclose = function (e) { 98 | 99 | }; 100 | ws.onerror = function (e) { 101 | 102 | }; 103 | } catch (e) { 104 | console.error('Sorry, the web socket at "%s" is un-available', url); 105 | } 106 | 107 | }, 108 | 109 | onClickTrackNode:function (clicked) { 110 | var textField = this._trackNode; 111 | if (clicked) { 112 | // TextFieldTTFTest be clicked 113 | //cc.log("TextFieldTTFDefaultTest:CCTextFieldTTF attachWithIME"); 114 | textField.attachWithIME(); 115 | } else { 116 | // TextFieldTTFTest not be clicked 117 | //cc.log("TextFieldTTFDefaultTest:CCTextFieldTTF detachWithIME"); 118 | textField.detachWithIME(); 119 | } 120 | }, 121 | }); 122 | 123 | var LoginScene = cc.Scene.extend({ 124 | onEnter:function () { 125 | this._super(); 126 | var layer = new LoginLayer(); 127 | this.addChild(layer); 128 | } 129 | 130 | }); 131 | 132 | -------------------------------------------------------------------------------- /Client/WarCardJS/src/cards.js: -------------------------------------------------------------------------------- 1 | var cards = { 2 | c1:"cardClubsA.png", 3 | c2:"cardClubsJ.png", 4 | c3:"cardClubsK.png", 5 | c4:"cardClubsQ.png", 6 | c5:"cardDiamonds10.png", 7 | c6:"cardDiamonds2.png", 8 | c7:"cardDiamonds3.png", 9 | c8:"cardDiamonds4.png", 10 | c9:"cardDiamonds5.png", 11 | c10:"cardDiamonds6.png", 12 | c11:"cardDiamonds7.png", 13 | c12:"cardDiamonds8.png", 14 | c13:"cardDiamonds9.png", 15 | c14:"cardDiamondsA.png", 16 | c15:"cardDiamondsJ.png", 17 | c16:"cardDiamondsK.png", 18 | c17:"cardDiamondsQ.png", 19 | c18:"cardHearts10.png", 20 | c19:"cardHearts2.png", 21 | c20:"cardHearts3.png", 22 | c21:"cardHearts4.png", 23 | c22:"cardHearts5.png", 24 | c23:"cardHearts6.png", 25 | c24:"cardHearts7.png", 26 | c25:"cardHearts8.png", 27 | c26:"cardHearts9.png", 28 | c27:"cardHeartsA.png", 29 | c28:"cardHeartsJ.png", 30 | c29:"cardHeartsK.png", 31 | c30:"cardHeartsQ.png", 32 | c31:"cardJoker.png", 33 | c32:"cardSpades10.png", 34 | c33:"cardSpades2.png", 35 | c34:"cardSpades3.png", 36 | c35:"cardSpades4.png", 37 | c36:"cardSpades5.png", 38 | c37:"cardSpades6.png", 39 | c38:"cardSpades7.png", 40 | c39:"cardSpades8.png", 41 | c40:"cardSpades9.png", 42 | c41:"cardSpadesA.png", 43 | c42:"cardSpadesJ.png", 44 | c43:"cardSpadesK.png", 45 | c44:"cardSpadesQ.png", 46 | c45:"cardClubs10.png", 47 | c46:"cardClubs2.png", 48 | c47:"cardClubs3.png", 49 | c48:"cardClubs4.png", 50 | c49:"cardClubs5.png", 51 | c50:"cardClubs6.png", 52 | c51:"cardClubs7.png", 53 | c52:"cardClubs8.png", 54 | c53:"cardClubs9.png", 55 | }; 56 | 57 | 58 | -------------------------------------------------------------------------------- /Client/WarCardJS/src/resource.js: -------------------------------------------------------------------------------- 1 | var res = { 2 | sprites_png : "res/sprites.png", 3 | sprites_plist : "res/sprites.plist", 4 | grossini_plist : "res/grossini.plist", 5 | grossini_png : "res/grossini.png", 6 | 7 | }; 8 | 9 | var g_resources = []; 10 | for (var i in res) { 11 | g_resources.push(res[i]); 12 | } 13 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # multiplayer_cocos2dx-js_using_netty_websockets 2 | Source code for the tutorial building simple multiplayercocos2dx-js using netty and websockets 3 | to see full tutorial please visit: 4 | https://gamedevcraft.blogspot.com/ 5 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/.classpath: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/.project: -------------------------------------------------------------------------------- 1 | 2 | 3 | CardWarNettyServer 4 | 5 | 6 | 7 | 8 | 9 | org.eclipse.jdt.core.javabuilder 10 | 11 | 12 | 13 | 14 | 15 | org.eclipse.jdt.core.javanature 16 | 17 | 18 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/.settings/org.eclipse.jdt.core.prefs: -------------------------------------------------------------------------------- 1 | eclipse.preferences.version=1 2 | org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled 3 | org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.7 4 | org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve 5 | org.eclipse.jdt.core.compiler.compliance=1.7 6 | org.eclipse.jdt.core.compiler.debug.lineNumber=generate 7 | org.eclipse.jdt.core.compiler.debug.localVariable=generate 8 | org.eclipse.jdt.core.compiler.debug.sourceFile=generate 9 | org.eclipse.jdt.core.compiler.problem.assertIdentifier=error 10 | org.eclipse.jdt.core.compiler.problem.enumIdentifier=error 11 | org.eclipse.jdt.core.compiler.source=1.7 12 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/json/JSONArray.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/json/JSONArray.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/json/JSONException.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/json/JSONException.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/json/JSONObject$Null.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/json/JSONObject$Null.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/json/JSONObject.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/json/JSONObject.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/json/JSONString.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/json/JSONString.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/json/JSONStringer.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/json/JSONStringer.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/json/JSONTokener.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/json/JSONTokener.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/json/JSONWriter.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/json/JSONWriter.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/server/Config.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/server/Config.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/server/GameEventHandler.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/server/GameEventHandler.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/server/GameManager.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/server/GameManager.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/server/GameResponseDispatcher.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/server/GameResponseDispatcher.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/server/GameServerInitializer.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/server/GameServerInitializer.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/server/GameServerMain.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/server/GameServerMain.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/server/HttpRequestHandler.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/server/HttpRequestHandler.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/server/LoggerManager.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/server/LoggerManager.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/server/Player.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/server/Player.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/server/TextWebSocketFrameHandler.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/server/TextWebSocketFrameHandler.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/bin/com/server/WebSocketServer.class: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/bin/com/server/WebSocketServer.class -------------------------------------------------------------------------------- /Server/CardWarNettyServer/conf/configuration.properties: -------------------------------------------------------------------------------- 1 | port=8888 2 | #How many game rooms can be created 3 | max_num_game_rooms=2 4 | #How many players can be in each room 5 | num_palyers_per_room=4 -------------------------------------------------------------------------------- /Server/CardWarNettyServer/conf/logger.properties: -------------------------------------------------------------------------------- 1 | java.util.logging.ConsoleHandler.level=ALL 2 | java.util.logging.ConsoleHandler.formatter=java.util.logging.SimpleFormatter 3 | confLogger.level=ALL 4 | 5 | java.util.logging.FileHandler.pattern=%h/my-application%u.log 6 | java.util.logging.FileHandler.limit = 50000 7 | java.util.logging.FileHandler.count = 1 8 | java.util.logging.FileHandler.formatter = java.util.logging.SimpleFormatter 9 | 10 | handlers=java.util.logging.ConsoleHandler,java.util.logging.FileHandler -------------------------------------------------------------------------------- /Server/CardWarNettyServer/lib/netty-all-4.0.33.Final-sources.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/lib/netty-all-4.0.33.Final-sources.jar -------------------------------------------------------------------------------- /Server/CardWarNettyServer/lib/netty-all-4.0.33.Final.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/meiry/multiplayer_cocos2dx-js_using_netty_websockets/f826310cde77ddca5ec5bbb308036a96a4a70c0b/Server/CardWarNettyServer/lib/netty-all-4.0.33.Final.jar -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/json/JSONArray.java: -------------------------------------------------------------------------------- 1 | package com.json; 2 | 3 | /* 4 | Copyright (c) 2002 JSON.org 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in all 14 | copies or substantial portions of the Software. 15 | 16 | The Software shall be used for Good, not Evil. 17 | 18 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 19 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 20 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 21 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 22 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 23 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 24 | SOFTWARE. 25 | */ 26 | 27 | import java.io.IOException; 28 | 29 | import java.io.StringWriter; 30 | import java.io.Writer; 31 | import java.lang.reflect.Array; 32 | import java.math.*; 33 | import java.util.ArrayList; 34 | import java.util.Collection; 35 | import java.util.Iterator; 36 | import java.util.Map; 37 | 38 | /** 39 | * A JSONArray is an ordered sequence of values. Its external text form is a 40 | * string wrapped in square brackets with commas separating the values. The 41 | * internal form is an object having get and opt 42 | * methods for accessing the values by index, and put methods for 43 | * adding or replacing values. The values can be any of these types: 44 | * Boolean, JSONArray, JSONObject, 45 | * Number, String, or the 46 | * JSONObject.NULL object. 47 | *

48 | * The constructor can convert a JSON text into a Java object. The 49 | * toString method converts to JSON text. 50 | *

51 | * A get method returns a value if one can be found, and throws an 52 | * exception if one cannot be found. An opt method returns a 53 | * default value instead of throwing an exception, and so is useful for 54 | * obtaining optional values. 55 | *

56 | * The generic get() and opt() methods return an 57 | * object which you can cast or query for type. There are also typed 58 | * get and opt methods that do type checking and type 59 | * coercion for you. 60 | *

61 | * The texts produced by the toString methods strictly conform to 62 | * JSON syntax rules. The constructors are more forgiving in the texts they will 63 | * accept: 64 | *

    65 | *
  • An extra , (comma) may appear just 66 | * before the closing bracket.
  • 67 | *
  • The null value will be inserted when there is , 68 | *  (comma) elision.
  • 69 | *
  • Strings may be quoted with ' (single 70 | * quote).
  • 71 | *
  • Strings do not need to be quoted at all if they do not begin with a quote 72 | * or single quote, and if they do not contain leading or trailing spaces, and 73 | * if they do not contain any of these characters: 74 | * { } [ ] / \ : , # and if they do not look like numbers and 75 | * if they are not the reserved words true, false, or 76 | * null.
  • 77 | *
78 | * 79 | * @author JSON.org 80 | * @version 2015-10-29 81 | */ 82 | public class JSONArray implements Iterable { 83 | 84 | /** 85 | * The arrayList where the JSONArray's properties are kept. 86 | */ 87 | private final ArrayList myArrayList; 88 | 89 | /** 90 | * Construct an empty JSONArray. 91 | */ 92 | public JSONArray() { 93 | this.myArrayList = new ArrayList(); 94 | } 95 | 96 | /** 97 | * Construct a JSONArray from a JSONTokener. 98 | * 99 | * @param x 100 | * A JSONTokener 101 | * @throws JSONException 102 | * If there is a syntax error. 103 | */ 104 | public JSONArray(JSONTokener x) throws JSONException { 105 | this(); 106 | if (x.nextClean() != '[') { 107 | throw x.syntaxError("A JSONArray text must start with '['"); 108 | } 109 | if (x.nextClean() != ']') { 110 | x.back(); 111 | for (;;) { 112 | if (x.nextClean() == ',') { 113 | x.back(); 114 | this.myArrayList.add(JSONObject.NULL); 115 | } else { 116 | x.back(); 117 | this.myArrayList.add(x.nextValue()); 118 | } 119 | switch (x.nextClean()) { 120 | case ',': 121 | if (x.nextClean() == ']') { 122 | return; 123 | } 124 | x.back(); 125 | break; 126 | case ']': 127 | return; 128 | default: 129 | throw x.syntaxError("Expected a ',' or ']'"); 130 | } 131 | } 132 | } 133 | } 134 | 135 | /** 136 | * Construct a JSONArray from a source JSON text. 137 | * 138 | * @param source 139 | * A string that begins with [ (left 140 | * bracket) and ends with ] 141 | *  (right bracket). 142 | * @throws JSONException 143 | * If there is a syntax error. 144 | */ 145 | public JSONArray(String source) throws JSONException { 146 | this(new JSONTokener(source)); 147 | } 148 | 149 | /** 150 | * Construct a JSONArray from a Collection. 151 | * 152 | * @param collection 153 | * A Collection. 154 | */ 155 | public JSONArray(Collection collection) { 156 | this.myArrayList = new ArrayList(); 157 | if (collection != null) { 158 | for (Object o: collection){ 159 | this.myArrayList.add(JSONObject.wrap(o)); 160 | } 161 | } 162 | } 163 | 164 | /** 165 | * Construct a JSONArray from an array 166 | * 167 | * @throws JSONException 168 | * If not an array. 169 | */ 170 | public JSONArray(Object array) throws JSONException { 171 | this(); 172 | if (array.getClass().isArray()) { 173 | int length = Array.getLength(array); 174 | for (int i = 0; i < length; i += 1) { 175 | this.put(JSONObject.wrap(Array.get(array, i))); 176 | } 177 | } else { 178 | throw new JSONException( 179 | "JSONArray initial value should be a string or collection or array."); 180 | } 181 | } 182 | 183 | @Override 184 | public Iterator iterator() { 185 | return myArrayList.iterator(); 186 | } 187 | 188 | /** 189 | * Get the object value associated with an index. 190 | * 191 | * @param index 192 | * The index must be between 0 and length() - 1. 193 | * @return An object value. 194 | * @throws JSONException 195 | * If there is no value for the index. 196 | */ 197 | public Object get(int index) throws JSONException { 198 | Object object = this.opt(index); 199 | if (object == null) { 200 | throw new JSONException("JSONArray[" + index + "] not found."); 201 | } 202 | return object; 203 | } 204 | 205 | /** 206 | * Get the boolean value associated with an index. The string values "true" 207 | * and "false" are converted to boolean. 208 | * 209 | * @param index 210 | * The index must be between 0 and length() - 1. 211 | * @return The truth. 212 | * @throws JSONException 213 | * If there is no value for the index or if the value is not 214 | * convertible to boolean. 215 | */ 216 | public boolean getBoolean(int index) throws JSONException { 217 | Object object = this.get(index); 218 | if (object.equals(Boolean.FALSE) 219 | || (object instanceof String && ((String) object) 220 | .equalsIgnoreCase("false"))) { 221 | return false; 222 | } else if (object.equals(Boolean.TRUE) 223 | || (object instanceof String && ((String) object) 224 | .equalsIgnoreCase("true"))) { 225 | return true; 226 | } 227 | throw new JSONException("JSONArray[" + index + "] is not a boolean."); 228 | } 229 | 230 | /** 231 | * Get the double value associated with an index. 232 | * 233 | * @param index 234 | * The index must be between 0 and length() - 1. 235 | * @return The value. 236 | * @throws JSONException 237 | * If the key is not found or if the value cannot be converted 238 | * to a number. 239 | */ 240 | public double getDouble(int index) throws JSONException { 241 | Object object = this.get(index); 242 | try { 243 | return object instanceof Number ? ((Number) object).doubleValue() 244 | : Double.parseDouble((String) object); 245 | } catch (Exception e) { 246 | throw new JSONException("JSONArray[" + index + "] is not a number."); 247 | } 248 | } 249 | 250 | /** 251 | * Get the enum value associated with an index. 252 | * 253 | * @param clazz 254 | * The type of enum to retrieve. 255 | * @param index 256 | * The index must be between 0 and length() - 1. 257 | * @return The enum value at the index location 258 | * @throws JSONException 259 | * if the key is not found or if the value cannot be converted 260 | * to an enum. 261 | */ 262 | public > E getEnum(Class clazz, int index) throws JSONException { 263 | E val = optEnum(clazz, index); 264 | if(val==null) { 265 | // JSONException should really take a throwable argument. 266 | // If it did, I would re-implement this with the Enum.valueOf 267 | // method and place any thrown exception in the JSONException 268 | throw new JSONException("JSONObject[" + JSONObject.quote(Integer.toString(index)) 269 | + "] is not an enum of type " + JSONObject.quote(clazz.getSimpleName()) 270 | + "."); 271 | } 272 | return val; 273 | } 274 | 275 | /** 276 | * Get the BigDecimal value associated with an index. 277 | * 278 | * @param index 279 | * The index must be between 0 and length() - 1. 280 | * @return The value. 281 | * @throws JSONException 282 | * If the key is not found or if the value cannot be converted 283 | * to a BigDecimal. 284 | */ 285 | public BigDecimal getBigDecimal (int index) throws JSONException { 286 | Object object = this.get(index); 287 | try { 288 | return new BigDecimal(object.toString()); 289 | } catch (Exception e) { 290 | throw new JSONException("JSONArray[" + index + 291 | "] could not convert to BigDecimal."); 292 | } 293 | } 294 | 295 | /** 296 | * Get the BigInteger value associated with an index. 297 | * 298 | * @param index 299 | * The index must be between 0 and length() - 1. 300 | * @return The value. 301 | * @throws JSONException 302 | * If the key is not found or if the value cannot be converted 303 | * to a BigInteger. 304 | */ 305 | public BigInteger getBigInteger (int index) throws JSONException { 306 | Object object = this.get(index); 307 | try { 308 | return new BigInteger(object.toString()); 309 | } catch (Exception e) { 310 | throw new JSONException("JSONArray[" + index + 311 | "] could not convert to BigInteger."); 312 | } 313 | } 314 | 315 | /** 316 | * Get the int value associated with an index. 317 | * 318 | * @param index 319 | * The index must be between 0 and length() - 1. 320 | * @return The value. 321 | * @throws JSONException 322 | * If the key is not found or if the value is not a number. 323 | */ 324 | public int getInt(int index) throws JSONException { 325 | Object object = this.get(index); 326 | try { 327 | return object instanceof Number ? ((Number) object).intValue() 328 | : Integer.parseInt((String) object); 329 | } catch (Exception e) { 330 | throw new JSONException("JSONArray[" + index + "] is not a number."); 331 | } 332 | } 333 | 334 | /** 335 | * Get the JSONArray associated with an index. 336 | * 337 | * @param index 338 | * The index must be between 0 and length() - 1. 339 | * @return A JSONArray value. 340 | * @throws JSONException 341 | * If there is no value for the index. or if the value is not a 342 | * JSONArray 343 | */ 344 | public JSONArray getJSONArray(int index) throws JSONException { 345 | Object object = this.get(index); 346 | if (object instanceof JSONArray) { 347 | return (JSONArray) object; 348 | } 349 | throw new JSONException("JSONArray[" + index + "] is not a JSONArray."); 350 | } 351 | 352 | /** 353 | * Get the JSONObject associated with an index. 354 | * 355 | * @param index 356 | * subscript 357 | * @return A JSONObject value. 358 | * @throws JSONException 359 | * If there is no value for the index or if the value is not a 360 | * JSONObject 361 | */ 362 | public JSONObject getJSONObject(int index) throws JSONException { 363 | Object object = this.get(index); 364 | if (object instanceof JSONObject) { 365 | return (JSONObject) object; 366 | } 367 | throw new JSONException("JSONArray[" + index + "] is not a JSONObject."); 368 | } 369 | 370 | /** 371 | * Get the long value associated with an index. 372 | * 373 | * @param index 374 | * The index must be between 0 and length() - 1. 375 | * @return The value. 376 | * @throws JSONException 377 | * If the key is not found or if the value cannot be converted 378 | * to a number. 379 | */ 380 | public long getLong(int index) throws JSONException { 381 | Object object = this.get(index); 382 | try { 383 | return object instanceof Number ? ((Number) object).longValue() 384 | : Long.parseLong((String) object); 385 | } catch (Exception e) { 386 | throw new JSONException("JSONArray[" + index + "] is not a number."); 387 | } 388 | } 389 | 390 | /** 391 | * Get the string associated with an index. 392 | * 393 | * @param index 394 | * The index must be between 0 and length() - 1. 395 | * @return A string value. 396 | * @throws JSONException 397 | * If there is no string value for the index. 398 | */ 399 | public String getString(int index) throws JSONException { 400 | Object object = this.get(index); 401 | if (object instanceof String) { 402 | return (String) object; 403 | } 404 | throw new JSONException("JSONArray[" + index + "] not a string."); 405 | } 406 | 407 | /** 408 | * Determine if the value is null. 409 | * 410 | * @param index 411 | * The index must be between 0 and length() - 1. 412 | * @return true if the value at the index is null, or if there is no value. 413 | */ 414 | public boolean isNull(int index) { 415 | return JSONObject.NULL.equals(this.opt(index)); 416 | } 417 | 418 | /** 419 | * Make a string from the contents of this JSONArray. The 420 | * separator string is inserted between each element. Warning: 421 | * This method assumes that the data structure is acyclical. 422 | * 423 | * @param separator 424 | * A string that will be inserted between the elements. 425 | * @return a string. 426 | * @throws JSONException 427 | * If the array contains an invalid number. 428 | */ 429 | public String join(String separator) throws JSONException { 430 | int len = this.length(); 431 | StringBuilder sb = new StringBuilder(); 432 | 433 | for (int i = 0; i < len; i += 1) { 434 | if (i > 0) { 435 | sb.append(separator); 436 | } 437 | sb.append(JSONObject.valueToString(this.myArrayList.get(i))); 438 | } 439 | return sb.toString(); 440 | } 441 | 442 | /** 443 | * Get the number of elements in the JSONArray, included nulls. 444 | * 445 | * @return The length (or size). 446 | */ 447 | public int length() { 448 | return this.myArrayList.size(); 449 | } 450 | 451 | /** 452 | * Get the optional object value associated with an index. 453 | * 454 | * @param index 455 | * The index must be between 0 and length() - 1. 456 | * @return An object value, or null if there is no object at that index. 457 | */ 458 | public Object opt(int index) { 459 | return (index < 0 || index >= this.length()) ? null : this.myArrayList 460 | .get(index); 461 | } 462 | 463 | /** 464 | * Get the optional boolean value associated with an index. It returns false 465 | * if there is no value at that index, or if the value is not Boolean.TRUE 466 | * or the String "true". 467 | * 468 | * @param index 469 | * The index must be between 0 and length() - 1. 470 | * @return The truth. 471 | */ 472 | public boolean optBoolean(int index) { 473 | return this.optBoolean(index, false); 474 | } 475 | 476 | /** 477 | * Get the optional boolean value associated with an index. It returns the 478 | * defaultValue if there is no value at that index or if it is not a Boolean 479 | * or the String "true" or "false" (case insensitive). 480 | * 481 | * @param index 482 | * The index must be between 0 and length() - 1. 483 | * @param defaultValue 484 | * A boolean default. 485 | * @return The truth. 486 | */ 487 | public boolean optBoolean(int index, boolean defaultValue) { 488 | try { 489 | return this.getBoolean(index); 490 | } catch (Exception e) { 491 | return defaultValue; 492 | } 493 | } 494 | 495 | /** 496 | * Get the optional double value associated with an index. NaN is returned 497 | * if there is no value for the index, or if the value is not a number and 498 | * cannot be converted to a number. 499 | * 500 | * @param index 501 | * The index must be between 0 and length() - 1. 502 | * @return The value. 503 | */ 504 | public double optDouble(int index) { 505 | return this.optDouble(index, Double.NaN); 506 | } 507 | 508 | /** 509 | * Get the optional double value associated with an index. The defaultValue 510 | * is returned if there is no value for the index, or if the value is not a 511 | * number and cannot be converted to a number. 512 | * 513 | * @param index 514 | * subscript 515 | * @param defaultValue 516 | * The default value. 517 | * @return The value. 518 | */ 519 | public double optDouble(int index, double defaultValue) { 520 | try { 521 | return this.getDouble(index); 522 | } catch (Exception e) { 523 | return defaultValue; 524 | } 525 | } 526 | 527 | /** 528 | * Get the optional int value associated with an index. Zero is returned if 529 | * there is no value for the index, or if the value is not a number and 530 | * cannot be converted to a number. 531 | * 532 | * @param index 533 | * The index must be between 0 and length() - 1. 534 | * @return The value. 535 | */ 536 | public int optInt(int index) { 537 | return this.optInt(index, 0); 538 | } 539 | 540 | /** 541 | * Get the optional int value associated with an index. The defaultValue is 542 | * returned if there is no value for the index, or if the value is not a 543 | * number and cannot be converted to a number. 544 | * 545 | * @param index 546 | * The index must be between 0 and length() - 1. 547 | * @param defaultValue 548 | * The default value. 549 | * @return The value. 550 | */ 551 | public int optInt(int index, int defaultValue) { 552 | try { 553 | return this.getInt(index); 554 | } catch (Exception e) { 555 | return defaultValue; 556 | } 557 | } 558 | 559 | /** 560 | * Get the enum value associated with a key. 561 | * 562 | * @param clazz 563 | * The type of enum to retrieve. 564 | * @param index 565 | * The index must be between 0 and length() - 1. 566 | * @return The enum value at the index location or null if not found 567 | */ 568 | public > E optEnum(Class clazz, int index) { 569 | return this.optEnum(clazz, index, null); 570 | } 571 | 572 | /** 573 | * Get the enum value associated with a key. 574 | * 575 | * @param clazz 576 | * The type of enum to retrieve. 577 | * @param index 578 | * The index must be between 0 and length() - 1. 579 | * @param defaultValue 580 | * The default in case the value is not found 581 | * @return The enum value at the index location or defaultValue if 582 | * the value is not found or cannot be assigned to clazz 583 | */ 584 | public > E optEnum(Class clazz, int index, E defaultValue) { 585 | try { 586 | Object val = this.opt(index); 587 | if (JSONObject.NULL.equals(val)) { 588 | return defaultValue; 589 | } 590 | if (clazz.isAssignableFrom(val.getClass())) { 591 | // we just checked it! 592 | @SuppressWarnings("unchecked") 593 | E myE = (E) val; 594 | return myE; 595 | } 596 | return Enum.valueOf(clazz, val.toString()); 597 | } catch (IllegalArgumentException | NullPointerException e) { 598 | return defaultValue; 599 | } 600 | } 601 | 602 | 603 | /** 604 | * Get the optional BigInteger value associated with an index. The 605 | * defaultValue is returned if there is no value for the index, or if the 606 | * value is not a number and cannot be converted to a number. 607 | * 608 | * @param index 609 | * The index must be between 0 and length() - 1. 610 | * @param defaultValue 611 | * The default value. 612 | * @return The value. 613 | */ 614 | public BigInteger optBigInteger(int index, BigInteger defaultValue) { 615 | try { 616 | return this.getBigInteger(index); 617 | } catch (Exception e) { 618 | return defaultValue; 619 | } 620 | } 621 | 622 | /** 623 | * Get the optional BigDecimal value associated with an index. The 624 | * defaultValue is returned if there is no value for the index, or if the 625 | * value is not a number and cannot be converted to a number. 626 | * 627 | * @param index 628 | * The index must be between 0 and length() - 1. 629 | * @param defaultValue 630 | * The default value. 631 | * @return The value. 632 | */ 633 | public BigDecimal optBigDecimal(int index, BigDecimal defaultValue) { 634 | try { 635 | return this.getBigDecimal(index); 636 | } catch (Exception e) { 637 | return defaultValue; 638 | } 639 | } 640 | 641 | /** 642 | * Get the optional JSONArray associated with an index. 643 | * 644 | * @param index 645 | * subscript 646 | * @return A JSONArray value, or null if the index has no value, or if the 647 | * value is not a JSONArray. 648 | */ 649 | public JSONArray optJSONArray(int index) { 650 | Object o = this.opt(index); 651 | return o instanceof JSONArray ? (JSONArray) o : null; 652 | } 653 | 654 | /** 655 | * Get the optional JSONObject associated with an index. Null is returned if 656 | * the key is not found, or null if the index has no value, or if the value 657 | * is not a JSONObject. 658 | * 659 | * @param index 660 | * The index must be between 0 and length() - 1. 661 | * @return A JSONObject value. 662 | */ 663 | public JSONObject optJSONObject(int index) { 664 | Object o = this.opt(index); 665 | return o instanceof JSONObject ? (JSONObject) o : null; 666 | } 667 | 668 | /** 669 | * Get the optional long value associated with an index. Zero is returned if 670 | * there is no value for the index, or if the value is not a number and 671 | * cannot be converted to a number. 672 | * 673 | * @param index 674 | * The index must be between 0 and length() - 1. 675 | * @return The value. 676 | */ 677 | public long optLong(int index) { 678 | return this.optLong(index, 0); 679 | } 680 | 681 | /** 682 | * Get the optional long value associated with an index. The defaultValue is 683 | * returned if there is no value for the index, or if the value is not a 684 | * number and cannot be converted to a number. 685 | * 686 | * @param index 687 | * The index must be between 0 and length() - 1. 688 | * @param defaultValue 689 | * The default value. 690 | * @return The value. 691 | */ 692 | public long optLong(int index, long defaultValue) { 693 | try { 694 | return this.getLong(index); 695 | } catch (Exception e) { 696 | return defaultValue; 697 | } 698 | } 699 | 700 | /** 701 | * Get the optional string value associated with an index. It returns an 702 | * empty string if there is no value at that index. If the value is not a 703 | * string and is not null, then it is coverted to a string. 704 | * 705 | * @param index 706 | * The index must be between 0 and length() - 1. 707 | * @return A String value. 708 | */ 709 | public String optString(int index) { 710 | return this.optString(index, ""); 711 | } 712 | 713 | /** 714 | * Get the optional string associated with an index. The defaultValue is 715 | * returned if the key is not found. 716 | * 717 | * @param index 718 | * The index must be between 0 and length() - 1. 719 | * @param defaultValue 720 | * The default value. 721 | * @return A String value. 722 | */ 723 | public String optString(int index, String defaultValue) { 724 | Object object = this.opt(index); 725 | return JSONObject.NULL.equals(object) ? defaultValue : object 726 | .toString(); 727 | } 728 | 729 | /** 730 | * Append a boolean value. This increases the array's length by one. 731 | * 732 | * @param value 733 | * A boolean value. 734 | * @return this. 735 | */ 736 | public JSONArray put(boolean value) { 737 | this.put(value ? Boolean.TRUE : Boolean.FALSE); 738 | return this; 739 | } 740 | 741 | /** 742 | * Put a value in the JSONArray, where the value will be a JSONArray which 743 | * is produced from a Collection. 744 | * 745 | * @param value 746 | * A Collection value. 747 | * @return this. 748 | */ 749 | public JSONArray put(Collection value) { 750 | this.put(new JSONArray(value)); 751 | return this; 752 | } 753 | 754 | /** 755 | * Append a double value. This increases the array's length by one. 756 | * 757 | * @param value 758 | * A double value. 759 | * @throws JSONException 760 | * if the value is not finite. 761 | * @return this. 762 | */ 763 | public JSONArray put(double value) throws JSONException { 764 | Double d = new Double(value); 765 | JSONObject.testValidity(d); 766 | this.put(d); 767 | return this; 768 | } 769 | 770 | /** 771 | * Append an int value. This increases the array's length by one. 772 | * 773 | * @param value 774 | * An int value. 775 | * @return this. 776 | */ 777 | public JSONArray put(int value) { 778 | this.put(new Integer(value)); 779 | return this; 780 | } 781 | 782 | /** 783 | * Append an long value. This increases the array's length by one. 784 | * 785 | * @param value 786 | * A long value. 787 | * @return this. 788 | */ 789 | public JSONArray put(long value) { 790 | this.put(new Long(value)); 791 | return this; 792 | } 793 | 794 | /** 795 | * Put a value in the JSONArray, where the value will be a JSONObject which 796 | * is produced from a Map. 797 | * 798 | * @param value 799 | * A Map value. 800 | * @return this. 801 | */ 802 | public JSONArray put(Map value) { 803 | this.put(new JSONObject(value)); 804 | return this; 805 | } 806 | 807 | /** 808 | * Append an object value. This increases the array's length by one. 809 | * 810 | * @param value 811 | * An object value. The value should be a Boolean, Double, 812 | * Integer, JSONArray, JSONObject, Long, or String, or the 813 | * JSONObject.NULL object. 814 | * @return this. 815 | */ 816 | public JSONArray put(Object value) { 817 | this.myArrayList.add(value); 818 | return this; 819 | } 820 | 821 | /** 822 | * Put or replace a boolean value in the JSONArray. If the index is greater 823 | * than the length of the JSONArray, then null elements will be added as 824 | * necessary to pad it out. 825 | * 826 | * @param index 827 | * The subscript. 828 | * @param value 829 | * A boolean value. 830 | * @return this. 831 | * @throws JSONException 832 | * If the index is negative. 833 | */ 834 | public JSONArray put(int index, boolean value) throws JSONException { 835 | this.put(index, value ? Boolean.TRUE : Boolean.FALSE); 836 | return this; 837 | } 838 | 839 | /** 840 | * Put a value in the JSONArray, where the value will be a JSONArray which 841 | * is produced from a Collection. 842 | * 843 | * @param index 844 | * The subscript. 845 | * @param value 846 | * A Collection value. 847 | * @return this. 848 | * @throws JSONException 849 | * If the index is negative or if the value is not finite. 850 | */ 851 | public JSONArray put(int index, Collection value) throws JSONException { 852 | this.put(index, new JSONArray(value)); 853 | return this; 854 | } 855 | 856 | /** 857 | * Put or replace a double value. If the index is greater than the length of 858 | * the JSONArray, then null elements will be added as necessary to pad it 859 | * out. 860 | * 861 | * @param index 862 | * The subscript. 863 | * @param value 864 | * A double value. 865 | * @return this. 866 | * @throws JSONException 867 | * If the index is negative or if the value is not finite. 868 | */ 869 | public JSONArray put(int index, double value) throws JSONException { 870 | this.put(index, new Double(value)); 871 | return this; 872 | } 873 | 874 | /** 875 | * Put or replace an int value. If the index is greater than the length of 876 | * the JSONArray, then null elements will be added as necessary to pad it 877 | * out. 878 | * 879 | * @param index 880 | * The subscript. 881 | * @param value 882 | * An int value. 883 | * @return this. 884 | * @throws JSONException 885 | * If the index is negative. 886 | */ 887 | public JSONArray put(int index, int value) throws JSONException { 888 | this.put(index, new Integer(value)); 889 | return this; 890 | } 891 | 892 | /** 893 | * Put or replace a long value. If the index is greater than the length of 894 | * the JSONArray, then null elements will be added as necessary to pad it 895 | * out. 896 | * 897 | * @param index 898 | * The subscript. 899 | * @param value 900 | * A long value. 901 | * @return this. 902 | * @throws JSONException 903 | * If the index is negative. 904 | */ 905 | public JSONArray put(int index, long value) throws JSONException { 906 | this.put(index, new Long(value)); 907 | return this; 908 | } 909 | 910 | /** 911 | * Put a value in the JSONArray, where the value will be a JSONObject that 912 | * is produced from a Map. 913 | * 914 | * @param index 915 | * The subscript. 916 | * @param value 917 | * The Map value. 918 | * @return this. 919 | * @throws JSONException 920 | * If the index is negative or if the the value is an invalid 921 | * number. 922 | */ 923 | public JSONArray put(int index, Map value) throws JSONException { 924 | this.put(index, new JSONObject(value)); 925 | return this; 926 | } 927 | 928 | /** 929 | * Put or replace an object value in the JSONArray. If the index is greater 930 | * than the length of the JSONArray, then null elements will be added as 931 | * necessary to pad it out. 932 | * 933 | * @param index 934 | * The subscript. 935 | * @param value 936 | * The value to put into the array. The value should be a 937 | * Boolean, Double, Integer, JSONArray, JSONObject, Long, or 938 | * String, or the JSONObject.NULL object. 939 | * @return this. 940 | * @throws JSONException 941 | * If the index is negative or if the the value is an invalid 942 | * number. 943 | */ 944 | public JSONArray put(int index, Object value) throws JSONException { 945 | JSONObject.testValidity(value); 946 | if (index < 0) { 947 | throw new JSONException("JSONArray[" + index + "] not found."); 948 | } 949 | if (index < this.length()) { 950 | this.myArrayList.set(index, value); 951 | } else { 952 | while (index != this.length()) { 953 | this.put(JSONObject.NULL); 954 | } 955 | this.put(value); 956 | } 957 | return this; 958 | } 959 | 960 | /** 961 | * Remove an index and close the hole. 962 | * 963 | * @param index 964 | * The index of the element to be removed. 965 | * @return The value that was associated with the index, or null if there 966 | * was no value. 967 | */ 968 | public Object remove(int index) { 969 | return index >= 0 && index < this.length() 970 | ? this.myArrayList.remove(index) 971 | : null; 972 | } 973 | 974 | /** 975 | * Determine if two JSONArrays are similar. 976 | * They must contain similar sequences. 977 | * 978 | * @param other The other JSONArray 979 | * @return true if they are equal 980 | */ 981 | public boolean similar(Object other) { 982 | if (!(other instanceof JSONArray)) { 983 | return false; 984 | } 985 | int len = this.length(); 986 | if (len != ((JSONArray)other).length()) { 987 | return false; 988 | } 989 | for (int i = 0; i < len; i += 1) { 990 | Object valueThis = this.get(i); 991 | Object valueOther = ((JSONArray)other).get(i); 992 | if (valueThis instanceof JSONObject) { 993 | if (!((JSONObject)valueThis).similar(valueOther)) { 994 | return false; 995 | } 996 | } else if (valueThis instanceof JSONArray) { 997 | if (!((JSONArray)valueThis).similar(valueOther)) { 998 | return false; 999 | } 1000 | } else if (!valueThis.equals(valueOther)) { 1001 | return false; 1002 | } 1003 | } 1004 | return true; 1005 | } 1006 | 1007 | /** 1008 | * Produce a JSONObject by combining a JSONArray of names with the values of 1009 | * this JSONArray. 1010 | * 1011 | * @param names 1012 | * A JSONArray containing a list of key strings. These will be 1013 | * paired with the values. 1014 | * @return A JSONObject, or null if there are no names or if this JSONArray 1015 | * has no values. 1016 | * @throws JSONException 1017 | * If any of the names are null. 1018 | */ 1019 | public JSONObject toJSONObject(JSONArray names) throws JSONException { 1020 | if (names == null || names.length() == 0 || this.length() == 0) { 1021 | return null; 1022 | } 1023 | JSONObject jo = new JSONObject(); 1024 | for (int i = 0; i < names.length(); i += 1) { 1025 | jo.put(names.getString(i), this.opt(i)); 1026 | } 1027 | return jo; 1028 | } 1029 | 1030 | /** 1031 | * Make a JSON text of this JSONArray. For compactness, no unnecessary 1032 | * whitespace is added. If it is not possible to produce a syntactically 1033 | * correct JSON text then null will be returned instead. This could occur if 1034 | * the array contains an invalid number. 1035 | *

1036 | * Warning: This method assumes that the data structure is acyclical. 1037 | * 1038 | * @return a printable, displayable, transmittable representation of the 1039 | * array. 1040 | */ 1041 | public String toString() { 1042 | try { 1043 | return this.toString(0); 1044 | } catch (Exception e) { 1045 | return null; 1046 | } 1047 | } 1048 | 1049 | /** 1050 | * Make a prettyprinted JSON text of this JSONArray. Warning: This method 1051 | * assumes that the data structure is acyclical. 1052 | * 1053 | * @param indentFactor 1054 | * The number of spaces to add to each level of indentation. 1055 | * @return a printable, displayable, transmittable representation of the 1056 | * object, beginning with [ (left 1057 | * bracket) and ending with ] 1058 | *  (right bracket). 1059 | * @throws JSONException 1060 | */ 1061 | public String toString(int indentFactor) throws JSONException { 1062 | StringWriter sw = new StringWriter(); 1063 | synchronized (sw.getBuffer()) { 1064 | return this.write(sw, indentFactor, 0).toString(); 1065 | } 1066 | } 1067 | 1068 | /** 1069 | * Write the contents of the JSONArray as JSON text to a writer. For 1070 | * compactness, no whitespace is added. 1071 | *

1072 | * Warning: This method assumes that the data structure is acyclical. 1073 | * 1074 | * @return The writer. 1075 | * @throws JSONException 1076 | */ 1077 | public Writer write(Writer writer) throws JSONException { 1078 | return this.write(writer, 0, 0); 1079 | } 1080 | 1081 | /** 1082 | * Write the contents of the JSONArray as JSON text to a writer. For 1083 | * compactness, no whitespace is added. 1084 | *

1085 | * Warning: This method assumes that the data structure is acyclical. 1086 | * 1087 | * @param writer 1088 | * Writes the serialized JSON 1089 | * @param indentFactor 1090 | * The number of spaces to add to each level of indentation. 1091 | * @param indent 1092 | * The indention of the top level. 1093 | * @return The writer. 1094 | * @throws JSONException 1095 | */ 1096 | public Writer write(Writer writer, int indentFactor, int indent) 1097 | throws JSONException { 1098 | try { 1099 | boolean commanate = false; 1100 | int length = this.length(); 1101 | writer.write('['); 1102 | 1103 | if (length == 1) { 1104 | JSONObject.writeValue(writer, this.myArrayList.get(0), 1105 | indentFactor, indent); 1106 | } else if (length != 0) { 1107 | final int newindent = indent + indentFactor; 1108 | 1109 | for (int i = 0; i < length; i += 1) { 1110 | if (commanate) { 1111 | writer.write(','); 1112 | } 1113 | if (indentFactor > 0) { 1114 | writer.write('\n'); 1115 | } 1116 | JSONObject.indent(writer, newindent); 1117 | JSONObject.writeValue(writer, this.myArrayList.get(i), 1118 | indentFactor, newindent); 1119 | commanate = true; 1120 | } 1121 | if (indentFactor > 0) { 1122 | writer.write('\n'); 1123 | } 1124 | JSONObject.indent(writer, indent); 1125 | } 1126 | writer.write(']'); 1127 | return writer; 1128 | } catch (IOException e) { 1129 | throw new JSONException(e); 1130 | } 1131 | } 1132 | } 1133 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/json/JSONException.java: -------------------------------------------------------------------------------- 1 | package com.json; 2 | 3 | /** 4 | * The JSONException is thrown by the JSON.org classes when things are amiss. 5 | * 6 | * @author JSON.org 7 | * @version 2015-12-09 8 | */ 9 | public class JSONException extends RuntimeException { 10 | /** Serialization ID */ 11 | private static final long serialVersionUID = 0; 12 | 13 | /** 14 | * Constructs a JSONException with an explanatory message. 15 | * 16 | * @param message 17 | * Detail about the reason for the exception. 18 | */ 19 | public JSONException(final String message) { 20 | super(message); 21 | } 22 | 23 | /** 24 | * Constructs a JSONException with an explanatory message and cause. 25 | * 26 | * @param message 27 | * Detail about the reason for the exception. 28 | * @param cause 29 | * The cause. 30 | */ 31 | public JSONException(final String message, final Throwable cause) { 32 | super(message, cause); 33 | } 34 | 35 | /** 36 | * Constructs a new JSONException with the specified cause. 37 | * 38 | * @param cause 39 | * The cause. 40 | */ 41 | public JSONException(final Throwable cause) { 42 | super(cause.getMessage(), cause); 43 | } 44 | 45 | } 46 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/json/JSONString.java: -------------------------------------------------------------------------------- 1 | package com.json; 2 | /** 3 | * The JSONString interface allows a toJSONString() 4 | * method so that a class can change the behavior of 5 | * JSONObject.toString(), JSONArray.toString(), 6 | * and JSONWriter.value(Object). The 7 | * toJSONString method will be used instead of the default behavior 8 | * of using the Object's toString() method and quoting the result. 9 | */ 10 | public interface JSONString { 11 | /** 12 | * The toJSONString method allows a class to produce its own JSON 13 | * serialization. 14 | * 15 | * @return A strictly syntactically correct JSON text. 16 | */ 17 | public String toJSONString(); 18 | } 19 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/json/JSONStringer.java: -------------------------------------------------------------------------------- 1 | package com.json; 2 | 3 | /* 4 | Copyright (c) 2006 JSON.org 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in all 14 | copies or substantial portions of the Software. 15 | 16 | The Software shall be used for Good, not Evil. 17 | 18 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 19 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 20 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 21 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 22 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 23 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 24 | SOFTWARE. 25 | */ 26 | 27 | import java.io.StringWriter; 28 | 29 | /** 30 | * JSONStringer provides a quick and convenient way of producing JSON text. 31 | * The texts produced strictly conform to JSON syntax rules. No whitespace is 32 | * added, so the results are ready for transmission or storage. Each instance of 33 | * JSONStringer can produce one JSON text. 34 | *

35 | * A JSONStringer instance provides a value method for appending 36 | * values to the 37 | * text, and a key 38 | * method for adding keys before values in objects. There are array 39 | * and endArray methods that make and bound array values, and 40 | * object and endObject methods which make and bound 41 | * object values. All of these methods return the JSONWriter instance, 42 | * permitting cascade style. For example,

43 |  * myString = new JSONStringer()
44 |  *     .object()
45 |  *         .key("JSON")
46 |  *         .value("Hello, World!")
47 |  *     .endObject()
48 |  *     .toString();
which produces the string
49 |  * {"JSON":"Hello, World!"}
50 | *

51 | * The first method called must be array or object. 52 | * There are no methods for adding commas or colons. JSONStringer adds them for 53 | * you. Objects and arrays can be nested up to 20 levels deep. 54 | *

55 | * This can sometimes be easier than using a JSONObject to build a string. 56 | * @author JSON.org 57 | * @version 2015-12-09 58 | */ 59 | public class JSONStringer extends JSONWriter { 60 | /** 61 | * Make a fresh JSONStringer. It can be used to build one JSON text. 62 | */ 63 | public JSONStringer() { 64 | super(new StringWriter()); 65 | } 66 | 67 | /** 68 | * Return the JSON text. This method is used to obtain the product of the 69 | * JSONStringer instance. It will return null if there was a 70 | * problem in the construction of the JSON text (such as the calls to 71 | * array were not properly balanced with calls to 72 | * endArray). 73 | * @return The JSON text. 74 | */ 75 | public String toString() { 76 | return this.mode == 'd' ? this.writer.toString() : null; 77 | } 78 | } 79 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/json/JSONTokener.java: -------------------------------------------------------------------------------- 1 | package com.json; 2 | 3 | import java.io.BufferedReader; 4 | import java.io.IOException; 5 | import java.io.InputStream; 6 | import java.io.InputStreamReader; 7 | import java.io.Reader; 8 | import java.io.StringReader; 9 | 10 | /* 11 | Copyright (c) 2002 JSON.org 12 | 13 | Permission is hereby granted, free of charge, to any person obtaining a copy 14 | of this software and associated documentation files (the "Software"), to deal 15 | in the Software without restriction, including without limitation the rights 16 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 17 | copies of the Software, and to permit persons to whom the Software is 18 | furnished to do so, subject to the following conditions: 19 | 20 | The above copyright notice and this permission notice shall be included in all 21 | copies or substantial portions of the Software. 22 | 23 | The Software shall be used for Good, not Evil. 24 | 25 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 26 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 27 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 28 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 29 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 30 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 31 | SOFTWARE. 32 | */ 33 | 34 | /** 35 | * A JSONTokener takes a source string and extracts characters and tokens from 36 | * it. It is used by the JSONObject and JSONArray constructors to parse 37 | * JSON source strings. 38 | * @author JSON.org 39 | * @version 2014-05-03 40 | */ 41 | public class JSONTokener { 42 | 43 | private long character; 44 | private boolean eof; 45 | private long index; 46 | private long line; 47 | private char previous; 48 | private Reader reader; 49 | private boolean usePrevious; 50 | 51 | 52 | /** 53 | * Construct a JSONTokener from a Reader. 54 | * 55 | * @param reader A reader. 56 | */ 57 | public JSONTokener(Reader reader) { 58 | this.reader = reader.markSupported() 59 | ? reader 60 | : new BufferedReader(reader); 61 | this.eof = false; 62 | this.usePrevious = false; 63 | this.previous = 0; 64 | this.index = 0; 65 | this.character = 1; 66 | this.line = 1; 67 | } 68 | 69 | 70 | /** 71 | * Construct a JSONTokener from an InputStream. 72 | * @param inputStream The source. 73 | */ 74 | public JSONTokener(InputStream inputStream) throws JSONException { 75 | this(new InputStreamReader(inputStream)); 76 | } 77 | 78 | 79 | /** 80 | * Construct a JSONTokener from a string. 81 | * 82 | * @param s A source string. 83 | */ 84 | public JSONTokener(String s) { 85 | this(new StringReader(s)); 86 | } 87 | 88 | 89 | /** 90 | * Back up one character. This provides a sort of lookahead capability, 91 | * so that you can test for a digit or letter before attempting to parse 92 | * the next number or identifier. 93 | */ 94 | public void back() throws JSONException { 95 | if (this.usePrevious || this.index <= 0) { 96 | throw new JSONException("Stepping back two steps is not supported"); 97 | } 98 | this.index -= 1; 99 | this.character -= 1; 100 | this.usePrevious = true; 101 | this.eof = false; 102 | } 103 | 104 | 105 | /** 106 | * Get the hex value of a character (base16). 107 | * @param c A character between '0' and '9' or between 'A' and 'F' or 108 | * between 'a' and 'f'. 109 | * @return An int between 0 and 15, or -1 if c was not a hex digit. 110 | */ 111 | public static int dehexchar(char c) { 112 | if (c >= '0' && c <= '9') { 113 | return c - '0'; 114 | } 115 | if (c >= 'A' && c <= 'F') { 116 | return c - ('A' - 10); 117 | } 118 | if (c >= 'a' && c <= 'f') { 119 | return c - ('a' - 10); 120 | } 121 | return -1; 122 | } 123 | 124 | public boolean end() { 125 | return this.eof && !this.usePrevious; 126 | } 127 | 128 | 129 | /** 130 | * Determine if the source string still contains characters that next() 131 | * can consume. 132 | * @return true if not yet at the end of the source. 133 | */ 134 | public boolean more() throws JSONException { 135 | this.next(); 136 | if (this.end()) { 137 | return false; 138 | } 139 | this.back(); 140 | return true; 141 | } 142 | 143 | 144 | /** 145 | * Get the next character in the source string. 146 | * 147 | * @return The next character, or 0 if past the end of the source string. 148 | */ 149 | public char next() throws JSONException { 150 | int c; 151 | if (this.usePrevious) { 152 | this.usePrevious = false; 153 | c = this.previous; 154 | } else { 155 | try { 156 | c = this.reader.read(); 157 | } catch (IOException exception) { 158 | throw new JSONException(exception); 159 | } 160 | 161 | if (c <= 0) { // End of stream 162 | this.eof = true; 163 | c = 0; 164 | } 165 | } 166 | this.index += 1; 167 | if (this.previous == '\r') { 168 | this.line += 1; 169 | this.character = c == '\n' ? 0 : 1; 170 | } else if (c == '\n') { 171 | this.line += 1; 172 | this.character = 0; 173 | } else { 174 | this.character += 1; 175 | } 176 | this.previous = (char) c; 177 | return this.previous; 178 | } 179 | 180 | 181 | /** 182 | * Consume the next character, and check that it matches a specified 183 | * character. 184 | * @param c The character to match. 185 | * @return The character. 186 | * @throws JSONException if the character does not match. 187 | */ 188 | public char next(char c) throws JSONException { 189 | char n = this.next(); 190 | if (n != c) { 191 | throw this.syntaxError("Expected '" + c + "' and instead saw '" + 192 | n + "'"); 193 | } 194 | return n; 195 | } 196 | 197 | 198 | /** 199 | * Get the next n characters. 200 | * 201 | * @param n The number of characters to take. 202 | * @return A string of n characters. 203 | * @throws JSONException 204 | * Substring bounds error if there are not 205 | * n characters remaining in the source string. 206 | */ 207 | public String next(int n) throws JSONException { 208 | if (n == 0) { 209 | return ""; 210 | } 211 | 212 | char[] chars = new char[n]; 213 | int pos = 0; 214 | 215 | while (pos < n) { 216 | chars[pos] = this.next(); 217 | if (this.end()) { 218 | throw this.syntaxError("Substring bounds error"); 219 | } 220 | pos += 1; 221 | } 222 | return new String(chars); 223 | } 224 | 225 | 226 | /** 227 | * Get the next char in the string, skipping whitespace. 228 | * @throws JSONException 229 | * @return A character, or 0 if there are no more characters. 230 | */ 231 | public char nextClean() throws JSONException { 232 | for (;;) { 233 | char c = this.next(); 234 | if (c == 0 || c > ' ') { 235 | return c; 236 | } 237 | } 238 | } 239 | 240 | 241 | /** 242 | * Return the characters up to the next close quote character. 243 | * Backslash processing is done. The formal JSON format does not 244 | * allow strings in single quotes, but an implementation is allowed to 245 | * accept them. 246 | * @param quote The quoting character, either 247 | * " (double quote) or 248 | * ' (single quote). 249 | * @return A String. 250 | * @throws JSONException Unterminated string. 251 | */ 252 | public String nextString(char quote) throws JSONException { 253 | char c; 254 | StringBuilder sb = new StringBuilder(); 255 | for (;;) { 256 | c = this.next(); 257 | switch (c) { 258 | case 0: 259 | case '\n': 260 | case '\r': 261 | throw this.syntaxError("Unterminated string"); 262 | case '\\': 263 | c = this.next(); 264 | switch (c) { 265 | case 'b': 266 | sb.append('\b'); 267 | break; 268 | case 't': 269 | sb.append('\t'); 270 | break; 271 | case 'n': 272 | sb.append('\n'); 273 | break; 274 | case 'f': 275 | sb.append('\f'); 276 | break; 277 | case 'r': 278 | sb.append('\r'); 279 | break; 280 | case 'u': 281 | sb.append((char)Integer.parseInt(this.next(4), 16)); 282 | break; 283 | case '"': 284 | case '\'': 285 | case '\\': 286 | case '/': 287 | sb.append(c); 288 | break; 289 | default: 290 | throw this.syntaxError("Illegal escape."); 291 | } 292 | break; 293 | default: 294 | if (c == quote) { 295 | return sb.toString(); 296 | } 297 | sb.append(c); 298 | } 299 | } 300 | } 301 | 302 | 303 | /** 304 | * Get the text up but not including the specified character or the 305 | * end of line, whichever comes first. 306 | * @param delimiter A delimiter character. 307 | * @return A string. 308 | */ 309 | public String nextTo(char delimiter) throws JSONException { 310 | StringBuilder sb = new StringBuilder(); 311 | for (;;) { 312 | char c = this.next(); 313 | if (c == delimiter || c == 0 || c == '\n' || c == '\r') { 314 | if (c != 0) { 315 | this.back(); 316 | } 317 | return sb.toString().trim(); 318 | } 319 | sb.append(c); 320 | } 321 | } 322 | 323 | 324 | /** 325 | * Get the text up but not including one of the specified delimiter 326 | * characters or the end of line, whichever comes first. 327 | * @param delimiters A set of delimiter characters. 328 | * @return A string, trimmed. 329 | */ 330 | public String nextTo(String delimiters) throws JSONException { 331 | char c; 332 | StringBuilder sb = new StringBuilder(); 333 | for (;;) { 334 | c = this.next(); 335 | if (delimiters.indexOf(c) >= 0 || c == 0 || 336 | c == '\n' || c == '\r') { 337 | if (c != 0) { 338 | this.back(); 339 | } 340 | return sb.toString().trim(); 341 | } 342 | sb.append(c); 343 | } 344 | } 345 | 346 | 347 | /** 348 | * Get the next value. The value can be a Boolean, Double, Integer, 349 | * JSONArray, JSONObject, Long, or String, or the JSONObject.NULL object. 350 | * @throws JSONException If syntax error. 351 | * 352 | * @return An object. 353 | */ 354 | public Object nextValue() throws JSONException { 355 | char c = this.nextClean(); 356 | String string; 357 | 358 | switch (c) { 359 | case '"': 360 | case '\'': 361 | return this.nextString(c); 362 | case '{': 363 | this.back(); 364 | return new JSONObject(this); 365 | case '[': 366 | this.back(); 367 | return new JSONArray(this); 368 | } 369 | 370 | /* 371 | * Handle unquoted text. This could be the values true, false, or 372 | * null, or it can be a number. An implementation (such as this one) 373 | * is allowed to also accept non-standard forms. 374 | * 375 | * Accumulate characters until we reach the end of the text or a 376 | * formatting character. 377 | */ 378 | 379 | StringBuilder sb = new StringBuilder(); 380 | while (c >= ' ' && ",:]}/\\\"[{;=#".indexOf(c) < 0) { 381 | sb.append(c); 382 | c = this.next(); 383 | } 384 | this.back(); 385 | 386 | string = sb.toString().trim(); 387 | if ("".equals(string)) { 388 | throw this.syntaxError("Missing value"); 389 | } 390 | return JSONObject.stringToValue(string); 391 | } 392 | 393 | 394 | /** 395 | * Skip characters until the next character is the requested character. 396 | * If the requested character is not found, no characters are skipped. 397 | * @param to A character to skip to. 398 | * @return The requested character, or zero if the requested character 399 | * is not found. 400 | */ 401 | public char skipTo(char to) throws JSONException { 402 | char c; 403 | try { 404 | long startIndex = this.index; 405 | long startCharacter = this.character; 406 | long startLine = this.line; 407 | this.reader.mark(1000000); 408 | do { 409 | c = this.next(); 410 | if (c == 0) { 411 | this.reader.reset(); 412 | this.index = startIndex; 413 | this.character = startCharacter; 414 | this.line = startLine; 415 | return c; 416 | } 417 | } while (c != to); 418 | } catch (IOException exception) { 419 | throw new JSONException(exception); 420 | } 421 | this.back(); 422 | return c; 423 | } 424 | 425 | 426 | /** 427 | * Make a JSONException to signal a syntax error. 428 | * 429 | * @param message The error message. 430 | * @return A JSONException object, suitable for throwing 431 | */ 432 | public JSONException syntaxError(String message) { 433 | return new JSONException(message + this.toString()); 434 | } 435 | 436 | 437 | /** 438 | * Make a printable string of this JSONTokener. 439 | * 440 | * @return " at {index} [character {character} line {line}]" 441 | */ 442 | public String toString() { 443 | return " at " + this.index + " [character " + this.character + " line " + 444 | this.line + "]"; 445 | } 446 | } 447 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/json/JSONWriter.java: -------------------------------------------------------------------------------- 1 | package com.json; 2 | 3 | import java.io.IOException; 4 | import java.io.Writer; 5 | 6 | /* 7 | Copyright (c) 2006 JSON.org 8 | 9 | Permission is hereby granted, free of charge, to any person obtaining a copy 10 | of this software and associated documentation files (the "Software"), to deal 11 | in the Software without restriction, including without limitation the rights 12 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 13 | copies of the Software, and to permit persons to whom the Software is 14 | furnished to do so, subject to the following conditions: 15 | 16 | The above copyright notice and this permission notice shall be included in all 17 | copies or substantial portions of the Software. 18 | 19 | The Software shall be used for Good, not Evil. 20 | 21 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 22 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 23 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 24 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 25 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 26 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 27 | SOFTWARE. 28 | */ 29 | 30 | /** 31 | * JSONWriter provides a quick and convenient way of producing JSON text. 32 | * The texts produced strictly conform to JSON syntax rules. No whitespace is 33 | * added, so the results are ready for transmission or storage. Each instance of 34 | * JSONWriter can produce one JSON text. 35 | *

36 | * A JSONWriter instance provides a value method for appending 37 | * values to the 38 | * text, and a key 39 | * method for adding keys before values in objects. There are array 40 | * and endArray methods that make and bound array values, and 41 | * object and endObject methods which make and bound 42 | * object values. All of these methods return the JSONWriter instance, 43 | * permitting a cascade style. For example,

 44 |  * new JSONWriter(myWriter)
 45 |  *     .object()
 46 |  *         .key("JSON")
 47 |  *         .value("Hello, World!")
 48 |  *     .endObject();
which writes
 49 |  * {"JSON":"Hello, World!"}
50 | *

51 | * The first method called must be array or object. 52 | * There are no methods for adding commas or colons. JSONWriter adds them for 53 | * you. Objects and arrays can be nested up to 20 levels deep. 54 | *

55 | * This can sometimes be easier than using a JSONObject to build a string. 56 | * @author JSON.org 57 | * @version 2015-12-09 58 | */ 59 | public class JSONWriter { 60 | private static final int maxdepth = 200; 61 | 62 | /** 63 | * The comma flag determines if a comma should be output before the next 64 | * value. 65 | */ 66 | private boolean comma; 67 | 68 | /** 69 | * The current mode. Values: 70 | * 'a' (array), 71 | * 'd' (done), 72 | * 'i' (initial), 73 | * 'k' (key), 74 | * 'o' (object). 75 | */ 76 | protected char mode; 77 | 78 | /** 79 | * The object/array stack. 80 | */ 81 | private final JSONObject stack[]; 82 | 83 | /** 84 | * The stack top index. A value of 0 indicates that the stack is empty. 85 | */ 86 | private int top; 87 | 88 | /** 89 | * The writer that will receive the output. 90 | */ 91 | protected Writer writer; 92 | 93 | /** 94 | * Make a fresh JSONWriter. It can be used to build one JSON text. 95 | */ 96 | public JSONWriter(Writer w) { 97 | this.comma = false; 98 | this.mode = 'i'; 99 | this.stack = new JSONObject[maxdepth]; 100 | this.top = 0; 101 | this.writer = w; 102 | } 103 | 104 | /** 105 | * Append a value. 106 | * @param string A string value. 107 | * @return this 108 | * @throws JSONException If the value is out of sequence. 109 | */ 110 | private JSONWriter append(String string) throws JSONException { 111 | if (string == null) { 112 | throw new JSONException("Null pointer"); 113 | } 114 | if (this.mode == 'o' || this.mode == 'a') { 115 | try { 116 | if (this.comma && this.mode == 'a') { 117 | this.writer.write(','); 118 | } 119 | this.writer.write(string); 120 | } catch (IOException e) { 121 | throw new JSONException(e); 122 | } 123 | if (this.mode == 'o') { 124 | this.mode = 'k'; 125 | } 126 | this.comma = true; 127 | return this; 128 | } 129 | throw new JSONException("Value out of sequence."); 130 | } 131 | 132 | /** 133 | * Begin appending a new array. All values until the balancing 134 | * endArray will be appended to this array. The 135 | * endArray method must be called to mark the array's end. 136 | * @return this 137 | * @throws JSONException If the nesting is too deep, or if the object is 138 | * started in the wrong place (for example as a key or after the end of the 139 | * outermost array or object). 140 | */ 141 | public JSONWriter array() throws JSONException { 142 | if (this.mode == 'i' || this.mode == 'o' || this.mode == 'a') { 143 | this.push(null); 144 | this.append("["); 145 | this.comma = false; 146 | return this; 147 | } 148 | throw new JSONException("Misplaced array."); 149 | } 150 | 151 | /** 152 | * End something. 153 | * @param mode Mode 154 | * @param c Closing character 155 | * @return this 156 | * @throws JSONException If unbalanced. 157 | */ 158 | private JSONWriter end(char mode, char c) throws JSONException { 159 | if (this.mode != mode) { 160 | throw new JSONException(mode == 'a' 161 | ? "Misplaced endArray." 162 | : "Misplaced endObject."); 163 | } 164 | this.pop(mode); 165 | try { 166 | this.writer.write(c); 167 | } catch (IOException e) { 168 | throw new JSONException(e); 169 | } 170 | this.comma = true; 171 | return this; 172 | } 173 | 174 | /** 175 | * End an array. This method most be called to balance calls to 176 | * array. 177 | * @return this 178 | * @throws JSONException If incorrectly nested. 179 | */ 180 | public JSONWriter endArray() throws JSONException { 181 | return this.end('a', ']'); 182 | } 183 | 184 | /** 185 | * End an object. This method most be called to balance calls to 186 | * object. 187 | * @return this 188 | * @throws JSONException If incorrectly nested. 189 | */ 190 | public JSONWriter endObject() throws JSONException { 191 | return this.end('k', '}'); 192 | } 193 | 194 | /** 195 | * Append a key. The key will be associated with the next value. In an 196 | * object, every value must be preceded by a key. 197 | * @param string A key string. 198 | * @return this 199 | * @throws JSONException If the key is out of place. For example, keys 200 | * do not belong in arrays or if the key is null. 201 | */ 202 | public JSONWriter key(String string) throws JSONException { 203 | if (string == null) { 204 | throw new JSONException("Null key."); 205 | } 206 | if (this.mode == 'k') { 207 | try { 208 | this.stack[this.top - 1].putOnce(string, Boolean.TRUE); 209 | if (this.comma) { 210 | this.writer.write(','); 211 | } 212 | this.writer.write(JSONObject.quote(string)); 213 | this.writer.write(':'); 214 | this.comma = false; 215 | this.mode = 'o'; 216 | return this; 217 | } catch (IOException e) { 218 | throw new JSONException(e); 219 | } 220 | } 221 | throw new JSONException("Misplaced key."); 222 | } 223 | 224 | 225 | /** 226 | * Begin appending a new object. All keys and values until the balancing 227 | * endObject will be appended to this object. The 228 | * endObject method must be called to mark the object's end. 229 | * @return this 230 | * @throws JSONException If the nesting is too deep, or if the object is 231 | * started in the wrong place (for example as a key or after the end of the 232 | * outermost array or object). 233 | */ 234 | public JSONWriter object() throws JSONException { 235 | if (this.mode == 'i') { 236 | this.mode = 'o'; 237 | } 238 | if (this.mode == 'o' || this.mode == 'a') { 239 | this.append("{"); 240 | this.push(new JSONObject()); 241 | this.comma = false; 242 | return this; 243 | } 244 | throw new JSONException("Misplaced object."); 245 | 246 | } 247 | 248 | 249 | /** 250 | * Pop an array or object scope. 251 | * @param c The scope to close. 252 | * @throws JSONException If nesting is wrong. 253 | */ 254 | private void pop(char c) throws JSONException { 255 | if (this.top <= 0) { 256 | throw new JSONException("Nesting error."); 257 | } 258 | char m = this.stack[this.top - 1] == null ? 'a' : 'k'; 259 | if (m != c) { 260 | throw new JSONException("Nesting error."); 261 | } 262 | this.top -= 1; 263 | this.mode = this.top == 0 264 | ? 'd' 265 | : this.stack[this.top - 1] == null 266 | ? 'a' 267 | : 'k'; 268 | } 269 | 270 | /** 271 | * Push an array or object scope. 272 | * @param jo The scope to open. 273 | * @throws JSONException If nesting is too deep. 274 | */ 275 | private void push(JSONObject jo) throws JSONException { 276 | if (this.top >= maxdepth) { 277 | throw new JSONException("Nesting too deep."); 278 | } 279 | this.stack[this.top] = jo; 280 | this.mode = jo == null ? 'a' : 'k'; 281 | this.top += 1; 282 | } 283 | 284 | 285 | /** 286 | * Append either the value true or the value 287 | * false. 288 | * @param b A boolean. 289 | * @return this 290 | * @throws JSONException 291 | */ 292 | public JSONWriter value(boolean b) throws JSONException { 293 | return this.append(b ? "true" : "false"); 294 | } 295 | 296 | /** 297 | * Append a double value. 298 | * @param d A double. 299 | * @return this 300 | * @throws JSONException If the number is not finite. 301 | */ 302 | public JSONWriter value(double d) throws JSONException { 303 | return this.value(new Double(d)); 304 | } 305 | 306 | /** 307 | * Append a long value. 308 | * @param l A long. 309 | * @return this 310 | * @throws JSONException 311 | */ 312 | public JSONWriter value(long l) throws JSONException { 313 | return this.append(Long.toString(l)); 314 | } 315 | 316 | 317 | /** 318 | * Append an object value. 319 | * @param object The object to append. It can be null, or a Boolean, Number, 320 | * String, JSONObject, or JSONArray, or an object that implements JSONString. 321 | * @return this 322 | * @throws JSONException If the value is out of sequence. 323 | */ 324 | public JSONWriter value(Object object) throws JSONException { 325 | return this.append(JSONObject.valueToString(object)); 326 | } 327 | } 328 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/server/Config.java: -------------------------------------------------------------------------------- 1 | package com.server; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | 6 | public class Config { 7 | 8 | 9 | //when the websocket http handshake complete 10 | public static final int HANDSHAKE_COMPLETE_SUCCESS = 1; 11 | public static final int LOGIN = 2; 12 | public static final int LOGIN_DONE = 3; 13 | public static final int NEW_USER_LOGIN_DONE = 4; 14 | public static final int PLAY = 5; 15 | public static final int PLAY_DONE = 6; 16 | 17 | 18 | } 19 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/server/GameEventHandler.java: -------------------------------------------------------------------------------- 1 | package com.server; 2 | 3 | import java.util.ArrayList; 4 | 5 | import java.util.Iterator; 6 | import java.util.Map; 7 | import java.util.Map.Entry; 8 | import java.util.logging.Logger; 9 | 10 | import com.json.JSONArray; 11 | import com.json.JSONObject; 12 | 13 | import io.netty.channel.Channel; 14 | import io.netty.channel.ChannelHandlerContext; 15 | import io.netty.handler.codec.http.websocketx.TextWebSocketFrame; 16 | import io.netty.util.AttributeKey; 17 | //this class will handle all the request / response logic and game protocol 18 | public class GameEventHandler { 19 | private final static Logger LOG = LoggerManager.GetLogger(GameEventHandler.class.getName()); 20 | private GameManager gameManager; 21 | private static int playerIdCounter = 0; 22 | private static int playerRegistretionCounter = 0; 23 | public GameEventHandler(GameManager _gameManager) 24 | { 25 | this.gameManager = _gameManager; 26 | 27 | } 28 | 29 | public int handleEvent(String _jsonRequest,Channel channel) 30 | { 31 | JSONObject jsonObject = new JSONObject(_jsonRequest); 32 | int Event = jsonObject.getInt("event"); 33 | int playerId = -1; 34 | String userName = jsonObject.getString("username"); 35 | switch(Event) 36 | { 37 | case Config.LOGIN: 38 | { 39 | Player newPlayer = setPlayerNewAttributes(userName,channel,Config.LOGIN_DONE); 40 | setPlayerInPlayersContainer(newPlayer); 41 | playerId = newPlayer.getId(); 42 | break; 43 | } 44 | case Config.PLAY: 45 | { 46 | playerId = invokePlayEvent(jsonObject); 47 | 48 | } 49 | } 50 | 51 | return playerId; 52 | } 53 | 54 | 55 | public boolean ResponseDispatcher(int _playerId,String _jsonRequest) 56 | { 57 | JSONObject jsonObject = new JSONObject(_jsonRequest); 58 | int Event = jsonObject.getInt("event"); 59 | boolean bDone = false; 60 | switch(Event) 61 | { 62 | case Config.LOGIN: 63 | { 64 | bDone = this.gameManager.getGameResponseDispatcher().ResponseDispatcheLoginDone(_playerId); 65 | break; 66 | } 67 | case Config.PLAY: 68 | { 69 | bDone = this.gameManager.getGameResponseDispatcher().ResponseDispatchePlayDone(_playerId); 70 | break; 71 | } 72 | } 73 | 74 | return bDone; 75 | } 76 | 77 | 78 | 79 | 80 | private int invokePlayEvent(JSONObject _jsonObject) 81 | { 82 | int activePlayerId = _jsonObject.getInt("id"); 83 | int currentPlayerID = this.gameManager.getPlayers().get(activePlayerId).getActiveplayerid(); 84 | //validation of turn 85 | if(activePlayerId==currentPlayerID) 86 | { 87 | 88 | //find out who is the previous player 89 | int playerInx = getPreviousePlayerIndex(currentPlayerID); 90 | 91 | 92 | String currentPlayerCardId = this.gameManager.getPlayers().get(activePlayerId).getActivecardid(); 93 | //check if the cards deck is active in there are cards in it 94 | if(this.gameManager.getCardsPlayDeck().size()>0) 95 | { 96 | String prevCardId = this.gameManager.getCardsPlayDeck().getFirst(); 97 | //check which card has greater value 98 | int prevCardValue = this.gameManager.getCardValueById(prevCardId); 99 | int currentCardValue = this.gameManager.getCardValueById(currentPlayerCardId); 100 | //check if previous card is greater 101 | if(prevCardValue > currentCardValue) 102 | { 103 | 104 | //set the cards to the winner which is previous player 105 | this.gameManager.getPlayerByIndex(playerInx).getPlayerCards().addLast(currentPlayerCardId); 106 | this.gameManager.getPlayerByIndex(playerInx).getPlayerCards().addLast(prevCardId); 107 | //set as winner 108 | this.gameManager.getPlayerByIndex(playerInx).setWinner(playerInx); 109 | this.gameManager.getPlayerByIndex(playerInx).setWinnercards(currentPlayerCardId+"_"+prevCardId); 110 | this.gameManager.getPlayerByIndex(currentPlayerID).setWinner(playerInx); 111 | this.gameManager.getPlayerByIndex(currentPlayerID).setWinnercards(currentPlayerCardId+"_"+prevCardId); 112 | 113 | String currentCartId = this.gameManager.getPlayers().get(activePlayerId).getPlayerCards().getFirst(); 114 | this.gameManager.getPlayers().get(activePlayerId).setActivecardid(currentCartId); 115 | 116 | String cardInDeck = this.gameManager.getCardsPlayDeck().getFirst(); 117 | this.gameManager.getPlayerByIndex(playerInx).setDeckcard(cardInDeck); 118 | this.gameManager.getCardsPlayDeck().clear(); 119 | 120 | } 121 | //check if current card is greater 122 | else if(prevCardValue < currentCardValue) 123 | { 124 | 125 | 126 | String prevPlayerCardId = this.gameManager.getPlayerByIndex(playerInx).getPlayerCards().getFirst(); 127 | this.gameManager.getPlayerByIndex(playerInx).getPlayerCards().removeFirst(); 128 | this.gameManager.getPlayers().get(currentPlayerID).getPlayerCards().addLast(prevPlayerCardId); 129 | 130 | //set as winner 131 | this.gameManager.getPlayerByIndex(playerInx).setWinner(playerInx); 132 | this.gameManager.getPlayerByIndex(playerInx).setWinnercards(currentPlayerCardId+"_"+prevPlayerCardId); 133 | this.gameManager.getPlayerByIndex(currentPlayerID).setWinner(playerInx); 134 | this.gameManager.getPlayerByIndex(currentPlayerID).setWinnercards(currentPlayerCardId+"_"+prevPlayerCardId); 135 | 136 | 137 | String currentCartId = this.gameManager.getPlayerByIndex(playerInx).getPlayerCards().getFirst(); 138 | this.gameManager.getPlayerByIndex(playerInx).setActivecardid(currentCartId); 139 | 140 | String cardInDeck = this.gameManager.getCardsPlayDeck().getFirst(); 141 | this.gameManager.getPlayerByIndex(playerInx).setDeckcard(cardInDeck); 142 | this.gameManager.getCardsPlayDeck().clear(); 143 | 144 | 145 | } 146 | else if(prevCardValue == currentCardValue) 147 | { 148 | 149 | String PreviousePlayerCards[] = getWarCards(playerInx); 150 | String currentPlayerCards[] = getWarCards(currentPlayerID); 151 | 152 | int prevCardValue_4 = this.gameManager.getCardValueById(PreviousePlayerCards[3]); 153 | int currentCardValue_4 = this.gameManager.getCardValueById(currentPlayerCards[3]); 154 | //check who is the winner 155 | if(prevCardValue_4 > currentCardValue_4) 156 | { 157 | String result = CardsArrayToString(PreviousePlayerCards,currentPlayerCards); 158 | this.gameManager.getPlayerByIndex(playerInx).setWinner(1); 159 | this.gameManager.getPlayerByIndex(playerInx).setWinnercards(result); 160 | String currentCartId = this.gameManager.getPlayerByIndex(playerInx).getPlayerCards().getFirst(); 161 | this.gameManager.getPlayerByIndex(playerInx).setActivecardid(currentCartId); 162 | 163 | } 164 | else if(prevCardValue_4 < currentCardValue_4) 165 | { 166 | String result = CardsArrayToString(currentPlayerCards,PreviousePlayerCards); 167 | this.gameManager.getPlayerByIndex(currentPlayerID).setWinner(1); 168 | this.gameManager.getPlayerByIndex(currentPlayerID).setWinnercards(result); 169 | String currentCartId = this.gameManager.getPlayerByIndex(currentPlayerID).getPlayerCards().getFirst(); 170 | this.gameManager.getPlayerByIndex(currentPlayerID).setActivecardid(currentCartId); 171 | } 172 | else if(prevCardValue_4 == currentCardValue_4) 173 | { 174 | //TODO 175 | int test =0; 176 | } 177 | this.gameManager.getCardsPlayDeck().clear(); 178 | } 179 | } 180 | else 181 | { 182 | this.gameManager.getCardsPlayDeck().addFirst(currentPlayerCardId); 183 | this.gameManager.getPlayers().get(activePlayerId).getPlayerCards().removeFirst(); 184 | String currentCartId = this.gameManager.getPlayers().get(activePlayerId).getPlayerCards().getFirst(); 185 | this.gameManager.getPlayers().get(activePlayerId).setActivecardid(currentCartId); 186 | 187 | String cardInDeck = this.gameManager.getCardsPlayDeck().getFirst(); 188 | this.gameManager.getPlayers().get(activePlayerId).setDeckcard(cardInDeck); 189 | 190 | 191 | } 192 | 193 | //Check if there are winners for this game 194 | int prevPlayerCardsSize = this.gameManager.getPlayerByIndex(playerInx).getPlayerCards().size(); 195 | if(prevPlayerCardsSize==0) 196 | { 197 | //game is ended 198 | this.gameManager.getPlayerByIndex(playerInx).setEndgame(currentPlayerID); 199 | this.gameManager.getPlayerByIndex(currentPlayerID).setEndgame(currentPlayerID); 200 | 201 | } 202 | } 203 | else 204 | { 205 | activePlayerId =-1; 206 | } 207 | return activePlayerId; 208 | } 209 | private String CardsArrayToString(String[] cardsPrev,String[] cardsCurrent) 210 | { 211 | String result =""; 212 | for (String s: cardsPrev) { 213 | //Do your stuff here 214 | result+=s; 215 | result+="_"; 216 | 217 | } 218 | for (String s: cardsCurrent) { 219 | //Do your stuff here 220 | result+=s; 221 | result+="_"; 222 | 223 | } 224 | result = result.substring(0, result.length()-1); 225 | return result; 226 | } 227 | private String[] getWarCards(int playerID) 228 | { 229 | 230 | String prevPlayerCardId_1 = this.gameManager.getPlayerByIndex(playerID).getPlayerCards().getFirst(); 231 | this.gameManager.getPlayerByIndex(playerID).getPlayerCards().removeFirst(); 232 | String prevPlayerCardId_2 = this.gameManager.getPlayerByIndex(playerID).getPlayerCards().getFirst(); 233 | this.gameManager.getPlayerByIndex(playerID).getPlayerCards().removeFirst(); 234 | String prevPlayerCardId_3 = this.gameManager.getPlayerByIndex(playerID).getPlayerCards().getFirst(); 235 | this.gameManager.getPlayerByIndex(playerID).getPlayerCards().removeFirst(); 236 | //the fourth card is to play the war 237 | String prevPlayerCardId_4 = this.gameManager.getPlayerByIndex(playerID).getPlayerCards().getFirst(); 238 | this.gameManager.getPlayerByIndex(playerID).getPlayerCards().removeFirst(); 239 | 240 | return new String[]{prevPlayerCardId_1, prevPlayerCardId_2,prevPlayerCardId_3,prevPlayerCardId_4}; 241 | } 242 | private int getPreviousePlayerIndex(int _currentPlayerID) 243 | { 244 | //find out who is the previous player 245 | int playerInx = this.gameManager.getPlayerIndexByKey(_currentPlayerID); 246 | if(playerInx == 0) 247 | { 248 | int playerSize = this.gameManager.getPlayers().size(); 249 | playerInx = playerSize-1; 250 | } 251 | else 252 | { 253 | --playerInx; 254 | } 255 | return playerInx; 256 | } 257 | private Player setPlayerNewAttributes(String _userName,Channel channel,int nextEvent) 258 | { 259 | Player newPlayer = new Player(channel); 260 | newPlayer.setUserName(_userName); 261 | int id = GenerateUniqueId(); 262 | int count = getPlayerRegistretionCounter(); 263 | newPlayer.setRegistertionNum(count); 264 | newPlayer.setId(id); 265 | newPlayer.setEvent(nextEvent); 266 | setPlayerCards(newPlayer); 267 | setNewPlayerCardId(newPlayer); 268 | return newPlayer; 269 | } 270 | 271 | private void setPlayerInPlayersContainer(Player _player) 272 | { 273 | this.gameManager.getPlayers().put(_player.getId(), _player); 274 | } 275 | 276 | private void setPlayerCards(Player _player) 277 | { 278 | //this is only good for 2 players 279 | int len = this.gameManager.getCardsRandomize().length-1; 280 | if(_player.getId()==0) 281 | { 282 | for(int i=0;i<(len/2);i++) 283 | { 284 | _player.getPlayerCards().push(this.gameManager.getCardsRandomizeByIndex(i)); 285 | } 286 | } 287 | else if(_player.getId()==1) 288 | { 289 | for(int i=len;i>(len/2);i--) 290 | { 291 | _player.getPlayerCards().push(this.gameManager.getCardsRandomizeByIndex(i)); 292 | } 293 | } 294 | 295 | 296 | } 297 | 298 | 299 | private void setNewPlayerCardId(Player _player) 300 | { 301 | String cardId = _player.getPlayerCards().removeFirst(); 302 | _player.setActivecardid(cardId); 303 | } 304 | 305 | private int GenerateUniqueId() 306 | { 307 | int id = this.playerIdCounter; 308 | this.playerIdCounter++; 309 | return id; 310 | } 311 | 312 | private int getPlayerRegistretionCounter() 313 | { 314 | int count = this.playerRegistretionCounter; 315 | this.playerRegistretionCounter++; 316 | return count; 317 | } 318 | 319 | } 320 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/server/GameManager.java: -------------------------------------------------------------------------------- 1 | package com.server; 2 | 3 | import java.util.ArrayList; 4 | import java.util.Arrays; 5 | import java.util.Collections; 6 | import java.util.HashMap; 7 | import java.util.Iterator; 8 | import java.util.LinkedHashMap; 9 | import java.util.LinkedList; 10 | import java.util.List; 11 | import java.util.Map; 12 | import java.util.ResourceBundle; 13 | import java.util.Vector; 14 | import java.util.logging.Logger; 15 | 16 | 17 | 18 | public class GameManager { 19 | private final static Logger LOG = LoggerManager.GetLogger(GameServerMain.class.getName()); 20 | 21 | private final String[] cardsNotRandomBase = {"c1","c2","c3","c4","c5","c6","c7","c8","c9","c10","c11","c12","c13","c14","c15","c16","c17","c18","c19","c20","c21","c22","c23","c24","c25","c26","c27","c28","c29","c30","c31","c32","c33","c34","c35","c36","c37","c38","c39","c40","c41","c42","c43","c44","c45","c46","c47","c48","c49","c50","c51","c52","c53"}; 22 | private final String[] cardsRandomize; 23 | public final HashMap cardsMap; 24 | 25 | private volatile Map players; 26 | private LinkedList cardsPlayDeck; 27 | private final GameResponseDispatcher gameResponseDispatcher; 28 | 29 | 30 | public GameManager( ) 31 | { 32 | 33 | cardsMap = new HashMap(); 34 | setCardsHash(); 35 | final ResourceBundle configurationBundle = ResourceBundle.getBundle("configuration"); 36 | //hashmap with predictable iteration order 37 | players = new LinkedHashMap(); 38 | cardsPlayDeck = new LinkedList(); 39 | this.cardsRandomize = Arrays.copyOf(cardsNotRandomBase , cardsNotRandomBase .length); 40 | Collections.shuffle(Arrays.asList(cardsRandomize)); 41 | gameResponseDispatcher = new GameResponseDispatcher(this); 42 | } 43 | public GameResponseDispatcher getGameResponseDispatcher() { 44 | return gameResponseDispatcher; 45 | } 46 | 47 | public HashMap getCardsMap() { 48 | return cardsMap; 49 | } 50 | 51 | public LinkedList getCardsPlayDeck() { 52 | return cardsPlayDeck; 53 | } 54 | 55 | public void setCardsPlayDeck(LinkedList cardsPlayDeck) { 56 | this.cardsPlayDeck = cardsPlayDeck; 57 | } 58 | 59 | public int getPlayerIndexByKey(int playerKey) 60 | { 61 | 62 | int pos = new ArrayList(players.keySet()).indexOf(playerKey); 63 | return pos; 64 | } 65 | public Player getPlayerByIndex(int inx) 66 | { 67 | List l = new ArrayList(players.values()); 68 | Player p = l.get(inx); 69 | return p; 70 | } 71 | 72 | 73 | public Map getPlayers() { 74 | return players; 75 | } 76 | 77 | public void setPlayers(Map players) { 78 | this.players = players; 79 | } 80 | 81 | public String[] getCardsRandomize() { 82 | return cardsRandomize; 83 | } 84 | public String getCardsRandomizeByIndex(int i) { 85 | return cardsRandomize[i]; 86 | } 87 | 88 | public int getCardValueById(String cardId) 89 | { 90 | String card = this.cardsMap.get(cardId); 91 | String rightPart= card.split("_")[1]; 92 | String number = rightPart.split(".png")[0]; 93 | int cardIntVal = Integer.valueOf(number); 94 | return cardIntVal; 95 | } 96 | 97 | public int getNextActivePlayer(int currentActivePlayer) 98 | { 99 | int currentPlyInx = getPlayerIndexByKey(currentActivePlayer); 100 | int activePlayer = 0; 101 | if(currentPlyInx < (players.size()-1)) 102 | { 103 | ++activePlayer; 104 | } 105 | 106 | return activePlayer; 107 | } 108 | 109 | private void setCardsHash() 110 | { 111 | cardsMap.put("c1","cardClubsA_20.png"); 112 | cardsMap.put("c2","cardClubsJ_17.png"); 113 | cardsMap.put("c3","cardClubsK_19.png"); 114 | cardsMap.put("c4","cardClubsQ_18.png"); 115 | cardsMap.put("c5","cardDiamonds10_10.png"); 116 | cardsMap.put("c6","cardDiamonds2_2.png"); 117 | cardsMap.put("c7","cardDiamonds3_3.png"); 118 | cardsMap.put("c8","cardDiamonds4_4.png"); 119 | cardsMap.put("c9","cardDiamonds5_5.png"); 120 | cardsMap.put("c10","cardDiamonds6_6.png"); 121 | cardsMap.put("c11","cardDiamonds7_7.png"); 122 | cardsMap.put("c12","cardDiamonds8_8.png"); 123 | cardsMap.put("c13","cardDiamonds9_9.png"); 124 | cardsMap.put("c14","cardDiamondsA_20.png"); 125 | cardsMap.put("c15","cardDiamondsJ_17.png"); 126 | cardsMap.put("c16","cardDiamondsK_19.png"); 127 | cardsMap.put("c17","cardDiamondsQ_18.png"); 128 | cardsMap.put("c18","cardHearts10_10.png"); 129 | cardsMap.put("c19","cardHearts2_2.png"); 130 | cardsMap.put("c20","cardHearts3_3.png"); 131 | cardsMap.put("c21","cardHearts4_4.png"); 132 | cardsMap.put("c22","cardHearts5_5.png"); 133 | cardsMap.put("c23","cardHearts6_6.png"); 134 | cardsMap.put("c24","cardHearts7_7.png"); 135 | cardsMap.put("c25","cardHearts8_8.png"); 136 | cardsMap.put("c26","cardHearts9_9.png"); 137 | cardsMap.put("c27","cardHeartsA_20.png"); 138 | cardsMap.put("c28","cardHeartsJ_17.png"); 139 | cardsMap.put("c29","cardHeartsK_19.png"); 140 | cardsMap.put("c30","cardHeartsQ.png"); 141 | cardsMap.put("c31","cardJoker_21.png"); 142 | cardsMap.put("c32","cardSpades10_10.png"); 143 | cardsMap.put("c33","cardSpades2_2.png"); 144 | cardsMap.put("c34","cardSpades3_3.png"); 145 | cardsMap.put("c35","cardSpades4_4.png"); 146 | cardsMap.put("c36","cardSpades5_5.png"); 147 | cardsMap.put("c37","cardSpades6_6.png"); 148 | cardsMap.put("c38","cardSpades7_7.png"); 149 | cardsMap.put("c39","cardSpades8_8.png"); 150 | cardsMap.put("c40","cardSpades9_9.png"); 151 | cardsMap.put("c41","cardSpadesA_20.png"); 152 | cardsMap.put("c42","cardSpadesJ_17.png"); 153 | cardsMap.put("c43","cardSpadesK_19.png"); 154 | cardsMap.put("c44","cardSpadesQ_18.png"); 155 | cardsMap.put("c45","cardClubs10_10.png"); 156 | cardsMap.put("c46","cardClubs2_2.png"); 157 | cardsMap.put("c47","cardClubs3_3.png"); 158 | cardsMap.put("c48","cardClubs4_4.png"); 159 | cardsMap.put("c49","cardClubs5_5.png"); 160 | cardsMap.put("c50","cardClubs6_6.png"); 161 | cardsMap.put("c51","cardClubs7_7.png"); 162 | cardsMap.put("c52","cardClubs8_8.png"); 163 | cardsMap.put("c53","cardClubs9_9.png"); 164 | } 165 | 166 | 167 | } 168 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/server/GameResponseDispatcher.java: -------------------------------------------------------------------------------- 1 | package com.server; 2 | 3 | import java.util.Iterator; 4 | import java.util.Map; 5 | import java.util.Map.Entry; 6 | import java.util.logging.Logger; 7 | 8 | import com.json.JSONArray; 9 | import com.json.JSONObject; 10 | 11 | public class GameResponseDispatcher { 12 | private final static Logger LOG = LoggerManager.GetLogger(GameEventHandler.class.getName()); 13 | private GameManager gameManager; 14 | 15 | public GameResponseDispatcher(GameManager _gameManager) 16 | { 17 | this.gameManager = _gameManager; 18 | 19 | } 20 | public boolean ResponseDispatcheLoginDone(int _playerId) 21 | { 22 | int currentPlayerId = _playerId; 23 | Player currentPlayer = this.gameManager.getPlayers().get(currentPlayerId); 24 | 25 | JSONObject currentPlayerJsonObj = setPlayerToJson(currentPlayer, 26 | currentPlayer.getEvent(), 27 | currentPlayer.getId()); 28 | 29 | JSONObject currentPlayerJsonObj2 = setPlayerToJson(currentPlayer, 30 | currentPlayer.getEvent(), 31 | currentPlayer.getId()); 32 | 33 | //build the other players json 34 | JSONArray currentPlayerArrayNewPlayers = new JSONArray(); 35 | JSONArray ArrayCurrentPlayers = new JSONArray(); 36 | ArrayCurrentPlayers.put(currentPlayerJsonObj2); 37 | 38 | Iterator> it = this.gameManager.getPlayers().entrySet().iterator(); 39 | while (it.hasNext()) { 40 | @SuppressWarnings("rawtypes") 41 | Map.Entry pair = (Map.Entry)it.next(); 42 | Player playerIt = ((Player)pair.getValue()); 43 | 44 | 45 | if(currentPlayerId != playerIt.getId()) 46 | { 47 | this.gameManager.getPlayers().get(playerIt.getId()).setEvent(Config.NEW_USER_LOGIN_DONE); 48 | JSONObject playerJsonObjIt = setPlayerToJson(playerIt, 49 | Config.NEW_USER_LOGIN_DONE, 50 | playerIt.getId()); 51 | JSONObject newPlayerForCurrent = setPlayerToJson(playerIt, 52 | Config.NEW_USER_LOGIN_DONE, 53 | playerIt.getId()); 54 | //to current 55 | //LOG.severe(newPlayerForCurrent.toString()); 56 | currentPlayerArrayNewPlayers.put(newPlayerForCurrent); 57 | //LOG.severe(currentPlayerArrayNewPlayers.toString()); 58 | //to others 59 | playerJsonObjIt.put("players",ArrayCurrentPlayers); 60 | String jsonStr = playerJsonObjIt.toString(); 61 | //LOG.severe("jsonStr in while:"+jsonStr); 62 | this.gameManager.getPlayers().get(playerIt.getId()).setPlayerJson(jsonStr); 63 | //LOG.severe("currentPlayerArrayNewPlayers:"+currentPlayerArrayNewPlayers.toString()); 64 | } 65 | 66 | 67 | } 68 | //current user array 69 | //LOG.severe(currentPlayerArrayNewPlayers.toString()); 70 | currentPlayerJsonObj.put("players",currentPlayerArrayNewPlayers); 71 | String jsonStr = currentPlayerJsonObj.toString(); 72 | // LOG.severe("jsonStr:"+jsonStr); 73 | // LOG.severe("getPlayerJson() BEFOR:"+this.gameManager.getPlayers().get(currentPlayerId).getPlayerJson()); 74 | this.gameManager.getPlayers().get(currentPlayerId).setPlayerJson(jsonStr); 75 | // LOG.severe("getPlayerJson() AFTER:"+this.gameManager.getPlayers().get(currentPlayerId).getPlayerJson()); 76 | 77 | 78 | return true; 79 | } 80 | 81 | public boolean ResponseDispatchePlayDone(int _playerId) 82 | { 83 | int currentPlayerId = _playerId; 84 | this.gameManager.getPlayers().get(currentPlayerId).setEvent(Config.PLAY_DONE); 85 | int newActivePlayer = this.gameManager.getNextActivePlayer(currentPlayerId); 86 | this.gameManager.getPlayers().get(currentPlayerId).setActiveplayerid(newActivePlayer); 87 | 88 | Player currentPlayer = this.gameManager.getPlayers().get(currentPlayerId); 89 | 90 | JSONObject currentPlayerJsonObj = setPlayerToJson(currentPlayer, 91 | currentPlayer.getEvent(), 92 | currentPlayer.getId()); 93 | 94 | JSONObject currentPlayerJsonObj2 = setPlayerToJson(currentPlayer, 95 | currentPlayer.getEvent(), 96 | currentPlayer.getId()); 97 | 98 | 99 | //build the other players json 100 | JSONArray currentPlayerArrayNewPlayers = new JSONArray(); 101 | JSONArray ArrayCurrentPlayers = new JSONArray(); 102 | ArrayCurrentPlayers.put(currentPlayerJsonObj2); 103 | 104 | Iterator> it = this.gameManager.getPlayers().entrySet().iterator(); 105 | while (it.hasNext()) { 106 | @SuppressWarnings("rawtypes") 107 | Map.Entry pair = (Map.Entry)it.next(); 108 | Player playerIt = ((Player)pair.getValue()); 109 | 110 | 111 | if(currentPlayerId != playerIt.getId()) 112 | { 113 | 114 | //update each user 115 | this.gameManager.getPlayers().get(playerIt.getId()).setDeckcard(currentPlayer.getDeckcard()); 116 | this.gameManager.getPlayers().get(playerIt.getId()).setEvent(Config.PLAY_DONE); 117 | this.gameManager.getPlayers().get(playerIt.getId()).setActiveplayerid(newActivePlayer); 118 | 119 | JSONObject playerJsonObjIt = setPlayerToJson(playerIt, 120 | Config.PLAY_DONE, 121 | playerIt.getId()); 122 | JSONObject newPlayerForCurrent = setPlayerToJson(playerIt, 123 | Config.PLAY_DONE, 124 | playerIt.getId()); 125 | 126 | 127 | currentPlayerArrayNewPlayers.put(newPlayerForCurrent); 128 | //to others 129 | playerJsonObjIt.put("players",ArrayCurrentPlayers); 130 | String jsonStr = playerJsonObjIt.toString(); 131 | //LOG.severe("jsonStr in while:"+jsonStr); 132 | this.gameManager.getPlayers().get(playerIt.getId()).setPlayerJson(jsonStr); 133 | //LOG.severe("currentPlayerArrayNewPlayers:"+currentPlayerArrayNewPlayers.toString()); 134 | } 135 | 136 | 137 | } 138 | //current user array 139 | //LOG.severe(currentPlayerArrayNewPlayers.toString()); 140 | currentPlayerJsonObj.put("players",currentPlayerArrayNewPlayers); 141 | //String cardInDeck = this.gameManager.getCardsPlayDeck().getFirst(); 142 | //currentPlayerJsonObj.put("deck", cardInDeck); 143 | String jsonStr = currentPlayerJsonObj.toString(); 144 | // LOG.severe("jsonStr:"+jsonStr); 145 | // LOG.severe("getPlayerJson() BEFOR:"+this.gameManager.getPlayers().get(currentPlayerId).getPlayerJson()); 146 | this.gameManager.getPlayers().get(currentPlayerId).setPlayerJson(jsonStr); 147 | // LOG.severe("getPlayerJson() AFTER:"+this.gameManager.getPlayers().get(currentPlayerId).getPlayerJson()); 148 | 149 | return true; 150 | } 151 | 152 | @SuppressWarnings("unused") 153 | private JSONObject setPlayerToJson(final Player _player,final int event, 154 | final int _playerId) 155 | { 156 | JSONObject _jsonPlayer = new JSONObject(); 157 | _jsonPlayer.put("id",_playerId); 158 | _jsonPlayer.put("event",event); 159 | _jsonPlayer.put("username",_player.getUserName()); 160 | _jsonPlayer.put("activecardid",_player.getActivecardid()); 161 | _jsonPlayer.put("activeplayerid",_player.getActiveplayerid()); 162 | _jsonPlayer.put("registertionnum",_player.getRegistertionNum()); 163 | _jsonPlayer.put("winner",_player.getWinner()); 164 | _jsonPlayer.put("deck",_player.getDeckcard()); 165 | _jsonPlayer.put("endgame",_player.getEndgame()); 166 | _jsonPlayer.put("winnercards",_player.getWinnercards()); 167 | _jsonPlayer.put("numcardsleft",_player.getPlayerCards().size()); 168 | 169 | 170 | return _jsonPlayer; 171 | } 172 | } 173 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/server/GameServerInitializer.java: -------------------------------------------------------------------------------- 1 | package com.server; 2 | import io.netty.channel.Channel; 3 | import io.netty.channel.ChannelInitializer; 4 | import io.netty.channel.ChannelPipeline; 5 | import io.netty.channel.group.ChannelGroup; 6 | import io.netty.handler.codec.http.HttpObjectAggregator; 7 | import io.netty.handler.codec.http.HttpServerCodec; 8 | import io.netty.handler.codec.http.websocketx.WebSocketServerProtocolHandler; 9 | import io.netty.handler.stream.ChunkedWriteHandler; 10 | 11 | public class GameServerInitializer extends ChannelInitializer { 12 | private final GameManager gameManager; 13 | 14 | public GameServerInitializer(GameManager _gameManager) { 15 | this.gameManager = _gameManager; 16 | } 17 | 18 | @Override 19 | protected void initChannel(Channel ch) throws Exception { 20 | ChannelPipeline pipeline = ch.pipeline(); 21 | pipeline.addLast("HttpServerCodec",new HttpServerCodec()); 22 | pipeline.addLast("HttpObjectAggregator",new HttpObjectAggregator(64 * 1024)); 23 | pipeline.addLast("ChunkedWriteHandler",new ChunkedWriteHandler()); 24 | pipeline.addLast("WebSocketServerProtocolHandler",new WebSocketServerProtocolHandler("/ws")); 25 | pipeline.addLast("TextWebSocketFrameHandler",new TextWebSocketFrameHandler(gameManager, 26 | new GameEventHandler(gameManager))); 27 | 28 | 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/server/GameServerMain.java: -------------------------------------------------------------------------------- 1 | package com.server; 2 | 3 | import java.util.ResourceBundle; 4 | import java.util.logging.Logger; 5 | 6 | public class GameServerMain { 7 | private final static Logger LOG = LoggerManager.GetLogger(GameServerMain.class.getName()); 8 | public static void main(String[] args) { 9 | 10 | final ResourceBundle configurationBundle = ResourceBundle.getBundle("configuration"); 11 | int port = Integer.valueOf(configurationBundle.getString("port")); 12 | WebSocketServer pWebSocketServer = new WebSocketServer(); 13 | pWebSocketServer.start(port); 14 | LOG.info("server started"); 15 | 16 | } 17 | 18 | } 19 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/server/HttpRequestHandler.java: -------------------------------------------------------------------------------- 1 | package com.server; 2 | 3 | 4 | 5 | import io.netty.channel.ChannelFuture; 6 | import io.netty.channel.ChannelFutureListener; 7 | import io.netty.channel.ChannelHandlerContext; 8 | import io.netty.channel.DefaultFileRegion; 9 | import io.netty.channel.SimpleChannelInboundHandler; 10 | import io.netty.handler.codec.http.DefaultFullHttpResponse; 11 | import io.netty.handler.codec.http.DefaultHttpResponse; 12 | import io.netty.handler.codec.http.FullHttpRequest; 13 | import io.netty.handler.codec.http.FullHttpResponse; 14 | import io.netty.handler.codec.http.HttpHeaders; 15 | import io.netty.handler.codec.http.HttpResponse; 16 | import io.netty.handler.codec.http.HttpResponseStatus; 17 | import io.netty.handler.codec.http.HttpVersion; 18 | import io.netty.handler.codec.http.LastHttpContent; 19 | import io.netty.handler.ssl.SslHandler; 20 | import io.netty.handler.stream.ChunkedNioFile; 21 | 22 | import java.io.File; 23 | import java.io.RandomAccessFile; 24 | import java.net.URISyntaxException; 25 | import java.net.URL; 26 | 27 | 28 | public class HttpRequestHandler extends SimpleChannelInboundHandler { 29 | private final String wsUri; 30 | private static final File INDEX; 31 | 32 | static { 33 | URL location = HttpRequestHandler.class.getProtectionDomain().getCodeSource().getLocation(); 34 | try { 35 | String path = location.toURI() + "index.html"; 36 | path = !path.contains("file:") ? path : path.substring(5); 37 | INDEX = new File(path); 38 | } catch (URISyntaxException e) { 39 | throw new IllegalStateException("Unable to locate index.html", e); 40 | } 41 | } 42 | 43 | public HttpRequestHandler(String wsUri) { 44 | this.wsUri = wsUri; 45 | } 46 | 47 | @Override 48 | public void channelRead0(ChannelHandlerContext ctx, FullHttpRequest request) throws Exception { 49 | if (wsUri.equalsIgnoreCase(request.getUri())) { 50 | ctx.fireChannelRead(request.retain()); 51 | } else { 52 | if (HttpHeaders.is100ContinueExpected(request)) { 53 | send100Continue(ctx); 54 | } 55 | 56 | RandomAccessFile file = new RandomAccessFile(INDEX, "r"); 57 | 58 | HttpResponse response = new DefaultHttpResponse(request.getProtocolVersion(), HttpResponseStatus.OK); 59 | response.headers().set(HttpHeaders.Names.CONTENT_TYPE, "text/html; charset=UTF-8"); 60 | 61 | boolean keepAlive = HttpHeaders.isKeepAlive(request); 62 | 63 | if (keepAlive) { 64 | response.headers().set(HttpHeaders.Names.CONTENT_LENGTH, file.length()); 65 | response.headers().set(HttpHeaders.Names.CONNECTION, HttpHeaders.Values.KEEP_ALIVE); 66 | } 67 | ctx.write(response); 68 | 69 | if (ctx.pipeline().get(SslHandler.class) == null) { 70 | ctx.write(new DefaultFileRegion(file.getChannel(), 0, file.length())); 71 | } else { 72 | ctx.write(new ChunkedNioFile(file.getChannel())); 73 | } 74 | ChannelFuture future = ctx.writeAndFlush(LastHttpContent.EMPTY_LAST_CONTENT); 75 | if (!keepAlive) { 76 | future.addListener(ChannelFutureListener.CLOSE); 77 | } 78 | } 79 | } 80 | 81 | private static void send100Continue(ChannelHandlerContext ctx) { 82 | FullHttpResponse response = new DefaultFullHttpResponse(HttpVersion.HTTP_1_1, HttpResponseStatus.CONTINUE); 83 | ctx.writeAndFlush(response); 84 | } 85 | 86 | @Override 87 | public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) 88 | throws Exception { 89 | cause.printStackTrace(); 90 | ctx.close(); 91 | } 92 | } 93 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/server/LoggerManager.java: -------------------------------------------------------------------------------- 1 | package com.server; 2 | 3 | import java.io.IOException; 4 | import java.io.InputStream; 5 | import java.util.logging.LogManager; 6 | import java.util.logging.Logger; 7 | 8 | public class LoggerManager { 9 | private static final LogManager logManager = LogManager.getLogManager(); 10 | 11 | /* 12 | * Java static block always loads before constructors 13 | */ 14 | static { 15 | try { 16 | InputStream inputStream = ClassLoader.class.getResourceAsStream("/logger.properties"); 17 | 18 | logManager.readConfiguration(inputStream); 19 | 20 | } catch (IOException exception) { 21 | exception.printStackTrace(); 22 | } 23 | } 24 | 25 | public static Logger GetLogger(String str) 26 | { 27 | return Logger.getLogger(str); 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/server/Player.java: -------------------------------------------------------------------------------- 1 | package com.server; 2 | 3 | import java.util.LinkedList; 4 | import java.util.Vector; 5 | import java.util.logging.Logger; 6 | 7 | import com.json.JSONObject; 8 | 9 | import io.netty.channel.Channel; 10 | 11 | public class Player { 12 | private final static Logger LOG = LoggerManager.GetLogger(GameServerMain.class.getName()); 13 | private LinkedList PlayerCards; 14 | private String userName; 15 | private int Event; 16 | //Session channel 17 | private Channel channel; 18 | //Player Json massage 19 | private String playerJson; 20 | //the player which is active and has the turn 21 | private int activeplayerid; 22 | private int id; 23 | private String activecardid; 24 | private int registertionNum; 25 | private int winner; 26 | private String winnercards; 27 | private String deckcard; 28 | //mark the end game the value will be the winner id 29 | private int endgame; 30 | 31 | 32 | 33 | public Player() 34 | { 35 | this.channel = null; 36 | Init(); 37 | } 38 | 39 | public Player(Channel _channel) 40 | { 41 | this.channel = _channel; 42 | Init(); 43 | } 44 | 45 | public String getWinnercards() { 46 | return winnercards; 47 | } 48 | 49 | public void setWinnercards(String winnercards) { 50 | this.winnercards = winnercards; 51 | } 52 | 53 | public int getWinner() { 54 | return winner; 55 | } 56 | 57 | public void setWinner(int winner) { 58 | this.winner = winner; 59 | } 60 | 61 | public int getEndgame() { 62 | return endgame; 63 | } 64 | 65 | public void setEndgame(int endgame) { 66 | this.endgame = endgame; 67 | } 68 | 69 | private void Init() 70 | { 71 | this.setPlayerCards(new LinkedList()); 72 | this.winner =-1; 73 | this.winnercards=""; 74 | this.deckcard=""; 75 | this.endgame =-1; 76 | } 77 | 78 | public String getPlayerJson() { 79 | return playerJson; 80 | } 81 | 82 | public void setPlayerJson(String playerJson) { 83 | this.playerJson=""; 84 | this.playerJson = playerJson; 85 | } 86 | public String getDeckcard() { 87 | return deckcard; 88 | } 89 | 90 | public void setDeckcard(String deckcard) { 91 | this.deckcard = deckcard; 92 | } 93 | 94 | public int getActiveplayerid() { 95 | return activeplayerid; 96 | } 97 | 98 | public void setActiveplayerid(int activeplayerid) { 99 | this.activeplayerid = activeplayerid; 100 | } 101 | 102 | 103 | public void setChannel(Channel channel) { 104 | this.channel = channel; 105 | } 106 | public Channel getChannel() { 107 | return channel; 108 | } 109 | 110 | public String getUserName() { 111 | return userName; 112 | } 113 | public void setUserName(String userName) { 114 | this.userName = userName; 115 | } 116 | 117 | public LinkedList getPlayerCards() { 118 | return PlayerCards; 119 | } 120 | 121 | public void setPlayerCards(LinkedList playerCards) { 122 | PlayerCards = playerCards; 123 | } 124 | 125 | public int getEvent() { 126 | return Event; 127 | } 128 | 129 | public void setEvent(int event) { 130 | Event = event; 131 | } 132 | 133 | public int getId() { 134 | return id; 135 | } 136 | 137 | public void setId(int id) { 138 | this.id = id; 139 | } 140 | public String getActivecardid() { 141 | return activecardid; 142 | } 143 | 144 | public void setActivecardid(String activecardid) { 145 | this.activecardid = activecardid; 146 | } 147 | public int getRegistertionNum() { 148 | return registertionNum; 149 | } 150 | 151 | public void setRegistertionNum(int registertionNum) { 152 | this.registertionNum = registertionNum; 153 | } 154 | 155 | 156 | } 157 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/server/TextWebSocketFrameHandler.java: -------------------------------------------------------------------------------- 1 | package com.server; 2 | 3 | 4 | 5 | import java.util.ArrayList; 6 | import java.util.HashMap; 7 | import java.util.Iterator; 8 | import java.util.Map; 9 | import java.util.Map.Entry; 10 | import java.util.logging.Logger; 11 | 12 | import com.json.JSONObject; 13 | 14 | import io.netty.channel.ChannelHandler.Sharable; 15 | import io.netty.channel.ChannelHandlerContext; 16 | import io.netty.channel.SimpleChannelInboundHandler; 17 | 18 | import io.netty.handler.codec.http.websocketx.TextWebSocketFrame; 19 | import io.netty.handler.codec.http.websocketx.WebSocketServerProtocolHandler; 20 | import io.netty.util.AttributeKey; 21 | 22 | //@Sharable 23 | public class TextWebSocketFrameHandler extends SimpleChannelInboundHandler{ 24 | //private static final AttributeKey GameManagerAttribute = AttributeKey.valueOf("gameManager"); 25 | private final static Logger LOG = LoggerManager.GetLogger(GameServerMain.class.getName()); 26 | private GameManager gameManager; 27 | private GameEventHandler gameEventHandler; 28 | 29 | public TextWebSocketFrameHandler(GameManager _gameManager,GameEventHandler _gameEventHandler) { 30 | this.gameManager = _gameManager; 31 | this.gameEventHandler = _gameEventHandler; 32 | 33 | } 34 | public TextWebSocketFrameHandler() 35 | { 36 | ; 37 | } 38 | 39 | @Override 40 | public void userEventTriggered(ChannelHandlerContext ctx, Object evt) throws Exception { 41 | 42 | 43 | if (evt == WebSocketServerProtocolHandler.ServerHandshakeStateEvent.HANDSHAKE_COMPLETE) { 44 | 45 | ctx.pipeline().remove(HttpRequestHandler.class); 46 | JSONObject responseJson = new JSONObject(); 47 | responseJson.put("event",Config.HANDSHAKE_COMPLETE_SUCCESS); 48 | LOG.severe("HANDSHAKE_COMPLETE "+responseJson.toString()); 49 | ctx.channel().writeAndFlush(new TextWebSocketFrame(responseJson.toString())); 50 | 51 | 52 | } else { 53 | super.userEventTriggered(ctx, evt); 54 | } 55 | } 56 | 57 | @Override 58 | public void channelRead0(ChannelHandlerContext ctx, TextWebSocketFrame msg) throws Exception { 59 | msg.retain(); 60 | TextWebSocketFrame frame = (TextWebSocketFrame) msg; 61 | String jsonRequest = frame.text(); 62 | LOG.severe("Recived from client :"+jsonRequest); 63 | try { 64 | 65 | int playerId = this.gameEventHandler.handleEvent(jsonRequest,ctx.channel()); 66 | if(playerId !=-1) 67 | { 68 | this.gameEventHandler.ResponseDispatcher(playerId,jsonRequest); 69 | Iterator> it = this.gameManager.getPlayers().entrySet().iterator(); 70 | while (it.hasNext()) { 71 | @SuppressWarnings("rawtypes") 72 | Map.Entry pair = (Map.Entry)it.next(); 73 | Player playerIt = ((Player)pair.getValue()); 74 | String PlayerMassage = playerIt.getPlayerJson().toString(); 75 | responseToClient(playerIt,PlayerMassage); 76 | LOG.severe("Sending to client id:"+String.valueOf(playerIt.getId())+" name:"+playerIt.getUserName()+" json:" +PlayerMassage); 77 | } 78 | } 79 | else 80 | { 81 | LOG.severe("Sending to clients Failed playerId is -1"); 82 | } 83 | 84 | } finally { 85 | frame.release(); 86 | } 87 | } 88 | 89 | private void responseToClient(Player _player,String responseJson) 90 | { 91 | _player.getChannel().writeAndFlush(new TextWebSocketFrame(responseJson)); 92 | } 93 | } 94 | -------------------------------------------------------------------------------- /Server/CardWarNettyServer/src/com/server/WebSocketServer.java: -------------------------------------------------------------------------------- 1 | package com.server; 2 | 3 | import java.net.InetSocketAddress; 4 | import java.util.HashMap; 5 | import java.util.Map; 6 | 7 | import io.netty.bootstrap.ServerBootstrap; 8 | import io.netty.channel.Channel; 9 | import io.netty.channel.ChannelFuture; 10 | import io.netty.channel.ChannelInitializer; 11 | import io.netty.channel.EventLoopGroup; 12 | import io.netty.channel.group.ChannelGroup; 13 | import io.netty.channel.group.DefaultChannelGroup; 14 | import io.netty.channel.nio.NioEventLoopGroup; 15 | import io.netty.channel.socket.nio.NioServerSocketChannel; 16 | import io.netty.util.concurrent.ImmediateEventExecutor; 17 | 18 | public class WebSocketServer { 19 | 20 | private final ChannelGroup channelGroup = new DefaultChannelGroup(ImmediateEventExecutor.INSTANCE); 21 | private final EventLoopGroup group = new NioEventLoopGroup(); 22 | private final GameManager gameManager = new GameManager(); 23 | 24 | private Channel channel; 25 | 26 | public ChannelFuture start(int address) { 27 | ServerBootstrap bootstrap = new ServerBootstrap(); 28 | bootstrap.group(group) 29 | .channel(NioServerSocketChannel.class) 30 | .childHandler(createInitializer(gameManager)); 31 | ChannelFuture future = bootstrap.bind(new InetSocketAddress(address)); 32 | future.syncUninterruptibly(); 33 | channel = future.channel(); 34 | return future; 35 | } 36 | 37 | protected ChannelInitializer createInitializer(GameManager _gameManager) { 38 | return new GameServerInitializer(gameManager); 39 | } 40 | 41 | public void destroy() { 42 | if (channel != null) { 43 | channel.close(); 44 | } 45 | channelGroup.close(); 46 | group.shutdownGracefully(); 47 | } 48 | 49 | } 50 | --------------------------------------------------------------------------------