diff options
Diffstat (limited to '')
-rw-r--r-- | linden/indra/llrender/llimagegl.cpp | 152 |
1 files changed, 111 insertions, 41 deletions
diff --git a/linden/indra/llrender/llimagegl.cpp b/linden/indra/llrender/llimagegl.cpp index 92d8eb4..fd934b9 100644 --- a/linden/indra/llrender/llimagegl.cpp +++ b/linden/indra/llrender/llimagegl.cpp | |||
@@ -41,7 +41,7 @@ | |||
41 | 41 | ||
42 | #include "llmath.h" | 42 | #include "llmath.h" |
43 | #include "llgl.h" | 43 | #include "llgl.h" |
44 | #include "llglimmediate.h" | 44 | #include "llrender.h" |
45 | 45 | ||
46 | 46 | ||
47 | //---------------------------------------------------------------------------- | 47 | //---------------------------------------------------------------------------- |
@@ -130,13 +130,13 @@ void LLImageGL::bindExternalTexture(LLGLuint gl_name, S32 stage, LLGLenum bind_t | |||
130 | gGL.flush(); | 130 | gGL.flush(); |
131 | if (stage > 0) | 131 | if (stage > 0) |
132 | { | 132 | { |
133 | glActiveTextureARB(GL_TEXTURE0_ARB + stage); | 133 | gGL.getTexUnit(stage)->activate(); |
134 | } | 134 | } |
135 | glBindTexture(bind_target, gl_name); | 135 | glBindTexture(bind_target, gl_name); |
136 | sCurrentBoundTextures[stage] = gl_name; | 136 | sCurrentBoundTextures[stage] = gl_name; |
137 | if (stage > 0) | 137 | if (stage > 0) |
138 | { | 138 | { |
139 | glActiveTextureARB(GL_TEXTURE0_ARB); | 139 | gGL.getTexUnit(0)->activate(); |
140 | } | 140 | } |
141 | } | 141 | } |
142 | 142 | ||
@@ -149,9 +149,9 @@ void LLImageGL::unbindTexture(S32 stage, LLGLenum bind_target) | |||
149 | gGL.flush(); | 149 | gGL.flush(); |
150 | if (stage > 0) | 150 | if (stage > 0) |
151 | { | 151 | { |
152 | glActiveTextureARB(GL_TEXTURE0_ARB + stage); | 152 | gGL.getTexUnit(stage)->activate(); |
153 | glBindTexture(GL_TEXTURE_2D, 0); | 153 | glBindTexture(GL_TEXTURE_2D, 0); |
154 | glActiveTextureARB(GL_TEXTURE0_ARB); | 154 | gGL.getTexUnit(0)->activate(); |
155 | } | 155 | } |
156 | else | 156 | else |
157 | { | 157 | { |
@@ -304,7 +304,9 @@ void LLImageGL::init(BOOL usemipmaps) | |||
304 | mIsResident = 0; | 304 | mIsResident = 0; |
305 | mClampS = FALSE; | 305 | mClampS = FALSE; |
306 | mClampT = FALSE; | 306 | mClampT = FALSE; |
307 | mMipFilterNearest = FALSE; | 307 | mClampR = FALSE; |
308 | mMagFilterNearest = FALSE; | ||
309 | mMinFilterNearest = FALSE; | ||
308 | mWidth = 0; | 310 | mWidth = 0; |
309 | mHeight = 0; | 311 | mHeight = 0; |
310 | mComponents = 0; | 312 | mComponents = 0; |
@@ -439,7 +441,7 @@ BOOL LLImageGL::bindTextureInternal(const S32 stage) const | |||
439 | gGL.flush(); | 441 | gGL.flush(); |
440 | if (stage > 0) | 442 | if (stage > 0) |
441 | { | 443 | { |
442 | glActiveTextureARB(GL_TEXTURE0_ARB + stage); | 444 | gGL.getTexUnit(stage)->activate(); |
443 | } | 445 | } |
444 | 446 | ||
445 | glBindTexture(mBindTarget, mTexName); | 447 | glBindTexture(mBindTarget, mTexName); |
@@ -448,7 +450,7 @@ BOOL LLImageGL::bindTextureInternal(const S32 stage) const | |||
448 | 450 | ||
449 | if (stage > 0) | 451 | if (stage > 0) |
450 | { | 452 | { |
451 | glActiveTextureARB(GL_TEXTURE0_ARB); | 453 | gGL.getTexUnit(0)->activate(); |
452 | } | 454 | } |
453 | 455 | ||
454 | if (mLastBindTime != sLastFrameTime) | 456 | if (mLastBindTime != sLastFrameTime) |
@@ -466,12 +468,12 @@ BOOL LLImageGL::bindTextureInternal(const S32 stage) const | |||
466 | gGL.flush(); | 468 | gGL.flush(); |
467 | if (stage > 0) | 469 | if (stage > 0) |
468 | { | 470 | { |
469 | glActiveTextureARB(GL_TEXTURE0_ARB+stage); | 471 | gGL.getTexUnit(stage)->activate(); |
470 | } | 472 | } |
471 | glBindTexture(mBindTarget, 0); | 473 | glBindTexture(mBindTarget, 0); |
472 | if (stage > 0) | 474 | if (stage > 0) |
473 | { | 475 | { |
474 | glActiveTextureARB(GL_TEXTURE0_ARB+stage); | 476 | gGL.getTexUnit(0)->activate(); |
475 | } | 477 | } |
476 | sCurrentBoundTextures[stage] = 0; | 478 | sCurrentBoundTextures[stage] = 0; |
477 | return FALSE; | 479 | return FALSE; |
@@ -628,7 +630,7 @@ void LLImageGL::setImage(const U8* data_in, BOOL data_hasmips) | |||
628 | { | 630 | { |
629 | S32 bytes = w * h * mComponents; | 631 | S32 bytes = w * h * mComponents; |
630 | llassert(prev_mip_data); | 632 | llassert(prev_mip_data); |
631 | llassert(prev_mip_size == bytes); | 633 | llassert(prev_mip_size == bytes*4); |
632 | U8* new_data = new U8[bytes]; | 634 | U8* new_data = new U8[bytes]; |
633 | llassert_always(new_data); | 635 | llassert_always(new_data); |
634 | LLImageBase::generateMip(prev_mip_data, new_data, w, h, mComponents); | 636 | LLImageBase::generateMip(prev_mip_data, new_data, w, h, mComponents); |
@@ -941,7 +943,7 @@ BOOL LLImageGL::createGLTexture(S32 discard_level, const U8* data_in, BOOL data_ | |||
941 | setImage(data_in, data_hasmips); | 943 | setImage(data_in, data_hasmips); |
942 | 944 | ||
943 | setClamp(mClampS, mClampT); | 945 | setClamp(mClampS, mClampT); |
944 | setMipFilterNearest(mMipFilterNearest); | 946 | setMipFilterNearest(mMagFilterNearest); |
945 | 947 | ||
946 | // things will break if we don't unbind after creation | 948 | // things will break if we don't unbind after creation |
947 | unbindTexture(0, mBindTarget); | 949 | unbindTexture(0, mBindTarget); |
@@ -1044,8 +1046,23 @@ BOOL LLImageGL::readBackRaw(S32 discard_level, LLImageRaw* imageraw, bool compre | |||
1044 | 1046 | ||
1045 | S32 gl_discard = discard_level - mCurrentDiscardLevel; | 1047 | S32 gl_discard = discard_level - mCurrentDiscardLevel; |
1046 | 1048 | ||
1047 | llverify(bindTextureInternal(0)); | 1049 | //explicitly unbind texture |
1048 | 1050 | LLImageGL::unbindTexture(0, mTarget); | |
1051 | llverify(bindTextureInternal(0)); | ||
1052 | |||
1053 | if (gDebugGL) | ||
1054 | { | ||
1055 | if (mTarget == GL_TEXTURE_2D) | ||
1056 | { | ||
1057 | GLint texname; | ||
1058 | glGetIntegerv(GL_TEXTURE_BINDING_2D, &texname); | ||
1059 | if (texname != mTexName) | ||
1060 | { | ||
1061 | llerrs << "Invalid texture bound!" << llendl; | ||
1062 | } | ||
1063 | } | ||
1064 | } | ||
1065 | |||
1049 | LLGLint glwidth = 0; | 1066 | LLGLint glwidth = 0; |
1050 | glGetTexLevelParameteriv(mTarget, gl_discard, GL_TEXTURE_WIDTH, (GLint*)&glwidth); | 1067 | glGetTexLevelParameteriv(mTarget, gl_discard, GL_TEXTURE_WIDTH, (GLint*)&glwidth); |
1051 | if (glwidth == 0) | 1068 | if (glwidth == 0) |
@@ -1067,40 +1084,63 @@ BOOL LLImageGL::readBackRaw(S32 discard_level, LLImageRaw* imageraw, bool compre | |||
1067 | llerrs << llformat("LLImageGL::readBackRaw: bogus params: %d x %d x %d",width,height,ncomponents) << llendl; | 1084 | llerrs << llformat("LLImageGL::readBackRaw: bogus params: %d x %d x %d",width,height,ncomponents) << llendl; |
1068 | } | 1085 | } |
1069 | 1086 | ||
1070 | BOOL return_result = TRUE ; | ||
1071 | LLGLint is_compressed = 0; | 1087 | LLGLint is_compressed = 0; |
1072 | if (compressed_ok) | 1088 | if (compressed_ok) |
1073 | { | 1089 | { |
1074 | glGetTexLevelParameteriv(mTarget, is_compressed, GL_TEXTURE_COMPRESSED, (GLint*)&is_compressed); | 1090 | glGetTexLevelParameteriv(mTarget, is_compressed, GL_TEXTURE_COMPRESSED, (GLint*)&is_compressed); |
1075 | } | 1091 | } |
1092 | |||
1093 | //----------------------------------------------------------------------------------------------- | ||
1094 | GLenum error ; | ||
1095 | while((error = glGetError()) != GL_NO_ERROR) | ||
1096 | { | ||
1097 | llwarns << "GL Error happens before reading back texture. Error code: " << error << llendl ; | ||
1098 | } | ||
1099 | //----------------------------------------------------------------------------------------------- | ||
1100 | |||
1076 | if (is_compressed) | 1101 | if (is_compressed) |
1077 | { | 1102 | { |
1078 | LLGLint glbytes; | 1103 | LLGLint glbytes; |
1079 | glGetTexLevelParameteriv(mTarget, gl_discard, GL_TEXTURE_COMPRESSED_IMAGE_SIZE, (GLint*)&glbytes); | 1104 | glGetTexLevelParameteriv(mTarget, gl_discard, GL_TEXTURE_COMPRESSED_IMAGE_SIZE, (GLint*)&glbytes); |
1080 | imageraw->allocateDataSize(width, height, ncomponents, glbytes); | 1105 | if(!imageraw->allocateDataSize(width, height, ncomponents, glbytes)) |
1081 | glGetCompressedTexImageARB(mTarget, gl_discard, (GLvoid*)(imageraw->getData())); | ||
1082 | if(glGetError() != GL_NO_ERROR) | ||
1083 | { | 1106 | { |
1084 | llwarns << "Error happens when reading back the compressed texture image." << llendl ; | 1107 | llwarns << "Memory allocation failed for reading back texture. Size is: " << glbytes << llendl ; |
1085 | imageraw->deleteData() ; | 1108 | llwarns << "width: " << width << "height: " << height << "components: " << ncomponents << llendl ; |
1086 | return_result = FALSE ; | 1109 | return FALSE ; |
1087 | } | 1110 | } |
1088 | stop_glerror(); | 1111 | |
1112 | glGetCompressedTexImageARB(mTarget, gl_discard, (GLvoid*)(imageraw->getData())); | ||
1113 | //stop_glerror(); | ||
1089 | } | 1114 | } |
1090 | else | 1115 | else |
1091 | { | 1116 | { |
1092 | imageraw->allocateDataSize(width, height, ncomponents); | 1117 | if(!imageraw->allocateDataSize(width, height, ncomponents)) |
1093 | glGetTexImage(GL_TEXTURE_2D, gl_discard, mFormatPrimary, mFormatType, (GLvoid*)(imageraw->getData())); | ||
1094 | if(glGetError() != GL_NO_ERROR) | ||
1095 | { | 1118 | { |
1096 | llwarns << "Error happens when reading back the texture image." << llendl ; | 1119 | llwarns << "Memory allocation failed for reading back texture." << llendl ; |
1097 | imageraw->deleteData() ; | 1120 | llwarns << "width: " << width << "height: " << height << "components: " << ncomponents << llendl ; |
1098 | return_result = FALSE ; | 1121 | return FALSE ; |
1099 | } | 1122 | } |
1100 | stop_glerror(); | 1123 | |
1124 | glGetTexImage(GL_TEXTURE_2D, gl_discard, mFormatPrimary, mFormatType, (GLvoid*)(imageraw->getData())); | ||
1125 | //stop_glerror(); | ||
1101 | } | 1126 | } |
1102 | 1127 | ||
1103 | return return_result ; | 1128 | //----------------------------------------------------------------------------------------------- |
1129 | if((error = glGetError()) != GL_NO_ERROR) | ||
1130 | { | ||
1131 | llwarns << "GL Error happens after reading back texture. Error code: " << error << llendl ; | ||
1132 | imageraw->deleteData() ; | ||
1133 | |||
1134 | while((error = glGetError()) != GL_NO_ERROR) | ||
1135 | { | ||
1136 | llwarns << "GL Error happens after reading back texture. Error code: " << error << llendl ; | ||
1137 | } | ||
1138 | |||
1139 | return FALSE ; | ||
1140 | } | ||
1141 | //----------------------------------------------------------------------------------------------- | ||
1142 | |||
1143 | return TRUE ; | ||
1104 | } | 1144 | } |
1105 | 1145 | ||
1106 | void LLImageGL::destroyGLTexture() | 1146 | void LLImageGL::destroyGLTexture() |
@@ -1130,25 +1170,55 @@ void LLImageGL::destroyGLTexture() | |||
1130 | 1170 | ||
1131 | //---------------------------------------------------------------------------- | 1171 | //---------------------------------------------------------------------------- |
1132 | 1172 | ||
1133 | void LLImageGL::setClamp(BOOL clamps, BOOL clampt) | 1173 | void LLImageGL::glClampCubemap (BOOL clamps, BOOL clampt, BOOL clampr) |
1174 | { | ||
1175 | glTexParameteri (GL_TEXTURE_CUBE_MAP_ARB, GL_TEXTURE_WRAP_S, clamps ? GL_CLAMP_TO_EDGE : GL_REPEAT); | ||
1176 | glTexParameteri (GL_TEXTURE_CUBE_MAP_ARB, GL_TEXTURE_WRAP_T, clamps ? GL_CLAMP_TO_EDGE : GL_REPEAT); | ||
1177 | glTexParameteri (GL_TEXTURE_CUBE_MAP_ARB, GL_TEXTURE_WRAP_R, clamps ? GL_CLAMP_TO_EDGE : GL_REPEAT); | ||
1178 | } | ||
1179 | |||
1180 | void LLImageGL::glClamp (BOOL clamps, BOOL clampt) | ||
1134 | { | 1181 | { |
1135 | mClampS = clamps; | ||
1136 | mClampT = clampt; | ||
1137 | if (mTexName != 0) | 1182 | if (mTexName != 0) |
1138 | { | 1183 | { |
1139 | glTexParameteri(mBindTarget, GL_TEXTURE_WRAP_S, clamps ? GL_CLAMP_TO_EDGE : GL_REPEAT); | 1184 | glTexParameteri (mBindTarget, GL_TEXTURE_WRAP_S, clamps ? GL_CLAMP_TO_EDGE : GL_REPEAT); |
1140 | glTexParameteri(mBindTarget, GL_TEXTURE_WRAP_T, clampt ? GL_CLAMP_TO_EDGE : GL_REPEAT); | 1185 | glTexParameteri (mBindTarget, GL_TEXTURE_WRAP_T, clampt ? GL_CLAMP_TO_EDGE : GL_REPEAT); |
1141 | } | 1186 | } |
1142 | stop_glerror(); | ||
1143 | } | 1187 | } |
1144 | 1188 | ||
1145 | void LLImageGL::setMipFilterNearest(BOOL nearest, BOOL min_nearest) | 1189 | void LLImageGL::setClampCubemap (BOOL clamps, BOOL clampt, BOOL clampr) |
1190 | { | ||
1191 | mClampS = clamps; | ||
1192 | mClampT = clampt; | ||
1193 | mClampR = clampr; | ||
1194 | glClampCubemap (clamps, clampt, clampr); | ||
1195 | } | ||
1196 | |||
1197 | void LLImageGL::setClamp(BOOL clamps, BOOL clampt) | ||
1198 | { | ||
1199 | mClampS = clamps; | ||
1200 | mClampT = clampt; | ||
1201 | glClamp (clamps, clampt); | ||
1202 | } | ||
1203 | |||
1204 | void LLImageGL::overrideClamp (BOOL clamps, BOOL clampt) | ||
1205 | { | ||
1206 | glClamp (clamps, clampt); | ||
1207 | } | ||
1208 | |||
1209 | void LLImageGL::restoreClamp (void) | ||
1210 | { | ||
1211 | glClamp (mClampS, mClampT); | ||
1212 | } | ||
1213 | |||
1214 | void LLImageGL::setMipFilterNearest(BOOL mag_nearest, BOOL min_nearest) | ||
1146 | { | 1215 | { |
1147 | mMipFilterNearest = nearest; | 1216 | mMagFilterNearest = mag_nearest; |
1217 | mMinFilterNearest = min_nearest; | ||
1148 | 1218 | ||
1149 | if (mTexName != 0) | 1219 | if (mTexName != 0) |
1150 | { | 1220 | { |
1151 | if (min_nearest) | 1221 | if (mMinFilterNearest) |
1152 | { | 1222 | { |
1153 | glTexParameteri(mBindTarget, GL_TEXTURE_MIN_FILTER, GL_NEAREST); | 1223 | glTexParameteri(mBindTarget, GL_TEXTURE_MIN_FILTER, GL_NEAREST); |
1154 | } | 1224 | } |
@@ -1160,7 +1230,7 @@ void LLImageGL::setMipFilterNearest(BOOL nearest, BOOL min_nearest) | |||
1160 | { | 1230 | { |
1161 | glTexParameteri(mBindTarget, GL_TEXTURE_MIN_FILTER, GL_LINEAR); | 1231 | glTexParameteri(mBindTarget, GL_TEXTURE_MIN_FILTER, GL_LINEAR); |
1162 | } | 1232 | } |
1163 | if (mMipFilterNearest) | 1233 | if (mMagFilterNearest) |
1164 | { | 1234 | { |
1165 | glTexParameteri(mBindTarget, GL_TEXTURE_MAG_FILTER, GL_NEAREST); | 1235 | glTexParameteri(mBindTarget, GL_TEXTURE_MAG_FILTER, GL_NEAREST); |
1166 | } | 1236 | } |
@@ -1170,7 +1240,7 @@ void LLImageGL::setMipFilterNearest(BOOL nearest, BOOL min_nearest) | |||
1170 | } | 1240 | } |
1171 | if (gGLManager.mHasAnisotropic) | 1241 | if (gGLManager.mHasAnisotropic) |
1172 | { | 1242 | { |
1173 | if (sGlobalUseAnisotropic && !mMipFilterNearest) | 1243 | if (sGlobalUseAnisotropic && !mMagFilterNearest) |
1174 | { | 1244 | { |
1175 | F32 largest_anisotropy; | 1245 | F32 largest_anisotropy; |
1176 | glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &largest_anisotropy); | 1246 | glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &largest_anisotropy); |