Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 /* | 1 /* |
| 2 * Copyright 2009, Google Inc. | 2 * Copyright 2009, Google Inc. |
| 3 * All rights reserved. | 3 * All rights reserved. |
| 4 * | 4 * |
| 5 * Redistribution and use in source and binary forms, with or without | 5 * Redistribution and use in source and binary forms, with or without |
| 6 * modification, are permitted provided that the following conditions are | 6 * modification, are permitted provided that the following conditions are |
| 7 * met: | 7 * met: |
| 8 * | 8 * |
| 9 * * Redistributions of source code must retain the above copyright | 9 * * Redistributions of source code must retain the above copyright |
| 10 * notice, this list of conditions and the following disclaimer. | 10 * notice, this list of conditions and the following disclaimer. |
| (...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 62 reinterpret_cast<wchar_t*>(&hLocal), | 62 reinterpret_cast<wchar_t*>(&hLocal), |
| 63 0, | 63 0, |
| 64 NULL); | 64 NULL); |
| 65 wchar_t* msg = reinterpret_cast<wchar_t*>(LocalLock(hLocal)); | 65 wchar_t* msg = reinterpret_cast<wchar_t*>(LocalLock(hLocal)); |
| 66 LOG(ERROR) << "Failed to compile effect: " << msg; | 66 LOG(ERROR) << "Failed to compile effect: " << msg; |
| 67 LocalFree(hLocal); | 67 LocalFree(hLocal); |
| 68 } | 68 } |
| 69 } | 69 } |
| 70 | 70 |
| 71 EffectD3D9::EffectD3D9(ID3DXEffect *d3d_effect, | 71 EffectD3D9::EffectD3D9(ID3DXEffect *d3d_effect, |
| 72 ID3DXConstantTable *fs_constant_table) | 72 ID3DXConstantTable *fs_constant_table, |
| 73 IDirect3DVertexShader9 *d3d_vertex_shader) | |
| 73 : d3d_effect_(d3d_effect), | 74 : d3d_effect_(d3d_effect), |
| 74 fs_constant_table_(fs_constant_table), | 75 fs_constant_table_(fs_constant_table), |
| 76 d3d_vertex_shader_(d3d_vertex_shader), | |
| 75 sync_parameters_(false) { | 77 sync_parameters_(false) { |
| 76 for (unsigned int i = 0; i < kMaxSamplerUnits; ++i) { | 78 for (unsigned int i = 0; i < kMaxSamplerUnits; ++i) { |
| 77 samplers_[i] = kInvalidResource; | 79 samplers_[i] = kInvalidResource; |
| 78 } | 80 } |
| 81 SetStreams(); | |
| 79 } | 82 } |
| 80 // Releases the D3D effect. | 83 // Releases the D3D effect. |
| 81 EffectD3D9::~EffectD3D9() { | 84 EffectD3D9::~EffectD3D9() { |
| 82 for (ParamList::iterator it = params_.begin(); it != params_.end(); ++it) { | 85 for (ParamList::iterator it = params_.begin(); it != params_.end(); ++it) { |
| 83 (*it)->ResetEffect(); | 86 (*it)->ResetEffect(); |
| 84 } | 87 } |
| 85 DCHECK(d3d_effect_); | 88 DCHECK(d3d_effect_); |
| 86 d3d_effect_->Release(); | 89 d3d_effect_->Release(); |
| 87 DCHECK(fs_constant_table_); | 90 DCHECK(fs_constant_table_); |
| 88 fs_constant_table_->Release(); | 91 fs_constant_table_->Release(); |
| 92 DCHECK(d3d_vertex_shader_); | |
| 93 d3d_vertex_shader_->Release(); | |
| 89 } | 94 } |
| 90 | 95 |
| 91 // Compiles the effect, and checks that the effect conforms to what we expect | 96 // Compiles the effect, and checks that the effect conforms to what we expect |
| 92 // (no extra technique or pass in the effect code, since one is implicitly added | 97 // (no extra technique or pass in the effect code, since one is implicitly added |
| 93 // using the program entry points) and that it validates. If successful, wrap | 98 // using the program entry points) and that it validates. If successful, wrap |
| 94 // the D3D effect into a new EffectD3D9. | 99 // the D3D effect into a new EffectD3D9. |
| 95 EffectD3D9 *EffectD3D9::Create(GAPID3D9 *gapi, | 100 EffectD3D9 *EffectD3D9::Create(GAPID3D9 *gapi, |
| 96 const String& effect_code, | 101 const String& effect_code, |
| 97 const String& vertex_program_entry, | 102 const String& vertex_program_entry, |
| 98 const String& fragment_program_entry) { | 103 const String& fragment_program_entry) { |
| (...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 145 D3DXPASS_DESC pass_desc; | 150 D3DXPASS_DESC pass_desc; |
| 146 HR(d3d_effect->GetPassDesc(pass, &pass_desc)); | 151 HR(d3d_effect->GetPassDesc(pass, &pass_desc)); |
| 147 ID3DXConstantTable *table = NULL; | 152 ID3DXConstantTable *table = NULL; |
| 148 HR(D3DXGetShaderConstantTable(pass_desc.pPixelShaderFunction, | 153 HR(D3DXGetShaderConstantTable(pass_desc.pPixelShaderFunction, |
| 149 &table)); | 154 &table)); |
| 150 if (!table) { | 155 if (!table) { |
| 151 LOG(ERROR) << "Could not get the constant table."; | 156 LOG(ERROR) << "Could not get the constant table."; |
| 152 d3d_effect->Release(); | 157 d3d_effect->Release(); |
| 153 return NULL; | 158 return NULL; |
| 154 } | 159 } |
| 155 return new EffectD3D9(d3d_effect, table); | 160 IDirect3DVertexShader9 *d3d_vertex_shader = NULL; |
| 161 HR(device->CreateVertexShader(pass_desc.pVertexShaderFunction, | |
| 162 &d3d_vertex_shader)); | |
| 163 if (!d3d_vertex_shader) { | |
| 164 d3d_effect->Release(); | |
| 165 table->Release(); | |
| 166 DLOG(ERROR) << "Failed to create vertex shader"; | |
| 167 return NULL; | |
| 168 } | |
| 169 | |
| 170 return new EffectD3D9(d3d_effect, table, d3d_vertex_shader); | |
| 156 } | 171 } |
| 157 | 172 |
| 158 // Begins rendering with the effect, setting all the appropriate states. | 173 // Begins rendering with the effect, setting all the appropriate states. |
| 159 bool EffectD3D9::Begin(GAPID3D9 *gapi) { | 174 bool EffectD3D9::Begin(GAPID3D9 *gapi) { |
| 160 UINT numpasses; | 175 UINT numpasses; |
| 161 HR(d3d_effect_->Begin(&numpasses, 0)); | 176 HR(d3d_effect_->Begin(&numpasses, 0)); |
| 162 HR(d3d_effect_->BeginPass(0)); | 177 HR(d3d_effect_->BeginPass(0)); |
| 163 sync_parameters_ = false; | 178 sync_parameters_ = false; |
| 164 return SetSamplers(gapi); | 179 return SetSamplers(gapi); |
| 165 } | 180 } |
| 166 | 181 |
| 167 // Terminates rendering with the effect, resetting all the appropriate states. | 182 // Terminates rendering with the effect, resetting all the appropriate states. |
| 168 void EffectD3D9::End(GAPID3D9 *gapi) { | 183 void EffectD3D9::End(GAPID3D9 *gapi) { |
| 169 HR(d3d_effect_->EndPass()); | 184 HR(d3d_effect_->EndPass()); |
| 170 HR(d3d_effect_->End()); | 185 HR(d3d_effect_->End()); |
| 171 } | 186 } |
| 172 | 187 |
| 173 // Gets the parameter count from the D3D effect description. | 188 // Gets the parameter count from the D3D effect description. |
| 174 unsigned int EffectD3D9::GetParamCount() { | 189 unsigned int EffectD3D9::GetParamCount() { |
| 175 D3DXEFFECT_DESC effect_desc; | 190 D3DXEFFECT_DESC effect_desc; |
| 176 HR(d3d_effect_->GetDesc(&effect_desc)); | 191 HR(d3d_effect_->GetDesc(&effect_desc)); |
| 177 return effect_desc.Parameters; | 192 return effect_desc.Parameters; |
| 178 } | 193 } |
| 179 | 194 |
| 195 // Gets the number of input streams from the shader. | |
| 196 unsigned int EffectD3D9::GetStreamCount() { | |
| 197 return streams_.size(); | |
| 198 } | |
| 199 | |
| 180 // Retrieves the matching DataType from a D3D parameter description. | 200 // Retrieves the matching DataType from a D3D parameter description. |
| 181 static effect_param::DataType GetDataTypeFromD3D( | 201 static effect_param::DataType GetDataTypeFromD3D( |
| 182 const D3DXPARAMETER_DESC &desc) { | 202 const D3DXPARAMETER_DESC &desc) { |
| 183 switch (desc.Type) { | 203 switch (desc.Type) { |
| 184 case D3DXPT_FLOAT: | 204 case D3DXPT_FLOAT: |
| 185 switch (desc.Class) { | 205 switch (desc.Class) { |
| 186 case D3DXPC_SCALAR: | 206 case D3DXPC_SCALAR: |
| 187 return effect_param::FLOAT1; | 207 return effect_param::FLOAT1; |
| 188 case D3DXPC_VECTOR: | 208 case D3DXPC_VECTOR: |
| 189 switch (desc.Columns) { | 209 switch (desc.Columns) { |
| (...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 275 SamplerD3D9 *sampler = gapi->GetSampler(samplers_[i]); | 295 SamplerD3D9 *sampler = gapi->GetSampler(samplers_[i]); |
| 276 if (sampler) { | 296 if (sampler) { |
| 277 result &= sampler->ApplyStates(gapi, i); | 297 result &= sampler->ApplyStates(gapi, i); |
| 278 } else { | 298 } else { |
| 279 HR(d3d_device->SetTexture(i, NULL)); | 299 HR(d3d_device->SetTexture(i, NULL)); |
| 280 } | 300 } |
| 281 } | 301 } |
| 282 return result; | 302 return result; |
| 283 } | 303 } |
| 284 | 304 |
| 305 bool EffectD3D9::SetStreams() { | |
| 306 if (!d3d_vertex_shader_) { | |
| 307 return false; | |
| 308 } | |
| 309 UINT size; | |
| 310 d3d_vertex_shader_->GetFunction(NULL, &size); | |
| 311 scoped_array<DWORD> function(new DWORD[size]); | |
| 312 d3d_vertex_shader_->GetFunction(function.get(), &size); | |
| 313 | |
| 314 UINT num_semantics; | |
| 315 HR(D3DXGetShaderInputSemantics(function.get(), | |
| 316 NULL, | |
| 317 &num_semantics)); | |
| 318 scoped_array<D3DXSEMANTIC> semantics(new D3DXSEMANTIC[num_semantics]); | |
| 319 HR(D3DXGetShaderInputSemantics(function.get(), | |
| 320 semantics.get(), | |
| 321 &num_semantics)); | |
| 322 | |
| 323 streams_.resize(num_semantics); | |
| 324 for (UINT i = 0; i < num_semantics; ++i) { | |
| 325 vertex_struct::Semantic semantic; | |
| 326 unsigned int semantic_index; | |
| 327 if (D3DSemanticToCBSemantic(static_cast<D3DDECLUSAGE>(semantics[i].Usage), | |
| 328 static_cast<int>(semantics[i].UsageIndex), | |
| 329 &semantic, &semantic_index)) { | |
| 330 streams_[i].semantic = semantic; | |
| 331 streams_[i].semantic_index = semantic_index; | |
| 332 } | |
| 333 } | |
| 334 return true; | |
| 335 } | |
| 336 | |
| 285 void EffectD3D9::LinkParam(EffectParamD3D9 *param) { | 337 void EffectD3D9::LinkParam(EffectParamD3D9 *param) { |
| 286 params_.push_back(param); | 338 params_.push_back(param); |
| 287 } | 339 } |
| 288 | 340 |
| 289 void EffectD3D9::UnlinkParam(EffectParamD3D9 *param) { | 341 void EffectD3D9::UnlinkParam(EffectParamD3D9 *param) { |
| 290 std::remove(params_.begin(), params_.end(), param); | 342 std::remove(params_.begin(), params_.end(), param); |
| 291 } | 343 } |
| 292 | 344 |
| 345 // Fills the Desc structure, appending name and semantic if any, and if enough | |
| 346 // room is available in the buffer. | |
| 347 bool EffectD3D9::GetStreamDesc(unsigned int index, | |
| 348 unsigned int size, | |
| 349 void *data) { | |
| 350 using effect_stream::Desc; | |
| 351 if (size < sizeof(Desc)) // NOLINT | |
| 352 return false; | |
| 353 | |
| 354 Desc stream = streams_[index]; | |
| 355 Desc *desc = static_cast<Desc *>(data); | |
| 356 memset(desc, 0, sizeof(*desc)); | |
| 357 desc->semantic = stream.semantic; | |
| 358 desc->semantic_index = stream.semantic_index; | |
|
Antoine Labour
2009/07/06 23:48:12
how about simply *desc = streams_[index]; instead
| |
| 359 return true; | |
| 360 } | |
| 361 | |
| 293 EffectParamD3D9::EffectParamD3D9(effect_param::DataType data_type, | 362 EffectParamD3D9::EffectParamD3D9(effect_param::DataType data_type, |
| 294 EffectD3D9 *effect, | 363 EffectD3D9 *effect, |
| 295 D3DXHANDLE handle) | 364 D3DXHANDLE handle) |
| 296 : EffectParam(data_type), | 365 : EffectParam(data_type), |
| 297 effect_(effect), | 366 effect_(effect), |
| 298 handle_(handle), | 367 handle_(handle), |
| 299 sampler_units_(NULL), | 368 sampler_units_(NULL), |
| 300 sampler_unit_count_(0) { | 369 sampler_unit_count_(0) { |
| 301 DCHECK(effect_); | 370 DCHECK(effect_); |
| 302 effect_->LinkParam(this); | 371 effect_->LinkParam(this); |
| (...skipping 249 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 552 ResourceID id, | 621 ResourceID id, |
| 553 unsigned int size, | 622 unsigned int size, |
| 554 void *data) { | 623 void *data) { |
| 555 EffectParamD3D9 *param = effect_params_.Get(id); | 624 EffectParamD3D9 *param = effect_params_.Get(id); |
| 556 if (!param) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS; | 625 if (!param) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS; |
| 557 return param->GetDesc(size, data) ? | 626 return param->GetDesc(size, data) ? |
| 558 BufferSyncInterface::PARSE_NO_ERROR : | 627 BufferSyncInterface::PARSE_NO_ERROR : |
| 559 BufferSyncInterface::PARSE_INVALID_ARGUMENTS; | 628 BufferSyncInterface::PARSE_INVALID_ARGUMENTS; |
| 560 } | 629 } |
| 561 | 630 |
| 631 // Gets the stream count from the effect and store it in the memory buffer. | |
| 632 BufferSyncInterface::ParseError GAPID3D9::GetStreamCount( | |
| 633 ResourceID id, | |
| 634 unsigned int size, | |
| 635 void *data) { | |
| 636 EffectD3D9 *effect = effects_.Get(id); | |
| 637 if (!effect || size < sizeof(Uint32)) // NOLINT | |
| 638 return BufferSyncInterface::PARSE_INVALID_ARGUMENTS; | |
| 639 *static_cast<Uint32 *>(data) = effect->GetStreamCount(); | |
| 640 return BufferSyncInterface::PARSE_NO_ERROR; | |
| 641 } | |
| 642 | |
| 643 BufferSyncInterface::ParseError GAPID3D9::GetStreamDesc( | |
| 644 ResourceID id, | |
| 645 unsigned int index, | |
| 646 unsigned int size, | |
| 647 void *data) { | |
| 648 EffectD3D9 *effect = effects_.Get(id); | |
| 649 if (!effect) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS; | |
| 650 return effect->GetStreamDesc(index, size, data) ? | |
| 651 BufferSyncInterface::PARSE_NO_ERROR : | |
| 652 BufferSyncInterface::PARSE_INVALID_ARGUMENTS; | |
| 653 } | |
| 654 | |
| 655 | |
| 562 // If the current effect is valid, call End on it, and tag for revalidation. | 656 // If the current effect is valid, call End on it, and tag for revalidation. |
| 563 void GAPID3D9::DirtyEffect() { | 657 void GAPID3D9::DirtyEffect() { |
| 564 if (validate_effect_) return; | 658 if (validate_effect_) return; |
| 565 DCHECK(current_effect_); | 659 DCHECK(current_effect_); |
| 566 current_effect_->End(this); | 660 current_effect_->End(this); |
| 567 current_effect_ = NULL; | 661 current_effect_ = NULL; |
| 568 validate_effect_ = true; | 662 validate_effect_ = true; |
| 569 } | 663 } |
| 570 | 664 |
| 571 // Gets the current effect, and calls Begin on it (if successful). | 665 // Gets the current effect, and calls Begin on it (if successful). |
| 572 // Should only be called if the current effect is not valid. | 666 // Should only be called if the current effect is not valid. |
| 573 bool GAPID3D9::ValidateEffect() { | 667 bool GAPID3D9::ValidateEffect() { |
| 574 DCHECK(validate_effect_); | 668 DCHECK(validate_effect_); |
| 575 DCHECK(!current_effect_); | 669 DCHECK(!current_effect_); |
| 576 current_effect_ = effects_.Get(current_effect_id_); | 670 current_effect_ = effects_.Get(current_effect_id_); |
| 577 if (!current_effect_) return false; | 671 if (!current_effect_) return false; |
| 578 validate_effect_ = false; | 672 validate_effect_ = false; |
| 579 return current_effect_->Begin(this); | 673 return current_effect_->Begin(this); |
| 580 } | 674 } |
| 581 | 675 |
| 582 } // namespace command_buffer | 676 } // namespace command_buffer |
| 583 } // namespace o3d | 677 } // namespace o3d |
| OLD | NEW |