/** * @brief Tries to load a model * @param[in] name The model path or name (with or without extension) - see notes * this parameter is always relative to the game base dir - it can also be relative * to the models/ dir in the game folder * @note trying all supported model formats is only supported when you are using * a name without extension and relative to models/ dir * @note if first char of name is a '*' - this is an inline model * @note if there is not extension in the given filename the function will * try to load one of the supported model formats * @return NULL if no model could be found with the given name, model_t otherwise */ model_t *R_FindModel (const char *name) { model_t *mod; model_t model; bool loaded = false; int i; if (!name || !name[0]) return NULL; /* search for existing models */ mod = R_GetModel(name); if (mod != NULL) return mod; /* no inline bsp models here */ if (name[0] == '*') return NULL; /* load model */ if (Com_GetExtension(name) == NULL) { char filename[MAX_QPATH]; for (i = 0; mod_extensions[i] != NULL; i++) { Com_sprintf(filename, sizeof(filename), "models/%s.%s", name, mod_extensions[i]); loaded = R_LoadModel(&model, filename); if (loaded) { /* use short name */ Q_strncpyz(model.name, name, sizeof(model.name)); break; } } } else { /** @todo this case should be useless, do we ever use extension? */ loaded = R_LoadModel(&model, name); } if (!loaded) { Com_Printf("R_FindModel: Could not find: '%s'\n", name); return NULL; } /* register the new model only after the loading is finished */ /* find a free model slot spot */ for (i = 0, mod = r_models; i < r_numModels; i++, mod++) { if (!mod->name[0]) break; } if (i == r_numModels) { if (r_numModels == MAX_MOD_KNOWN) Com_Error(ERR_FATAL, "r_numModels == MAX_MOD_KNOWN"); r_numModels++; } /* copy the model to the slot */ r_models[i] = model; return &r_models[i]; }
/* * @brief */ void Cl_ParseConfigString(void) { const uint16_t i = (uint16_t) Net_ReadShort(&net_message); if (i >= MAX_CONFIG_STRINGS) { Com_Error(ERR_DROP, "Invalid index %i\n", i); } strcpy(cl.config_strings[i], Net_ReadString(&net_message)); const char *s = cl.config_strings[i]; if (i > CS_MODELS && i < CS_MODELS + MAX_MODELS) { if (cls.state == CL_ACTIVE) { cl.model_precache[i - CS_MODELS] = R_LoadModel(s); if (cl.config_strings[i][0] == '*') { cl.model_clip[i - CS_MODELS] = Cm_Model(s); } else { cl.model_clip[i - CS_MODELS] = NULL; } } } else if (i >= CS_SOUNDS && i < CS_SOUNDS + MAX_SOUNDS) { if (cls.state == CL_ACTIVE) { cl.sound_precache[i - CS_SOUNDS] = S_LoadSample(s); } } else if (i >= CS_IMAGES && i < CS_IMAGES + MAX_IMAGES) { if (cls.state == CL_ACTIVE) { cl.image_precache[i - CS_IMAGES] = R_LoadImage(s, IT_PIC); } } cls.cgame->UpdateConfigString(i); }
/* * @brief Loads all media for the renderer subsystem. */ void R_LoadMedia(void) { extern cl_client_t cl; uint32_t i; if (!cl.config_strings[CS_MODELS][0]) { return; // no map specified } R_InitView(); R_BeginLoading(); Cl_LoadProgress(1); R_LoadModel(cl.config_strings[CS_MODELS]); // load the world Cl_LoadProgress(60); // load all other models for (i = 1; i < MAX_MODELS && cl.config_strings[CS_MODELS + i][0]; i++) { cl.model_precache[i] = R_LoadModel(cl.config_strings[CS_MODELS + i]); if (i <= 30) // bump loading progress Cl_LoadProgress(60 + (i / 3)); } Cl_LoadProgress(70); // load all known images for (i = 0; i < MAX_IMAGES && cl.config_strings[CS_IMAGES + i][0]; i++) { cl.image_precache[i] = R_LoadImage(cl.config_strings[CS_IMAGES + i], IT_PIC); } Cl_LoadProgress(75); // sky environment map R_SetSky(cl.config_strings[CS_SKY]); Cl_LoadProgress(77); r_view.update = true; }
/* * R_BeginLoading * * Loads the specified level after resetting all model data. */ void R_BeginLoading(const char *bsp_name, int bsp_size) { R_FreeModels(); // free all models // load bsp for collision detection (prediction) if (!Com_WasInit(Q2W_SERVER)) { int bs; Cm_LoadBsp(bsp_name, &bs); if (bs != bsp_size) { Com_Error(ERR_DROP, "Local map version differs from server: " "%i != %i.", bs, bsp_size); } } // then load materials R_LoadMaterials(bsp_name); // finally load the bsp for rendering (surface arrays) r_world_model = R_LoadModel(bsp_name); }