I agree that having a fixed timer is probably better than dynamically adjusting the timer period, you can end up with some serious weirdness when a piece of code adjusts it’s own timing. Clothing, windchill, and dampness would influence the magnitude of temperature changes rather than how often adjustments happen.
I’d actually prefer to have the sampling rate be pretty quick, possibly around once a minute (10 turns). This is to make extreme environments take effect more smoothly. For example, if you go out into a blizzard wearing jeans and a tshirt for 5 minutes, there should be a noticeable effect, but if you have the refresh rate set to 30 mins there’s a really good chance that it will have no effect at all, whereas ducking out for literally just a few turns should have a decent chance of having no noticeable effect.
I’d prefer that the turn counter be checked in the main loop and conditionally call the function to handle temperature changes, because after having it brought to my attention I’d really like to unify all of that in a systematic way so it’s easier to understand what’s happening.
Why the 35 in “change = bodytemp - temperature + 35;”? Body temp should just move toward ambient temp for the time being, right? (basically the player is coldblooded right now, we can add warm-bloodedness once the endurance system gets added).
Not sure what units temperature are in right now, probably whole degrees in either C or F, if we’re doing this we might want to change that to degrees C or F * 10 or so so it adjusts more smoothly, and just convert to the nearest degree when outputting, or even just output a descriptive label.
Looking at Glyphgryph’s pseudocode:
I’m not sure about windchill only influencing cold temperatures, when it’s hot a breeze helps you stay cooler too.
As such I’m not sure it’s necessary to distinguish between losing heat and gaining heat, though something might come up that makes it necessary.
There’re a few different formulas for calculating windchill, just google wind chill chart. Might as well use one of them as a starting point as long as windchill is an issue.
More as a FYI than anything else, this is a sketch of how I’d start out.
// Might just want to push all of this down into a function in weather.cpp, and just pass in the ambient temp according to the game object.
// There might be more weather-based factors that influence effective temperature.
// regardless, the idea here is to do the calculations where they make the most sense. On the other hand, it needs access to all the
// pertinent data, so it might want to know if the player is wearing a hat or not, it's a balancing act.
int game::effective_temperature(bool is_outside, bool is_wet) {
int local_temp = temperature;
if( is_outside ) {
// This one might want to know if you're wearing a hat to adjust the results.
local_temp = weather::adjust_for_sunlight( local_temp, is_wet );
//Magic function that calculates windchill based on one of the weather service formulas
//Wind speed might be internal to weather, so no need to pass it in.
local_temp = weather::windchill( local_temp, wind_speed, is_wet );
}
// Kind of like windchill for heat, factors humidity into the temperature.
// Since it's based on humidity, it doesn't care if you're inside or outside.
local_temp = weather::heat_index( local_temp, is_wet );
return local_temp;
}
player::update_body_temp(game *g) {
normalize_temp(); //I think it's better to normalize the previous result, then apply the new effects, makes it lag a little bit.
for( int i = 0; i < num_hp_parts ; i++ ) {
int effective_body_temp = temp[i] + ( MAGIC_WARMTH_SCALING_FACTOR * warmth(i);
const int temp_difference = g->effective_temperature( g->m.is_outside(posx, posy), p->is_wet() ) - effective_body_temp;
temp[i] += temp_difference * MAGIC_TEMP_SCALING_FACTOR;
}