2016-06-12 5 views
0

Недавно я сделал систему объемного рендеринга в надежде использовать их для эффектов частиц, одновременно пытаясь излучать пыль, я заметил, что позиционирование частиц было совершенно неправильным. Я генерирую сеянные случайные числа, которые я подаю в каждую отдельную частицу, чтобы установить положение. Когда я начинаю отлаживать, как обычно, частицы будут возникать только друг над другом в двух положениях. При применении точки останова и шага по петле с одной частицей за раз, а затем продолжая, каждая частица находилась в назначенной случайной позиции. В дополнение к этому, одновременно проверяя проблему с большим пулом частиц, я использовал hitcount для разрыва цикла на определенном количестве и обнаружил, что когда это происходит, он только инициализирует их одной из двух вышеупомянутых позиций. Что может быть причиной этого?Значения конструктора, которые не применяются при запуске

VolumetricDust::VolumetricDust(string type, Transform* transform, ID3D11Device* pDevice, int width, int height, int depth, bool instanceFlag, int instanceCount) 
{ 

    for (int i = 0; i < POOL_SIZE; i++) 
{ 
    // PROBLEM LOOP 
    particles_[i] = new ParticleVolume("Resources\\nucleon.raw", transform, width, height, depth, instanceFlag, instanceCount); 
    particles_[i]->Initialise(pDevice); 

    srand((unsigned int)time(NULL)); 
    int test = (rand() % 100 + 1); 
    int test1 = rand() % 30 + 1; 
    int test2 = rand() % 50 + 1; 

    particles_[i]->SetVelocity(XMFLOAT3(0.0f, (float)test, 0.0f)); 
    particles_[i]->GetTransform()->SetPosition((float)test, (float)test1, (float)test2); 


    } 

posReset = transform; 
_transform = transform; 

mWidth = width; 
mHeight = height; 
mDepth = depth; 

isInstance = instanceFlag; 
instanceNum = instanceCount; 

_currentTime = 0.0f; 
_spawnTime = 5.0f; 
_newTime = 0.1f; 
_dustTime = 0.0f; 
particleTime = 5.0f; 
_type = type; 
_pd3dDevice = pDevice; 
} 

void VolumetricDust::SpawnEmitter() 
{ 

for (int i = 0; i < POOL_SIZE; i++) 
{ 
    if (!particles_[i]->GetParticleOn()) 
    { 

     particles_[i]->SetParticleOn(true); 
     break; 
    } 

} 

} 

void VolumetricDust::Update(float dt, Camera* cam) 
{ 
_transform->Update(); 
_currentTime += dt; 
_dustTime += dt; 


for (int i = 0; i < POOL_SIZE; i++) 
{ 
    SpawnEmitter(); 

    if (particles_[i]->GetParticleOn()) 
    { 

     //posReset->SetPosition(XMFLOAT3(0.0f, 0.0f, 0.0f)); 

     particles_[i]->Update(dt, cam, posReset->GetPosition()); 
    } 

    if (_transform) 
    { 
     _transform->Update(); 
    } 

} 



} 

void VolumetricDust::Draw(ID3D11DeviceContext * _pImmediateContext, ConstantBuffer3D & cb, ID3D11Buffer* _pConstantBuffer) 
{ 
for (int i = 0; i < POOL_SIZE; i++) 
{ 
    if (particles_[i]->GetParticleOn()) 
    { 
     particles_[i]->Draw(_pImmediateContext, cb, _pConstantBuffer); 
    } 

} 

} 

ответ

4

Вы должны позвонить srand только один раз.

Когда вы вызываете это в такой петле, шансы очень высоки, и вы получаете одинаковое значение времени каждый раунд. Это сбрасывает случайные числа, и вы получите тот же результат для большинства, если не всех, баллов.

Остановка в отладчике позволит изменить реальное время между вызовами до time, и вы получите отдельные случайные значения, потому что теперь семя будет другим.

+0

Большое вам спасибо! Я только недавно начал использовать srand, и я не знал об этом! – MrPurple

+2

Вам следует рассмотреть возможность использования [] (http://en.cppreference.com/w/cpp/numeric/random) вместо устаревших функций '' rand''' '' srand'' –

Смежные вопросы