1 // Copyright 2016 The SwiftShader Authors. All Rights Reserved. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 // Context.cpp: Implements the es1::Context class, managing all GL state and performing 16 // rendering operations. It is the GLES2 specific implementation of EGLContext. 17 18 #include "Context.h" 19 20 #include "main.h" 21 #include "mathutil.h" 22 #include "utilities.h" 23 #include "ResourceManager.h" 24 #include "Buffer.h" 25 #include "Framebuffer.h" 26 #include "Renderbuffer.h" 27 #include "Texture.h" 28 #include "VertexDataManager.h" 29 #include "IndexDataManager.h" 30 #include "libEGL/Display.h" 31 #include "libEGL/Surface.h" 32 #include "Common/Half.hpp" 33 34 #include <EGL/eglext.h> 35 36 using std::abs; 37 38 namespace es1 39 { 40 Context::Context(const egl::Config *config, const Context *shareContext) 41 : modelViewStack(MAX_MODELVIEW_STACK_DEPTH), 42 projectionStack(MAX_PROJECTION_STACK_DEPTH), 43 textureStack0(MAX_TEXTURE_STACK_DEPTH), 44 textureStack1(MAX_TEXTURE_STACK_DEPTH) 45 { 46 sw::Context *context = new sw::Context(); 47 device = new es1::Device(context); 48 49 mVertexDataManager = new VertexDataManager(this); 50 mIndexDataManager = new IndexDataManager(); 51 52 setClearColor(0.0f, 0.0f, 0.0f, 0.0f); 53 54 mState.depthClearValue = 1.0f; 55 mState.stencilClearValue = 0; 56 57 mState.cullFaceEnabled = false; 58 mState.cullMode = GL_BACK; 59 mState.frontFace = GL_CCW; 60 mState.depthTestEnabled = false; 61 mState.depthFunc = GL_LESS; 62 mState.blendEnabled = false; 63 mState.sourceBlendRGB = GL_ONE; 64 mState.sourceBlendAlpha = GL_ONE; 65 mState.destBlendRGB = GL_ZERO; 66 mState.destBlendAlpha = GL_ZERO; 67 mState.blendEquationRGB = GL_FUNC_ADD_OES; 68 mState.blendEquationAlpha = GL_FUNC_ADD_OES; 69 mState.stencilTestEnabled = false; 70 mState.stencilFunc = GL_ALWAYS; 71 mState.stencilRef = 0; 72 mState.stencilMask = -1; 73 mState.stencilWritemask = -1; 74 mState.stencilFail = GL_KEEP; 75 mState.stencilPassDepthFail = GL_KEEP; 76 mState.stencilPassDepthPass = GL_KEEP; 77 mState.polygonOffsetFillEnabled = false; 78 mState.polygonOffsetFactor = 0.0f; 79 mState.polygonOffsetUnits = 0.0f; 80 mState.sampleAlphaToCoverageEnabled = false; 81 mState.sampleCoverageEnabled = false; 82 mState.sampleCoverageValue = 1.0f; 83 mState.sampleCoverageInvert = false; 84 mState.scissorTestEnabled = false; 85 mState.ditherEnabled = true; 86 mState.shadeModel = GL_SMOOTH; 87 mState.generateMipmapHint = GL_DONT_CARE; 88 mState.perspectiveCorrectionHint = GL_DONT_CARE; 89 mState.fogHint = GL_DONT_CARE; 90 91 mState.lineWidth = 1.0f; 92 93 mState.viewportX = 0; 94 mState.viewportY = 0; 95 mState.viewportWidth = 0; 96 mState.viewportHeight = 0; 97 mState.zNear = 0.0f; 98 mState.zFar = 1.0f; 99 100 mState.scissorX = 0; 101 mState.scissorY = 0; 102 mState.scissorWidth = 0; 103 mState.scissorHeight = 0; 104 105 mState.colorMaskRed = true; 106 mState.colorMaskGreen = true; 107 mState.colorMaskBlue = true; 108 mState.colorMaskAlpha = true; 109 mState.depthMask = true; 110 111 for(int i = 0; i < MAX_TEXTURE_UNITS; i++) 112 { 113 mState.textureUnit[i].color = {0, 0, 0, 0}; 114 mState.textureUnit[i].environmentMode = GL_MODULATE; 115 mState.textureUnit[i].combineRGB = GL_MODULATE; 116 mState.textureUnit[i].combineAlpha = GL_MODULATE; 117 mState.textureUnit[i].src0RGB = GL_TEXTURE; 118 mState.textureUnit[i].src1RGB = GL_PREVIOUS; 119 mState.textureUnit[i].src2RGB = GL_CONSTANT; 120 mState.textureUnit[i].src0Alpha = GL_TEXTURE; 121 mState.textureUnit[i].src1Alpha = GL_PREVIOUS; 122 mState.textureUnit[i].src2Alpha = GL_CONSTANT; 123 mState.textureUnit[i].operand0RGB = GL_SRC_COLOR; 124 mState.textureUnit[i].operand1RGB = GL_SRC_COLOR; 125 mState.textureUnit[i].operand2RGB = GL_SRC_ALPHA; 126 mState.textureUnit[i].operand0Alpha = GL_SRC_ALPHA; 127 mState.textureUnit[i].operand1Alpha = GL_SRC_ALPHA; 128 mState.textureUnit[i].operand2Alpha = GL_SRC_ALPHA; 129 } 130 131 if(shareContext) 132 { 133 mResourceManager = shareContext->mResourceManager; 134 mResourceManager->addRef(); 135 } 136 else 137 { 138 mResourceManager = new ResourceManager(); 139 } 140 141 // [OpenGL ES 2.0.24] section 3.7 page 83: 142 // In the initial state, TEXTURE_2D and TEXTURE_CUBE_MAP have twodimensional 143 // and cube map texture state vectors respectively associated with them. 144 // In order that access to these initial textures not be lost, they are treated as texture 145 // objects all of whose names are 0. 146 147 mTexture2DZero = new Texture2D(0); 148 mTextureExternalZero = new TextureExternal(0); 149 150 mState.activeSampler = 0; 151 bindArrayBuffer(0); 152 bindElementArrayBuffer(0); 153 bindTexture2D(0); 154 bindFramebuffer(0); 155 bindRenderbuffer(0); 156 157 mState.packAlignment = 4; 158 mState.unpackAlignment = 4; 159 160 mInvalidEnum = false; 161 mInvalidValue = false; 162 mInvalidOperation = false; 163 mOutOfMemory = false; 164 mInvalidFramebufferOperation = false; 165 mMatrixStackOverflow = false; 166 mMatrixStackUnderflow = false; 167 168 lightingEnabled = false; 169 170 for(int i = 0; i < MAX_LIGHTS; i++) 171 { 172 light[i].enabled = false; 173 light[i].ambient = {0.0f, 0.0f, 0.0f, 1.0f}; 174 light[i].diffuse = {0.0f, 0.0f, 0.0f, 1.0f}; 175 light[i].specular = {0.0f, 0.0f, 0.0f, 1.0f}; 176 light[i].position = {0.0f, 0.0f, 1.0f, 0.0f}; 177 light[i].direction = {0.0f, 0.0f, -1.0f}; 178 light[i].attenuation = {1.0f, 0.0f, 0.0f}; 179 light[i].spotExponent = 0.0f; 180 light[i].spotCutoffAngle = 180.0f; 181 } 182 183 light[0].diffuse = {1.0f, 1.0f, 1.0f, 1.0f}; 184 light[0].specular = {1.0f, 1.0f, 1.0f, 1.0f}; 185 186 globalAmbient = {0.2f, 0.2f, 0.2f, 1.0f}; 187 materialAmbient = {0.2f, 0.2f, 0.2f, 1.0f}; 188 materialDiffuse = {0.8f, 0.8f, 0.8f, 1.0f}; 189 materialSpecular = {0.0f, 0.0f, 0.0f, 1.0f}; 190 materialEmission = {0.0f, 0.0f, 0.0f, 1.0f}; 191 materialShininess = 0.0f; 192 lightModelTwoSide = false; 193 194 matrixMode = GL_MODELVIEW; 195 196 for(int i = 0; i < MAX_TEXTURE_UNITS; i++) 197 { 198 texture2Denabled[i] = false; 199 textureExternalEnabled[i] = false; 200 } 201 202 clientTexture = GL_TEXTURE0; 203 204 setVertexAttrib(sw::Color0, 1.0f, 1.0f, 1.0f, 1.0f); 205 206 for(int i = 0; i < MAX_TEXTURE_UNITS; i++) 207 { 208 setVertexAttrib(sw::TexCoord0 + i, 0.0f, 0.0f, 0.0f, 1.0f); 209 } 210 211 setVertexAttrib(sw::Normal, 0.0f, 0.0f, 1.0f, 1.0f); 212 setVertexAttrib(sw::PointSize, 1.0f, 1.0f, 1.0f, 1.0f); 213 214 clipFlags = 0; 215 216 alphaTestEnabled = false; 217 alphaTestFunc = GL_ALWAYS; 218 alphaTestRef = 0; 219 220 fogEnabled = false; 221 fogMode = GL_EXP; 222 fogDensity = 1.0f; 223 fogStart = 0.0f; 224 fogEnd = 1.0f; 225 fogColor = {0, 0, 0, 0}; 226 227 lineSmoothEnabled = false; 228 colorMaterialEnabled = false; 229 normalizeEnabled = false; 230 rescaleNormalEnabled = false; 231 multisampleEnabled = true; 232 sampleAlphaToOneEnabled = false; 233 234 colorLogicOpEnabled = false; 235 logicalOperation = GL_COPY; 236 237 pointSpriteEnabled = false; 238 pointSmoothEnabled = false; 239 pointSizeMin = 0.0f; 240 pointSizeMax = 1.0f; 241 pointDistanceAttenuation = {1.0f, 0.0f, 0.0f}; 242 pointFadeThresholdSize = 1.0f; 243 244 mHasBeenCurrent = false; 245 246 markAllStateDirty(); 247 } 248 249 Context::~Context() 250 { 251 while(!mFramebufferNameSpace.empty()) 252 { 253 deleteFramebuffer(mFramebufferNameSpace.firstName()); 254 } 255 256 for(int type = 0; type < TEXTURE_TYPE_COUNT; type++) 257 { 258 for(int sampler = 0; sampler < MAX_TEXTURE_UNITS; sampler++) 259 { 260 mState.samplerTexture[type][sampler] = nullptr; 261 } 262 } 263 264 for(int i = 0; i < MAX_VERTEX_ATTRIBS; i++) 265 { 266 mState.vertexAttribute[i].mBoundBuffer = nullptr; 267 } 268 269 mState.arrayBuffer = nullptr; 270 mState.elementArrayBuffer = nullptr; 271 mState.renderbuffer = nullptr; 272 273 mTexture2DZero = nullptr; 274 mTextureExternalZero = nullptr; 275 276 delete mVertexDataManager; 277 delete mIndexDataManager; 278 279 mResourceManager->release(); 280 delete device; 281 } 282 283 void Context::makeCurrent(egl::Surface *surface) 284 { 285 if(!mHasBeenCurrent) 286 { 287 mState.viewportX = 0; 288 mState.viewportY = 0; 289 mState.viewportWidth = surface->getWidth(); 290 mState.viewportHeight = surface->getHeight(); 291 292 mState.scissorX = 0; 293 mState.scissorY = 0; 294 mState.scissorWidth = surface->getWidth(); 295 mState.scissorHeight = surface->getHeight(); 296 297 mHasBeenCurrent = true; 298 } 299 300 // Wrap the existing resources into GL objects and assign them to the '0' names 301 egl::Image *defaultRenderTarget = surface->getRenderTarget(); 302 egl::Image *depthStencil = surface->getDepthStencil(); 303 304 Colorbuffer *colorbufferZero = new Colorbuffer(defaultRenderTarget); 305 DepthStencilbuffer *depthStencilbufferZero = new DepthStencilbuffer(depthStencil); 306 Framebuffer *framebufferZero = new DefaultFramebuffer(colorbufferZero, depthStencilbufferZero); 307 308 setFramebufferZero(framebufferZero); 309 310 if(defaultRenderTarget) 311 { 312 defaultRenderTarget->release(); 313 } 314 315 if(depthStencil) 316 { 317 depthStencil->release(); 318 } 319 320 markAllStateDirty(); 321 } 322 323 int Context::getClientVersion() const 324 { 325 return 1; 326 } 327 328 // This function will set all of the state-related dirty flags, so that all state is set during next pre-draw. 329 void Context::markAllStateDirty() 330 { 331 mDepthStateDirty = true; 332 mMaskStateDirty = true; 333 mBlendStateDirty = true; 334 mStencilStateDirty = true; 335 mPolygonOffsetStateDirty = true; 336 mSampleStateDirty = true; 337 mDitherStateDirty = true; 338 mFrontFaceDirty = true; 339 } 340 341 void Context::setClearColor(float red, float green, float blue, float alpha) 342 { 343 mState.colorClearValue.red = red; 344 mState.colorClearValue.green = green; 345 mState.colorClearValue.blue = blue; 346 mState.colorClearValue.alpha = alpha; 347 } 348 349 void Context::setClearDepth(float depth) 350 { 351 mState.depthClearValue = depth; 352 } 353 354 void Context::setClearStencil(int stencil) 355 { 356 mState.stencilClearValue = stencil; 357 } 358 359 void Context::setCullFaceEnabled(bool enabled) 360 { 361 mState.cullFaceEnabled = enabled; 362 } 363 364 bool Context::isCullFaceEnabled() const 365 { 366 return mState.cullFaceEnabled; 367 } 368 369 void Context::setCullMode(GLenum mode) 370 { 371 mState.cullMode = mode; 372 } 373 374 void Context::setFrontFace(GLenum front) 375 { 376 if(mState.frontFace != front) 377 { 378 mState.frontFace = front; 379 mFrontFaceDirty = true; 380 } 381 } 382 383 void Context::setDepthTestEnabled(bool enabled) 384 { 385 if(mState.depthTestEnabled != enabled) 386 { 387 mState.depthTestEnabled = enabled; 388 mDepthStateDirty = true; 389 } 390 } 391 392 bool Context::isDepthTestEnabled() const 393 { 394 return mState.depthTestEnabled; 395 } 396 397 void Context::setDepthFunc(GLenum depthFunc) 398 { 399 if(mState.depthFunc != depthFunc) 400 { 401 mState.depthFunc = depthFunc; 402 mDepthStateDirty = true; 403 } 404 } 405 406 void Context::setDepthRange(float zNear, float zFar) 407 { 408 mState.zNear = zNear; 409 mState.zFar = zFar; 410 } 411 412 void Context::setAlphaTestEnabled(bool enabled) 413 { 414 alphaTestEnabled = enabled; 415 } 416 417 bool Context::isAlphaTestEnabled() const 418 { 419 return alphaTestEnabled; 420 } 421 422 void Context::setAlphaFunc(GLenum alphaFunc, GLclampf reference) 423 { 424 alphaTestFunc = alphaFunc; 425 alphaTestRef = reference; 426 } 427 428 void Context::setBlendEnabled(bool enabled) 429 { 430 if(mState.blendEnabled != enabled) 431 { 432 mState.blendEnabled = enabled; 433 mBlendStateDirty = true; 434 } 435 } 436 437 bool Context::isBlendEnabled() const 438 { 439 return mState.blendEnabled; 440 } 441 442 void Context::setBlendFactors(GLenum sourceRGB, GLenum destRGB, GLenum sourceAlpha, GLenum destAlpha) 443 { 444 if(mState.sourceBlendRGB != sourceRGB || 445 mState.sourceBlendAlpha != sourceAlpha || 446 mState.destBlendRGB != destRGB || 447 mState.destBlendAlpha != destAlpha) 448 { 449 mState.sourceBlendRGB = sourceRGB; 450 mState.destBlendRGB = destRGB; 451 mState.sourceBlendAlpha = sourceAlpha; 452 mState.destBlendAlpha = destAlpha; 453 mBlendStateDirty = true; 454 } 455 } 456 457 void Context::setBlendEquation(GLenum rgbEquation, GLenum alphaEquation) 458 { 459 if(mState.blendEquationRGB != rgbEquation || 460 mState.blendEquationAlpha != alphaEquation) 461 { 462 mState.blendEquationRGB = rgbEquation; 463 mState.blendEquationAlpha = alphaEquation; 464 mBlendStateDirty = true; 465 } 466 } 467 468 void Context::setStencilTestEnabled(bool enabled) 469 { 470 if(mState.stencilTestEnabled != enabled) 471 { 472 mState.stencilTestEnabled = enabled; 473 mStencilStateDirty = true; 474 } 475 } 476 477 bool Context::isStencilTestEnabled() const 478 { 479 return mState.stencilTestEnabled; 480 } 481 482 void Context::setStencilParams(GLenum stencilFunc, GLint stencilRef, GLuint stencilMask) 483 { 484 if(mState.stencilFunc != stencilFunc || 485 mState.stencilRef != stencilRef || 486 mState.stencilMask != stencilMask) 487 { 488 mState.stencilFunc = stencilFunc; 489 mState.stencilRef = (stencilRef > 0) ? stencilRef : 0; 490 mState.stencilMask = stencilMask; 491 mStencilStateDirty = true; 492 } 493 } 494 495 void Context::setStencilWritemask(GLuint stencilWritemask) 496 { 497 if(mState.stencilWritemask != stencilWritemask) 498 { 499 mState.stencilWritemask = stencilWritemask; 500 mStencilStateDirty = true; 501 } 502 } 503 504 void Context::setStencilOperations(GLenum stencilFail, GLenum stencilPassDepthFail, GLenum stencilPassDepthPass) 505 { 506 if(mState.stencilFail != stencilFail || 507 mState.stencilPassDepthFail != stencilPassDepthFail || 508 mState.stencilPassDepthPass != stencilPassDepthPass) 509 { 510 mState.stencilFail = stencilFail; 511 mState.stencilPassDepthFail = stencilPassDepthFail; 512 mState.stencilPassDepthPass = stencilPassDepthPass; 513 mStencilStateDirty = true; 514 } 515 } 516 517 void Context::setPolygonOffsetFillEnabled(bool enabled) 518 { 519 if(mState.polygonOffsetFillEnabled != enabled) 520 { 521 mState.polygonOffsetFillEnabled = enabled; 522 mPolygonOffsetStateDirty = true; 523 } 524 } 525 526 bool Context::isPolygonOffsetFillEnabled() const 527 { 528 return mState.polygonOffsetFillEnabled; 529 } 530 531 void Context::setPolygonOffsetParams(GLfloat factor, GLfloat units) 532 { 533 if(mState.polygonOffsetFactor != factor || 534 mState.polygonOffsetUnits != units) 535 { 536 mState.polygonOffsetFactor = factor; 537 mState.polygonOffsetUnits = units; 538 mPolygonOffsetStateDirty = true; 539 } 540 } 541 542 void Context::setSampleAlphaToCoverageEnabled(bool enabled) 543 { 544 if(mState.sampleAlphaToCoverageEnabled != enabled) 545 { 546 mState.sampleAlphaToCoverageEnabled = enabled; 547 mSampleStateDirty = true; 548 } 549 } 550 551 bool Context::isSampleAlphaToCoverageEnabled() const 552 { 553 return mState.sampleAlphaToCoverageEnabled; 554 } 555 556 void Context::setSampleCoverageEnabled(bool enabled) 557 { 558 if(mState.sampleCoverageEnabled != enabled) 559 { 560 mState.sampleCoverageEnabled = enabled; 561 mSampleStateDirty = true; 562 } 563 } 564 565 bool Context::isSampleCoverageEnabled() const 566 { 567 return mState.sampleCoverageEnabled; 568 } 569 570 void Context::setSampleCoverageParams(GLclampf value, bool invert) 571 { 572 if(mState.sampleCoverageValue != value || 573 mState.sampleCoverageInvert != invert) 574 { 575 mState.sampleCoverageValue = value; 576 mState.sampleCoverageInvert = invert; 577 mSampleStateDirty = true; 578 } 579 } 580 581 void Context::setScissorTestEnabled(bool enabled) 582 { 583 mState.scissorTestEnabled = enabled; 584 } 585 586 bool Context::isScissorTestEnabled() const 587 { 588 return mState.scissorTestEnabled; 589 } 590 591 void Context::setShadeModel(GLenum mode) 592 { 593 mState.shadeModel = mode; 594 } 595 596 void Context::setDitherEnabled(bool enabled) 597 { 598 if(mState.ditherEnabled != enabled) 599 { 600 mState.ditherEnabled = enabled; 601 mDitherStateDirty = true; 602 } 603 } 604 605 bool Context::isDitherEnabled() const 606 { 607 return mState.ditherEnabled; 608 } 609 610 void Context::setLightingEnabled(bool enable) 611 { 612 lightingEnabled = enable; 613 } 614 615 bool Context::isLightingEnabled() const 616 { 617 return lightingEnabled; 618 } 619 620 void Context::setLightEnabled(int index, bool enable) 621 { 622 light[index].enabled = enable; 623 } 624 625 bool Context::isLightEnabled(int index) const 626 { 627 return light[index].enabled; 628 } 629 630 void Context::setLightAmbient(int index, float r, float g, float b, float a) 631 { 632 light[index].ambient = {r, g, b, a}; 633 } 634 635 void Context::setLightDiffuse(int index, float r, float g, float b, float a) 636 { 637 light[index].diffuse = {r, g, b, a}; 638 } 639 640 void Context::setLightSpecular(int index, float r, float g, float b, float a) 641 { 642 light[index].specular = {r, g, b, a}; 643 } 644 645 void Context::setLightPosition(int index, float x, float y, float z, float w) 646 { 647 sw::float4 v = {x, y, z, w}; 648 649 // Transform from object coordinates to eye coordinates 650 v = modelViewStack.current() * v; 651 652 light[index].position = {v.x, v.y, v.z, v.w}; 653 } 654 655 void Context::setLightDirection(int index, float x, float y, float z) 656 { 657 // FIXME: Transform by inverse of 3x3 model-view matrix 658 light[index].direction = {x, y, z}; 659 } 660 661 void Context::setLightAttenuationConstant(int index, float constant) 662 { 663 light[index].attenuation.constant = constant; 664 } 665 666 void Context::setLightAttenuationLinear(int index, float linear) 667 { 668 light[index].attenuation.linear = linear; 669 } 670 671 void Context::setLightAttenuationQuadratic(int index, float quadratic) 672 { 673 light[index].attenuation.quadratic = quadratic; 674 } 675 676 void Context::setSpotLightExponent(int index, float exponent) 677 { 678 light[index].spotExponent = exponent; 679 } 680 681 void Context::setSpotLightCutoff(int index, float cutoff) 682 { 683 light[index].spotCutoffAngle = cutoff; 684 } 685 686 void Context::setGlobalAmbient(float red, float green, float blue, float alpha) 687 { 688 globalAmbient.red = red; 689 globalAmbient.green = green; 690 globalAmbient.blue = blue; 691 globalAmbient.alpha = alpha; 692 } 693 694 void Context::setMaterialAmbient(float red, float green, float blue, float alpha) 695 { 696 materialAmbient.red = red; 697 materialAmbient.green = green; 698 materialAmbient.blue = blue; 699 materialAmbient.alpha = alpha; 700 } 701 702 void Context::setMaterialDiffuse(float red, float green, float blue, float alpha) 703 { 704 materialDiffuse.red = red; 705 materialDiffuse.green = green; 706 materialDiffuse.blue = blue; 707 materialDiffuse.alpha = alpha; 708 } 709 710 void Context::setMaterialSpecular(float red, float green, float blue, float alpha) 711 { 712 materialSpecular.red = red; 713 materialSpecular.green = green; 714 materialSpecular.blue = blue; 715 materialSpecular.alpha = alpha; 716 } 717 718 void Context::setMaterialEmission(float red, float green, float blue, float alpha) 719 { 720 materialEmission.red = red; 721 materialEmission.green = green; 722 materialEmission.blue = blue; 723 materialEmission.alpha = alpha; 724 } 725 726 void Context::setMaterialShininess(float shininess) 727 { 728 materialShininess = shininess; 729 } 730 731 void Context::setLightModelTwoSide(bool enable) 732 { 733 lightModelTwoSide = enable; 734 } 735 736 void Context::setFogEnabled(bool enable) 737 { 738 fogEnabled = enable; 739 } 740 741 bool Context::isFogEnabled() const 742 { 743 return fogEnabled; 744 } 745 746 void Context::setFogMode(GLenum mode) 747 { 748 fogMode = mode; 749 } 750 751 void Context::setFogDensity(float fogDensity) 752 { 753 this->fogDensity = fogDensity; 754 } 755 756 void Context::setFogStart(float fogStart) 757 { 758 this->fogStart = fogStart; 759 } 760 761 void Context::setFogEnd(float fogEnd) 762 { 763 this->fogEnd = fogEnd; 764 } 765 766 void Context::setFogColor(float r, float g, float b, float a) 767 { 768 this->fogColor = {r, g, b, a}; 769 } 770 771 void Context::setTexture2Denabled(bool enable) 772 { 773 texture2Denabled[mState.activeSampler] = enable; 774 } 775 776 bool Context::isTexture2Denabled() const 777 { 778 return texture2Denabled[mState.activeSampler]; 779 } 780 781 void Context::setTextureExternalEnabled(bool enable) 782 { 783 textureExternalEnabled[mState.activeSampler] = enable; 784 } 785 786 bool Context::isTextureExternalEnabled() const 787 { 788 return textureExternalEnabled[mState.activeSampler]; 789 } 790 791 void Context::setLineWidth(GLfloat width) 792 { 793 mState.lineWidth = width; 794 device->setLineWidth(clamp(width, ALIASED_LINE_WIDTH_RANGE_MIN, ALIASED_LINE_WIDTH_RANGE_MAX)); 795 } 796 797 void Context::setGenerateMipmapHint(GLenum hint) 798 { 799 mState.generateMipmapHint = hint; 800 } 801 802 void Context::setPerspectiveCorrectionHint(GLenum hint) 803 { 804 mState.perspectiveCorrectionHint = hint; 805 } 806 807 void Context::setFogHint(GLenum hint) 808 { 809 mState.fogHint = hint; 810 } 811 812 void Context::setViewportParams(GLint x, GLint y, GLsizei width, GLsizei height) 813 { 814 mState.viewportX = x; 815 mState.viewportY = y; 816 mState.viewportWidth = width; 817 mState.viewportHeight = height; 818 } 819 820 void Context::setScissorParams(GLint x, GLint y, GLsizei width, GLsizei height) 821 { 822 mState.scissorX = x; 823 mState.scissorY = y; 824 mState.scissorWidth = width; 825 mState.scissorHeight = height; 826 } 827 828 void Context::setColorMask(bool red, bool green, bool blue, bool alpha) 829 { 830 if(mState.colorMaskRed != red || mState.colorMaskGreen != green || 831 mState.colorMaskBlue != blue || mState.colorMaskAlpha != alpha) 832 { 833 mState.colorMaskRed = red; 834 mState.colorMaskGreen = green; 835 mState.colorMaskBlue = blue; 836 mState.colorMaskAlpha = alpha; 837 mMaskStateDirty = true; 838 } 839 } 840 841 void Context::setDepthMask(bool mask) 842 { 843 if(mState.depthMask != mask) 844 { 845 mState.depthMask = mask; 846 mMaskStateDirty = true; 847 } 848 } 849 850 void Context::setActiveSampler(unsigned int active) 851 { 852 mState.activeSampler = active; 853 } 854 855 GLuint Context::getFramebufferName() const 856 { 857 return mState.framebuffer; 858 } 859 860 GLuint Context::getRenderbufferName() const 861 { 862 return mState.renderbuffer.name(); 863 } 864 865 GLuint Context::getArrayBufferName() const 866 { 867 return mState.arrayBuffer.name(); 868 } 869 870 void Context::setVertexAttribArrayEnabled(unsigned int attribNum, bool enabled) 871 { 872 mState.vertexAttribute[attribNum].mArrayEnabled = enabled; 873 } 874 875 const VertexAttribute &Context::getVertexAttribState(unsigned int attribNum) 876 { 877 return mState.vertexAttribute[attribNum]; 878 } 879 880 void Context::setVertexAttribState(unsigned int attribNum, Buffer *boundBuffer, GLint size, GLenum type, bool normalized, 881 GLsizei stride, const void *pointer) 882 { 883 mState.vertexAttribute[attribNum].mBoundBuffer = boundBuffer; 884 mState.vertexAttribute[attribNum].mSize = size; 885 mState.vertexAttribute[attribNum].mType = type; 886 mState.vertexAttribute[attribNum].mNormalized = normalized; 887 mState.vertexAttribute[attribNum].mStride = stride; 888 mState.vertexAttribute[attribNum].mPointer = pointer; 889 } 890 891 const void *Context::getVertexAttribPointer(unsigned int attribNum) const 892 { 893 return mState.vertexAttribute[attribNum].mPointer; 894 } 895 896 const VertexAttributeArray &Context::getVertexAttributes() 897 { 898 return mState.vertexAttribute; 899 } 900 901 void Context::setPackAlignment(GLint alignment) 902 { 903 mState.packAlignment = alignment; 904 } 905 906 GLint Context::getPackAlignment() const 907 { 908 return mState.packAlignment; 909 } 910 911 void Context::setUnpackAlignment(GLint alignment) 912 { 913 mState.unpackAlignment = alignment; 914 } 915 916 GLint Context::getUnpackAlignment() const 917 { 918 return mState.unpackAlignment; 919 } 920 921 GLuint Context::createBuffer() 922 { 923 return mResourceManager->createBuffer(); 924 } 925 926 GLuint Context::createTexture() 927 { 928 return mResourceManager->createTexture(); 929 } 930 931 GLuint Context::createRenderbuffer() 932 { 933 return mResourceManager->createRenderbuffer(); 934 } 935 936 // Returns an unused framebuffer name 937 GLuint Context::createFramebuffer() 938 { 939 return mFramebufferNameSpace.allocate(); 940 } 941 942 void Context::deleteBuffer(GLuint buffer) 943 { 944 detachBuffer(buffer); 945 946 mResourceManager->deleteBuffer(buffer); 947 } 948 949 void Context::deleteTexture(GLuint texture) 950 { 951 detachTexture(texture); 952 953 mResourceManager->deleteTexture(texture); 954 } 955 956 void Context::deleteRenderbuffer(GLuint renderbuffer) 957 { 958 detachRenderbuffer(renderbuffer); 959 960 mResourceManager->deleteRenderbuffer(renderbuffer); 961 } 962 963 void Context::deleteFramebuffer(GLuint framebuffer) 964 { 965 detachFramebuffer(framebuffer); 966 967 Framebuffer *framebufferObject = mFramebufferNameSpace.remove(framebuffer); 968 969 if(framebufferObject) 970 { 971 delete framebufferObject; 972 } 973 } 974 975 Buffer *Context::getBuffer(GLuint handle) 976 { 977 return mResourceManager->getBuffer(handle); 978 } 979 980 Texture *Context::getTexture(GLuint handle) 981 { 982 return mResourceManager->getTexture(handle); 983 } 984 985 Renderbuffer *Context::getRenderbuffer(GLuint handle) 986 { 987 return mResourceManager->getRenderbuffer(handle); 988 } 989 990 Framebuffer *Context::getFramebuffer() 991 { 992 return getFramebuffer(mState.framebuffer); 993 } 994 995 void Context::bindArrayBuffer(unsigned int buffer) 996 { 997 mResourceManager->checkBufferAllocation(buffer); 998 999 mState.arrayBuffer = getBuffer(buffer); 1000 } 1001 1002 void Context::bindElementArrayBuffer(unsigned int buffer) 1003 { 1004 mResourceManager->checkBufferAllocation(buffer); 1005 1006 mState.elementArrayBuffer = getBuffer(buffer); 1007 } 1008 1009 void Context::bindTexture2D(GLuint texture) 1010 { 1011 mResourceManager->checkTextureAllocation(texture, TEXTURE_2D); 1012 1013 mState.samplerTexture[TEXTURE_2D][mState.activeSampler] = getTexture(texture); 1014 } 1015 1016 void Context::bindTextureExternal(GLuint texture) 1017 { 1018 mResourceManager->checkTextureAllocation(texture, TEXTURE_EXTERNAL); 1019 1020 mState.samplerTexture[TEXTURE_EXTERNAL][mState.activeSampler] = getTexture(texture); 1021 } 1022 1023 void Context::bindFramebuffer(GLuint framebuffer) 1024 { 1025 if(!getFramebuffer(framebuffer)) 1026 { 1027 mFramebufferNameSpace.insert(framebuffer, new Framebuffer()); 1028 } 1029 1030 mState.framebuffer = framebuffer; 1031 } 1032 1033 void Context::bindRenderbuffer(GLuint renderbuffer) 1034 { 1035 mResourceManager->checkRenderbufferAllocation(renderbuffer); 1036 1037 mState.renderbuffer = getRenderbuffer(renderbuffer); 1038 } 1039 1040 void Context::setFramebufferZero(Framebuffer *buffer) 1041 { 1042 delete mFramebufferNameSpace.remove(0); 1043 mFramebufferNameSpace.insert(0, buffer); 1044 } 1045 1046 void Context::setRenderbufferStorage(RenderbufferStorage *renderbuffer) 1047 { 1048 Renderbuffer *renderbufferObject = mState.renderbuffer; 1049 renderbufferObject->setStorage(renderbuffer); 1050 } 1051 1052 Framebuffer *Context::getFramebuffer(unsigned int handle) 1053 { 1054 return mFramebufferNameSpace.find(handle); 1055 } 1056 1057 Buffer *Context::getArrayBuffer() 1058 { 1059 return mState.arrayBuffer; 1060 } 1061 1062 Buffer *Context::getElementArrayBuffer() 1063 { 1064 return mState.elementArrayBuffer; 1065 } 1066 1067 Texture2D *Context::getTexture2D() 1068 { 1069 return static_cast<Texture2D*>(getSamplerTexture(mState.activeSampler, TEXTURE_2D)); 1070 } 1071 1072 TextureExternal *Context::getTextureExternal() 1073 { 1074 return static_cast<TextureExternal*>(getSamplerTexture(mState.activeSampler, TEXTURE_EXTERNAL)); 1075 } 1076 1077 Texture *Context::getSamplerTexture(unsigned int sampler, TextureType type) 1078 { 1079 GLuint texid = mState.samplerTexture[type][sampler].name(); 1080 1081 if(texid == 0) // Special case: 0 refers to different initial textures based on the target 1082 { 1083 switch(type) 1084 { 1085 case TEXTURE_2D: return mTexture2DZero; 1086 case TEXTURE_EXTERNAL: return mTextureExternalZero; 1087 default: UNREACHABLE(type); 1088 } 1089 } 1090 1091 return mState.samplerTexture[type][sampler]; 1092 } 1093 1094 bool Context::getBooleanv(GLenum pname, GLboolean *params) 1095 { 1096 switch(pname) 1097 { 1098 case GL_SAMPLE_COVERAGE_INVERT: *params = mState.sampleCoverageInvert; break; 1099 case GL_DEPTH_WRITEMASK: *params = mState.depthMask; break; 1100 case GL_COLOR_WRITEMASK: 1101 params[0] = mState.colorMaskRed; 1102 params[1] = mState.colorMaskGreen; 1103 params[2] = mState.colorMaskBlue; 1104 params[3] = mState.colorMaskAlpha; 1105 break; 1106 case GL_CULL_FACE: *params = mState.cullFaceEnabled; break; 1107 case GL_POLYGON_OFFSET_FILL: *params = mState.polygonOffsetFillEnabled; break; 1108 case GL_SAMPLE_ALPHA_TO_COVERAGE: *params = mState.sampleAlphaToCoverageEnabled; break; 1109 case GL_SAMPLE_COVERAGE: *params = mState.sampleCoverageEnabled; break; 1110 case GL_SCISSOR_TEST: *params = mState.scissorTestEnabled; break; 1111 case GL_STENCIL_TEST: *params = mState.stencilTestEnabled; break; 1112 case GL_DEPTH_TEST: *params = mState.depthTestEnabled; break; 1113 case GL_BLEND: *params = mState.blendEnabled; break; 1114 case GL_DITHER: *params = mState.ditherEnabled; break; 1115 case GL_LIGHT_MODEL_TWO_SIDE: *params = lightModelTwoSide; break; 1116 default: 1117 return false; 1118 } 1119 1120 return true; 1121 } 1122 1123 bool Context::getFloatv(GLenum pname, GLfloat *params) 1124 { 1125 // Please note: DEPTH_CLEAR_VALUE is included in our internal getFloatv implementation 1126 // because it is stored as a float, despite the fact that the GL ES 2.0 spec names 1127 // GetIntegerv as its native query function. As it would require conversion in any 1128 // case, this should make no difference to the calling application. 1129 switch(pname) 1130 { 1131 case GL_LINE_WIDTH: *params = mState.lineWidth; break; 1132 case GL_SAMPLE_COVERAGE_VALUE: *params = mState.sampleCoverageValue; break; 1133 case GL_DEPTH_CLEAR_VALUE: *params = mState.depthClearValue; break; 1134 case GL_POLYGON_OFFSET_FACTOR: *params = mState.polygonOffsetFactor; break; 1135 case GL_POLYGON_OFFSET_UNITS: *params = mState.polygonOffsetUnits; break; 1136 case GL_ALIASED_LINE_WIDTH_RANGE: 1137 params[0] = ALIASED_LINE_WIDTH_RANGE_MIN; 1138 params[1] = ALIASED_LINE_WIDTH_RANGE_MAX; 1139 break; 1140 case GL_ALIASED_POINT_SIZE_RANGE: 1141 params[0] = ALIASED_POINT_SIZE_RANGE_MIN; 1142 params[1] = ALIASED_POINT_SIZE_RANGE_MAX; 1143 break; 1144 case GL_SMOOTH_LINE_WIDTH_RANGE: 1145 params[0] = SMOOTH_LINE_WIDTH_RANGE_MIN; 1146 params[1] = SMOOTH_LINE_WIDTH_RANGE_MAX; 1147 break; 1148 case GL_SMOOTH_POINT_SIZE_RANGE: 1149 params[0] = SMOOTH_POINT_SIZE_RANGE_MIN; 1150 params[1] = SMOOTH_POINT_SIZE_RANGE_MAX; 1151 break; 1152 case GL_DEPTH_RANGE: 1153 params[0] = mState.zNear; 1154 params[1] = mState.zFar; 1155 break; 1156 case GL_COLOR_CLEAR_VALUE: 1157 params[0] = mState.colorClearValue.red; 1158 params[1] = mState.colorClearValue.green; 1159 params[2] = mState.colorClearValue.blue; 1160 params[3] = mState.colorClearValue.alpha; 1161 break; 1162 case GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT: 1163 *params = MAX_TEXTURE_MAX_ANISOTROPY; 1164 break; 1165 case GL_MODELVIEW_MATRIX: 1166 for(int i = 0; i < 16; i++) 1167 { 1168 params[i] = modelViewStack.current()[i % 4][i / 4]; 1169 } 1170 break; 1171 case GL_PROJECTION_MATRIX: 1172 for(int i = 0; i < 16; i++) 1173 { 1174 params[i] = projectionStack.current()[i % 4][i / 4]; 1175 } 1176 break; 1177 default: 1178 return false; 1179 } 1180 1181 return true; 1182 } 1183 1184 bool Context::getIntegerv(GLenum pname, GLint *params) 1185 { 1186 // Please note: DEPTH_CLEAR_VALUE is not included in our internal getIntegerv implementation 1187 // because it is stored as a float, despite the fact that the GL ES 2.0 spec names 1188 // GetIntegerv as its native query function. As it would require conversion in any 1189 // case, this should make no difference to the calling application. You may find it in 1190 // Context::getFloatv. 1191 switch(pname) 1192 { 1193 case GL_ARRAY_BUFFER_BINDING: *params = mState.arrayBuffer.name(); break; 1194 case GL_ELEMENT_ARRAY_BUFFER_BINDING: *params = mState.elementArrayBuffer.name(); break; 1195 case GL_FRAMEBUFFER_BINDING_OES: *params = mState.framebuffer; break; 1196 case GL_RENDERBUFFER_BINDING_OES: *params = mState.renderbuffer.name(); break; 1197 case GL_PACK_ALIGNMENT: *params = mState.packAlignment; break; 1198 case GL_UNPACK_ALIGNMENT: *params = mState.unpackAlignment; break; 1199 case GL_GENERATE_MIPMAP_HINT: *params = mState.generateMipmapHint; break; 1200 case GL_PERSPECTIVE_CORRECTION_HINT: *params = mState.perspectiveCorrectionHint; break; 1201 case GL_ACTIVE_TEXTURE: *params = (mState.activeSampler + GL_TEXTURE0); break; 1202 case GL_STENCIL_FUNC: *params = mState.stencilFunc; break; 1203 case GL_STENCIL_REF: *params = mState.stencilRef; break; 1204 case GL_STENCIL_VALUE_MASK: *params = mState.stencilMask; break; 1205 case GL_STENCIL_FAIL: *params = mState.stencilFail; break; 1206 case GL_STENCIL_PASS_DEPTH_FAIL: *params = mState.stencilPassDepthFail; break; 1207 case GL_STENCIL_PASS_DEPTH_PASS: *params = mState.stencilPassDepthPass; break; 1208 case GL_DEPTH_FUNC: *params = mState.depthFunc; break; 1209 case GL_BLEND_SRC_RGB_OES: *params = mState.sourceBlendRGB; break; 1210 case GL_BLEND_SRC_ALPHA_OES: *params = mState.sourceBlendAlpha; break; 1211 case GL_BLEND_DST_RGB_OES: *params = mState.destBlendRGB; break; 1212 case GL_BLEND_DST_ALPHA_OES: *params = mState.destBlendAlpha; break; 1213 case GL_BLEND_EQUATION_RGB_OES: *params = mState.blendEquationRGB; break; 1214 case GL_BLEND_EQUATION_ALPHA_OES: *params = mState.blendEquationAlpha; break; 1215 case GL_STENCIL_WRITEMASK: *params = mState.stencilWritemask; break; 1216 case GL_STENCIL_CLEAR_VALUE: *params = mState.stencilClearValue; break; 1217 case GL_SUBPIXEL_BITS: *params = 4; break; 1218 case GL_MAX_TEXTURE_SIZE: *params = IMPLEMENTATION_MAX_TEXTURE_SIZE; break; 1219 case GL_NUM_COMPRESSED_TEXTURE_FORMATS: *params = NUM_COMPRESSED_TEXTURE_FORMATS; break; 1220 case GL_SAMPLE_BUFFERS: 1221 case GL_SAMPLES: 1222 { 1223 Framebuffer *framebuffer = getFramebuffer(); 1224 int width, height, samples; 1225 1226 if(framebuffer->completeness(width, height, samples) == GL_FRAMEBUFFER_COMPLETE_OES) 1227 { 1228 switch(pname) 1229 { 1230 case GL_SAMPLE_BUFFERS: 1231 if(samples > 1) 1232 { 1233 *params = 1; 1234 } 1235 else 1236 { 1237 *params = 0; 1238 } 1239 break; 1240 case GL_SAMPLES: 1241 *params = samples; 1242 break; 1243 } 1244 } 1245 else 1246 { 1247 *params = 0; 1248 } 1249 } 1250 break; 1251 case GL_IMPLEMENTATION_COLOR_READ_TYPE_OES: 1252 { 1253 Framebuffer *framebuffer = getFramebuffer(); 1254 *params = framebuffer->getImplementationColorReadType(); 1255 } 1256 break; 1257 case GL_IMPLEMENTATION_COLOR_READ_FORMAT_OES: 1258 { 1259 Framebuffer *framebuffer = getFramebuffer(); 1260 *params = framebuffer->getImplementationColorReadFormat(); 1261 } 1262 break; 1263 case GL_MAX_VIEWPORT_DIMS: 1264 { 1265 int maxDimension = IMPLEMENTATION_MAX_RENDERBUFFER_SIZE; 1266 params[0] = maxDimension; 1267 params[1] = maxDimension; 1268 } 1269 break; 1270 case GL_COMPRESSED_TEXTURE_FORMATS: 1271 { 1272 for(int i = 0; i < NUM_COMPRESSED_TEXTURE_FORMATS; i++) 1273 { 1274 params[i] = compressedTextureFormats[i]; 1275 } 1276 } 1277 break; 1278 case GL_VIEWPORT: 1279 params[0] = mState.viewportX; 1280 params[1] = mState.viewportY; 1281 params[2] = mState.viewportWidth; 1282 params[3] = mState.viewportHeight; 1283 break; 1284 case GL_SCISSOR_BOX: 1285 params[0] = mState.scissorX; 1286 params[1] = mState.scissorY; 1287 params[2] = mState.scissorWidth; 1288 params[3] = mState.scissorHeight; 1289 break; 1290 case GL_CULL_FACE_MODE: *params = mState.cullMode; break; 1291 case GL_FRONT_FACE: *params = mState.frontFace; break; 1292 case GL_RED_BITS: 1293 case GL_GREEN_BITS: 1294 case GL_BLUE_BITS: 1295 case GL_ALPHA_BITS: 1296 { 1297 Framebuffer *framebuffer = getFramebuffer(); 1298 Renderbuffer *colorbuffer = framebuffer->getColorbuffer(); 1299 1300 if(colorbuffer) 1301 { 1302 switch(pname) 1303 { 1304 case GL_RED_BITS: *params = colorbuffer->getRedSize(); break; 1305 case GL_GREEN_BITS: *params = colorbuffer->getGreenSize(); break; 1306 case GL_BLUE_BITS: *params = colorbuffer->getBlueSize(); break; 1307 case GL_ALPHA_BITS: *params = colorbuffer->getAlphaSize(); break; 1308 } 1309 } 1310 else 1311 { 1312 *params = 0; 1313 } 1314 } 1315 break; 1316 case GL_DEPTH_BITS: 1317 { 1318 Framebuffer *framebuffer = getFramebuffer(); 1319 Renderbuffer *depthbuffer = framebuffer->getDepthbuffer(); 1320 1321 if(depthbuffer) 1322 { 1323 *params = depthbuffer->getDepthSize(); 1324 } 1325 else 1326 { 1327 *params = 0; 1328 } 1329 } 1330 break; 1331 case GL_STENCIL_BITS: 1332 { 1333 Framebuffer *framebuffer = getFramebuffer(); 1334 Renderbuffer *stencilbuffer = framebuffer->getStencilbuffer(); 1335 1336 if(stencilbuffer) 1337 { 1338 *params = stencilbuffer->getStencilSize(); 1339 } 1340 else 1341 { 1342 *params = 0; 1343 } 1344 } 1345 break; 1346 case GL_TEXTURE_BINDING_2D: *params = mState.samplerTexture[TEXTURE_2D][mState.activeSampler].name(); break; 1347 case GL_TEXTURE_BINDING_CUBE_MAP_OES: *params = mState.samplerTexture[TEXTURE_CUBE][mState.activeSampler].name(); break; 1348 case GL_TEXTURE_BINDING_EXTERNAL_OES: *params = mState.samplerTexture[TEXTURE_EXTERNAL][mState.activeSampler].name(); break; 1349 case GL_MAX_LIGHTS: *params = MAX_LIGHTS; break; 1350 case GL_MAX_MODELVIEW_STACK_DEPTH: *params = MAX_MODELVIEW_STACK_DEPTH; break; 1351 case GL_MAX_PROJECTION_STACK_DEPTH: *params = MAX_PROJECTION_STACK_DEPTH; break; 1352 case GL_MAX_TEXTURE_STACK_DEPTH: *params = MAX_TEXTURE_STACK_DEPTH; break; 1353 case GL_MAX_TEXTURE_UNITS: *params = MAX_TEXTURE_UNITS; break; 1354 case GL_MAX_CLIP_PLANES: *params = MAX_CLIP_PLANES; break; 1355 case GL_POINT_SIZE_ARRAY_TYPE_OES: *params = mState.vertexAttribute[sw::PointSize].mType; break; 1356 case GL_POINT_SIZE_ARRAY_STRIDE_OES: *params = mState.vertexAttribute[sw::PointSize].mStride; break; 1357 case GL_POINT_SIZE_ARRAY_BUFFER_BINDING_OES: *params = mState.vertexAttribute[sw::PointSize].mBoundBuffer.name(); break; 1358 case GL_VERTEX_ARRAY_SIZE: *params = mState.vertexAttribute[sw::Position].mSize; break; 1359 case GL_VERTEX_ARRAY_TYPE: *params = mState.vertexAttribute[sw::Position].mType; break; 1360 case GL_VERTEX_ARRAY_STRIDE: *params = mState.vertexAttribute[sw::Position].mStride; break; 1361 case GL_VERTEX_ARRAY_BUFFER_BINDING: *params = mState.vertexAttribute[sw::Position].mBoundBuffer.name(); break; 1362 case GL_NORMAL_ARRAY_TYPE: *params = mState.vertexAttribute[sw::Normal].mType; break; 1363 case GL_NORMAL_ARRAY_STRIDE: *params = mState.vertexAttribute[sw::Normal].mStride; break; 1364 case GL_NORMAL_ARRAY_BUFFER_BINDING: *params = mState.vertexAttribute[sw::Normal].mBoundBuffer.name(); break; 1365 case GL_COLOR_ARRAY_SIZE: *params = mState.vertexAttribute[sw::Color0].mSize; break; 1366 case GL_COLOR_ARRAY_TYPE: *params = mState.vertexAttribute[sw::Color0].mType; break; 1367 case GL_COLOR_ARRAY_STRIDE: *params = mState.vertexAttribute[sw::Color0].mStride; break; 1368 case GL_COLOR_ARRAY_BUFFER_BINDING: *params = mState.vertexAttribute[sw::Color0].mBoundBuffer.name(); break; 1369 case GL_TEXTURE_COORD_ARRAY_SIZE: *params = mState.vertexAttribute[sw::TexCoord0 + mState.activeSampler].mSize; break; 1370 case GL_TEXTURE_COORD_ARRAY_TYPE: *params = mState.vertexAttribute[sw::TexCoord0 + mState.activeSampler].mType; break; 1371 case GL_TEXTURE_COORD_ARRAY_STRIDE: *params = mState.vertexAttribute[sw::TexCoord0 + mState.activeSampler].mStride; break; 1372 case GL_TEXTURE_COORD_ARRAY_BUFFER_BINDING: *params = mState.vertexAttribute[sw::TexCoord0 + mState.activeSampler].mBoundBuffer.name(); break; 1373 default: 1374 return false; 1375 } 1376 1377 return true; 1378 } 1379 1380 bool Context::getPointerv(GLenum pname, const GLvoid **params) 1381 { 1382 switch(pname) 1383 { 1384 case GL_VERTEX_ARRAY_POINTER: *params = mState.vertexAttribute[sw::Position].mPointer; break; 1385 case GL_NORMAL_ARRAY_POINTER: *params = mState.vertexAttribute[sw::Normal].mPointer; break; 1386 case GL_COLOR_ARRAY_POINTER: *params = mState.vertexAttribute[sw::Color0].mPointer; break; 1387 case GL_POINT_SIZE_ARRAY_POINTER_OES: *params = mState.vertexAttribute[sw::PointSize].mPointer; break; 1388 case GL_TEXTURE_COORD_ARRAY_POINTER: *params = mState.vertexAttribute[sw::TexCoord0 + mState.activeSampler].mPointer; break; 1389 default: 1390 return false; 1391 } 1392 1393 return true; 1394 } 1395 1396 int Context::getQueryParameterNum(GLenum pname) 1397 { 1398 // Please note: the query type returned for DEPTH_CLEAR_VALUE in this implementation 1399 // is FLOAT rather than INT, as would be suggested by the GL ES 2.0 spec. This is due 1400 // to the fact that it is stored internally as a float, and so would require conversion 1401 // if returned from Context::getIntegerv. Since this conversion is already implemented 1402 // in the case that one calls glGetIntegerv to retrieve a float-typed state variable, we 1403 // place DEPTH_CLEAR_VALUE with the floats. This should make no difference to the calling 1404 // application. 1405 switch(pname) 1406 { 1407 case GL_COMPRESSED_TEXTURE_FORMATS: 1408 return NUM_COMPRESSED_TEXTURE_FORMATS; 1409 case GL_NUM_COMPRESSED_TEXTURE_FORMATS: 1410 case GL_ARRAY_BUFFER_BINDING: 1411 case GL_FRAMEBUFFER_BINDING_OES: 1412 case GL_RENDERBUFFER_BINDING_OES: 1413 case GL_PACK_ALIGNMENT: 1414 case GL_UNPACK_ALIGNMENT: 1415 case GL_GENERATE_MIPMAP_HINT: 1416 case GL_RED_BITS: 1417 case GL_GREEN_BITS: 1418 case GL_BLUE_BITS: 1419 case GL_ALPHA_BITS: 1420 case GL_DEPTH_BITS: 1421 case GL_STENCIL_BITS: 1422 case GL_ELEMENT_ARRAY_BUFFER_BINDING: 1423 case GL_CULL_FACE_MODE: 1424 case GL_FRONT_FACE: 1425 case GL_ACTIVE_TEXTURE: 1426 case GL_STENCIL_FUNC: 1427 case GL_STENCIL_VALUE_MASK: 1428 case GL_STENCIL_REF: 1429 case GL_STENCIL_FAIL: 1430 case GL_STENCIL_PASS_DEPTH_FAIL: 1431 case GL_STENCIL_PASS_DEPTH_PASS: 1432 case GL_DEPTH_FUNC: 1433 case GL_BLEND_SRC_RGB_OES: 1434 case GL_BLEND_SRC_ALPHA_OES: 1435 case GL_BLEND_DST_RGB_OES: 1436 case GL_BLEND_DST_ALPHA_OES: 1437 case GL_BLEND_EQUATION_RGB_OES: 1438 case GL_BLEND_EQUATION_ALPHA_OES: 1439 case GL_STENCIL_WRITEMASK: 1440 case GL_STENCIL_CLEAR_VALUE: 1441 case GL_SUBPIXEL_BITS: 1442 case GL_MAX_TEXTURE_SIZE: 1443 case GL_MAX_CUBE_MAP_TEXTURE_SIZE_OES: 1444 case GL_SAMPLE_BUFFERS: 1445 case GL_SAMPLES: 1446 case GL_IMPLEMENTATION_COLOR_READ_TYPE_OES: 1447 case GL_IMPLEMENTATION_COLOR_READ_FORMAT_OES: 1448 case GL_TEXTURE_BINDING_2D: 1449 case GL_TEXTURE_BINDING_CUBE_MAP_OES: 1450 case GL_TEXTURE_BINDING_EXTERNAL_OES: 1451 return 1; 1452 case GL_MAX_VIEWPORT_DIMS: 1453 return 2; 1454 case GL_VIEWPORT: 1455 case GL_SCISSOR_BOX: 1456 return 4; 1457 case GL_SAMPLE_COVERAGE_INVERT: 1458 case GL_DEPTH_WRITEMASK: 1459 case GL_CULL_FACE: // CULL_FACE through DITHER are natural to IsEnabled, 1460 case GL_POLYGON_OFFSET_FILL: // but can be retrieved through the Get{Type}v queries. 1461 case GL_SAMPLE_ALPHA_TO_COVERAGE: // For this purpose, they are treated here as bool-natural 1462 case GL_SAMPLE_COVERAGE: 1463 case GL_SCISSOR_TEST: 1464 case GL_STENCIL_TEST: 1465 case GL_DEPTH_TEST: 1466 case GL_BLEND: 1467 case GL_DITHER: 1468 return 1; 1469 case GL_COLOR_WRITEMASK: 1470 return 4; 1471 case GL_POLYGON_OFFSET_FACTOR: 1472 case GL_POLYGON_OFFSET_UNITS: 1473 case GL_SAMPLE_COVERAGE_VALUE: 1474 case GL_DEPTH_CLEAR_VALUE: 1475 case GL_LINE_WIDTH: 1476 return 1; 1477 case GL_ALIASED_LINE_WIDTH_RANGE: 1478 case GL_ALIASED_POINT_SIZE_RANGE: 1479 case GL_DEPTH_RANGE: 1480 return 2; 1481 case GL_COLOR_CLEAR_VALUE: 1482 return 4; 1483 case GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT: 1484 case GL_MAX_LIGHTS: 1485 case GL_MAX_MODELVIEW_STACK_DEPTH: 1486 case GL_MAX_PROJECTION_STACK_DEPTH: 1487 case GL_MAX_TEXTURE_STACK_DEPTH: 1488 case GL_MAX_TEXTURE_UNITS: 1489 case GL_MAX_CLIP_PLANES: 1490 case GL_POINT_SIZE_ARRAY_TYPE_OES: 1491 case GL_POINT_SIZE_ARRAY_STRIDE_OES: 1492 case GL_POINT_SIZE_ARRAY_BUFFER_BINDING_OES: 1493 return 1; 1494 case GL_CURRENT_COLOR: 1495 return 4; 1496 case GL_CURRENT_NORMAL: 1497 return 3; 1498 case GL_CURRENT_TEXTURE_COORDS: 1499 return 4; 1500 case GL_POINT_SIZE: 1501 case GL_POINT_SIZE_MIN: 1502 case GL_POINT_SIZE_MAX: 1503 case GL_POINT_FADE_THRESHOLD_SIZE: 1504 return 1; 1505 case GL_POINT_DISTANCE_ATTENUATION: 1506 return 3; 1507 case GL_SMOOTH_POINT_SIZE_RANGE: 1508 case GL_SMOOTH_LINE_WIDTH_RANGE: 1509 return 2; 1510 case GL_SHADE_MODEL: 1511 case GL_MATRIX_MODE: 1512 case GL_MODELVIEW_STACK_DEPTH: 1513 case GL_PROJECTION_STACK_DEPTH: 1514 case GL_TEXTURE_STACK_DEPTH: 1515 return 1; 1516 case GL_MODELVIEW_MATRIX: 1517 case GL_PROJECTION_MATRIX: 1518 case GL_TEXTURE_MATRIX: 1519 return 16; 1520 case GL_ALPHA_TEST_FUNC: 1521 case GL_ALPHA_TEST_REF: 1522 case GL_BLEND_DST: 1523 case GL_BLEND_SRC: 1524 case GL_LOGIC_OP_MODE: 1525 case GL_VERTEX_ARRAY_SIZE: 1526 case GL_VERTEX_ARRAY_TYPE: 1527 case GL_VERTEX_ARRAY_STRIDE: 1528 case GL_NORMAL_ARRAY_TYPE: 1529 case GL_NORMAL_ARRAY_STRIDE: 1530 case GL_COLOR_ARRAY_SIZE: 1531 case GL_COLOR_ARRAY_TYPE: 1532 case GL_COLOR_ARRAY_STRIDE: 1533 case GL_TEXTURE_COORD_ARRAY_SIZE: 1534 case GL_TEXTURE_COORD_ARRAY_TYPE: 1535 case GL_TEXTURE_COORD_ARRAY_STRIDE: 1536 case GL_VERTEX_ARRAY_POINTER: 1537 case GL_NORMAL_ARRAY_POINTER: 1538 case GL_COLOR_ARRAY_POINTER: 1539 case GL_TEXTURE_COORD_ARRAY_POINTER: 1540 case GL_LIGHT_MODEL_TWO_SIDE: 1541 return 1; 1542 default: 1543 UNREACHABLE(pname); 1544 } 1545 1546 return -1; 1547 } 1548 1549 bool Context::isQueryParameterInt(GLenum pname) 1550 { 1551 // Please note: the query type returned for DEPTH_CLEAR_VALUE in this implementation 1552 // is FLOAT rather than INT, as would be suggested by the GL ES 2.0 spec. This is due 1553 // to the fact that it is stored internally as a float, and so would require conversion 1554 // if returned from Context::getIntegerv. Since this conversion is already implemented 1555 // in the case that one calls glGetIntegerv to retrieve a float-typed state variable, we 1556 // place DEPTH_CLEAR_VALUE with the floats. This should make no difference to the calling 1557 // application. 1558 switch(pname) 1559 { 1560 case GL_COMPRESSED_TEXTURE_FORMATS: 1561 case GL_NUM_COMPRESSED_TEXTURE_FORMATS: 1562 case GL_ARRAY_BUFFER_BINDING: 1563 case GL_FRAMEBUFFER_BINDING_OES: 1564 case GL_RENDERBUFFER_BINDING_OES: 1565 case GL_PACK_ALIGNMENT: 1566 case GL_UNPACK_ALIGNMENT: 1567 case GL_GENERATE_MIPMAP_HINT: 1568 case GL_RED_BITS: 1569 case GL_GREEN_BITS: 1570 case GL_BLUE_BITS: 1571 case GL_ALPHA_BITS: 1572 case GL_DEPTH_BITS: 1573 case GL_STENCIL_BITS: 1574 case GL_ELEMENT_ARRAY_BUFFER_BINDING: 1575 case GL_CULL_FACE_MODE: 1576 case GL_FRONT_FACE: 1577 case GL_ACTIVE_TEXTURE: 1578 case GL_STENCIL_FUNC: 1579 case GL_STENCIL_VALUE_MASK: 1580 case GL_STENCIL_REF: 1581 case GL_STENCIL_FAIL: 1582 case GL_STENCIL_PASS_DEPTH_FAIL: 1583 case GL_STENCIL_PASS_DEPTH_PASS: 1584 case GL_DEPTH_FUNC: 1585 case GL_BLEND_SRC_RGB_OES: 1586 case GL_BLEND_SRC_ALPHA_OES: 1587 case GL_BLEND_DST_RGB_OES: 1588 case GL_BLEND_DST_ALPHA_OES: 1589 case GL_BLEND_EQUATION_RGB_OES: 1590 case GL_BLEND_EQUATION_ALPHA_OES: 1591 case GL_STENCIL_WRITEMASK: 1592 case GL_STENCIL_CLEAR_VALUE: 1593 case GL_SUBPIXEL_BITS: 1594 case GL_MAX_TEXTURE_SIZE: 1595 case GL_MAX_CUBE_MAP_TEXTURE_SIZE_OES: 1596 case GL_SAMPLE_BUFFERS: 1597 case GL_SAMPLES: 1598 case GL_IMPLEMENTATION_COLOR_READ_TYPE_OES: 1599 case GL_IMPLEMENTATION_COLOR_READ_FORMAT_OES: 1600 case GL_TEXTURE_BINDING_2D: 1601 case GL_TEXTURE_BINDING_CUBE_MAP_OES: 1602 case GL_TEXTURE_BINDING_EXTERNAL_OES: 1603 case GL_MAX_VIEWPORT_DIMS: 1604 case GL_VIEWPORT: 1605 case GL_SCISSOR_BOX: 1606 case GL_MAX_LIGHTS: 1607 case GL_MAX_MODELVIEW_STACK_DEPTH: 1608 case GL_MAX_PROJECTION_STACK_DEPTH: 1609 case GL_MAX_TEXTURE_STACK_DEPTH: 1610 case GL_MAX_TEXTURE_UNITS: 1611 case GL_MAX_CLIP_PLANES: 1612 case GL_POINT_SIZE_ARRAY_TYPE_OES: 1613 case GL_POINT_SIZE_ARRAY_STRIDE_OES: 1614 case GL_POINT_SIZE_ARRAY_BUFFER_BINDING_OES: 1615 return true; 1616 } 1617 1618 return false; 1619 } 1620 1621 bool Context::isQueryParameterFloat(GLenum pname) 1622 { 1623 // Please note: the query type returned for DEPTH_CLEAR_VALUE in this implementation 1624 // is FLOAT rather than INT, as would be suggested by the GL ES 2.0 spec. This is due 1625 // to the fact that it is stored internally as a float, and so would require conversion 1626 // if returned from Context::getIntegerv. Since this conversion is already implemented 1627 // in the case that one calls glGetIntegerv to retrieve a float-typed state variable, we 1628 // place DEPTH_CLEAR_VALUE with the floats. This should make no difference to the calling 1629 // application. 1630 switch(pname) 1631 { 1632 case GL_POLYGON_OFFSET_FACTOR: 1633 case GL_POLYGON_OFFSET_UNITS: 1634 case GL_SAMPLE_COVERAGE_VALUE: 1635 case GL_DEPTH_CLEAR_VALUE: 1636 case GL_LINE_WIDTH: 1637 case GL_ALIASED_LINE_WIDTH_RANGE: 1638 case GL_ALIASED_POINT_SIZE_RANGE: 1639 case GL_SMOOTH_LINE_WIDTH_RANGE: 1640 case GL_SMOOTH_POINT_SIZE_RANGE: 1641 case GL_DEPTH_RANGE: 1642 case GL_COLOR_CLEAR_VALUE: 1643 case GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT: 1644 case GL_LIGHT_MODEL_AMBIENT: 1645 case GL_POINT_SIZE_MIN: 1646 case GL_POINT_SIZE_MAX: 1647 case GL_POINT_DISTANCE_ATTENUATION: 1648 case GL_POINT_FADE_THRESHOLD_SIZE: 1649 return true; 1650 } 1651 1652 return false; 1653 } 1654 1655 bool Context::isQueryParameterBool(GLenum pname) 1656 { 1657 switch(pname) 1658 { 1659 case GL_SAMPLE_COVERAGE_INVERT: 1660 case GL_DEPTH_WRITEMASK: 1661 case GL_CULL_FACE: // CULL_FACE through DITHER are natural to IsEnabled, 1662 case GL_POLYGON_OFFSET_FILL: // but can be retrieved through the Get{Type}v queries. 1663 case GL_SAMPLE_ALPHA_TO_COVERAGE: // For this purpose, they are treated here as bool-natural 1664 case GL_SAMPLE_COVERAGE: 1665 case GL_SCISSOR_TEST: 1666 case GL_STENCIL_TEST: 1667 case GL_DEPTH_TEST: 1668 case GL_BLEND: 1669 case GL_DITHER: 1670 case GL_COLOR_WRITEMASK: 1671 case GL_LIGHT_MODEL_TWO_SIDE: 1672 return true; 1673 } 1674 1675 return false; 1676 } 1677 1678 bool Context::isQueryParameterPointer(GLenum pname) 1679 { 1680 switch(pname) 1681 { 1682 case GL_VERTEX_ARRAY_POINTER: 1683 case GL_NORMAL_ARRAY_POINTER: 1684 case GL_COLOR_ARRAY_POINTER: 1685 case GL_TEXTURE_COORD_ARRAY_POINTER: 1686 case GL_POINT_SIZE_ARRAY_POINTER_OES: 1687 return true; 1688 } 1689 1690 return false; 1691 } 1692 1693 // Applies the render target surface, depth stencil surface, viewport rectangle and scissor rectangle 1694 bool Context::applyRenderTarget() 1695 { 1696 Framebuffer *framebuffer = getFramebuffer(); 1697 int width, height, samples; 1698 1699 if(!framebuffer || framebuffer->completeness(width, height, samples) != GL_FRAMEBUFFER_COMPLETE_OES) 1700 { 1701 return error(GL_INVALID_FRAMEBUFFER_OPERATION_OES, false); 1702 } 1703 1704 egl::Image *renderTarget = framebuffer->getRenderTarget(); 1705 device->setRenderTarget(0, renderTarget); 1706 if(renderTarget) renderTarget->release(); 1707 1708 egl::Image *depthBuffer = framebuffer->getDepthBuffer(); 1709 device->setDepthBuffer(depthBuffer); 1710 if(depthBuffer) depthBuffer->release(); 1711 1712 egl::Image *stencilBuffer = framebuffer->getStencilBuffer(); 1713 device->setStencilBuffer(stencilBuffer); 1714 if(stencilBuffer) stencilBuffer->release(); 1715 1716 Viewport viewport; 1717 float zNear = clamp01(mState.zNear); 1718 float zFar = clamp01(mState.zFar); 1719 1720 viewport.x0 = mState.viewportX; 1721 viewport.y0 = mState.viewportY; 1722 viewport.width = mState.viewportWidth; 1723 viewport.height = mState.viewportHeight; 1724 viewport.minZ = zNear; 1725 viewport.maxZ = zFar; 1726 1727 device->setViewport(viewport); 1728 1729 if(mState.scissorTestEnabled) 1730 { 1731 sw::Rect scissor = {mState.scissorX, mState.scissorY, mState.scissorX + mState.scissorWidth, mState.scissorY + mState.scissorHeight}; 1732 scissor.clip(0, 0, width, height); 1733 1734 device->setScissorRect(scissor); 1735 device->setScissorEnable(true); 1736 } 1737 else 1738 { 1739 device->setScissorEnable(false); 1740 } 1741 1742 return true; 1743 } 1744 1745 // Applies the fixed-function state (culling, depth test, alpha blending, stenciling, etc) 1746 void Context::applyState(GLenum drawMode) 1747 { 1748 Framebuffer *framebuffer = getFramebuffer(); 1749 1750 if(mState.cullFaceEnabled) 1751 { 1752 device->setCullMode(es2sw::ConvertCullMode(mState.cullMode, mState.frontFace)); 1753 } 1754 else 1755 { 1756 device->setCullMode(sw::CULL_NONE); 1757 } 1758 1759 if(mDepthStateDirty) 1760 { 1761 if(mState.depthTestEnabled) 1762 { 1763 device->setDepthBufferEnable(true); 1764 device->setDepthCompare(es2sw::ConvertDepthComparison(mState.depthFunc)); 1765 } 1766 else 1767 { 1768 device->setDepthBufferEnable(false); 1769 } 1770 1771 mDepthStateDirty = false; 1772 } 1773 1774 if(mBlendStateDirty) 1775 { 1776 if(mState.blendEnabled) 1777 { 1778 device->setAlphaBlendEnable(true); 1779 device->setSeparateAlphaBlendEnable(true); 1780 1781 device->setSourceBlendFactor(es2sw::ConvertBlendFunc(mState.sourceBlendRGB)); 1782 device->setDestBlendFactor(es2sw::ConvertBlendFunc(mState.destBlendRGB)); 1783 device->setBlendOperation(es2sw::ConvertBlendOp(mState.blendEquationRGB)); 1784 1785 device->setSourceBlendFactorAlpha(es2sw::ConvertBlendFunc(mState.sourceBlendAlpha)); 1786 device->setDestBlendFactorAlpha(es2sw::ConvertBlendFunc(mState.destBlendAlpha)); 1787 device->setBlendOperationAlpha(es2sw::ConvertBlendOp(mState.blendEquationAlpha)); 1788 } 1789 else 1790 { 1791 device->setAlphaBlendEnable(false); 1792 } 1793 1794 mBlendStateDirty = false; 1795 } 1796 1797 if(mStencilStateDirty || mFrontFaceDirty) 1798 { 1799 if(mState.stencilTestEnabled && framebuffer->hasStencil()) 1800 { 1801 device->setStencilEnable(true); 1802 device->setTwoSidedStencil(true); 1803 1804 // get the maximum size of the stencil ref 1805 Renderbuffer *stencilbuffer = framebuffer->getStencilbuffer(); 1806 GLuint maxStencil = (1 << stencilbuffer->getStencilSize()) - 1; 1807 1808 device->setStencilWriteMask(mState.stencilWritemask); 1809 device->setStencilCompare(es2sw::ConvertStencilComparison(mState.stencilFunc)); 1810 1811 device->setStencilReference((mState.stencilRef < (GLint)maxStencil) ? mState.stencilRef : maxStencil); 1812 device->setStencilMask(mState.stencilMask); 1813 1814 device->setStencilFailOperation(es2sw::ConvertStencilOp(mState.stencilFail)); 1815 device->setStencilZFailOperation(es2sw::ConvertStencilOp(mState.stencilPassDepthFail)); 1816 device->setStencilPassOperation(es2sw::ConvertStencilOp(mState.stencilPassDepthPass)); 1817 1818 device->setStencilWriteMaskCCW(mState.stencilWritemask); 1819 device->setStencilCompareCCW(es2sw::ConvertStencilComparison(mState.stencilFunc)); 1820 1821 device->setStencilReferenceCCW((mState.stencilRef < (GLint)maxStencil) ? mState.stencilRef : maxStencil); 1822 device->setStencilMaskCCW(mState.stencilMask); 1823 1824 device->setStencilFailOperationCCW(es2sw::ConvertStencilOp(mState.stencilFail)); 1825 device->setStencilZFailOperationCCW(es2sw::ConvertStencilOp(mState.stencilPassDepthFail)); 1826 device->setStencilPassOperationCCW(es2sw::ConvertStencilOp(mState.stencilPassDepthPass)); 1827 } 1828 else 1829 { 1830 device->setStencilEnable(false); 1831 } 1832 1833 mStencilStateDirty = false; 1834 mFrontFaceDirty = false; 1835 } 1836 1837 if(mMaskStateDirty) 1838 { 1839 device->setColorWriteMask(0, es2sw::ConvertColorMask(mState.colorMaskRed, mState.colorMaskGreen, mState.colorMaskBlue, mState.colorMaskAlpha)); 1840 device->setDepthWriteEnable(mState.depthMask); 1841 1842 mMaskStateDirty = false; 1843 } 1844 1845 if(mPolygonOffsetStateDirty) 1846 { 1847 if(mState.polygonOffsetFillEnabled) 1848 { 1849 Renderbuffer *depthbuffer = framebuffer->getDepthbuffer(); 1850 if(depthbuffer) 1851 { 1852 device->setSlopeDepthBias(mState.polygonOffsetFactor); 1853 float depthBias = ldexp(mState.polygonOffsetUnits, -(int)(depthbuffer->getDepthSize())); 1854 device->setDepthBias(depthBias); 1855 } 1856 } 1857 else 1858 { 1859 device->setSlopeDepthBias(0); 1860 device->setDepthBias(0); 1861 } 1862 1863 mPolygonOffsetStateDirty = false; 1864 } 1865 1866 if(mSampleStateDirty) 1867 { 1868 if(mState.sampleAlphaToCoverageEnabled) 1869 { 1870 device->setTransparencyAntialiasing(sw::TRANSPARENCY_ALPHA_TO_COVERAGE); 1871 } 1872 else 1873 { 1874 device->setTransparencyAntialiasing(sw::TRANSPARENCY_NONE); 1875 } 1876 1877 if(mState.sampleCoverageEnabled) 1878 { 1879 unsigned int mask = 0; 1880 if(mState.sampleCoverageValue != 0) 1881 { 1882 int width, height, samples; 1883 framebuffer->completeness(width, height, samples); 1884 1885 float threshold = 0.5f; 1886 1887 for(int i = 0; i < samples; i++) 1888 { 1889 mask <<= 1; 1890 1891 if((i + 1) * mState.sampleCoverageValue >= threshold) 1892 { 1893 threshold += 1.0f; 1894 mask |= 1; 1895 } 1896 } 1897 } 1898 1899 if(mState.sampleCoverageInvert) 1900 { 1901 mask = ~mask; 1902 } 1903 1904 device->setMultiSampleMask(mask); 1905 } 1906 else 1907 { 1908 device->setMultiSampleMask(0xFFFFFFFF); 1909 } 1910 1911 mSampleStateDirty = false; 1912 } 1913 1914 if(mDitherStateDirty) 1915 { 1916 // UNIMPLEMENTED(); // FIXME 1917 1918 mDitherStateDirty = false; 1919 } 1920 1921 switch(mState.shadeModel) 1922 { 1923 default: UNREACHABLE(mState.shadeModel); 1924 case GL_SMOOTH: device->setShadingMode(sw::SHADING_GOURAUD); break; 1925 case GL_FLAT: device->setShadingMode(sw::SHADING_FLAT); break; 1926 } 1927 1928 device->setLightingEnable(lightingEnabled); 1929 device->setGlobalAmbient(sw::Color<float>(globalAmbient.red, globalAmbient.green, globalAmbient.blue, globalAmbient.alpha)); 1930 1931 for(int i = 0; i < MAX_LIGHTS; i++) 1932 { 1933 device->setLightEnable(i, light[i].enabled); 1934 device->setLightAmbient(i, sw::Color<float>(light[i].ambient.red, light[i].ambient.green, light[i].ambient.blue, light[i].ambient.alpha)); 1935 device->setLightDiffuse(i, sw::Color<float>(light[i].diffuse.red, light[i].diffuse.green, light[i].diffuse.blue, light[i].diffuse.alpha)); 1936 device->setLightSpecular(i, sw::Color<float>(light[i].specular.red, light[i].specular.green, light[i].specular.blue, light[i].specular.alpha)); 1937 device->setLightAttenuation(i, light[i].attenuation.constant, light[i].attenuation.linear, light[i].attenuation.quadratic); 1938 1939 if(light[i].position.w != 0.0f) 1940 { 1941 device->setLightPosition(i, sw::Point(light[i].position.x / light[i].position.w, light[i].position.y / light[i].position.w, light[i].position.z / light[i].position.w)); 1942 } 1943 else // Directional light 1944 { 1945 // Hack: set the position far way 1946 float max = sw::max(abs(light[i].position.x), abs(light[i].position.y), abs(light[i].position.z)); 1947 device->setLightPosition(i, sw::Point(1e10f * (light[i].position.x / max), 1e10f * (light[i].position.y / max), 1e10f * (light[i].position.z / max))); 1948 } 1949 } 1950 1951 device->setMaterialAmbient(sw::Color<float>(materialAmbient.red, materialAmbient.green, materialAmbient.blue, materialAmbient.alpha)); 1952 device->setMaterialDiffuse(sw::Color<float>(materialDiffuse.red, materialDiffuse.green, materialDiffuse.blue, materialDiffuse.alpha)); 1953 device->setMaterialSpecular(sw::Color<float>(materialSpecular.red, materialSpecular.green, materialSpecular.blue, materialSpecular.alpha)); 1954 device->setMaterialEmission(sw::Color<float>(materialEmission.red, materialEmission.green, materialEmission.blue, materialEmission.alpha)); 1955 device->setMaterialShininess(materialShininess); 1956 1957 device->setDiffuseMaterialSource(sw::MATERIAL_MATERIAL); 1958 device->setSpecularMaterialSource(sw::MATERIAL_MATERIAL); 1959 device->setAmbientMaterialSource(sw::MATERIAL_MATERIAL); 1960 device->setEmissiveMaterialSource(sw::MATERIAL_MATERIAL); 1961 1962 device->setProjectionMatrix(projectionStack.current()); 1963 device->setModelMatrix(modelViewStack.current()); 1964 device->setTextureMatrix(0, textureStack0.current()); 1965 device->setTextureMatrix(1, textureStack1.current()); 1966 device->setTextureTransform(0, textureStack0.isIdentity() ? 0 : 4, false); 1967 device->setTextureTransform(1, textureStack1.isIdentity() ? 0 : 4, false); 1968 device->setTexGen(0, sw::TEXGEN_NONE); 1969 device->setTexGen(1, sw::TEXGEN_NONE); 1970 1971 device->setAlphaTestEnable(alphaTestEnabled); 1972 device->setAlphaCompare(es2sw::ConvertAlphaComparison(alphaTestFunc)); 1973 device->setAlphaReference(alphaTestRef * 0xFF); 1974 1975 device->setFogEnable(fogEnabled); 1976 device->setFogColor(sw::Color<float>(fogColor.red, fogColor.green, fogColor.blue, fogColor.alpha)); 1977 device->setFogDensity(fogDensity); 1978 device->setFogStart(fogStart); 1979 device->setFogEnd(fogEnd); 1980 1981 switch(fogMode) 1982 { 1983 case GL_LINEAR: device->setVertexFogMode(sw::FOG_LINEAR); break; 1984 case GL_EXP: device->setVertexFogMode(sw::FOG_EXP); break; 1985 case GL_EXP2: device->setVertexFogMode(sw::FOG_EXP2); break; 1986 default: UNREACHABLE(fogMode); 1987 } 1988 1989 device->setColorLogicOpEnabled(colorLogicOpEnabled); 1990 device->setLogicalOperation(es2sw::ConvertLogicalOperation(logicalOperation)); 1991 1992 device->setNormalizeNormals(normalizeEnabled || rescaleNormalEnabled); 1993 } 1994 1995 GLenum Context::applyVertexBuffer(GLint base, GLint first, GLsizei count) 1996 { 1997 TranslatedAttribute attributes[MAX_VERTEX_ATTRIBS]; 1998 1999 GLenum err = mVertexDataManager->prepareVertexData(first, count, attributes); 2000 if(err != GL_NO_ERROR) 2001 { 2002 return err; 2003 } 2004 2005 device->resetInputStreams(false); 2006 2007 for(int i = 0; i < MAX_VERTEX_ATTRIBS; i++) 2008 { 2009 sw::Resource *resource = attributes[i].vertexBuffer; 2010 const void *buffer = (char*)resource->data() + attributes[i].offset; 2011 2012 int stride = attributes[i].stride; 2013 2014 buffer = (char*)buffer + stride * base; 2015 2016 sw::Stream attribute(resource, buffer, stride); 2017 2018 attribute.type = attributes[i].type; 2019 attribute.count = attributes[i].count; 2020 attribute.normalized = attributes[i].normalized; 2021 2022 device->setInputStream(i, attribute); 2023 } 2024 2025 return GL_NO_ERROR; 2026 } 2027 2028 // Applies the indices and element array bindings 2029 GLenum Context::applyIndexBuffer(const void *indices, GLsizei count, GLenum mode, GLenum type, TranslatedIndexData *indexInfo) 2030 { 2031 GLenum err = mIndexDataManager->prepareIndexData(type, count, mState.elementArrayBuffer, indices, indexInfo); 2032 2033 if(err == GL_NO_ERROR) 2034 { 2035 device->setIndexBuffer(indexInfo->indexBuffer); 2036 } 2037 2038 return err; 2039 } 2040 2041 void Context::applyTextures() 2042 { 2043 for(int unit = 0; unit < MAX_TEXTURE_UNITS; unit++) 2044 { 2045 Texture *texture = nullptr; 2046 2047 if(textureExternalEnabled[unit]) 2048 { 2049 texture = getSamplerTexture(unit, TEXTURE_EXTERNAL); 2050 } 2051 else if(texture2Denabled[unit]) 2052 { 2053 texture = getSamplerTexture(unit, TEXTURE_2D); 2054 } 2055 2056 if(texture && texture->isSamplerComplete()) 2057 { 2058 texture->autoGenerateMipmaps(); 2059 2060 GLenum wrapS = texture->getWrapS(); 2061 GLenum wrapT = texture->getWrapT(); 2062 GLenum minFilter = texture->getMinFilter(); 2063 GLenum magFilter = texture->getMagFilter(); 2064 GLfloat maxAnisotropy = texture->getMaxAnisotropy(); 2065 2066 device->setAddressingModeU(sw::SAMPLER_PIXEL, unit, es2sw::ConvertTextureWrap(wrapS)); 2067 device->setAddressingModeV(sw::SAMPLER_PIXEL, unit, es2sw::ConvertTextureWrap(wrapT)); 2068 2069 device->setTextureFilter(sw::SAMPLER_PIXEL, unit, es2sw::ConvertTextureFilter(minFilter, magFilter, maxAnisotropy)); 2070 device->setMipmapFilter(sw::SAMPLER_PIXEL, unit, es2sw::ConvertMipMapFilter(minFilter)); 2071 device->setMaxAnisotropy(sw::SAMPLER_PIXEL, unit, maxAnisotropy); 2072 2073 applyTexture(unit, texture); 2074 2075 device->setConstantColor(unit, sw::Color<float>(mState.textureUnit[unit].color.red, mState.textureUnit[unit].color.green, mState.textureUnit[unit].color.blue, mState.textureUnit[unit].color.alpha)); 2076 2077 if(mState.textureUnit[unit].environmentMode != GL_COMBINE) 2078 { 2079 device->setFirstArgument(unit, sw::TextureStage::SOURCE_TEXTURE); // Cs 2080 device->setFirstModifier(unit, sw::TextureStage::MODIFIER_COLOR); 2081 device->setSecondArgument(unit, sw::TextureStage::SOURCE_CURRENT); // Cp 2082 device->setSecondModifier(unit, sw::TextureStage::MODIFIER_COLOR); 2083 device->setThirdArgument(unit, sw::TextureStage::SOURCE_CONSTANT); // Cc 2084 device->setThirdModifier(unit, sw::TextureStage::MODIFIER_COLOR); 2085 2086 device->setFirstArgumentAlpha(unit, sw::TextureStage::SOURCE_TEXTURE); // As 2087 device->setFirstModifierAlpha(unit, sw::TextureStage::MODIFIER_ALPHA); 2088 device->setSecondArgumentAlpha(unit, sw::TextureStage::SOURCE_CURRENT); // Ap 2089 device->setSecondModifierAlpha(unit, sw::TextureStage::MODIFIER_ALPHA); 2090 device->setThirdArgumentAlpha(unit, sw::TextureStage::SOURCE_CONSTANT); // Ac 2091 device->setThirdModifierAlpha(unit, sw::TextureStage::MODIFIER_ALPHA); 2092 2093 GLenum texFormat = texture->getFormat(GL_TEXTURE_2D, 0); 2094 2095 switch(mState.textureUnit[unit].environmentMode) 2096 { 2097 case GL_REPLACE: 2098 if(IsAlpha(texFormat)) // GL_ALPHA 2099 { 2100 // Cv = Cp, Av = As 2101 device->setStageOperation(unit, sw::TextureStage::STAGE_SELECTARG2); 2102 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_SELECTARG1); 2103 } 2104 else if(IsRGB(texFormat)) // GL_LUMINANCE (or 1) / GL_RGB (or 3) 2105 { 2106 // Cv = Cs, Av = Ap 2107 device->setStageOperation(unit, sw::TextureStage::STAGE_SELECTARG1); 2108 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_SELECTARG2); 2109 } 2110 else if(IsRGBA(texFormat)) // GL_LUMINANCE_ALPHA (or 2) / GL_RGBA (or 4) 2111 { 2112 // Cv = Cs, Av = As 2113 device->setStageOperation(unit, sw::TextureStage::STAGE_SELECTARG1); 2114 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_SELECTARG1); 2115 } 2116 else UNREACHABLE(texFormat); 2117 break; 2118 case GL_MODULATE: 2119 if(IsAlpha(texFormat)) // GL_ALPHA 2120 { 2121 // Cv = Cp, Av = ApAs 2122 device->setStageOperation(unit, sw::TextureStage::STAGE_SELECTARG2); 2123 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_MODULATE); 2124 } 2125 else if(IsRGB(texFormat)) // GL_LUMINANCE (or 1) / GL_RGB (or 3) 2126 { 2127 // Cv = CpCs, Av = Ap 2128 device->setStageOperation(unit, sw::TextureStage::STAGE_MODULATE); 2129 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_SELECTARG2); 2130 } 2131 else if(IsRGBA(texFormat)) // GL_LUMINANCE_ALPHA (or 2) / GL_RGBA (or 4) 2132 { 2133 // Cv = CpCs, Av = ApAs 2134 device->setStageOperation(unit, sw::TextureStage::STAGE_MODULATE); 2135 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_MODULATE); 2136 } 2137 else UNREACHABLE(texFormat); 2138 break; 2139 case GL_DECAL: 2140 if(texFormat == GL_ALPHA || 2141 texFormat == GL_LUMINANCE || 2142 texFormat == GL_LUMINANCE_ALPHA) 2143 { 2144 // undefined // FIXME: Log 2145 device->setStageOperation(unit, sw::TextureStage::STAGE_SELECTARG2); 2146 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_SELECTARG2); 2147 } 2148 else if(IsRGB(texFormat)) // GL_LUMINANCE (or 1) / GL_RGB (or 3) 2149 { 2150 // Cv = Cs, Av = Ap 2151 device->setStageOperation(unit, sw::TextureStage::STAGE_SELECTARG1); 2152 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_SELECTARG2); 2153 } 2154 else if(IsRGBA(texFormat)) // GL_LUMINANCE_ALPHA (or 2) / GL_RGBA (or 4) 2155 { 2156 // Cv = Cp(1 - As) + CsAs, Av = Ap 2157 device->setStageOperation(unit, sw::TextureStage::STAGE_BLENDTEXTUREALPHA); // Alpha * (Arg1 - Arg2) + Arg2 2158 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_SELECTARG2); 2159 } 2160 else UNREACHABLE(texFormat); 2161 break; 2162 case GL_BLEND: 2163 if(IsAlpha(texFormat)) // GL_ALPHA 2164 { 2165 // Cv = Cp, Av = ApAs 2166 device->setStageOperation(unit, sw::TextureStage::STAGE_SELECTARG2); 2167 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_MODULATE); 2168 } 2169 else if(IsRGB(texFormat)) // GL_LUMINANCE (or 1) / GL_RGB (or 3) 2170 { 2171 // Cv = Cp(1 - Cs) + CcCs, Av = Ap 2172 device->setStageOperation(unit, sw::TextureStage::STAGE_LERP); // Arg3 * (Arg1 - Arg2) + Arg2 2173 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_SELECTARG2); 2174 } 2175 else if(IsRGBA(texFormat)) // GL_LUMINANCE_ALPHA (or 2) / GL_RGBA (or 4) 2176 { 2177 // Cv = Cp(1 - Cs) + CcCs, Av = ApAs 2178 device->setStageOperation(unit, sw::TextureStage::STAGE_LERP); // Arg3 * (Arg1 - Arg2) + Arg2 2179 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_MODULATE); 2180 } 2181 else UNREACHABLE(texFormat); 2182 break; 2183 case GL_ADD: 2184 if(IsAlpha(texFormat)) // GL_ALPHA 2185 { 2186 // Cv = Cp, Av = ApAs 2187 device->setStageOperation(unit, sw::TextureStage::STAGE_SELECTARG2); 2188 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_MODULATE); 2189 } 2190 else if(IsRGB(texFormat)) // GL_LUMINANCE (or 1) / GL_RGB (or 3) 2191 { 2192 // Cv = Cp + Cs, Av = Ap 2193 device->setStageOperation(unit, sw::TextureStage::STAGE_ADD); 2194 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_SELECTARG2); 2195 } 2196 else if(IsRGBA(texFormat)) // GL_LUMINANCE_ALPHA (or 2) / GL_RGBA (or 4) 2197 { 2198 // Cv = Cp + Cs, Av = ApAs 2199 device->setStageOperation(unit, sw::TextureStage::STAGE_ADD); 2200 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_MODULATE); 2201 } 2202 else UNREACHABLE(texFormat); 2203 break; 2204 default: 2205 UNREACHABLE(mState.textureUnit[unit].environmentMode); 2206 } 2207 } 2208 else // GL_COMBINE 2209 { 2210 device->setFirstArgument(unit, es2sw::ConvertSourceArgument(mState.textureUnit[unit].src0RGB)); 2211 device->setFirstModifier(unit, es2sw::ConvertSourceOperand(mState.textureUnit[unit].operand0RGB)); 2212 device->setSecondArgument(unit, es2sw::ConvertSourceArgument(mState.textureUnit[unit].src1RGB)); 2213 device->setSecondModifier(unit, es2sw::ConvertSourceOperand(mState.textureUnit[unit].operand1RGB)); 2214 device->setThirdArgument(unit, es2sw::ConvertSourceArgument(mState.textureUnit[unit].src2RGB)); 2215 device->setThirdModifier(unit, es2sw::ConvertSourceOperand(mState.textureUnit[unit].operand2RGB)); 2216 2217 device->setStageOperation(unit, es2sw::ConvertCombineOperation(mState.textureUnit[unit].combineRGB)); 2218 2219 device->setFirstArgumentAlpha(unit, es2sw::ConvertSourceArgument(mState.textureUnit[unit].src0Alpha)); 2220 device->setFirstModifierAlpha(unit, es2sw::ConvertSourceOperand(mState.textureUnit[unit].operand0Alpha)); 2221 device->setSecondArgumentAlpha(unit, es2sw::ConvertSourceArgument(mState.textureUnit[unit].src1Alpha)); 2222 device->setSecondModifierAlpha(unit, es2sw::ConvertSourceOperand(mState.textureUnit[unit].operand1Alpha)); 2223 device->setThirdArgumentAlpha(unit, es2sw::ConvertSourceArgument(mState.textureUnit[unit].src2Alpha)); 2224 device->setThirdModifierAlpha(unit, es2sw::ConvertSourceOperand(mState.textureUnit[unit].operand2Alpha)); 2225 2226 device->setStageOperationAlpha(unit, es2sw::ConvertCombineOperation(mState.textureUnit[unit].combineAlpha)); 2227 } 2228 } 2229 else 2230 { 2231 applyTexture(unit, nullptr); 2232 2233 device->setFirstArgument(unit, sw::TextureStage::SOURCE_CURRENT); 2234 device->setFirstModifier(unit, sw::TextureStage::MODIFIER_COLOR); 2235 device->setStageOperation(unit, sw::TextureStage::STAGE_SELECTARG1); 2236 2237 device->setFirstArgumentAlpha(unit, sw::TextureStage::SOURCE_CURRENT); 2238 device->setFirstModifierAlpha(unit, sw::TextureStage::MODIFIER_ALPHA); 2239 device->setStageOperationAlpha(unit, sw::TextureStage::STAGE_SELECTARG1); 2240 } 2241 } 2242 } 2243 2244 void Context::setTextureEnvMode(GLenum texEnvMode) 2245 { 2246 mState.textureUnit[mState.activeSampler].environmentMode = texEnvMode; 2247 } 2248 2249 void Context::setTextureEnvColor(GLclampf red, GLclampf green, GLclampf blue, GLclampf alpha) 2250 { 2251 mState.textureUnit[mState.activeSampler].color = {red, green, blue, alpha}; 2252 } 2253 2254 void Context::setCombineRGB(GLenum combineRGB) 2255 { 2256 mState.textureUnit[mState.activeSampler].combineRGB = combineRGB; 2257 } 2258 2259 void Context::setCombineAlpha(GLenum combineAlpha) 2260 { 2261 mState.textureUnit[mState.activeSampler].combineAlpha = combineAlpha; 2262 } 2263 2264 void Context::setOperand0RGB(GLenum operand) 2265 { 2266 mState.textureUnit[mState.activeSampler].operand0RGB = operand; 2267 } 2268 2269 void Context::setOperand1RGB(GLenum operand) 2270 { 2271 mState.textureUnit[mState.activeSampler].operand1RGB = operand; 2272 } 2273 2274 void Context::setOperand2RGB(GLenum operand) 2275 { 2276 mState.textureUnit[mState.activeSampler].operand2RGB = operand; 2277 } 2278 2279 void Context::setOperand0Alpha(GLenum operand) 2280 { 2281 mState.textureUnit[mState.activeSampler].operand0Alpha = operand; 2282 } 2283 2284 void Context::setOperand1Alpha(GLenum operand) 2285 { 2286 mState.textureUnit[mState.activeSampler].operand1Alpha = operand; 2287 } 2288 2289 void Context::setOperand2Alpha(GLenum operand) 2290 { 2291 mState.textureUnit[mState.activeSampler].operand2Alpha = operand; 2292 } 2293 2294 void Context::setSrc0RGB(GLenum src) 2295 { 2296 mState.textureUnit[mState.activeSampler].src0RGB = src; 2297 } 2298 2299 void Context::setSrc1RGB(GLenum src) 2300 { 2301 mState.textureUnit[mState.activeSampler].src1RGB = src; 2302 } 2303 2304 void Context::setSrc2RGB(GLenum src) 2305 { 2306 mState.textureUnit[mState.activeSampler].src2RGB = src; 2307 } 2308 2309 void Context::setSrc0Alpha(GLenum src) 2310 { 2311 mState.textureUnit[mState.activeSampler].src0Alpha = src; 2312 } 2313 2314 void Context::setSrc1Alpha(GLenum src) 2315 { 2316 mState.textureUnit[mState.activeSampler].src1Alpha = src; 2317 } 2318 2319 void Context::setSrc2Alpha(GLenum src) 2320 { 2321 mState.textureUnit[mState.activeSampler].src2Alpha = src; 2322 } 2323 2324 void Context::applyTexture(int index, Texture *baseTexture) 2325 { 2326 sw::Resource *resource = 0; 2327 2328 if(baseTexture) 2329 { 2330 resource = baseTexture->getResource(); 2331 } 2332 2333 device->setTextureResource(index, resource); 2334 2335 if(baseTexture) 2336 { 2337 int levelCount = baseTexture->getLevelCount(); 2338 2339 if(baseTexture->getTarget() == GL_TEXTURE_2D || baseTexture->getTarget() == GL_TEXTURE_EXTERNAL_OES) 2340 { 2341 Texture2D *texture = static_cast<Texture2D*>(baseTexture); 2342 2343 for(int mipmapLevel = 0; mipmapLevel < sw::MIPMAP_LEVELS; mipmapLevel++) 2344 { 2345 int surfaceLevel = mipmapLevel; 2346 2347 if(surfaceLevel < 0) 2348 { 2349 surfaceLevel = 0; 2350 } 2351 else if(surfaceLevel >= levelCount) 2352 { 2353 surfaceLevel = levelCount - 1; 2354 } 2355 2356 egl::Image *surface = texture->getImage(surfaceLevel); 2357 device->setTextureLevel(index, 0, mipmapLevel, surface, sw::TEXTURE_2D); 2358 } 2359 } 2360 else UNIMPLEMENTED(); 2361 } 2362 else 2363 { 2364 device->setTextureLevel(index, 0, 0, 0, sw::TEXTURE_NULL); 2365 } 2366 } 2367 2368 void Context::readPixels(GLint x, GLint y, GLsizei width, GLsizei height, 2369 GLenum format, GLenum type, GLsizei *bufSize, void* pixels) 2370 { 2371 Framebuffer *framebuffer = getFramebuffer(); 2372 int framebufferWidth, framebufferHeight, framebufferSamples; 2373 2374 if(framebuffer->completeness(framebufferWidth, framebufferHeight, framebufferSamples) != GL_FRAMEBUFFER_COMPLETE_OES) 2375 { 2376 return error(GL_INVALID_FRAMEBUFFER_OPERATION_OES); 2377 } 2378 2379 if(getFramebufferName() != 0 && framebufferSamples != 0) 2380 { 2381 return error(GL_INVALID_OPERATION); 2382 } 2383 2384 if(format != GL_RGBA || type != GL_UNSIGNED_BYTE) 2385 { 2386 if(format != framebuffer->getImplementationColorReadFormat() || type != framebuffer->getImplementationColorReadType()) 2387 { 2388 return error(GL_INVALID_OPERATION); 2389 } 2390 } 2391 2392 GLsizei outputPitch = egl::ComputePitch(width, format, type, mState.packAlignment); 2393 2394 // Sized query sanity check 2395 if(bufSize) 2396 { 2397 int requiredSize = outputPitch * height; 2398 if(requiredSize > *bufSize) 2399 { 2400 return error(GL_INVALID_OPERATION); 2401 } 2402 } 2403 2404 egl::Image *renderTarget = framebuffer->getRenderTarget(); 2405 2406 if(!renderTarget) 2407 { 2408 return error(GL_OUT_OF_MEMORY); 2409 } 2410 2411 sw::Rect rect = {x, y, x + width, y + height}; 2412 rect.clip(0, 0, renderTarget->getWidth(), renderTarget->getHeight()); 2413 2414 unsigned char *source = (unsigned char*)renderTarget->lock(rect.x0, rect.y0, sw::LOCK_READONLY); 2415 unsigned char *dest = (unsigned char*)pixels; 2416 int inputPitch = (int)renderTarget->getPitch(); 2417 2418 for(int j = 0; j < rect.y1 - rect.y0; j++) 2419 { 2420 unsigned short *dest16 = (unsigned short*)dest; 2421 unsigned int *dest32 = (unsigned int*)dest; 2422 2423 if(renderTarget->getInternalFormat() == sw::FORMAT_A8B8G8R8 && 2424 format == GL_RGBA && type == GL_UNSIGNED_BYTE) 2425 { 2426 memcpy(dest, source, (rect.x1 - rect.x0) * 4); 2427 } 2428 else if(renderTarget->getInternalFormat() == sw::FORMAT_A8R8G8B8 && 2429 format == GL_RGBA && type == GL_UNSIGNED_BYTE) 2430 { 2431 for(int i = 0; i < rect.x1 - rect.x0; i++) 2432 { 2433 unsigned int argb = *(unsigned int*)(source + 4 * i); 2434 2435 dest32[i] = (argb & 0xFF00FF00) | ((argb & 0x000000FF) << 16) | ((argb & 0x00FF0000) >> 16); 2436 } 2437 } 2438 else if(renderTarget->getInternalFormat() == sw::FORMAT_X8R8G8B8 && 2439 format == GL_RGBA && type == GL_UNSIGNED_BYTE) 2440 { 2441 for(int i = 0; i < rect.x1 - rect.x0; i++) 2442 { 2443 unsigned int xrgb = *(unsigned int*)(source + 4 * i); 2444 2445 dest32[i] = (xrgb & 0xFF00FF00) | ((xrgb & 0x000000FF) << 16) | ((xrgb & 0x00FF0000) >> 16) | 0xFF000000; 2446 } 2447 } 2448 else if(renderTarget->getInternalFormat() == sw::FORMAT_X8R8G8B8 && 2449 format == GL_BGRA_EXT && type == GL_UNSIGNED_BYTE) 2450 { 2451 for(int i = 0; i < rect.x1 - rect.x0; i++) 2452 { 2453 unsigned int xrgb = *(unsigned int*)(source + 4 * i); 2454 2455 dest32[i] = xrgb | 0xFF000000; 2456 } 2457 } 2458 else if(renderTarget->getInternalFormat() == sw::FORMAT_A8R8G8B8 && 2459 format == GL_BGRA_EXT && type == GL_UNSIGNED_BYTE) 2460 { 2461 memcpy(dest, source, (rect.x1 - rect.x0) * 4); 2462 } 2463 else if(renderTarget->getInternalFormat() == sw::FORMAT_A1R5G5B5 && 2464 format == GL_BGRA_EXT && type == GL_UNSIGNED_SHORT_1_5_5_5_REV_EXT) 2465 { 2466 memcpy(dest, source, (rect.x1 - rect.x0) * 2); 2467 } 2468 else if(renderTarget->getInternalFormat() == sw::FORMAT_R5G6B5 && 2469 format == 0x80E0 && type == GL_UNSIGNED_SHORT_5_6_5) // GL_BGR_EXT 2470 { 2471 memcpy(dest, source, (rect.x1 - rect.x0) * 2); 2472 } 2473 else 2474 { 2475 for(int i = 0; i < rect.x1 - rect.x0; i++) 2476 { 2477 float r; 2478 float g; 2479 float b; 2480 float a; 2481 2482 switch(renderTarget->getInternalFormat()) 2483 { 2484 case sw::FORMAT_R5G6B5: 2485 { 2486 unsigned short rgb = *(unsigned short*)(source + 2 * i); 2487 2488 a = 1.0f; 2489 b = (rgb & 0x001F) * (1.0f / 0x001F); 2490 g = (rgb & 0x07E0) * (1.0f / 0x07E0); 2491 r = (rgb & 0xF800) * (1.0f / 0xF800); 2492 } 2493 break; 2494 case sw::FORMAT_A1R5G5B5: 2495 { 2496 unsigned short argb = *(unsigned short*)(source + 2 * i); 2497 2498 a = (argb & 0x8000) ? 1.0f : 0.0f; 2499 b = (argb & 0x001F) * (1.0f / 0x001F); 2500 g = (argb & 0x03E0) * (1.0f / 0x03E0); 2501 r = (argb & 0x7C00) * (1.0f / 0x7C00); 2502 } 2503 break; 2504 case sw::FORMAT_A8R8G8B8: 2505 { 2506 unsigned int argb = *(unsigned int*)(source + 4 * i); 2507 2508 a = (argb & 0xFF000000) * (1.0f / 0xFF000000); 2509 b = (argb & 0x000000FF) * (1.0f / 0x000000FF); 2510 g = (argb & 0x0000FF00) * (1.0f / 0x0000FF00); 2511 r = (argb & 0x00FF0000) * (1.0f / 0x00FF0000); 2512 } 2513 break; 2514 case sw::FORMAT_A8B8G8R8: 2515 { 2516 unsigned int abgr = *(unsigned int*)(source + 4 * i); 2517 2518 a = (abgr & 0xFF000000) * (1.0f / 0xFF000000); 2519 b = (abgr & 0x00FF0000) * (1.0f / 0x00FF0000); 2520 g = (abgr & 0x0000FF00) * (1.0f / 0x0000FF00); 2521 r = (abgr & 0x000000FF) * (1.0f / 0x000000FF); 2522 } 2523 break; 2524 case sw::FORMAT_X8R8G8B8: 2525 { 2526 unsigned int xrgb = *(unsigned int*)(source + 4 * i); 2527 2528 a = 1.0f; 2529 b = (xrgb & 0x000000FF) * (1.0f / 0x000000FF); 2530 g = (xrgb & 0x0000FF00) * (1.0f / 0x0000FF00); 2531 r = (xrgb & 0x00FF0000) * (1.0f / 0x00FF0000); 2532 } 2533 break; 2534 case sw::FORMAT_X8B8G8R8: 2535 { 2536 unsigned int xbgr = *(unsigned int*)(source + 4 * i); 2537 2538 a = 1.0f; 2539 b = (xbgr & 0x00FF0000) * (1.0f / 0x00FF0000); 2540 g = (xbgr & 0x0000FF00) * (1.0f / 0x0000FF00); 2541 r = (xbgr & 0x000000FF) * (1.0f / 0x000000FF); 2542 } 2543 break; 2544 case sw::FORMAT_A2R10G10B10: 2545 { 2546 unsigned int argb = *(unsigned int*)(source + 4 * i); 2547 2548 a = (argb & 0xC0000000) * (1.0f / 0xC0000000); 2549 b = (argb & 0x000003FF) * (1.0f / 0x000003FF); 2550 g = (argb & 0x000FFC00) * (1.0f / 0x000FFC00); 2551 r = (argb & 0x3FF00000) * (1.0f / 0x3FF00000); 2552 } 2553 break; 2554 default: 2555 UNIMPLEMENTED(); // FIXME 2556 UNREACHABLE(renderTarget->getInternalFormat()); 2557 } 2558 2559 switch(format) 2560 { 2561 case GL_RGBA: 2562 switch(type) 2563 { 2564 case GL_UNSIGNED_BYTE: 2565 dest[4 * i + 0] = (unsigned char)(255 * r + 0.5f); 2566 dest[4 * i + 1] = (unsigned char)(255 * g + 0.5f); 2567 dest[4 * i + 2] = (unsigned char)(255 * b + 0.5f); 2568 dest[4 * i + 3] = (unsigned char)(255 * a + 0.5f); 2569 break; 2570 default: UNREACHABLE(type); 2571 } 2572 break; 2573 case GL_BGRA_EXT: 2574 switch(type) 2575 { 2576 case GL_UNSIGNED_BYTE: 2577 dest[4 * i + 0] = (unsigned char)(255 * b + 0.5f); 2578 dest[4 * i + 1] = (unsigned char)(255 * g + 0.5f); 2579 dest[4 * i + 2] = (unsigned char)(255 * r + 0.5f); 2580 dest[4 * i + 3] = (unsigned char)(255 * a + 0.5f); 2581 break; 2582 case GL_UNSIGNED_SHORT_4_4_4_4_REV_EXT: 2583 // According to the desktop GL spec in the "Transfer of Pixel Rectangles" section 2584 // this type is packed as follows: 2585 // 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 2586 // -------------------------------------------------------------------------------- 2587 // | 4th | 3rd | 2nd | 1st component | 2588 // -------------------------------------------------------------------------------- 2589 // in the case of BGRA_EXT, B is the first component, G the second, and so forth. 2590 dest16[i] = 2591 ((unsigned short)(15 * a + 0.5f) << 12)| 2592 ((unsigned short)(15 * r + 0.5f) << 8) | 2593 ((unsigned short)(15 * g + 0.5f) << 4) | 2594 ((unsigned short)(15 * b + 0.5f) << 0); 2595 break; 2596 case GL_UNSIGNED_SHORT_1_5_5_5_REV_EXT: 2597 // According to the desktop GL spec in the "Transfer of Pixel Rectangles" section 2598 // this type is packed as follows: 2599 // 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 2600 // -------------------------------------------------------------------------------- 2601 // | 4th | 3rd | 2nd | 1st component | 2602 // -------------------------------------------------------------------------------- 2603 // in the case of BGRA_EXT, B is the first component, G the second, and so forth. 2604 dest16[i] = 2605 ((unsigned short)( a + 0.5f) << 15) | 2606 ((unsigned short)(31 * r + 0.5f) << 10) | 2607 ((unsigned short)(31 * g + 0.5f) << 5) | 2608 ((unsigned short)(31 * b + 0.5f) << 0); 2609 break; 2610 default: UNREACHABLE(type); 2611 } 2612 break; 2613 case GL_RGB: 2614 switch(type) 2615 { 2616 case GL_UNSIGNED_SHORT_5_6_5: 2617 dest16[i] = 2618 ((unsigned short)(31 * b + 0.5f) << 0) | 2619 ((unsigned short)(63 * g + 0.5f) << 5) | 2620 ((unsigned short)(31 * r + 0.5f) << 11); 2621 break; 2622 default: UNREACHABLE(type); 2623 } 2624 break; 2625 default: UNREACHABLE(format); 2626 } 2627 } 2628 } 2629 2630 source += inputPitch; 2631 dest += outputPitch; 2632 } 2633 2634 renderTarget->unlock(); 2635 renderTarget->release(); 2636 } 2637 2638 void Context::clear(GLbitfield mask) 2639 { 2640 Framebuffer *framebuffer = getFramebuffer(); 2641 2642 if(!framebuffer || framebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE_OES) 2643 { 2644 return error(GL_INVALID_FRAMEBUFFER_OPERATION_OES); 2645 } 2646 2647 if(!applyRenderTarget()) 2648 { 2649 return; 2650 } 2651 2652 float depth = clamp01(mState.depthClearValue); 2653 int stencil = mState.stencilClearValue & 0x000000FF; 2654 2655 if(mask & GL_COLOR_BUFFER_BIT) 2656 { 2657 unsigned int rgbaMask = (mState.colorMaskRed ? 0x1 : 0) | 2658 (mState.colorMaskGreen ? 0x2 : 0) | 2659 (mState.colorMaskBlue ? 0x4 : 0) | 2660 (mState.colorMaskAlpha ? 0x8 : 0); 2661 2662 if(rgbaMask != 0) 2663 { 2664 device->clearColor(mState.colorClearValue.red, mState.colorClearValue.green, mState.colorClearValue.blue, mState.colorClearValue.alpha, rgbaMask); 2665 } 2666 } 2667 2668 if(mask & GL_DEPTH_BUFFER_BIT) 2669 { 2670 if(mState.depthMask != 0) 2671 { 2672 device->clearDepth(depth); 2673 } 2674 } 2675 2676 if(mask & GL_STENCIL_BUFFER_BIT) 2677 { 2678 if(mState.stencilWritemask != 0) 2679 { 2680 device->clearStencil(stencil, mState.stencilWritemask); 2681 } 2682 } 2683 } 2684 2685 void Context::drawArrays(GLenum mode, GLint first, GLsizei count) 2686 { 2687 sw::DrawType primitiveType; 2688 int primitiveCount; 2689 2690 if(!es2sw::ConvertPrimitiveType(mode, count, GL_NONE, primitiveType, primitiveCount)) 2691 return error(GL_INVALID_ENUM); 2692 2693 if(primitiveCount <= 0) 2694 { 2695 return; 2696 } 2697 2698 if(!applyRenderTarget()) 2699 { 2700 return; 2701 } 2702 2703 applyState(mode); 2704 2705 GLenum err = applyVertexBuffer(0, first, count); 2706 if(err != GL_NO_ERROR) 2707 { 2708 return error(err); 2709 } 2710 2711 applyTextures(); 2712 2713 if(!cullSkipsDraw(mode)) 2714 { 2715 device->drawPrimitive(primitiveType, primitiveCount); 2716 } 2717 } 2718 2719 void Context::drawElements(GLenum mode, GLsizei count, GLenum type, const void *indices) 2720 { 2721 if(!indices && !mState.elementArrayBuffer) 2722 { 2723 return error(GL_INVALID_OPERATION); 2724 } 2725 2726 sw::DrawType primitiveType; 2727 int primitiveCount; 2728 2729 if(!es2sw::ConvertPrimitiveType(mode, count, type, primitiveType, primitiveCount)) 2730 return error(GL_INVALID_ENUM); 2731 2732 if(primitiveCount <= 0) 2733 { 2734 return; 2735 } 2736 2737 if(!applyRenderTarget()) 2738 { 2739 return; 2740 } 2741 2742 applyState(mode); 2743 2744 TranslatedIndexData indexInfo; 2745 GLenum err = applyIndexBuffer(indices, count, mode, type, &indexInfo); 2746 if(err != GL_NO_ERROR) 2747 { 2748 return error(err); 2749 } 2750 2751 GLsizei vertexCount = indexInfo.maxIndex - indexInfo.minIndex + 1; 2752 err = applyVertexBuffer(-(int)indexInfo.minIndex, indexInfo.minIndex, vertexCount); 2753 if(err != GL_NO_ERROR) 2754 { 2755 return error(err); 2756 } 2757 2758 applyTextures(); 2759 2760 if(!cullSkipsDraw(mode)) 2761 { 2762 device->drawIndexedPrimitive(primitiveType, indexInfo.indexOffset, primitiveCount); 2763 } 2764 } 2765 2766 void Context::drawTexture(GLfloat x, GLfloat y, GLfloat z, GLfloat width, GLfloat height) 2767 { 2768 es1::Framebuffer *framebuffer = getFramebuffer(); 2769 es1::Renderbuffer *renderbuffer = framebuffer->getColorbuffer(); 2770 float targetWidth = (float)renderbuffer->getWidth(); 2771 float targetHeight = (float)renderbuffer->getHeight(); 2772 float x0 = 2.0f * x / targetWidth - 1.0f; 2773 float y0 = 2.0f * y / targetHeight - 1.0f; 2774 float x1 = 2.0f * (x + width) / targetWidth - 1.0f; 2775 float y1 = 2.0f * (y + height) / targetHeight - 1.0f; 2776 float Zw = sw::clamp(mState.zNear + z * (mState.zFar - mState.zNear), mState.zNear, mState.zFar); 2777 2778 float vertices[][3] = {{x0, y0, Zw}, 2779 {x0, y1, Zw}, 2780 {x1, y0, Zw}, 2781 {x1, y1, Zw}}; 2782 2783 ASSERT(mState.samplerTexture[TEXTURE_2D][1].name() == 0); // Multi-texturing unimplemented 2784 es1::Texture *texture = getSamplerTexture(0, TEXTURE_2D); 2785 float textureWidth = (float)texture->getWidth(GL_TEXTURE_2D, 0); 2786 float textureHeight = (float)texture->getHeight(GL_TEXTURE_2D, 0); 2787 int Ucr = texture->getCropRectU(); 2788 int Vcr = texture->getCropRectV(); 2789 int Wcr = texture->getCropRectW(); 2790 int Hcr = texture->getCropRectH(); 2791 2792 float texCoords[][2] = {{Ucr / textureWidth, Vcr / textureHeight}, 2793 {Ucr / textureWidth, (Vcr + Hcr) / textureHeight}, 2794 {(Ucr + Wcr) / textureWidth, Vcr / textureHeight}, 2795 {(Ucr + Wcr) / textureWidth, (Vcr + Hcr) / textureHeight}}; 2796 2797 VertexAttribute oldPositionAttribute = mState.vertexAttribute[sw::Position]; 2798 VertexAttribute oldTexCoord0Attribute = mState.vertexAttribute[sw::TexCoord0]; 2799 gl::BindingPointer<Buffer> oldArrayBuffer = mState.arrayBuffer; 2800 mState.arrayBuffer = nullptr; 2801 2802 glVertexPointer(3, GL_FLOAT, 3 * sizeof(float), vertices); 2803 glEnableClientState(GL_VERTEX_ARRAY); 2804 glTexCoordPointer(2, GL_FLOAT, 2 * sizeof(float), texCoords); 2805 glEnableClientState(GL_TEXTURE_COORD_ARRAY); 2806 2807 sw::Matrix P = projectionStack.current(); 2808 sw::Matrix M = modelViewStack.current(); 2809 sw::Matrix T = textureStack0.current(); 2810 2811 projectionStack.identity(); 2812 modelViewStack.identity(); 2813 textureStack0.identity(); 2814 2815 drawArrays(GL_TRIANGLE_STRIP, 0, 4); 2816 2817 // Restore state 2818 mState.vertexAttribute[sw::Position] = oldPositionAttribute; 2819 mState.vertexAttribute[sw::TexCoord0] = oldTexCoord0Attribute; 2820 mState.arrayBuffer = oldArrayBuffer; 2821 oldArrayBuffer = nullptr; 2822 oldPositionAttribute.mBoundBuffer = nullptr; 2823 oldTexCoord0Attribute.mBoundBuffer = nullptr; 2824 textureStack0.load(T); 2825 modelViewStack.load(M); 2826 projectionStack.load(P); 2827 } 2828 2829 void Context::finish() 2830 { 2831 device->finish(); 2832 } 2833 2834 void Context::flush() 2835 { 2836 // We don't queue anything without processing it as fast as possible 2837 } 2838 2839 void Context::recordInvalidEnum() 2840 { 2841 mInvalidEnum = true; 2842 } 2843 2844 void Context::recordInvalidValue() 2845 { 2846 mInvalidValue = true; 2847 } 2848 2849 void Context::recordInvalidOperation() 2850 { 2851 mInvalidOperation = true; 2852 } 2853 2854 void Context::recordOutOfMemory() 2855 { 2856 mOutOfMemory = true; 2857 } 2858 2859 void Context::recordInvalidFramebufferOperation() 2860 { 2861 mInvalidFramebufferOperation = true; 2862 } 2863 2864 void Context::recordMatrixStackOverflow() 2865 { 2866 mMatrixStackOverflow = true; 2867 } 2868 2869 void Context::recordMatrixStackUnderflow() 2870 { 2871 mMatrixStackUnderflow = true; 2872 } 2873 2874 // Get one of the recorded errors and clear its flag, if any. 2875 // [OpenGL ES 2.0.24] section 2.5 page 13. 2876 GLenum Context::getError() 2877 { 2878 if(mInvalidEnum) 2879 { 2880 mInvalidEnum = false; 2881 2882 return GL_INVALID_ENUM; 2883 } 2884 2885 if(mInvalidValue) 2886 { 2887 mInvalidValue = false; 2888 2889 return GL_INVALID_VALUE; 2890 } 2891 2892 if(mInvalidOperation) 2893 { 2894 mInvalidOperation = false; 2895 2896 return GL_INVALID_OPERATION; 2897 } 2898 2899 if(mOutOfMemory) 2900 { 2901 mOutOfMemory = false; 2902 2903 return GL_OUT_OF_MEMORY; 2904 } 2905 2906 if(mInvalidFramebufferOperation) 2907 { 2908 mInvalidFramebufferOperation = false; 2909 2910 return GL_INVALID_FRAMEBUFFER_OPERATION_OES; 2911 } 2912 2913 if(mMatrixStackOverflow) 2914 { 2915 mMatrixStackOverflow = false; 2916 2917 return GL_INVALID_FRAMEBUFFER_OPERATION_OES; 2918 } 2919 2920 if(mMatrixStackUnderflow) 2921 { 2922 mMatrixStackUnderflow = false; 2923 2924 return GL_INVALID_FRAMEBUFFER_OPERATION_OES; 2925 } 2926 2927 return GL_NO_ERROR; 2928 } 2929 2930 int Context::getSupportedMultisampleCount(int requested) 2931 { 2932 int supported = 0; 2933 2934 for(int i = NUM_MULTISAMPLE_COUNTS - 1; i >= 0; i--) 2935 { 2936 if(supported >= requested) 2937 { 2938 return supported; 2939 } 2940 2941 supported = multisampleCount[i]; 2942 } 2943 2944 return supported; 2945 } 2946 2947 void Context::detachBuffer(GLuint buffer) 2948 { 2949 // [OpenGL ES 2.0.24] section 2.9 page 22: 2950 // If a buffer object is deleted while it is bound, all bindings to that object in the current context 2951 // (i.e. in the thread that called Delete-Buffers) are reset to zero. 2952 2953 if(mState.arrayBuffer.name() == buffer) 2954 { 2955 mState.arrayBuffer = nullptr; 2956 } 2957 2958 if(mState.elementArrayBuffer.name() == buffer) 2959 { 2960 mState.elementArrayBuffer = nullptr; 2961 } 2962 2963 for(int attribute = 0; attribute < MAX_VERTEX_ATTRIBS; attribute++) 2964 { 2965 if(mState.vertexAttribute[attribute].mBoundBuffer.name() == buffer) 2966 { 2967 mState.vertexAttribute[attribute].mBoundBuffer = nullptr; 2968 } 2969 } 2970 } 2971 2972 void Context::detachTexture(GLuint texture) 2973 { 2974 // [OpenGL ES 2.0.24] section 3.8 page 84: 2975 // If a texture object is deleted, it is as if all texture units which are bound to that texture object are 2976 // rebound to texture object zero 2977 2978 for(int type = 0; type < TEXTURE_TYPE_COUNT; type++) 2979 { 2980 for(int sampler = 0; sampler < MAX_TEXTURE_UNITS; sampler++) 2981 { 2982 if(mState.samplerTexture[type][sampler].name() == texture) 2983 { 2984 mState.samplerTexture[type][sampler] = nullptr; 2985 } 2986 } 2987 } 2988 2989 // [OpenGL ES 2.0.24] section 4.4 page 112: 2990 // If a texture object is deleted while its image is attached to the currently bound framebuffer, then it is 2991 // as if FramebufferTexture2D had been called, with a texture of 0, for each attachment point to which this 2992 // image was attached in the currently bound framebuffer. 2993 2994 Framebuffer *framebuffer = getFramebuffer(); 2995 2996 if(framebuffer) 2997 { 2998 framebuffer->detachTexture(texture); 2999 } 3000 } 3001 3002 void Context::detachFramebuffer(GLuint framebuffer) 3003 { 3004 // [OpenGL ES 2.0.24] section 4.4 page 107: 3005 // If a framebuffer that is currently bound to the target FRAMEBUFFER is deleted, it is as though 3006 // BindFramebuffer had been executed with the target of FRAMEBUFFER and framebuffer of zero. 3007 3008 if(mState.framebuffer == framebuffer) 3009 { 3010 bindFramebuffer(0); 3011 } 3012 } 3013 3014 void Context::detachRenderbuffer(GLuint renderbuffer) 3015 { 3016 // [OpenGL ES 2.0.24] section 4.4 page 109: 3017 // If a renderbuffer that is currently bound to RENDERBUFFER is deleted, it is as though BindRenderbuffer 3018 // had been executed with the target RENDERBUFFER and name of zero. 3019 3020 if(mState.renderbuffer.name() == renderbuffer) 3021 { 3022 bindRenderbuffer(0); 3023 } 3024 3025 // [OpenGL ES 2.0.24] section 4.4 page 111: 3026 // If a renderbuffer object is deleted while its image is attached to the currently bound framebuffer, 3027 // then it is as if FramebufferRenderbuffer had been called, with a renderbuffer of 0, for each attachment 3028 // point to which this image was attached in the currently bound framebuffer. 3029 3030 Framebuffer *framebuffer = getFramebuffer(); 3031 3032 if(framebuffer) 3033 { 3034 framebuffer->detachRenderbuffer(renderbuffer); 3035 } 3036 } 3037 3038 bool Context::cullSkipsDraw(GLenum drawMode) 3039 { 3040 return mState.cullFaceEnabled && mState.cullMode == GL_FRONT_AND_BACK && isTriangleMode(drawMode); 3041 } 3042 3043 bool Context::isTriangleMode(GLenum drawMode) 3044 { 3045 switch(drawMode) 3046 { 3047 case GL_TRIANGLES: 3048 case GL_TRIANGLE_FAN: 3049 case GL_TRIANGLE_STRIP: 3050 return true; 3051 case GL_POINTS: 3052 case GL_LINES: 3053 case GL_LINE_LOOP: 3054 case GL_LINE_STRIP: 3055 return false; 3056 default: UNREACHABLE(drawMode); 3057 } 3058 3059 return false; 3060 } 3061 3062 void Context::setVertexAttrib(GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w) 3063 { 3064 ASSERT(index < MAX_VERTEX_ATTRIBS); 3065 3066 mState.vertexAttribute[index].mCurrentValue[0] = x; 3067 mState.vertexAttribute[index].mCurrentValue[1] = y; 3068 mState.vertexAttribute[index].mCurrentValue[2] = z; 3069 mState.vertexAttribute[index].mCurrentValue[3] = w; 3070 3071 mVertexDataManager->dirtyCurrentValue(index); 3072 } 3073 3074 void Context::bindTexImage(egl::Surface *surface) 3075 { 3076 es1::Texture2D *textureObject = getTexture2D(); 3077 3078 if(textureObject) 3079 { 3080 textureObject->bindTexImage(surface); 3081 } 3082 } 3083 3084 EGLenum Context::validateSharedImage(EGLenum target, GLuint name, GLuint textureLevel) 3085 { 3086 switch(target) 3087 { 3088 case EGL_GL_TEXTURE_2D_KHR: 3089 break; 3090 case EGL_GL_RENDERBUFFER_KHR: 3091 break; 3092 default: 3093 return EGL_BAD_PARAMETER; 3094 } 3095 3096 if(textureLevel >= IMPLEMENTATION_MAX_TEXTURE_LEVELS) 3097 { 3098 return EGL_BAD_MATCH; 3099 } 3100 3101 if(target == EGL_GL_TEXTURE_2D_KHR) 3102 { 3103 Texture *texture = getTexture(name); 3104 3105 if(!texture || texture->getTarget() != GL_TEXTURE_2D) 3106 { 3107 return EGL_BAD_PARAMETER; 3108 } 3109 3110 if(texture->isShared(GL_TEXTURE_2D, textureLevel)) // Bound to an EGLSurface or already an EGLImage sibling 3111 { 3112 return EGL_BAD_ACCESS; 3113 } 3114 3115 if(textureLevel != 0 && !texture->isSamplerComplete()) 3116 { 3117 return EGL_BAD_PARAMETER; 3118 } 3119 3120 if(textureLevel == 0 && !(texture->isSamplerComplete() && texture->getLevelCount() == 1)) 3121 { 3122 return EGL_BAD_PARAMETER; 3123 } 3124 } 3125 else if(target == EGL_GL_RENDERBUFFER_KHR) 3126 { 3127 Renderbuffer *renderbuffer = getRenderbuffer(name); 3128 3129 if(!renderbuffer) 3130 { 3131 return EGL_BAD_PARAMETER; 3132 } 3133 3134 if(renderbuffer->isShared()) // Already an EGLImage sibling 3135 { 3136 return EGL_BAD_ACCESS; 3137 } 3138 } 3139 else UNREACHABLE(target); 3140 3141 return EGL_SUCCESS; 3142 } 3143 3144 egl::Image *Context::createSharedImage(EGLenum target, GLuint name, GLuint textureLevel) 3145 { 3146 if(target == EGL_GL_TEXTURE_2D_KHR) 3147 { 3148 es1::Texture *texture = getTexture(name); 3149 3150 return texture->createSharedImage(GL_TEXTURE_2D, textureLevel); 3151 } 3152 else if(target == EGL_GL_RENDERBUFFER_KHR) 3153 { 3154 es1::Renderbuffer *renderbuffer = getRenderbuffer(name); 3155 3156 return renderbuffer->createSharedImage(); 3157 } 3158 else UNREACHABLE(target); 3159 3160 return 0; 3161 } 3162 3163 Device *Context::getDevice() 3164 { 3165 return device; 3166 } 3167 3168 void Context::setMatrixMode(GLenum mode) 3169 { 3170 matrixMode = mode; 3171 } 3172 3173 sw::MatrixStack &Context::currentMatrixStack() 3174 { 3175 switch(matrixMode) 3176 { 3177 case GL_MODELVIEW: 3178 return modelViewStack; 3179 case GL_PROJECTION: 3180 return projectionStack; 3181 case GL_TEXTURE: 3182 switch(mState.activeSampler) 3183 { 3184 case 0: return textureStack0; 3185 case 1: return textureStack1; 3186 } 3187 break; 3188 } 3189 3190 UNREACHABLE(matrixMode); 3191 return textureStack0; 3192 } 3193 3194 void Context::loadIdentity() 3195 { 3196 currentMatrixStack().identity(); 3197 } 3198 3199 void Context::load(const GLfloat *m) 3200 { 3201 currentMatrixStack().load(m); 3202 } 3203 3204 void Context::pushMatrix() 3205 { 3206 if(!currentMatrixStack().push()) 3207 { 3208 return error(GL_STACK_OVERFLOW); 3209 } 3210 } 3211 3212 void Context::popMatrix() 3213 { 3214 if(!currentMatrixStack().pop()) 3215 { 3216 return error(GL_STACK_OVERFLOW); 3217 } 3218 } 3219 3220 void Context::rotate(GLfloat angle, GLfloat x, GLfloat y, GLfloat z) 3221 { 3222 currentMatrixStack().rotate(angle, x, y, z); 3223 } 3224 3225 void Context::translate(GLfloat x, GLfloat y, GLfloat z) 3226 { 3227 currentMatrixStack().translate(x, y, z); 3228 } 3229 3230 void Context::scale(GLfloat x, GLfloat y, GLfloat z) 3231 { 3232 currentMatrixStack().scale(x, y, z); 3233 } 3234 3235 void Context::multiply(const GLfloat *m) 3236 { 3237 currentMatrixStack().multiply(m); 3238 } 3239 3240 void Context::frustum(GLfloat left, GLfloat right, GLfloat bottom, GLfloat top, GLfloat zNear, GLfloat zFar) 3241 { 3242 currentMatrixStack().frustum(left, right, bottom, top, zNear, zFar); 3243 } 3244 3245 void Context::ortho(GLfloat left, GLfloat right, GLfloat bottom, GLfloat top, GLfloat zNear, GLfloat zFar) 3246 { 3247 currentMatrixStack().ortho(left, right, bottom, top, zNear, zFar); 3248 } 3249 3250 void Context::setClipPlane(int index, const float plane[4]) 3251 { 3252 sw::Plane clipPlane = modelViewStack.current() * sw::Plane(plane); 3253 device->setClipPlane(index, &clipPlane.A); 3254 } 3255 3256 void Context::setClipPlaneEnabled(int index, bool enable) 3257 { 3258 clipFlags = (clipFlags & ~((int)!enable << index)) | ((int)enable << index); 3259 device->setClipFlags(clipFlags); 3260 } 3261 3262 bool Context::isClipPlaneEnabled(int index) const 3263 { 3264 return (clipFlags & (1 << index)) != 0; 3265 } 3266 3267 void Context::setColorLogicOpEnabled(bool enable) 3268 { 3269 colorLogicOpEnabled = enable; 3270 } 3271 3272 bool Context::isColorLogicOpEnabled() const 3273 { 3274 return colorLogicOpEnabled; 3275 } 3276 3277 void Context::setLogicalOperation(GLenum logicOp) 3278 { 3279 logicalOperation = logicOp; 3280 } 3281 3282 void Context::setLineSmoothEnabled(bool enable) 3283 { 3284 lineSmoothEnabled = enable; 3285 } 3286 3287 bool Context::isLineSmoothEnabled() const 3288 { 3289 return lineSmoothEnabled; 3290 } 3291 3292 void Context::setColorMaterialEnabled(bool enable) 3293 { 3294 colorMaterialEnabled = enable; 3295 } 3296 3297 bool Context::isColorMaterialEnabled() const 3298 { 3299 return colorMaterialEnabled; 3300 } 3301 3302 void Context::setNormalizeEnabled(bool enable) 3303 { 3304 normalizeEnabled = enable; 3305 } 3306 3307 bool Context::isNormalizeEnabled() const 3308 { 3309 return normalizeEnabled; 3310 } 3311 3312 void Context::setRescaleNormalEnabled(bool enable) 3313 { 3314 rescaleNormalEnabled = enable; 3315 } 3316 3317 bool Context::isRescaleNormalEnabled() const 3318 { 3319 return rescaleNormalEnabled; 3320 } 3321 3322 void Context::setVertexArrayEnabled(bool enable) 3323 { 3324 mState.vertexAttribute[sw::Position].mArrayEnabled = enable; 3325 } 3326 3327 bool Context::isVertexArrayEnabled() const 3328 { 3329 return mState.vertexAttribute[sw::Position].mArrayEnabled; 3330 } 3331 3332 void Context::setNormalArrayEnabled(bool enable) 3333 { 3334 mState.vertexAttribute[sw::Normal].mArrayEnabled = enable; 3335 } 3336 3337 bool Context::isNormalArrayEnabled() const 3338 { 3339 return mState.vertexAttribute[sw::Normal].mArrayEnabled; 3340 } 3341 3342 void Context::setColorArrayEnabled(bool enable) 3343 { 3344 mState.vertexAttribute[sw::Color0].mArrayEnabled = enable; 3345 } 3346 3347 bool Context::isColorArrayEnabled() const 3348 { 3349 return mState.vertexAttribute[sw::Color0].mArrayEnabled; 3350 } 3351 3352 void Context::setPointSizeArrayEnabled(bool enable) 3353 { 3354 mState.vertexAttribute[sw::PointSize].mArrayEnabled = enable; 3355 } 3356 3357 bool Context::isPointSizeArrayEnabled() const 3358 { 3359 return mState.vertexAttribute[sw::PointSize].mArrayEnabled; 3360 } 3361 3362 void Context::setTextureCoordArrayEnabled(bool enable) 3363 { 3364 mState.vertexAttribute[sw::TexCoord0 + clientTexture].mArrayEnabled = enable; 3365 } 3366 3367 bool Context::isTextureCoordArrayEnabled() const 3368 { 3369 return mState.vertexAttribute[sw::TexCoord0 + clientTexture].mArrayEnabled; 3370 } 3371 3372 void Context::setMultisampleEnabled(bool enable) 3373 { 3374 multisampleEnabled = enable; 3375 } 3376 3377 bool Context::isMultisampleEnabled() const 3378 { 3379 return multisampleEnabled; 3380 } 3381 3382 void Context::setSampleAlphaToOneEnabled(bool enable) 3383 { 3384 sampleAlphaToOneEnabled = enable; 3385 } 3386 3387 bool Context::isSampleAlphaToOneEnabled() const 3388 { 3389 return sampleAlphaToOneEnabled; 3390 } 3391 3392 void Context::setPointSpriteEnabled(bool enable) 3393 { 3394 pointSpriteEnabled = enable; 3395 } 3396 3397 bool Context::isPointSpriteEnabled() const 3398 { 3399 return pointSpriteEnabled; 3400 } 3401 3402 void Context::setPointSmoothEnabled(bool enable) 3403 { 3404 pointSmoothEnabled = enable; 3405 } 3406 3407 bool Context::isPointSmoothEnabled() const 3408 { 3409 return pointSmoothEnabled; 3410 } 3411 3412 void Context::setPointSizeMin(float min) 3413 { 3414 pointSizeMin = min; 3415 } 3416 3417 void Context::setPointSizeMax(float max) 3418 { 3419 pointSizeMax = max; 3420 } 3421 3422 void Context::setPointDistanceAttenuation(float a, float b, float c) 3423 { 3424 pointDistanceAttenuation = {a, b, c}; 3425 } 3426 3427 void Context::setPointFadeThresholdSize(float threshold) 3428 { 3429 pointFadeThresholdSize = threshold; 3430 } 3431 3432 void Context::clientActiveTexture(GLenum texture) 3433 { 3434 clientTexture = texture; 3435 } 3436 3437 GLenum Context::getClientActiveTexture() const 3438 { 3439 return clientTexture; 3440 } 3441 3442 unsigned int Context::getActiveTexture() const 3443 { 3444 return mState.activeSampler; 3445 } 3446 3447 } 3448 3449 egl::Context *es1CreateContext(const egl::Config *config, const egl::Context *shareContext) 3450 { 3451 ASSERT(!shareContext || shareContext->getClientVersion() == 1); // Should be checked by eglCreateContext 3452 return new es1::Context(config, static_cast<const es1::Context*>(shareContext)); 3453 } 3454