ServerInfo::ServerInfo(UserConfig& config) { memset(this, 0, sizeof(ServerInfo)); std::string tmp; tmp = config.getString("name"); strncpy(name, tmp.c_str(), sizeof(name) - 1); tmp = config.getString("description"); strncpy(description, tmp.c_str(), sizeof(description) - 1); gamespeed = config.getInteger("speed"); }
void ConfigItem::show() { UserConfig *dlg = static_cast<UserConfig*>(listView()->topLevelWidget()); if (m_widget == NULL){ m_widget = getWidget(dlg); if (m_widget == NULL) return; dlg->wnd->addWidget(m_widget, id() ? id() : defId++); dlg->wnd->setMinimumSize(dlg->wnd->sizeHint()); QObject::connect(dlg, SIGNAL(applyChanges()), m_widget, SLOT(apply())); } dlg->showUpdate(m_bShowUpdate); dlg->wnd->raiseWidget(m_widget); }
DuelMatch::DuelMatch(InputSource* linput, InputSource* rinput, bool global, bool remote):mLogic(createGameLogic("rules.lua")), mPaused(false), events(0), external_events(0), mRemote(remote) { mGlobal = global; if (mGlobal) { assert(mMainGame == 0); mMainGame = this; } mLeftInput = linput; mRightInput = rinput; mBallDown = false; mPhysicWorld.resetPlayer(); mPhysicWorld.step(); UserConfig gameConfig; gameConfig.loadFile("config.xml"); mLogic->setScoreToWin(gameConfig.getInteger("scoretowin")); };
int main(int argc, char* argv[]) { PHYSFS_init(argv[0]); setupPHYSFS(); SDL_Init(SDL_INIT_VIDEO | SDL_INIT_AUDIO | SDL_INIT_JOYSTICK); SDL_EnableUNICODE(1); atexit(SDL_Quit); srand(SDL_GetTicks()); // Default is OpenGL and false // choose renderer RenderManager *rmanager = 0; SoundManager *smanager = 0; try { UserConfig gameConfig; gameConfig.loadFile("config.xml"); TextManager::createTextManager(gameConfig.getString("language")); if(gameConfig.getString("device") == "SDL") rmanager = RenderManager::createRenderManagerSDL(); else if (gameConfig.getString("device") == "GP2X") rmanager = RenderManager::createRenderManagerGP2X(); else if (gameConfig.getString("device") == "OpenGL") rmanager = RenderManager::createRenderManagerGL2D(); else { std::cerr << "Warning: Unknown renderer selected!"; std::cerr << "Falling back to OpenGL" << std::endl; rmanager = RenderManager::createRenderManagerGL2D(); } // fullscreen? if(gameConfig.getString("fullscreen") == "true") rmanager->init(800, 600, true); else rmanager->init(800, 600, false); if(gameConfig.getString("show_shadow") == "true") rmanager->showShadow(true); else rmanager->showShadow(false); SpeedController scontroller(gameConfig.getFloat("gamefps")); SpeedController::setMainInstance(&scontroller); scontroller.setDrawFPS(gameConfig.getBool("showfps")); smanager = SoundManager::createSoundManager(); smanager->init(); smanager->setVolume(gameConfig.getFloat("global_volume")); smanager->setMute(gameConfig.getBool("mute")); smanager->playSound("sounds/bums.wav", 0.0); smanager->playSound("sounds/pfiff.wav", 0.0); std::string bg = std::string("backgrounds/") + gameConfig.getString("background"); if (PHYSFS_exists(bg.c_str())) rmanager->setBackground(bg); InputManager* inputmgr = InputManager::createInputManager(); if (argc == 3) { if (strstr(argv[1], ".lua")) { gameConfig.setString("left_player_human", "false"); gameConfig.setString("left_script_name", argv[1]); } else { gameConfig.setString("left_player_human", "true"); gameConfig.setString("left_player_name", argv[1]); } if (strstr(argv[2], ".lua")) { gameConfig.setString("right_player_human", "false"); gameConfig.setString("right_script_name", argv[2]); } else { gameConfig.setString("right_player_human", "true"); gameConfig.setString("right_player_name", argv[2]); } gameConfig.saveFile("config.xml"); State::setCurrentState(new LocalGameState(), true); } int running = 1; while (running) { inputmgr->updateInput(); running = inputmgr->running(); // This is true by default for compatibility, GUI states may // disable it if necessary rmanager->drawGame(true); IMGUI::getSingleton().begin(); State::getCurrentState()->step(); rmanager = &RenderManager::getSingleton(); //RenderManager may change //draw FPS: if (scontroller.getDrawFPS()) { // We need to ensure that the title bar is only set // when the framerate changed, because setting the // title can ne quite resource intensive on some // windows manager, like for example metacity. static int lastfps = 0; int newfps = scontroller.getFPS(); if (newfps != lastfps) { std::stringstream tmp; tmp << AppTitle << " FPS: " << newfps; rmanager->setTitle(tmp.str()); } lastfps = newfps; } if (!scontroller.doFramedrop()) { rmanager->draw(); IMGUI::getSingleton().end(); BloodManager::getSingleton().step(); rmanager->refresh(); } scontroller.update(); } } catch (std::exception& e) { std::cerr << e.what() << std::endl; if (rmanager) rmanager->deinit(); if (smanager) smanager->deinit(); SDL_Quit(); PHYSFS_deinit(); exit (EXIT_FAILURE); } deinit(); exit(EXIT_SUCCESS); }
int main(void) { ALLEGRO_COLOR background, active, inactive, info; old_dialog = NULL; cur_dialog = NULL; bool redraw = false; bool close_log = false; bool message_log = true; if (!al_init()) { abort_example("Could not init Allegro.\n"); } //open_log(); log_printf("Starting up log window.\n"); al_init_image_addon(); al_init_font_addon(); al_init_ttf_addon(); al_init_primitives_addon(); background = al_map_rgb(0,0,98); active = al_color_name("white"); inactive = al_color_name("gray"); info = al_color_name("red"); user_config.save_values(); user_config.load_file(); user_config.retrieve_values(); if((!user_config.map_path.empty()) && user_config.map_autoload) { populate_filenames(user_config.map_path, &path_list); load_bitmaps(&path_list, &map_list); } al_install_mouse(); al_install_keyboard(); al_set_new_display_flags(ALLEGRO_RESIZABLE); display = al_create_display(user_config.res_x, user_config.res_y); if (!display) { log_printf("failure.\n"); abort_example("Error creating display\n"); return 1; } ALLEGRO_BITMAP * isoicon = al_load_bitmap("isoworld/isoWorld.png"); if(isoicon) { al_set_display_icon(display, isoicon); } al_set_window_title(display, "IsoWorld"); log_printf("success.\n"); log_printf("Loading font '%s'...", "isoworld/DejaVuSans.ttf"); user_config.font = al_load_font("isoworld/DejaVuSans.ttf", 14, 0); if (!user_config.font) { log_printf("failure.\n"); abort_example("Error loading isoworld/DejaVuSans.ttf\n"); return 1; } log_printf("success.\n"); timer = al_create_timer(1.0 / 30); network_timer = al_create_timer(1.0); log_printf("Starting main loop.\n"); allegro_queue = al_create_event_queue(); al_register_event_source(allegro_queue, al_get_keyboard_event_source()); al_register_event_source(allegro_queue, al_get_mouse_event_source()); al_register_event_source(allegro_queue, al_get_display_event_source(display)); al_register_event_source(allegro_queue, al_get_timer_event_source(timer)); al_register_event_source(allegro_queue, al_get_timer_event_source(network_timer)); if (textlog) { al_register_event_source(allegro_queue, al_get_native_text_log_event_source( textlog)); } al_start_timer(timer); al_start_timer(network_timer); initializeAgui(); add_widgets(); MapSection test_map; test_map.set_size(user_config.map_width, user_config.map_height); minimap.reload(); test_map.load_tilesets("isoworld/tilesets.ini"); main_screen->UpdateTilesetList(&test_map); test_map.board_center_x = 0; test_map.board_top_y = 0; load_detailed_tiles(path_list.elevation_map, &test_map); int selection = 0; bool mapmove = 0; bool rightmove = 0; int mousemove_start_x = 0; int mousemove_start_y = 0; int mapmove_start_x = 0; int mapmove_start_y = 0; ALLEGRO_COLOR unselected = al_map_rgb(255,255,255); ALLEGRO_COLOR selected = al_map_rgb(128,128,128); ALLEGRO_KEYBOARD_STATE keys; while (1) { float h = al_get_display_height(display); float w = al_get_display_width(display); ALLEGRO_EVENT event; al_wait_for_event(allegro_queue, &event); if (event.type == ALLEGRO_EVENT_DISPLAY_CLOSE && !cur_dialog) break; if (event.type == ALLEGRO_EVENT_KEY_CHAR) { al_get_keyboard_state(&keys); if (event.keyboard.keycode == ALLEGRO_KEY_ESCAPE && !cur_dialog) break; else if (event.keyboard.keycode == ALLEGRO_KEY_UP && !cur_dialog) { if(al_key_down(&keys, ALLEGRO_KEY_LSHIFT) || al_key_down(&keys, ALLEGRO_KEY_RSHIFT)) user_config.map_y-=10; else user_config.map_y--; continue; } else if (event.keyboard.keycode == ALLEGRO_KEY_DOWN && !cur_dialog) { if(al_key_down(&keys, ALLEGRO_KEY_LSHIFT) || al_key_down(&keys, ALLEGRO_KEY_RSHIFT)) user_config.map_y+=10; else user_config.map_y++; continue; } else if (event.keyboard.keycode == ALLEGRO_KEY_RIGHT && !cur_dialog) { if(al_key_down(&keys, ALLEGRO_KEY_LSHIFT) || al_key_down(&keys, ALLEGRO_KEY_RSHIFT)) user_config.map_x+=10; else user_config.map_x++; continue; } else if (event.keyboard.keycode == ALLEGRO_KEY_LEFT && !cur_dialog) { if(al_key_down(&keys, ALLEGRO_KEY_LSHIFT) || al_key_down(&keys, ALLEGRO_KEY_RSHIFT)) user_config.map_x-=10; else user_config.map_x--; continue; } else if (event.keyboard.keycode == ALLEGRO_KEY_F5 && !cur_dialog) { saveScreenshot(); continue; } else if (event.keyboard.keycode == ALLEGRO_KEY_G && !cur_dialog) { user_config.showgrid = !user_config.showgrid; continue; } else if (event.keyboard.keycode == ALLEGRO_KEY_Q && !cur_dialog) { if(user_config.ray_distance > 1) user_config.ray_distance --; continue; } else if (event.keyboard.keycode == ALLEGRO_KEY_W && !cur_dialog) { user_config.ray_distance++; continue; } else if (event.keyboard.keycode == ALLEGRO_KEY_D && !cur_dialog) { user_config.debugmode = !user_config.debugmode; continue; } } /* When a mouse button is pressed, and no native dialog is * shown already, we show a new one. */ if(event.type == ALLEGRO_EVENT_MOUSE_BUTTON_UP) { mapmove = false; rightmove = false; } if(event.type == ALLEGRO_EVENT_MOUSE_AXES) { if(mapmove) { if ((event.mouse.x >= w - user_config.minimap_size) && (event.mouse.y >= user_config.minimap_size)) { mapmove = true; int relx = event.mouse.x - w + user_config.minimap_size -1; int rely = event.mouse.y - h + user_config.minimap_size -1; user_config.map_x = (float)al_get_bitmap_width(map_list.biome_map)/user_config.minimap_size * relx - user_config.map_width/2; user_config.map_y = (float)al_get_bitmap_height(map_list.biome_map)/user_config.minimap_size * rely - user_config.map_height/2; } else mapmove = false; } if(rightmove) { user_config.map_x = mapmove_start_x - ((event.mouse.x - mousemove_start_x) / test_map.tileset_list[test_map.current_tileset].tile_width) - ((event.mouse.y - mousemove_start_y) / test_map.tileset_list[test_map.current_tileset].tile_height); user_config.map_y = mapmove_start_y + ((event.mouse.x - mousemove_start_x) / test_map.tileset_list[test_map.current_tileset].tile_width) - ((event.mouse.y - mousemove_start_y) / test_map.tileset_list[test_map.current_tileset].tile_height); } } if (event.type == ALLEGRO_EVENT_MOUSE_BUTTON_DOWN) { //log_printf("Mouse clicked at %d,%d.\n", event.mouse.x, event.mouse.y); if(event.mouse.button == 2) { rightmove = true; mousemove_start_x = event.mouse.x; mousemove_start_y = event.mouse.y; mapmove_start_x = user_config.map_x; mapmove_start_y = user_config.map_y; } else if ((event.mouse.x >= w - user_config.minimap_size) && (event.mouse.y >= user_config.minimap_size)) { mapmove = true; int relx = event.mouse.x - w + user_config.minimap_size -1; int rely = event.mouse.y - h + user_config.minimap_size -1; user_config.map_x = (float)al_get_bitmap_width(map_list.biome_map)/user_config.minimap_size * relx - user_config.map_width/2; user_config.map_y = (float)al_get_bitmap_height(map_list.biome_map)/user_config.minimap_size * rely - user_config.map_height/2; } else if (event.mouse.y > 30) { if (event.mouse.y > h - 30) { message_log = !message_log; if (message_log) { textlog = al_open_native_text_log("Log", 0); if (textlog) { al_register_event_source(allegro_queue, al_get_native_text_log_event_source(textlog)); } } else { close_log = true; } } } } /* We receive this event from the other thread when the dialog is * closed. */ if (event.type == ASYNC_DIALOG_EVENT1) { al_unregister_event_source(allegro_queue, &cur_dialog->event_source); /* If files were selected, we replace the old files list. * Otherwise the dialog was cancelled, and we keep the old results. */ if (al_get_native_file_dialog_count(cur_dialog->file_dialog) > 0) { if (old_dialog) stop_async_dialog(old_dialog); old_dialog = cur_dialog; } else { stop_async_dialog(cur_dialog); } cur_dialog = NULL; } if (event.type == ALLEGRO_EVENT_NATIVE_DIALOG_CLOSE) { close_log = true; } if (event.type == ALLEGRO_EVENT_TIMER) { if(event.timer.source == timer) redraw = true; else if(event.timer.source == network_timer) { if(connection_state) { al_stop_timer(network_timer); //wait at least a second between the end of load and the start of the next, not between the start and start. connection_state->net_request.set_save_folder(current_save); if(!color_list.has_names){ if(connection_state->MaterialInfoCall(&connection_state->net_request, &connection_state->net_material_names) == DFHack::command_result::CR_OK) { if(connection_state->net_material_names.available()) { color_list.import_names(&connection_state->net_material_names); if(!color_list.has_colors) { color_list.import_colors("isoworld/material_colors.ini"); } } } else { delete connection_state; connection_state = NULL; goto EXIT_LOOP; } } if(connection_state->EmbarkInfoCall(&connection_state->net_request, &connection_state->net_reply) == DFHack::command_result::CR_OK) { if(connection_state->net_reply.available()) { if(center_on_loaded_map) { user_config.map_x = connection_state->net_reply.region_x() + (connection_state->net_reply.region_size_x() / 2) - (user_config.map_width / 2); user_config.map_y = connection_state->net_reply.region_y() + (connection_state->net_reply.region_size_y() / 2) - (user_config.map_height / 2); } for(int yy = 0; yy < connection_state->net_reply.region_size_y(); yy++) { for(int xx = 0; xx < connection_state->net_reply.region_size_x(); xx++) { if(!test_map.query_tile(&connection_state->net_reply, xx, yy)) continue; connection_state->net_tile_request.set_want_x(xx); connection_state->net_tile_request.set_want_y(yy); if(connection_state->EmbarkTileCall(&connection_state->net_tile_request, &connection_state->net_embark_tile) == DFHack::command_result::CR_OK) { if(!connection_state->net_embark_tile.is_valid()) continue; test_map.make_tile(&connection_state->net_embark_tile, &connection_state->net_reply); goto EXIT_LOOP; } else { delete connection_state; connection_state = NULL; goto EXIT_LOOP; } } } } } else { delete connection_state; connection_state = NULL; goto EXIT_LOOP; } EXIT_LOOP: ; al_start_timer(network_timer); } } } if (event.type == ALLEGRO_EVENT_DISPLAY_RESIZE) { al_acknowledge_resize(event.display.source); user_config.res_x = al_get_display_width(display); user_config.res_y = al_get_display_height(display); //Resize Agui gui->resizeToDisplay(); redraw = true; } if (redraw && al_is_event_queue_empty(allegro_queue)) { float x = al_get_display_width(display) / 2; float y = 0; redraw = false; al_clear_to_color(background); al_set_blender(ALLEGRO_ADD, ALLEGRO_ALPHA, ALLEGRO_INVERSE_ALPHA); if (old_dialog) { if(old_dialog->newimages) { show_files_list(old_dialog->file_dialog, user_config.font, info); old_dialog->newimages = 0; for(int i=0;i<test_map.tileset_list.size();i++){ delete test_map.tileset_list[test_map.current_tileset].rendered_map; test_map.tileset_list[test_map.current_tileset].rendered_map = NULL; } load_detailed_tiles(path_list.elevation_map, &test_map); } } test_map.propogate_tiles(&map_list); test_map.draw(al_get_display_width(display) / 2, (al_get_display_height(display) / 2) + user_config.map_shift); minimap.draw(); if(user_config.debugmode) { test_map.draw_debug_info(); al_draw_textf(user_config.font, cur_dialog ? inactive : active, 0, y, ALLEGRO_ALIGN_LEFT, "Drawtime: %dms", test_map.draw_time); al_draw_textf(user_config.font, cur_dialog ? inactive : active, 0, y + al_get_font_line_height(user_config.font), ALLEGRO_ALIGN_LEFT, "Load Time: %dms", test_map.load_time); al_draw_textf(user_config.font, cur_dialog ? inactive : active, 0, y + al_get_font_line_height(user_config.font)*2, ALLEGRO_ALIGN_LEFT, "Fetch Time: %dms", test_map.tile_fetch_time); } gui->logic(); render_gui(); al_flip_display(); } if (close_log && textlog) { close_log = false; message_log = false; al_unregister_event_source(allegro_queue, al_get_native_text_log_event_source(textlog)); al_close_native_text_log(textlog); textlog = NULL; } //Let Agui process the event last, because f**k Agui inputHandler->processEvent(event); } log_printf("Exiting.\n"); if(connection_state) { delete connection_state; connection_state = NULL; } imagelist.unload_bitmaps(); user_config.save_values(); user_config.save_file(); al_destroy_event_queue(allegro_queue); stop_async_dialog(old_dialog); stop_async_dialog(cur_dialog); return 0; }
int main(int argc, char* argv[]) #endif { DEBUG_STATUS("started main"); FileSystem filesys(argv[0]); setupPHYSFS(); DEBUG_STATUS("physfs initialised"); SDL_Init(SDL_INIT_VIDEO | SDL_INIT_AUDIO | SDL_INIT_JOYSTICK); DEBUG_STATUS("SDL initialised"); atexit(SDL_Quit); srand(SDL_GetTicks()); // Default is OpenGL and false // choose renderer RenderManager *rmanager = 0; SoundManager *smanager = 0; // Test Version Startup Warning #ifdef TEST_VERSION struct tm* ptm; time_t time = std::time(0); ptm = gmtime ( &time ); if( ptm->tm_year > (2014-1900) || ptm->tm_mon >= 4 ) { SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "TEST VERISON OUTDATED", (std::string("This is a test version of ") + AppTitle + " which expired on " "1.04.2014. Please visit blobby.sourceforge.net for a newer version").c_str(), 0); return -1; } SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_INFORMATION, "TEST VERISON WARNING", (std::string("This is a test version of ") + AppTitle + " for testing only.\n" "It might be unstable and/or incompatible to the current release. " "Use of this version is limited to 1.04.2014.\nUntil then, " "the final version will most likely be released and you should update to that one.\n" "Visit blobby.sourceforge.net for more information or bug reporting.").c_str(), 0); #endif try { UserConfig gameConfig; gameConfig.loadFile("config.xml"); TextManager::createTextManager(gameConfig.getString("language")); if(gameConfig.getString("device") == "SDL") rmanager = RenderManager::createRenderManagerSDL(); /*else if (gameConfig.getString("device") == "GP2X") rmanager = RenderManager::createRenderManagerGP2X();*/ #ifndef __ANDROID__ #ifndef __APPLE__ else if (gameConfig.getString("device") == "OpenGL") rmanager = RenderManager::createRenderManagerGL2D(); else { std::cerr << "Warning: Unknown renderer selected!"; std::cerr << "Falling back to OpenGL" << std::endl; rmanager = RenderManager::createRenderManagerGL2D(); } #else #if MAC_OS_X else if (gameConfig.getString("device") == "OpenGL") rmanager = RenderManager::createRenderManagerGL2D(); else { std::cerr << "Warning: Unknown renderer selected!"; std::cerr << "Falling back to OpenGL" << std::endl; rmanager = RenderManager::createRenderManagerGL2D(); } #endif #endif #endif // fullscreen? if(gameConfig.getString("fullscreen") == "true") rmanager->init(BASE_RESOLUTION_X, BASE_RESOLUTION_Y, true); else rmanager->init(BASE_RESOLUTION_X, BASE_RESOLUTION_Y, false); if(gameConfig.getString("show_shadow") == "true") rmanager->showShadow(true); else rmanager->showShadow(false); SpeedController scontroller(gameConfig.getFloat("gamefps")); SpeedController::setMainInstance(&scontroller); scontroller.setDrawFPS(gameConfig.getBool("showfps")); smanager = SoundManager::createSoundManager(); smanager->init(); smanager->setVolume(gameConfig.getFloat("global_volume")); smanager->setMute(gameConfig.getBool("mute")); /// \todo play sound is misleading. what we actually want to do is load the sound smanager->playSound("sounds/bums.wav", 0.0); smanager->playSound("sounds/pfiff.wav", 0.0); std::string bg = std::string("backgrounds/") + gameConfig.getString("background"); if ( FileSystem::getSingleton().exists(bg) ) rmanager->setBackground(bg); InputManager* inputmgr = InputManager::createInputManager(); int running = 1; DEBUG_STATUS("starting mainloop"); while (running) { inputmgr->updateInput(); running = inputmgr->running(); IMGUI::getSingleton().begin(); State::step(); rmanager = &RenderManager::getSingleton(); //RenderManager may change //draw FPS: static int lastfps = 0; if (scontroller.getDrawFPS()) { // We need to ensure that the title bar is only set // when the framerate changed, because setting the // title can ne quite resource intensive on some // windows manager, like for example metacity. int newfps = scontroller.getFPS(); if (newfps != lastfps) { std::stringstream tmp; tmp << AppTitle << " FPS: " << newfps; rmanager->setTitle(tmp.str()); } lastfps = newfps; } // Dirty workarround for hiding fps in title if (!scontroller.getDrawFPS() && (lastfps != -1)) { std::stringstream tmp; tmp << AppTitle; rmanager->setTitle(tmp.str()); lastfps = -1; } if (!scontroller.doFramedrop()) { rmanager->draw(); IMGUI::getSingleton().end(); BloodManager::getSingleton().step(); rmanager->refresh(); } scontroller.update(); } }
void Player::loadFromConfig(const std::string& prefix, bool initInput) { UserConfig gameConfig; gameConfig.loadFile("config.xml"); // init local input if(initInput){ if (gameConfig.getBool(prefix + "_player_human")) { mInputSource = new LocalInputSource(mPlayerSide); } else { mInputSource = new ScriptedInputSource("scripts/" + gameConfig.getString(prefix + "_script_name"), mPlayerSide, gameConfig.getInteger(prefix + "_script_strength")); } mName = gameConfig.getBool(prefix + "_player_human") ? gameConfig.getString(prefix + "_player_name") : gameConfig.getString(prefix + "_script_name"); }else{ // input is set externally (network) // so we need not to create any input source mInputSource = 0; // don't use bot name if extern input is used mName = gameConfig.getString(prefix + "_player_name"); } mInitialised = true; mStaticColor = Color( gameConfig.getInteger(prefix + "_blobby_color_r"), gameConfig.getInteger(prefix + "_blobby_color_g"), gameConfig.getInteger(prefix + "_blobby_color_b")); mOscillating = gameConfig.getBool(prefix + "_blobby_oscillate"); mInitialised = true; }
void NetworkSearchState::step_impl() { packet_ptr packet; // set to true to initiate server connection bool doEnterServer = false; for (ClientList::iterator iter = mQueryClients.begin(); iter != mQueryClients.end(); ++iter) { bool skip = false; bool skip_iter = false; while ((packet = (*iter)->Receive()) && !skip) { switch(packet->data[0]) { case ID_CONNECTION_REQUEST_ACCEPTED: { printf("connection accepted from %s:%d\n", mPingClient->PlayerIDToDottedIP( packet->playerId), packet->playerId.port); RakNet::BitStream stream; stream.Write((unsigned char)ID_BLOBBY_SERVER_PRESENT); stream.Write(BLOBBY_VERSION_MAJOR); stream.Write(BLOBBY_VERSION_MINOR); (*iter)->Send(&stream, LOW_PRIORITY, RELIABLE_ORDERED, 0); break; } case ID_BLOBBY_SERVER_PRESENT: { //FIXME: We must copy the needed informations, so that we can call DeallocatePacket(packet) //FIXME: The client finds a server at this point, which is not valid RakNet::BitStream stream((char*)packet->data, packet->length, false); stream.IgnoreBytes(1); //ID_BLOBBY_SERVER_PRESENT ServerInfo info(stream, (*iter)->PlayerIDToDottedIP(packet->playerId), packet->playerId.port); printf("server %s at %s is a blobby server\n", info.name, info.hostname); // check that the packet sizes match if(packet->length == ServerInfo::BLOBBY_SERVER_PRESENT_PACKET_SIZE) { if (std::find( mScannedServers.begin(), mScannedServers.end(), info) == mScannedServers.end() ) { mScannedServers.push_back(info); // check whether this was a direct connect server if(*iter == mDirectConnectClient) { mSelectedServer = mScannedServers.size() - 1; doEnterServer = true; } } else { std::cout << "duplicate server entry\n"; std::cout << info << "\n"; } } else { std::cout << " server invalid " << packet->length << " " << ServerInfo::BLOBBY_SERVER_PRESENT_PACKET_SIZE << "\n"; } // the RakClient will be deleted, so // we must free the packet here packet.reset(); (*iter)->Disconnect(50); delete *iter; iter = mQueryClients.erase(iter); if (iter == mQueryClients.end()) skip_iter = true; skip = true; // if one server is the one this PC is hosting, auto connect if( mHostedServer && std::string(info.hostname) == mHostedServer->hostname && info.port == mHostedServer->port) { switchState(new LobbyState(info, dynamic_cast<OnlineSearchState*>(this) == nullptr ? PreviousState::LAN : PreviousState::ONLINE) ); return; } break; } case ID_VERSION_MISMATCH: { // this packet is send when the client is older than the server! // so RakNet::BitStream stream((char*)packet->data, packet->length, false); stream.IgnoreBytes(1); // ID_VERSION_MISMATCH // default values if server does not send versions. // thats the 0.9 behaviour int smajor = 0, sminor = 9; stream.Read(smajor); // load server version information stream.Read(sminor); printf("found blobby server with version %d.%d\n", smajor, sminor); mDisplayUpdateNotification = true; // the RakClient will be deleted, so // we must free the packet here packet.reset(); (*iter)->Disconnect(50); delete *iter; iter = mQueryClients.erase(iter); if (iter == mQueryClients.end()) skip_iter = true; skip = true; break; } default: break; } if (skip) break; } if (skip_iter) break; } while (packet = mPingClient->Receive()) { switch (packet->data[0]) { case ID_PONG: { std::string hostname = mPingClient->PlayerIDToDottedIP(packet->playerId); printf("got ping response by \"%s:%d\", trying to connect\n", hostname.c_str(), packet->playerId.port); RakClient* newClient = new RakClient; newClient->Connect( hostname.c_str(), packet->playerId.port, 0, 0, RAKNET_THREAD_SLEEP_TIME); mQueryClients.push_back(newClient); } default: break; } } IMGUI& imgui = IMGUI::getSingleton(); imgui.doCursor(); imgui.doImage(GEN_ID, Vector2(400.0, 300.0), "background"); imgui.doOverlay(GEN_ID, Vector2(0.0, 0.0), Vector2(800.0, 600.0)); imgui.doInactiveMode(false); if (mDisplayInfo || mEnteringServer) { imgui.doInactiveMode(true); } if (imgui.doButton(GEN_ID, Vector2(10, 20), TextManager::NET_SERVER_SCAN)) searchServers(); if (imgui.doButton(GEN_ID, Vector2(420, 20), TextManager::NET_DIRECT_CONNECT) && !mEnteringServer) { mEnteringServer = true; imgui.resetSelection(); mEnteredServer = ""; mServerBoxPosition = 0; } std::vector<std::string> servernames; for (unsigned int i = 0; i < mScannedServers.size(); i++) { servernames.push_back(std::string(mScannedServers[i].name) + " (" + boost::lexical_cast<std::string>(mScannedServers[i].waitingplayers) + ")" ); } if( imgui.doSelectbox(GEN_ID, Vector2(25.0, 60.0), Vector2(775.0, 470.0), servernames, mSelectedServer) == SBA_DBL_CLICK ) { doEnterServer = true; } if (imgui.doButton(GEN_ID, Vector2(50, 480), TextManager::NET_SERVER_INFO) && !mDisplayInfo && !mScannedServers.empty()) { mDisplayInfo = true; imgui.resetSelection(); } if (mEnteringServer) { imgui.doInactiveMode(false); imgui.doOverlay(GEN_ID, Vector2(100.0, 200.0), Vector2(650.0, 400.0)); // Game crashes if the mEnteredServer is not a possible input imgui.doEditbox(GEN_ID, Vector2(130.0, 210.0), 20, mEnteredServer, mServerBoxPosition); if (imgui.doButton(GEN_ID, Vector2(270.0, 300.0), TextManager::LBL_OK)) { /// \todo adapt direct connect std::string server = mEnteredServer; int port = BLOBBY_PORT; std::size_t found = mEnteredServer.find(':'); if (found != std::string::npos) { server = mEnteredServer.substr(0, found); try { port = boost::lexical_cast<int>(mEnteredServer.substr(found+1)); } catch (boost::bad_lexical_cast) { /// \todo inform the user that default port was selected } if ((port <= 0) || (port > 65535)) port = BLOBBY_PORT; } // add this address / port info as client mDirectConnectClient = new RakClient; mDirectConnectClient->Connect(server.c_str(), port, 0, 0, RAKNET_THREAD_SLEEP_TIME); mQueryClients.push_back( mDirectConnectClient ); mEnteringServer = false; imgui.resetSelection(); } if (imgui.doButton(GEN_ID, Vector2(370.0, 300.0), TextManager::LBL_CANCEL)) { mEnteringServer = false; imgui.resetSelection(); } imgui.doInactiveMode(true); } if (mDisplayInfo) { imgui.doInactiveMode(false); imgui.doOverlay(GEN_ID, Vector2(40.0, 80.0), Vector2(760.0, 440.0), Color(0,0,0), 1.0); imgui.doText(GEN_ID, Vector2(50, 100), mScannedServers[mSelectedServer].name); imgui.doText(GEN_ID, Vector2(50, 130), mScannedServers[mSelectedServer].hostname); std::stringstream activegames; activegames << TextManager::getSingleton()->getString(TextManager::NET_ACTIVE_GAMES) << mScannedServers[mSelectedServer].activegames; imgui.doText(GEN_ID, Vector2(50, 160), activegames.str()); std::stringstream waitingplayer; waitingplayer << TextManager::getSingleton()->getString(TextManager::NET_WAITING_PLAYER) << mScannedServers[mSelectedServer].waitingplayers; imgui.doText(GEN_ID, Vector2(50, 190), waitingplayer.str()); std::string description = mScannedServers[mSelectedServer].description; for (unsigned int i = 0; i < description.length(); i += 29) { imgui.doText(GEN_ID, Vector2(50, 250 + i / 29 * 30), description.substr(i, 29)); } if (imgui.doButton(GEN_ID, Vector2(410, 405), TextManager::LBL_OK)) { mDisplayInfo = false; imgui.resetSelection(); } imgui.doInactiveMode(true); } if (imgui.doButton(GEN_ID, Vector2(450, 480), TextManager::NET_HOST_GAME) && !mDisplayInfo) { auto server_func = []() { // read config /// \todo we need read-only access here! UserConfig config; config.loadFile("config.xml"); PlayerSide localSide = (PlayerSide)config.getInteger("network_side"); PlayerIdentity local_player = config.loadPlayerIdentity(localSide, true); ServerInfo info( local_player.getName().c_str()); std::vector<std::string> rule_vec{config.getString("rules")}; DedicatedServer server(info, rule_vec, std::vector<float>{ SpeedController::getMainInstance()->getGameSpeed() }, 4, true); SpeedController scontroller( 10 ); gKillHostThread = false; while(!gKillHostThread) { // now run the server if(server.hasActiveGame()) { server.allowNewPlayers(false); } server.processPackets(); server.updateGames(); scontroller.update(); } }; gKillHostThread = true; gHostedServerThread = boost::make_shared<std::thread>(server_func); SDL_Delay(100); // give the server some time to start up. // might cause a slight visible delay, but I think we can // live with that right now. searchServers(); // getting the server info UserConfig config; config.loadFile("config.xml"); PlayerIdentity local_player = config.loadPlayerIdentity((PlayerSide)config.getInteger("network_side"), true); mHostedServer.reset(new ServerInfo( local_player.getName().c_str())); std::strncpy(mHostedServer->hostname, mPingClient->PlayerIDToDottedIP(mPingClient->GetInternalID()), sizeof(mHostedServer->hostname)); } if ((imgui.doButton(GEN_ID, Vector2(230, 530), TextManager::LBL_OK) && !mScannedServers.empty()) || doEnterServer) { ServerInfo server = mScannedServers[mSelectedServer]; switchState(new LobbyState(server, dynamic_cast<OnlineSearchState*>(this) == nullptr ? PreviousState::LAN : PreviousState::ONLINE)); } if (imgui.doButton(GEN_ID, Vector2(480, 530), TextManager::LBL_CANCEL)) { switchState(new MainMenuState); } if(mDisplayUpdateNotification) { imgui.doOverlay(GEN_ID, Vector2(71, 572), Vector2(729, 590), Color(128, 0, 0)); imgui.doText(GEN_ID, Vector2(85, 577), TextManager::UPDATE_NOTIFICATION, TF_SMALL_FONT); } }