void EngineMain::runGameLoop(const bpo::variables_map& variables, const std::string& pathEXE) { FALevelGen::FAsrand(static_cast<int> (time(nullptr))); FAWorld::Player* player; FARender::Renderer& renderer = *FARender::Renderer::get(); Settings::Settings settings; if(!settings.loadUserSettings()) return; std::string characterClass = variables["character"].as<std::string>(); DiabloExe::DiabloExe exe(pathEXE); if (!exe.isLoaded()) { renderer.stop(); return; } FAWorld::ItemManager& itemManager = FAWorld::ItemManager::get(); FAWorld::World world(exe); FAWorld::PlayerFactory playerFactory(exe); bool isServer = variables["mode"].as<std::string>() == "server"; if(isServer) world.generateLevels(); itemManager.loadItems(&exe); player = playerFactory.create(characterClass); world.addCurrentPlayer(player); if (variables["invuln"].as<std::string>() == "on") player->setInvuln(true); mInputManager->registerKeyboardObserver(&world); mInputManager->registerMouseObserver(&world); int32_t currentLevel = variables["level"].as<int32_t>(); FAGui::GuiManager guiManager(*this, *player); world.setGuiManager (&guiManager); if (currentLevel == -1) currentLevel = 0; bool clientWaitingForLevel = false; // -1 represents the main menu if(currentLevel != -1 && isServer) world.setLevel(currentLevel); else clientWaitingForLevel = true; boost::asio::io_service io; NetManager netManager(isServer, playerFactory); // Main game logic loop while(!mDone) { boost::asio::deadline_timer timer(io, boost::posix_time::milliseconds(1000/FAWorld::World::ticksPerSecond)); if (clientWaitingForLevel) { clientWaitingForLevel = world.getCurrentLevel() != nullptr; } mInputManager->update(mPaused); if(!mPaused && !clientWaitingForLevel) { world.update(mNoclip); } nk_context* ctx = renderer.getNuklearContext(); netManager.update(); guiManager.update(mPaused, ctx); FAWorld::GameLevel* level = world.getCurrentLevel(); FARender::RenderState* state = renderer.getFreeState(); if(state) { state->mPos = player->getPos(); if(level != NULL) state->tileset = renderer.getTileset(*level); state->level = level; if(!FAGui::cursorPath.empty()) state->mCursorEmpty = false; else state->mCursorEmpty = true; state->mCursorFrame = FAGui::cursorFrame; state->mCursorSpriteGroup = renderer.loadImage("data/inv/objcurs.cel"); state->mCursorHotspot = FAGui::cursorHotspot; world.fillRenderState(state); state->nuklearData.fill(ctx); } std::vector<uint32_t> spritesToPreload; if (renderer.getAndClearSpritesNeedingPreloading(spritesToPreload)) ThreadManager::get()->sendSpritesForPreload(spritesToPreload); nk_clear(ctx); renderer.setCurrentState(state); auto remainingTickTime = timer.expires_from_now().total_milliseconds(); if(remainingTickTime < 0) std::cerr << "tick time exceeded by " << -remainingTickTime << "ms" << std::endl; timer.wait(); } renderer.stop(); renderer.waitUntilDone(); }
NK_API int* nk_headless_render(struct nk_context* ctx, int *draw_buffer) { const struct nk_command *cmd; command_count = 0; buffer_index = BUFFER_INDEX_CMD_START; // Headless_Surface *screen_surface = headless.screen_surface; // nk_headless_clear(screen_surface, clear); nk_foreach(cmd, ctx) { switch (cmd->type) { case NK_COMMAND_NOP: break; case NK_COMMAND_SCISSOR: { const struct nk_command_scissor *s =(const struct nk_command_scissor*)cmd; nk_headless_scissor(draw_buffer, s->x, s->y, s->w, s->h); command_count++; } break; case NK_COMMAND_LINE: { const struct nk_command_line *l = (const struct nk_command_line *)cmd; nk_headless_stroke_line(draw_buffer, l->begin.x, l->begin.y, l->end.x, l->end.y, l->line_thickness, l->color); command_count++; } break; case NK_COMMAND_RECT: { const struct nk_command_rect *r = (const struct nk_command_rect *)cmd; nk_headless_stroke_rect(draw_buffer, r->x, r->y, r->w, r->h, (unsigned short)r->rounding, r->line_thickness, r->color); command_count++; } break; case NK_COMMAND_RECT_FILLED: { const struct nk_command_rect_filled *r = (const struct nk_command_rect_filled *)cmd; nk_headless_fill_rect(draw_buffer, r->x, r->y, r->w, r->h, (unsigned short)r->rounding, r->color); command_count++; } break; case NK_COMMAND_CIRCLE: { const struct nk_command_circle *c = (const struct nk_command_circle *)cmd; nk_headless_stroke_circle(draw_buffer, c->x, c->y, c->w, c->h, c->line_thickness, c->color); command_count++; } break; case NK_COMMAND_CIRCLE_FILLED: { const struct nk_command_circle_filled *c = (const struct nk_command_circle_filled *)cmd; nk_headless_fill_circle(draw_buffer, c->x, c->y, c->w, c->h, c->color); command_count++; } break; case NK_COMMAND_TRIANGLE: { const struct nk_command_triangle*t = (const struct nk_command_triangle*)cmd; nk_headless_stroke_triangle(draw_buffer, t->a.x, t->a.y, t->b.x, t->b.y, t->c.x, t->c.y, t->line_thickness, t->color); command_count++; } break; case NK_COMMAND_TRIANGLE_FILLED: { const struct nk_command_triangle_filled *t = (const struct nk_command_triangle_filled *)cmd; nk_headless_fill_triangle(draw_buffer, t->a.x, t->a.y, t->b.x, t->b.y, t->c.x, t->c.y, t->color); command_count++; } break; case NK_COMMAND_POLYGON: { const struct nk_command_polygon *p =(const struct nk_command_polygon*)cmd; nk_headless_stroke_polygon(draw_buffer, p->points, p->point_count, p->line_thickness,p->color); } break; case NK_COMMAND_POLYGON_FILLED: { const struct nk_command_polygon_filled *p = (const struct nk_command_polygon_filled *)cmd; nk_headless_fill_polygon(draw_buffer, p->points, p->point_count, p->color); } break; case NK_COMMAND_POLYLINE: { const struct nk_command_polyline *p = (const struct nk_command_polyline *)cmd; nk_headless_stroke_polyline(draw_buffer, p->points, p->point_count, p->line_thickness, p->color); } break; case NK_COMMAND_TEXT: { const struct nk_command_text *t = (const struct nk_command_text*)cmd; nk_headless_draw_text(draw_buffer, t->x, t->y, t->w, t->h, (const char*)t->string, t->length, (nk_headless_Font*)t->font->userdata.ptr, t->background, t->foreground); command_count++; } break; case NK_COMMAND_CURVE: { const struct nk_command_curve *q = (const struct nk_command_curve *)cmd; nk_headless_stroke_curve(draw_buffer, q->begin, q->ctrl[0], q->ctrl[1], q->end, 22, q->line_thickness, q->color); } break; case NK_COMMAND_RECT_MULTI_COLOR: { const struct nk_command_rect_multi_color *r = (const struct nk_command_rect_multi_color *)cmd; nk_headless_fill_rect_multi_color(draw_buffer, r->x, r->y, r->w, r->h, r->left, r->top, r->right, r->bottom); } break; case NK_COMMAND_IMAGE: { const struct nk_command_image *q = (const struct nk_command_image *) cmd; nk_headless_draw_image(draw_buffer, q->x, q->y, q->w, q->h, q->img); command_count++; } break; case NK_COMMAND_ARC: case NK_COMMAND_ARC_FILLED: default: break; } } //nk_headless_blit(headless.screen_surface); nk_clear(ctx); draw_buffer[BUFFER_INDEX_CMD_COUNT] = command_count; return draw_buffer; }