OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "gpu/command_buffer/service/texture_manager.h" | 5 #include "gpu/command_buffer/service/texture_manager.h" |
6 | 6 |
7 #include <stddef.h> | 7 #include <stddef.h> |
8 #include <stdint.h> | 8 #include <stdint.h> |
9 | 9 |
10 #include <algorithm> | 10 #include <algorithm> |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
62 bool can_render_; | 62 bool can_render_; |
63 bool can_render_to_; | 63 bool can_render_to_; |
64 bool npot_; | 64 bool npot_; |
65 | 65 |
66 // Since we will be hashing this signature structure, the padding must be | 66 // Since we will be hashing this signature structure, the padding must be |
67 // zero initialized. Although the C++11 specifications specify that this is | 67 // zero initialized. Although the C++11 specifications specify that this is |
68 // true, we will use a constructor with a memset to further enforce it instead | 68 // true, we will use a constructor with a memset to further enforce it instead |
69 // of relying on compilers adhering to this deep dark corner specification. | 69 // of relying on compilers adhering to this deep dark corner specification. |
70 TextureSignature(GLenum target, | 70 TextureSignature(GLenum target, |
71 GLint level, | 71 GLint level, |
72 GLenum min_filter, | 72 const SamplerState& sampler_state, |
73 GLenum mag_filter, | |
74 GLenum wrap_r, | |
75 GLenum wrap_s, | |
76 GLenum wrap_t, | |
77 GLenum usage, | 73 GLenum usage, |
78 GLenum internal_format, | 74 GLenum internal_format, |
79 GLenum compare_func, | |
80 GLenum compare_mode, | |
81 GLsizei width, | 75 GLsizei width, |
82 GLsizei height, | 76 GLsizei height, |
83 GLsizei depth, | 77 GLsizei depth, |
84 GLfloat max_lod, | |
85 GLfloat min_lod, | |
86 GLint base_level, | 78 GLint base_level, |
87 GLint border, | 79 GLint border, |
88 GLint max_level, | 80 GLint max_level, |
89 GLenum format, | 81 GLenum format, |
90 GLenum type, | 82 GLenum type, |
91 bool has_image, | 83 bool has_image, |
92 bool can_render, | 84 bool can_render, |
93 bool can_render_to, | 85 bool can_render_to, |
94 bool npot) { | 86 bool npot) { |
95 memset(this, 0, sizeof(TextureSignature)); | 87 memset(this, 0, sizeof(TextureSignature)); |
96 target_ = target; | 88 target_ = target; |
97 level_ = level; | 89 level_ = level; |
98 min_filter_ = min_filter; | 90 min_filter_ = sampler_state.min_filter; |
99 mag_filter_ = mag_filter; | 91 mag_filter_ = sampler_state.mag_filter; |
100 wrap_r_ = wrap_r; | 92 wrap_r_ = sampler_state.wrap_r; |
101 wrap_s_ = wrap_s; | 93 wrap_s_ = sampler_state.wrap_s; |
102 wrap_t_ = wrap_t; | 94 wrap_t_ = sampler_state.wrap_t; |
103 usage_ = usage; | 95 usage_ = usage; |
104 internal_format_ = internal_format; | 96 internal_format_ = internal_format; |
105 compare_func_ = compare_func; | 97 compare_func_ = sampler_state.compare_func; |
106 compare_mode_ = compare_mode; | 98 compare_mode_ = sampler_state.compare_mode; |
107 width_ = width; | 99 width_ = width; |
108 height_ = height; | 100 height_ = height; |
109 depth_ = depth; | 101 depth_ = depth; |
110 max_lod_ = max_lod; | 102 max_lod_ = sampler_state.max_lod; |
111 min_lod_ = min_lod; | 103 min_lod_ = sampler_state.min_lod; |
112 base_level_ = base_level; | 104 base_level_ = base_level; |
113 border_ = border; | 105 border_ = border; |
114 max_level_ = max_level; | 106 max_level_ = max_level; |
115 format_ = format; | 107 format_ = format; |
116 type_ = type; | 108 type_ = type; |
117 has_image_ = has_image; | 109 has_image_ = has_image; |
118 can_render_ = can_render; | 110 can_render_ = can_render; |
119 can_render_to_ = can_render_to; | 111 can_render_to_ = can_render_to; |
120 npot_ = npot; | 112 npot_ = npot; |
121 } | 113 } |
(...skipping 158 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
280 TextureManager::~TextureManager() { | 272 TextureManager::~TextureManager() { |
281 for (unsigned int i = 0; i < destruction_observers_.size(); i++) | 273 for (unsigned int i = 0; i < destruction_observers_.size(); i++) |
282 destruction_observers_[i]->OnTextureManagerDestroying(this); | 274 destruction_observers_[i]->OnTextureManagerDestroying(this); |
283 | 275 |
284 DCHECK(textures_.empty()); | 276 DCHECK(textures_.empty()); |
285 | 277 |
286 // If this triggers, that means something is keeping a reference to | 278 // If this triggers, that means something is keeping a reference to |
287 // a Texture belonging to this. | 279 // a Texture belonging to this. |
288 CHECK_EQ(texture_count_, 0u); | 280 CHECK_EQ(texture_count_, 0u); |
289 | 281 |
290 DCHECK_EQ(0, num_unrenderable_textures_); | |
291 DCHECK_EQ(0, num_unsafe_textures_); | 282 DCHECK_EQ(0, num_unsafe_textures_); |
292 DCHECK_EQ(0, num_uncleared_mips_); | 283 DCHECK_EQ(0, num_uncleared_mips_); |
293 DCHECK_EQ(0, num_images_); | 284 DCHECK_EQ(0, num_images_); |
294 | 285 |
295 base::trace_event::MemoryDumpManager::GetInstance()->UnregisterDumpProvider( | 286 base::trace_event::MemoryDumpManager::GetInstance()->UnregisterDumpProvider( |
296 this); | 287 this); |
297 } | 288 } |
298 | 289 |
299 void TextureManager::Destroy(bool have_context) { | 290 void TextureManager::Destroy(bool have_context) { |
300 have_context_ = have_context; | 291 have_context_ = have_context; |
(...skipping 10 matching lines...) Expand all Loading... |
311 } | 302 } |
312 | 303 |
313 Texture::Texture(GLuint service_id) | 304 Texture::Texture(GLuint service_id) |
314 : mailbox_manager_(NULL), | 305 : mailbox_manager_(NULL), |
315 memory_tracking_ref_(NULL), | 306 memory_tracking_ref_(NULL), |
316 service_id_(service_id), | 307 service_id_(service_id), |
317 cleared_(true), | 308 cleared_(true), |
318 num_uncleared_mips_(0), | 309 num_uncleared_mips_(0), |
319 num_npot_faces_(0), | 310 num_npot_faces_(0), |
320 target_(0), | 311 target_(0), |
321 min_filter_(GL_NEAREST_MIPMAP_LINEAR), | |
322 mag_filter_(GL_LINEAR), | |
323 wrap_r_(GL_REPEAT), | |
324 wrap_s_(GL_REPEAT), | |
325 wrap_t_(GL_REPEAT), | |
326 usage_(GL_NONE), | 312 usage_(GL_NONE), |
327 compare_func_(GL_LEQUAL), | |
328 compare_mode_(GL_NONE), | |
329 max_lod_(1000.0f), | |
330 min_lod_(-1000.0f), | |
331 base_level_(0), | 313 base_level_(0), |
332 max_level_(1000), | 314 max_level_(1000), |
333 max_level_set_(-1), | 315 max_level_set_(-1), |
334 texture_complete_(false), | 316 texture_complete_(false), |
335 texture_mips_dirty_(false), | 317 texture_mips_dirty_(false), |
336 cube_complete_(false), | 318 cube_complete_(false), |
337 texture_level0_dirty_(false), | 319 texture_level0_dirty_(false), |
338 npot_(false), | 320 npot_(false), |
339 has_been_bound_(false), | 321 has_been_bound_(false), |
340 framebuffer_attachment_count_(0), | 322 framebuffer_attachment_count_(0), |
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
434 } | 416 } |
435 const Texture::LevelInfo& first_face = | 417 const Texture::LevelInfo& first_face = |
436 face_infos_[0].level_infos[base_level_]; | 418 face_infos_[0].level_infos[base_level_]; |
437 if (first_face.width == 0 || | 419 if (first_face.width == 0 || |
438 first_face.height == 0 || | 420 first_face.height == 0 || |
439 first_face.depth == 0) { | 421 first_face.depth == 0) { |
440 return CAN_RENDER_NEVER; | 422 return CAN_RENDER_NEVER; |
441 } | 423 } |
442 } | 424 } |
443 | 425 |
444 bool needs_mips = NeedsMips(); | |
445 if (needs_mips) { | |
446 if (!texture_complete()) | |
447 return CAN_RENDER_NEVER; | |
448 } | |
449 | |
450 if (target_ == GL_TEXTURE_CUBE_MAP && !cube_complete()) | 426 if (target_ == GL_TEXTURE_CUBE_MAP && !cube_complete()) |
451 return CAN_RENDER_NEVER; | 427 return CAN_RENDER_NEVER; |
452 | 428 |
453 bool is_npot_compatible = !needs_mips && | 429 // Texture may be renderable, but it depends on the sampler it's used with, |
454 wrap_s_ == GL_CLAMP_TO_EDGE && | 430 // the context that's using it, and the extensions available. |
455 wrap_t_ == GL_CLAMP_TO_EDGE; | 431 return CAN_RENDER_NEEDS_VALIDATION; |
456 | |
457 if (!is_npot_compatible) { | |
458 if (target_ == GL_TEXTURE_RECTANGLE_ARB) | |
459 return CAN_RENDER_NEVER; | |
460 else if (npot()) | |
461 return CAN_RENDER_ONLY_IF_NPOT; | |
462 } | |
463 | |
464 return CAN_RENDER_ALWAYS; | |
465 } | 432 } |
466 | 433 |
467 bool Texture::CanRender(const FeatureInfo* feature_info) const { | 434 bool Texture::CanRender(const FeatureInfo* feature_info) const { |
| 435 return CanRenderWithSampler(feature_info, sampler_state()); |
| 436 } |
| 437 |
| 438 bool Texture::CanRenderWithSampler(const FeatureInfo* feature_info, |
| 439 const SamplerState& sampler_state) const { |
468 switch (can_render_condition_) { | 440 switch (can_render_condition_) { |
469 case CAN_RENDER_ALWAYS: | 441 case CAN_RENDER_ALWAYS: |
470 return true; | 442 return true; |
471 case CAN_RENDER_NEVER: | 443 case CAN_RENDER_NEVER: |
472 return false; | 444 return false; |
473 case CAN_RENDER_ONLY_IF_NPOT: | 445 case CAN_RENDER_NEEDS_VALIDATION: |
474 break; | 446 break; |
475 } | 447 } |
476 return feature_info->feature_flags().npot_ok; | 448 |
| 449 bool needs_mips = sampler_state.min_filter != GL_NEAREST && |
| 450 sampler_state.min_filter != GL_LINEAR; |
| 451 if (needs_mips && !texture_complete()) |
| 452 return false; |
| 453 |
| 454 if (!feature_info->IsES3Enabled()) { |
| 455 bool is_npot_compatible = !needs_mips && |
| 456 sampler_state.wrap_s == GL_CLAMP_TO_EDGE && |
| 457 sampler_state.wrap_t == GL_CLAMP_TO_EDGE; |
| 458 |
| 459 if (!is_npot_compatible) { |
| 460 if (target_ == GL_TEXTURE_RECTANGLE_ARB) |
| 461 return false; |
| 462 else if (npot()) |
| 463 return feature_info->feature_flags().npot_ok; |
| 464 } |
| 465 } |
| 466 |
| 467 if (static_cast<size_t>(base_level_) >= face_infos_[0].level_infos.size()) { |
| 468 return false; |
| 469 } |
| 470 |
| 471 const Texture::LevelInfo& first_level = |
| 472 face_infos_[0].level_infos[base_level_]; |
| 473 |
| 474 if (first_level.type == GL_FLOAT && |
| 475 !feature_info->feature_flags().enable_texture_float_linear && |
| 476 (sampler_state.min_filter != GL_NEAREST_MIPMAP_NEAREST || |
| 477 sampler_state.mag_filter != GL_NEAREST)) { |
| 478 return false; |
| 479 } else if (first_level.type == GL_HALF_FLOAT_OES && |
| 480 !feature_info->feature_flags().enable_texture_half_float_linear && |
| 481 (sampler_state.min_filter != GL_NEAREST_MIPMAP_NEAREST || |
| 482 sampler_state.mag_filter != GL_NEAREST)) { |
| 483 return false; |
| 484 } |
| 485 |
| 486 return true; |
477 } | 487 } |
478 | 488 |
479 void Texture::AddToSignature( | 489 void Texture::AddToSignature( |
480 const FeatureInfo* feature_info, | 490 const FeatureInfo* feature_info, |
481 GLenum target, | 491 GLenum target, |
482 GLint level, | 492 GLint level, |
483 std::string* signature) const { | 493 std::string* signature) const { |
484 DCHECK(feature_info); | 494 DCHECK(feature_info); |
485 DCHECK(signature); | 495 DCHECK(signature); |
486 DCHECK_GE(level, 0); | 496 DCHECK_GE(level, 0); |
487 size_t face_index = GLES2Util::GLTargetToFaceIndex(target); | 497 size_t face_index = GLES2Util::GLTargetToFaceIndex(target); |
488 DCHECK_LT(static_cast<size_t>(face_index), | 498 DCHECK_LT(static_cast<size_t>(face_index), |
489 face_infos_.size()); | 499 face_infos_.size()); |
490 DCHECK_LT(static_cast<size_t>(level), | 500 DCHECK_LT(static_cast<size_t>(level), |
491 face_infos_[face_index].level_infos.size()); | 501 face_infos_[face_index].level_infos.size()); |
492 | 502 |
493 const Texture::LevelInfo& info = | 503 const Texture::LevelInfo& info = |
494 face_infos_[face_index].level_infos[level]; | 504 face_infos_[face_index].level_infos[level]; |
495 | 505 |
496 TextureSignature signature_data(target, | 506 TextureSignature signature_data(target, |
497 level, | 507 level, |
498 min_filter_, | 508 sampler_state_, |
499 mag_filter_, | |
500 wrap_r_, | |
501 wrap_s_, | |
502 wrap_t_, | |
503 usage_, | 509 usage_, |
504 info.internal_format, | 510 info.internal_format, |
505 compare_func_, | |
506 compare_mode_, | |
507 info.width, | 511 info.width, |
508 info.height, | 512 info.height, |
509 info.depth, | 513 info.depth, |
510 max_lod_, | |
511 min_lod_, | |
512 base_level_, | 514 base_level_, |
513 info.border, | 515 info.border, |
514 max_level_, | 516 max_level_, |
515 info.format, | 517 info.format, |
516 info.type, | 518 info.type, |
517 info.image.get() != NULL, | 519 info.image.get() != NULL, |
518 CanRender(feature_info), | 520 CanRender(feature_info), |
519 CanRenderTo(), | 521 CanRenderTo(), |
520 npot_); | 522 npot_); |
521 | 523 |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
562 const FeatureInfo* feature_info, GLenum target, GLint max_levels) { | 564 const FeatureInfo* feature_info, GLenum target, GLint max_levels) { |
563 DCHECK_EQ(0u, target_); // you can only set this once. | 565 DCHECK_EQ(0u, target_); // you can only set this once. |
564 target_ = target; | 566 target_ = target; |
565 size_t num_faces = (target == GL_TEXTURE_CUBE_MAP) ? 6 : 1; | 567 size_t num_faces = (target == GL_TEXTURE_CUBE_MAP) ? 6 : 1; |
566 face_infos_.resize(num_faces); | 568 face_infos_.resize(num_faces); |
567 for (size_t ii = 0; ii < num_faces; ++ii) { | 569 for (size_t ii = 0; ii < num_faces; ++ii) { |
568 face_infos_[ii].level_infos.resize(max_levels); | 570 face_infos_[ii].level_infos.resize(max_levels); |
569 } | 571 } |
570 | 572 |
571 if (target == GL_TEXTURE_EXTERNAL_OES || target == GL_TEXTURE_RECTANGLE_ARB) { | 573 if (target == GL_TEXTURE_EXTERNAL_OES || target == GL_TEXTURE_RECTANGLE_ARB) { |
572 min_filter_ = GL_LINEAR; | 574 sampler_state_.min_filter = GL_LINEAR; |
573 wrap_s_ = wrap_t_ = GL_CLAMP_TO_EDGE; | 575 sampler_state_.wrap_s = sampler_state_.wrap_t = GL_CLAMP_TO_EDGE; |
574 } | 576 } |
575 | 577 |
576 if (target == GL_TEXTURE_EXTERNAL_OES) { | 578 if (target == GL_TEXTURE_EXTERNAL_OES) { |
577 immutable_ = true; | 579 immutable_ = true; |
578 } | 580 } |
579 Update(feature_info); | 581 Update(feature_info); |
580 UpdateCanRenderCondition(); | 582 UpdateCanRenderCondition(); |
581 } | 583 } |
582 | 584 |
583 bool Texture::CanGenerateMipmaps( | 585 bool Texture::CanGenerateMipmaps( |
(...skipping 150 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
734 bool cleared = info->cleared_rect == gfx::Rect(info->width, info->height); | 736 bool cleared = info->cleared_rect == gfx::Rect(info->width, info->height); |
735 if (cleared == was_cleared) | 737 if (cleared == was_cleared) |
736 return; | 738 return; |
737 int delta = cleared ? -1 : +1; | 739 int delta = cleared ? -1 : +1; |
738 num_uncleared_mips_ += delta; | 740 num_uncleared_mips_ += delta; |
739 for (RefSet::iterator it = refs_.begin(); it != refs_.end(); ++it) | 741 for (RefSet::iterator it = refs_.begin(); it != refs_.end(); ++it) |
740 (*it)->manager()->UpdateUnclearedMips(delta); | 742 (*it)->manager()->UpdateUnclearedMips(delta); |
741 } | 743 } |
742 | 744 |
743 void Texture::UpdateCanRenderCondition() { | 745 void Texture::UpdateCanRenderCondition() { |
744 CanRenderCondition can_render_condition = GetCanRenderCondition(); | 746 can_render_condition_ = GetCanRenderCondition(); |
745 if (can_render_condition_ == can_render_condition) | |
746 return; | |
747 for (RefSet::iterator it = refs_.begin(); it != refs_.end(); ++it) | |
748 (*it)->manager()->UpdateCanRenderCondition(can_render_condition_, | |
749 can_render_condition); | |
750 can_render_condition_ = can_render_condition; | |
751 } | 747 } |
752 | 748 |
753 void Texture::UpdateHasImages() { | 749 void Texture::UpdateHasImages() { |
754 if (face_infos_.empty()) | 750 if (face_infos_.empty()) |
755 return; | 751 return; |
756 | 752 |
757 bool has_images = false; | 753 bool has_images = false; |
758 for (size_t ii = 0; ii < face_infos_.size(); ++ii) { | 754 for (size_t ii = 0; ii < face_infos_.size(); ++ii) { |
759 for (size_t jj = 0; jj < face_infos_[ii].level_infos.size(); ++jj) { | 755 for (size_t jj = 0; jj < face_infos_[ii].level_infos.size(); ++jj) { |
760 const Texture::LevelInfo& info = face_infos_[ii].level_infos[jj]; | 756 const Texture::LevelInfo& info = face_infos_[ii].level_infos[jj]; |
(...skipping 218 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
979 case GL_TEXTURE_MIN_LOD: | 975 case GL_TEXTURE_MIN_LOD: |
980 case GL_TEXTURE_MAX_LOD: | 976 case GL_TEXTURE_MAX_LOD: |
981 { | 977 { |
982 GLfloat fparam = static_cast<GLfloat>(param); | 978 GLfloat fparam = static_cast<GLfloat>(param); |
983 return SetParameterf(feature_info, pname, fparam); | 979 return SetParameterf(feature_info, pname, fparam); |
984 } | 980 } |
985 case GL_TEXTURE_MIN_FILTER: | 981 case GL_TEXTURE_MIN_FILTER: |
986 if (!feature_info->validators()->texture_min_filter_mode.IsValid(param)) { | 982 if (!feature_info->validators()->texture_min_filter_mode.IsValid(param)) { |
987 return GL_INVALID_ENUM; | 983 return GL_INVALID_ENUM; |
988 } | 984 } |
989 min_filter_ = param; | 985 sampler_state_.min_filter = param; |
990 break; | 986 break; |
991 case GL_TEXTURE_MAG_FILTER: | 987 case GL_TEXTURE_MAG_FILTER: |
992 if (!feature_info->validators()->texture_mag_filter_mode.IsValid(param)) { | 988 if (!feature_info->validators()->texture_mag_filter_mode.IsValid(param)) { |
993 return GL_INVALID_ENUM; | 989 return GL_INVALID_ENUM; |
994 } | 990 } |
995 mag_filter_ = param; | 991 sampler_state_.mag_filter = param; |
996 break; | 992 break; |
997 case GL_TEXTURE_WRAP_R: | 993 case GL_TEXTURE_WRAP_R: |
998 if (!feature_info->validators()->texture_wrap_mode.IsValid(param)) { | 994 if (!feature_info->validators()->texture_wrap_mode.IsValid(param)) { |
999 return GL_INVALID_ENUM; | 995 return GL_INVALID_ENUM; |
1000 } | 996 } |
1001 wrap_r_ = param; | 997 sampler_state_.wrap_r = param; |
1002 break; | 998 break; |
1003 case GL_TEXTURE_WRAP_S: | 999 case GL_TEXTURE_WRAP_S: |
1004 if (!feature_info->validators()->texture_wrap_mode.IsValid(param)) { | 1000 if (!feature_info->validators()->texture_wrap_mode.IsValid(param)) { |
1005 return GL_INVALID_ENUM; | 1001 return GL_INVALID_ENUM; |
1006 } | 1002 } |
1007 wrap_s_ = param; | 1003 sampler_state_.wrap_s = param; |
1008 break; | 1004 break; |
1009 case GL_TEXTURE_WRAP_T: | 1005 case GL_TEXTURE_WRAP_T: |
1010 if (!feature_info->validators()->texture_wrap_mode.IsValid(param)) { | 1006 if (!feature_info->validators()->texture_wrap_mode.IsValid(param)) { |
1011 return GL_INVALID_ENUM; | 1007 return GL_INVALID_ENUM; |
1012 } | 1008 } |
1013 wrap_t_ = param; | 1009 sampler_state_.wrap_t = param; |
1014 break; | 1010 break; |
1015 case GL_TEXTURE_COMPARE_FUNC: | 1011 case GL_TEXTURE_COMPARE_FUNC: |
1016 if (!feature_info->validators()->texture_compare_func.IsValid(param)) { | 1012 if (!feature_info->validators()->texture_compare_func.IsValid(param)) { |
1017 return GL_INVALID_ENUM; | 1013 return GL_INVALID_ENUM; |
1018 } | 1014 } |
1019 compare_func_ = param; | 1015 sampler_state_.compare_func = param; |
1020 break; | 1016 break; |
1021 case GL_TEXTURE_COMPARE_MODE: | 1017 case GL_TEXTURE_COMPARE_MODE: |
1022 if (!feature_info->validators()->texture_compare_mode.IsValid(param)) { | 1018 if (!feature_info->validators()->texture_compare_mode.IsValid(param)) { |
1023 return GL_INVALID_ENUM; | 1019 return GL_INVALID_ENUM; |
1024 } | 1020 } |
1025 compare_mode_ = param; | 1021 sampler_state_.compare_mode = param; |
1026 break; | 1022 break; |
1027 case GL_TEXTURE_BASE_LEVEL: | 1023 case GL_TEXTURE_BASE_LEVEL: |
1028 if (param < 0) { | 1024 if (param < 0) { |
1029 return GL_INVALID_VALUE; | 1025 return GL_INVALID_VALUE; |
1030 } | 1026 } |
1031 UpdateBaseLevel(param); | 1027 UpdateBaseLevel(param); |
1032 break; | 1028 break; |
1033 case GL_TEXTURE_MAX_LEVEL: | 1029 case GL_TEXTURE_MAX_LEVEL: |
1034 if (param < 0) { | 1030 if (param < 0) { |
1035 return GL_INVALID_VALUE; | 1031 return GL_INVALID_VALUE; |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1068 case GL_TEXTURE_COMPARE_FUNC: | 1064 case GL_TEXTURE_COMPARE_FUNC: |
1069 case GL_TEXTURE_COMPARE_MODE: | 1065 case GL_TEXTURE_COMPARE_MODE: |
1070 case GL_TEXTURE_BASE_LEVEL: | 1066 case GL_TEXTURE_BASE_LEVEL: |
1071 case GL_TEXTURE_MAX_LEVEL: | 1067 case GL_TEXTURE_MAX_LEVEL: |
1072 case GL_TEXTURE_USAGE_ANGLE: | 1068 case GL_TEXTURE_USAGE_ANGLE: |
1073 { | 1069 { |
1074 GLint iparam = static_cast<GLint>(param); | 1070 GLint iparam = static_cast<GLint>(param); |
1075 return SetParameteri(feature_info, pname, iparam); | 1071 return SetParameteri(feature_info, pname, iparam); |
1076 } | 1072 } |
1077 case GL_TEXTURE_MIN_LOD: | 1073 case GL_TEXTURE_MIN_LOD: |
1078 min_lod_ = param; | 1074 sampler_state_.min_lod = param; |
1079 break; | 1075 break; |
1080 case GL_TEXTURE_MAX_LOD: | 1076 case GL_TEXTURE_MAX_LOD: |
1081 max_lod_ = param; | 1077 sampler_state_.max_lod = param; |
1082 break; | 1078 break; |
1083 case GL_TEXTURE_MAX_ANISOTROPY_EXT: | 1079 case GL_TEXTURE_MAX_ANISOTROPY_EXT: |
1084 if (param < 1.f) { | 1080 if (param < 1.f) { |
1085 return GL_INVALID_VALUE; | 1081 return GL_INVALID_VALUE; |
1086 } | 1082 } |
1087 break; | 1083 break; |
1088 default: | 1084 default: |
1089 NOTREACHED(); | 1085 NOTREACHED(); |
1090 return GL_INVALID_ENUM; | 1086 return GL_INVALID_ENUM; |
1091 } | 1087 } |
(...skipping 17 matching lines...) Expand all Loading... |
1109 const Texture::LevelInfo& first_level = first_face.level_infos[base_level_]; | 1105 const Texture::LevelInfo& first_level = first_face.level_infos[base_level_]; |
1110 const GLsizei levels_needed = first_face.num_mip_levels; | 1106 const GLsizei levels_needed = first_face.num_mip_levels; |
1111 | 1107 |
1112 texture_complete_ = | 1108 texture_complete_ = |
1113 max_level_set_ >= (levels_needed - 1) && max_level_set_ >= 0; | 1109 max_level_set_ >= (levels_needed - 1) && max_level_set_ >= 0; |
1114 cube_complete_ = (face_infos_.size() == 6) && | 1110 cube_complete_ = (face_infos_.size() == 6) && |
1115 (first_level.width == first_level.height); | 1111 (first_level.width == first_level.height); |
1116 | 1112 |
1117 if (first_level.width == 0 || first_level.height == 0) { | 1113 if (first_level.width == 0 || first_level.height == 0) { |
1118 texture_complete_ = false; | 1114 texture_complete_ = false; |
1119 } else if (first_level.type == GL_FLOAT && | |
1120 !feature_info->feature_flags().enable_texture_float_linear && | |
1121 (min_filter_ != GL_NEAREST_MIPMAP_NEAREST || | |
1122 mag_filter_ != GL_NEAREST)) { | |
1123 texture_complete_ = false; | |
1124 } else if (first_level.type == GL_HALF_FLOAT_OES && | |
1125 !feature_info->feature_flags().enable_texture_half_float_linear && | |
1126 (min_filter_ != GL_NEAREST_MIPMAP_NEAREST || | |
1127 mag_filter_ != GL_NEAREST)) { | |
1128 texture_complete_ = false; | |
1129 } | 1115 } |
1130 | 1116 |
1131 bool texture_level0_complete = true; | 1117 bool texture_level0_complete = true; |
1132 if (cube_complete_ && texture_level0_dirty_) { | 1118 if (cube_complete_ && texture_level0_dirty_) { |
1133 for (size_t ii = 0; ii < face_infos_.size(); ++ii) { | 1119 for (size_t ii = 0; ii < face_infos_.size(); ++ii) { |
1134 const Texture::LevelInfo& face_base_level = | 1120 const Texture::LevelInfo& face_base_level = |
1135 face_infos_[ii].level_infos[base_level_]; | 1121 face_infos_[ii].level_infos[base_level_]; |
1136 if (!TextureFaceComplete(first_level, | 1122 if (!TextureFaceComplete(first_level, |
1137 ii, | 1123 ii, |
1138 face_base_level.target, | 1124 face_base_level.target, |
(...skipping 275 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1414 max_cube_map_levels_(ComputeMipMapCount(GL_TEXTURE_CUBE_MAP, | 1400 max_cube_map_levels_(ComputeMipMapCount(GL_TEXTURE_CUBE_MAP, |
1415 max_cube_map_texture_size, | 1401 max_cube_map_texture_size, |
1416 max_cube_map_texture_size, | 1402 max_cube_map_texture_size, |
1417 max_cube_map_texture_size)), | 1403 max_cube_map_texture_size)), |
1418 max_3d_levels_(ComputeMipMapCount(GL_TEXTURE_3D, | 1404 max_3d_levels_(ComputeMipMapCount(GL_TEXTURE_3D, |
1419 // Same as GL_TEXTURE_2D_ARRAY | 1405 // Same as GL_TEXTURE_2D_ARRAY |
1420 max_3d_texture_size, | 1406 max_3d_texture_size, |
1421 max_3d_texture_size, | 1407 max_3d_texture_size, |
1422 max_3d_texture_size)), | 1408 max_3d_texture_size)), |
1423 use_default_textures_(use_default_textures), | 1409 use_default_textures_(use_default_textures), |
1424 num_unrenderable_textures_(0), | |
1425 num_unsafe_textures_(0), | 1410 num_unsafe_textures_(0), |
1426 num_uncleared_mips_(0), | 1411 num_uncleared_mips_(0), |
1427 num_images_(0), | 1412 num_images_(0), |
1428 texture_count_(0), | 1413 texture_count_(0), |
1429 have_context_(true) { | 1414 have_context_(true) { |
1430 for (int ii = 0; ii < kNumDefaultTextures; ++ii) { | 1415 for (int ii = 0; ii < kNumDefaultTextures; ++ii) { |
1431 black_texture_ids_[ii] = 0; | 1416 black_texture_ids_[ii] = 0; |
1432 } | 1417 } |
1433 } | 1418 } |
1434 | 1419 |
(...skipping 267 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1702 textures_.erase(it); | 1687 textures_.erase(it); |
1703 } | 1688 } |
1704 } | 1689 } |
1705 | 1690 |
1706 void TextureManager::StartTracking(TextureRef* ref) { | 1691 void TextureManager::StartTracking(TextureRef* ref) { |
1707 Texture* texture = ref->texture(); | 1692 Texture* texture = ref->texture(); |
1708 ++texture_count_; | 1693 ++texture_count_; |
1709 num_uncleared_mips_ += texture->num_uncleared_mips(); | 1694 num_uncleared_mips_ += texture->num_uncleared_mips(); |
1710 if (!texture->SafeToRenderFrom()) | 1695 if (!texture->SafeToRenderFrom()) |
1711 ++num_unsafe_textures_; | 1696 ++num_unsafe_textures_; |
1712 if (!texture->CanRender(feature_info_.get())) | |
1713 ++num_unrenderable_textures_; | |
1714 if (texture->HasImages()) | 1697 if (texture->HasImages()) |
1715 ++num_images_; | 1698 ++num_images_; |
1716 } | 1699 } |
1717 | 1700 |
1718 void TextureManager::StopTracking(TextureRef* ref) { | 1701 void TextureManager::StopTracking(TextureRef* ref) { |
1719 if (ref->num_observers()) { | 1702 if (ref->num_observers()) { |
1720 for (unsigned int i = 0; i < destruction_observers_.size(); i++) { | 1703 for (unsigned int i = 0; i < destruction_observers_.size(); i++) { |
1721 destruction_observers_[i]->OnTextureRefDestroying(ref); | 1704 destruction_observers_[i]->OnTextureRefDestroying(ref); |
1722 } | 1705 } |
1723 DCHECK_EQ(ref->num_observers(), 0); | 1706 DCHECK_EQ(ref->num_observers(), 0); |
1724 } | 1707 } |
1725 | 1708 |
1726 Texture* texture = ref->texture(); | 1709 Texture* texture = ref->texture(); |
1727 | 1710 |
1728 --texture_count_; | 1711 --texture_count_; |
1729 if (texture->HasImages()) { | 1712 if (texture->HasImages()) { |
1730 DCHECK_NE(0, num_images_); | 1713 DCHECK_NE(0, num_images_); |
1731 --num_images_; | 1714 --num_images_; |
1732 } | 1715 } |
1733 if (!texture->CanRender(feature_info_.get())) { | |
1734 DCHECK_NE(0, num_unrenderable_textures_); | |
1735 --num_unrenderable_textures_; | |
1736 } | |
1737 if (!texture->SafeToRenderFrom()) { | 1716 if (!texture->SafeToRenderFrom()) { |
1738 DCHECK_NE(0, num_unsafe_textures_); | 1717 DCHECK_NE(0, num_unsafe_textures_); |
1739 --num_unsafe_textures_; | 1718 --num_unsafe_textures_; |
1740 } | 1719 } |
1741 num_uncleared_mips_ -= texture->num_uncleared_mips(); | 1720 num_uncleared_mips_ -= texture->num_uncleared_mips(); |
1742 DCHECK_GE(num_uncleared_mips_, 0); | 1721 DCHECK_GE(num_uncleared_mips_, 0); |
1743 } | 1722 } |
1744 | 1723 |
1745 MemoryTypeTracker* TextureManager::GetMemTracker() { | 1724 MemoryTypeTracker* TextureManager::GetMemTracker() { |
1746 return memory_type_tracker_.get(); | 1725 return memory_type_tracker_.get(); |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1794 void TextureManager::UpdateSafeToRenderFrom(int delta) { | 1773 void TextureManager::UpdateSafeToRenderFrom(int delta) { |
1795 num_unsafe_textures_ += delta; | 1774 num_unsafe_textures_ += delta; |
1796 DCHECK_GE(num_unsafe_textures_, 0); | 1775 DCHECK_GE(num_unsafe_textures_, 0); |
1797 } | 1776 } |
1798 | 1777 |
1799 void TextureManager::UpdateUnclearedMips(int delta) { | 1778 void TextureManager::UpdateUnclearedMips(int delta) { |
1800 num_uncleared_mips_ += delta; | 1779 num_uncleared_mips_ += delta; |
1801 DCHECK_GE(num_uncleared_mips_, 0); | 1780 DCHECK_GE(num_uncleared_mips_, 0); |
1802 } | 1781 } |
1803 | 1782 |
1804 void TextureManager::UpdateCanRenderCondition( | |
1805 Texture::CanRenderCondition old_condition, | |
1806 Texture::CanRenderCondition new_condition) { | |
1807 if (old_condition == Texture::CAN_RENDER_NEVER || | |
1808 (old_condition == Texture::CAN_RENDER_ONLY_IF_NPOT && | |
1809 !feature_info_->feature_flags().npot_ok)) { | |
1810 DCHECK_GT(num_unrenderable_textures_, 0); | |
1811 --num_unrenderable_textures_; | |
1812 } | |
1813 if (new_condition == Texture::CAN_RENDER_NEVER || | |
1814 (new_condition == Texture::CAN_RENDER_ONLY_IF_NPOT && | |
1815 !feature_info_->feature_flags().npot_ok)) | |
1816 ++num_unrenderable_textures_; | |
1817 } | |
1818 | |
1819 void TextureManager::UpdateNumImages(int delta) { | 1783 void TextureManager::UpdateNumImages(int delta) { |
1820 num_images_ += delta; | 1784 num_images_ += delta; |
1821 DCHECK_GE(num_images_, 0); | 1785 DCHECK_GE(num_images_, 0); |
1822 } | 1786 } |
1823 | 1787 |
1824 void TextureManager::IncFramebufferStateChangeCount() { | 1788 void TextureManager::IncFramebufferStateChangeCount() { |
1825 if (framebuffer_manager_) | 1789 if (framebuffer_manager_) |
1826 framebuffer_manager_->IncFramebufferStateChangeCount(); | 1790 framebuffer_manager_->IncFramebufferStateChangeCount(); |
1827 } | 1791 } |
1828 | 1792 |
(...skipping 793 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2622 return GL_HALF_FLOAT_OES; | 2586 return GL_HALF_FLOAT_OES; |
2623 case GL_BGRA8_EXT: | 2587 case GL_BGRA8_EXT: |
2624 return GL_UNSIGNED_BYTE; | 2588 return GL_UNSIGNED_BYTE; |
2625 default: | 2589 default: |
2626 return GL_NONE; | 2590 return GL_NONE; |
2627 } | 2591 } |
2628 } | 2592 } |
2629 | 2593 |
2630 } // namespace gles2 | 2594 } // namespace gles2 |
2631 } // namespace gpu | 2595 } // namespace gpu |
OLD | NEW |