|
|
|
|
@@ -152,12 +152,7 @@ void LLStandardBumpmap::addstandard()
|
|
|
|
|
// llinfos << "Loading bumpmap: " << bump_file << " from viewerart" << llendl;
|
|
|
|
|
gStandardBumpmapList[LLStandardBumpmap::sStandardBumpmapCount].mLabel = label;
|
|
|
|
|
gStandardBumpmapList[LLStandardBumpmap::sStandardBumpmapCount].mImage =
|
|
|
|
|
LLViewerTextureManager::getFetchedTexture(LLUUID(bump_image_id),
|
|
|
|
|
TRUE,
|
|
|
|
|
LLViewerTexture::BOOST_NONE,
|
|
|
|
|
LLViewerTexture::LOD_TEXTURE,
|
|
|
|
|
0,
|
|
|
|
|
0);
|
|
|
|
|
LLViewerTextureManager::getFetchedTexture(LLUUID(bump_image_id));
|
|
|
|
|
gStandardBumpmapList[LLStandardBumpmap::sStandardBumpmapCount].mImage->setBoostLevel(LLViewerTexture::BOOST_BUMP) ;
|
|
|
|
|
gStandardBumpmapList[LLStandardBumpmap::sStandardBumpmapCount].mImage->setLoadedCallback(LLBumpImageList::onSourceStandardLoaded, 0, TRUE, FALSE, NULL, NULL );
|
|
|
|
|
LLStandardBumpmap::sStandardBumpmapCount++;
|
|
|
|
|
@@ -342,30 +337,43 @@ void LLDrawPoolBump::beginShiny(bool invisible)
|
|
|
|
|
sVertexMask = VERTEX_MASK_SHINY | LLVertexBuffer::MAP_TEXCOORD0;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (LLPipeline::sUnderWaterRender)
|
|
|
|
|
if (getVertexShaderLevel() > 0)
|
|
|
|
|
{
|
|
|
|
|
shader = &gObjectShinyWaterProgram;
|
|
|
|
|
if (LLPipeline::sUnderWaterRender)
|
|
|
|
|
{
|
|
|
|
|
shader = &gObjectShinyWaterProgram;
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
shader = &gObjectShinyProgram;
|
|
|
|
|
}
|
|
|
|
|
shader->bind();
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
shader = &gObjectShinyProgram;
|
|
|
|
|
shader = NULL;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bindCubeMap(shader, mVertexShaderLevel, diffuse_channel, cube_channel, invisible);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//static
|
|
|
|
|
void LLDrawPoolBump::bindCubeMap(LLGLSLShader* shader, S32 shader_level, S32& diffuse_channel, S32& cube_channel, bool invisible)
|
|
|
|
|
{
|
|
|
|
|
LLCubeMap* cube_map = gSky.mVOSkyp ? gSky.mVOSkyp->getCubeMap() : NULL;
|
|
|
|
|
if( cube_map )
|
|
|
|
|
{
|
|
|
|
|
if (!invisible && LLViewerShaderMgr::instance()->getVertexShaderLevel(LLViewerShaderMgr::SHADER_OBJECT) > 0 )
|
|
|
|
|
if (!invisible && shader )
|
|
|
|
|
{
|
|
|
|
|
LLMatrix4 mat;
|
|
|
|
|
mat.initRows(LLVector4(gGLModelView+0),
|
|
|
|
|
LLVector4(gGLModelView+4),
|
|
|
|
|
LLVector4(gGLModelView+8),
|
|
|
|
|
LLVector4(gGLModelView+12));
|
|
|
|
|
shader->bind();
|
|
|
|
|
LLVector3 vec = LLVector3(gShinyOrigin) * mat;
|
|
|
|
|
LLVector4 vec4(vec, gShinyOrigin.mV[3]);
|
|
|
|
|
shader->uniform4fv(LLViewerShaderMgr::SHINY_ORIGIN, 1, vec4.mV);
|
|
|
|
|
if (mVertexShaderLevel > 1)
|
|
|
|
|
if (shader_level > 1)
|
|
|
|
|
{
|
|
|
|
|
cube_map->setMatrix(1);
|
|
|
|
|
// Make sure that texture coord generation happens for tex unit 1, as that's the one we use for
|
|
|
|
|
@@ -427,22 +435,16 @@ void LLDrawPoolBump::renderShiny(bool invisible)
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void LLDrawPoolBump::endShiny(bool invisible)
|
|
|
|
|
//static
|
|
|
|
|
void LLDrawPoolBump::unbindCubeMap(LLGLSLShader* shader, S32 shader_level, S32& diffuse_channel, S32& cube_channel, bool invisible)
|
|
|
|
|
{
|
|
|
|
|
LLFastTimer t(LLFastTimer::FTM_RENDER_SHINY);
|
|
|
|
|
if ((!invisible && !gPipeline.hasRenderBatches(LLRenderPass::PASS_SHINY))||
|
|
|
|
|
(invisible && !gPipeline.hasRenderBatches(LLRenderPass::PASS_INVISI_SHINY)))
|
|
|
|
|
{
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
LLCubeMap* cube_map = gSky.mVOSkyp ? gSky.mVOSkyp->getCubeMap() : NULL;
|
|
|
|
|
if( cube_map )
|
|
|
|
|
{
|
|
|
|
|
cube_map->disable();
|
|
|
|
|
cube_map->restoreMatrix();
|
|
|
|
|
|
|
|
|
|
if (!invisible && mVertexShaderLevel > 1)
|
|
|
|
|
if (!invisible && shader_level > 1)
|
|
|
|
|
{
|
|
|
|
|
shader->disableTexture(LLViewerShaderMgr::ENVIRONMENT_MAP, LLTexUnit::TT_CUBE_MAP);
|
|
|
|
|
|
|
|
|
|
@@ -453,7 +455,6 @@ void LLDrawPoolBump::endShiny(bool invisible)
|
|
|
|
|
shader->disableTexture(LLViewerShaderMgr::DIFFUSE_MAP);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
shader->unbind();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
gGL.getTexUnit(diffuse_channel)->disable();
|
|
|
|
|
@@ -461,6 +462,22 @@ void LLDrawPoolBump::endShiny(bool invisible)
|
|
|
|
|
|
|
|
|
|
gGL.getTexUnit(0)->unbind(LLTexUnit::TT_TEXTURE);
|
|
|
|
|
gGL.getTexUnit(0)->setTextureBlendType(LLTexUnit::TB_MULT);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void LLDrawPoolBump::endShiny(bool invisible)
|
|
|
|
|
{
|
|
|
|
|
LLFastTimer t(LLFastTimer::FTM_RENDER_SHINY);
|
|
|
|
|
if ((!invisible && !gPipeline.hasRenderBatches(LLRenderPass::PASS_SHINY))||
|
|
|
|
|
(invisible && !gPipeline.hasRenderBatches(LLRenderPass::PASS_INVISI_SHINY)))
|
|
|
|
|
{
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
unbindCubeMap(shader, mVertexShaderLevel, diffuse_channel, cube_channel, invisible);
|
|
|
|
|
if (shader)
|
|
|
|
|
{
|
|
|
|
|
shader->unbind();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
diffuse_channel = -1;
|
|
|
|
|
cube_channel = 0;
|
|
|
|
|
@@ -481,7 +498,7 @@ void LLDrawPoolBump::beginFullbrightShiny()
|
|
|
|
|
|
|
|
|
|
if (LLPipeline::sUnderWaterRender)
|
|
|
|
|
{
|
|
|
|
|
shader = &gObjectShinyWaterProgram;
|
|
|
|
|
shader = &gObjectFullbrightShinyWaterProgram;
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
@@ -588,18 +605,37 @@ void LLDrawPoolBump::renderGroup(LLSpatialGroup* group, U32 type, U32 mask, BOOL
|
|
|
|
|
// static
|
|
|
|
|
BOOL LLDrawPoolBump::bindBumpMap(LLDrawInfo& params, S32 channel)
|
|
|
|
|
{
|
|
|
|
|
LLViewerTexture* bump = NULL;
|
|
|
|
|
|
|
|
|
|
U8 bump_code = params.mBump;
|
|
|
|
|
|
|
|
|
|
return bindBumpMap(bump_code, params.mTexture, params.mVSize, channel);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//static
|
|
|
|
|
BOOL LLDrawPoolBump::bindBumpMap(LLFace* face, S32 channel)
|
|
|
|
|
{
|
|
|
|
|
const LLTextureEntry* te = face->getTextureEntry();
|
|
|
|
|
if (te)
|
|
|
|
|
{
|
|
|
|
|
U8 bump_code = te->getBumpmap();
|
|
|
|
|
return bindBumpMap(bump_code, face->getTexture(), face->getVirtualSize(), channel);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return FALSE;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//static
|
|
|
|
|
BOOL LLDrawPoolBump::bindBumpMap(U8 bump_code, LLViewerTexture* texture, F32 vsize, S32 channel)
|
|
|
|
|
{
|
|
|
|
|
//Note: texture atlas does not support bump texture now.
|
|
|
|
|
LLViewerFetchedTexture* tex = LLViewerTextureManager::staticCastToFetchedTexture(params.mTexture) ;
|
|
|
|
|
LLViewerFetchedTexture* tex = LLViewerTextureManager::staticCastToFetchedTexture(texture) ;
|
|
|
|
|
if(!tex)
|
|
|
|
|
{
|
|
|
|
|
//if the texture is not a fetched texture
|
|
|
|
|
return FALSE;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
LLViewerTexture* bump = NULL;
|
|
|
|
|
|
|
|
|
|
switch( bump_code )
|
|
|
|
|
{
|
|
|
|
|
case BE_NO_BUMP:
|
|
|
|
|
@@ -613,7 +649,7 @@ BOOL LLDrawPoolBump::bindBumpMap(LLDrawInfo& params, S32 channel)
|
|
|
|
|
if( bump_code < LLStandardBumpmap::sStandardBumpmapCount )
|
|
|
|
|
{
|
|
|
|
|
bump = gStandardBumpmapList[bump_code].mImage;
|
|
|
|
|
gBumpImageList.addTextureStats(bump_code, tex->getID(), params.mVSize);
|
|
|
|
|
gBumpImageList.addTextureStats(bump_code, tex->getID(), vsize);
|
|
|
|
|
}
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
@@ -968,25 +1004,28 @@ LLViewerTexture* LLBumpImageList::getBrightnessDarknessImage(LLViewerFetchedText
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bump_image_map_t::iterator iter = entries_list->find(src_image->getID());
|
|
|
|
|
if (iter != entries_list->end())
|
|
|
|
|
if (iter != entries_list->end() && iter->second.notNull())
|
|
|
|
|
{
|
|
|
|
|
bump = iter->second;
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
LLPointer<LLImageRaw> raw = new LLImageRaw(1,1,1);
|
|
|
|
|
raw->clear(0x77, 0x77, 0x77, 0xFF);
|
|
|
|
|
raw->clear(0x77, 0x77, 0xFF, 0xFF);
|
|
|
|
|
|
|
|
|
|
(*entries_list)[src_image->getID()] = LLViewerTextureManager::getLocalTexture( raw.get(), TRUE);
|
|
|
|
|
(*entries_list)[src_image->getID()]->setExplicitFormat(GL_ALPHA8, GL_ALPHA);
|
|
|
|
|
|
|
|
|
|
// Note: this may create an LLImageGL immediately
|
|
|
|
|
src_image->setBoostLevel(LLViewerTexture::BOOST_BUMP) ;
|
|
|
|
|
src_image->setLoadedCallback( callback_func, 0, TRUE, FALSE, new LLUUID(src_image->getID()), NULL );
|
|
|
|
|
bump = (*entries_list)[src_image->getID()]; // In case callback was called immediately and replaced the image
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// bump_total++;
|
|
|
|
|
// llinfos << "*** Creating " << (void*)bump << " " << bump_total << llendl;
|
|
|
|
|
if (!src_image->hasCallbacks())
|
|
|
|
|
{ //if image has no callbacks but resolutions don't match, trigger raw image loaded callback again
|
|
|
|
|
if (src_image->getWidth() != bump->getWidth() ||
|
|
|
|
|
src_image->getHeight() != bump->getHeight() ||
|
|
|
|
|
(LLPipeline::sRenderDeferred && bump->getComponents() != 4))
|
|
|
|
|
{
|
|
|
|
|
src_image->setBoostLevel(LLViewerTexture::BOOST_BUMP) ;
|
|
|
|
|
src_image->setLoadedCallback( callback_func, 0, TRUE, FALSE, new LLUUID(src_image->getID()), NULL );
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
@@ -1089,7 +1128,21 @@ void LLBumpImageList::onSourceLoaded( BOOL success, LLViewerTexture *src_vi, LLI
|
|
|
|
|
{
|
|
|
|
|
bump_image_map_t& entries_list(bump_code == BE_BRIGHTNESS ? gBumpImageList.mBrightnessEntries : gBumpImageList.mDarknessEntries );
|
|
|
|
|
bump_image_map_t::iterator iter = entries_list.find(source_asset_id);
|
|
|
|
|
if (iter != entries_list.end())
|
|
|
|
|
|
|
|
|
|
if (iter == entries_list.end() ||
|
|
|
|
|
iter->second.isNull() ||
|
|
|
|
|
iter->second->getWidth() != src->getWidth() ||
|
|
|
|
|
iter->second->getHeight() != src->getHeight()) // bump not cached yet or has changed resolution
|
|
|
|
|
{ //make sure an entry exists for this image
|
|
|
|
|
LLPointer<LLImageRaw> raw = new LLImageRaw(1,1,1);
|
|
|
|
|
raw->clear(0x77, 0x77, 0xFF, 0xFF);
|
|
|
|
|
|
|
|
|
|
entries_list[src_vi->getID()] = LLViewerTextureManager::getLocalTexture( raw.get(), TRUE);
|
|
|
|
|
iter = entries_list.find(src_vi->getID());
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//if (iter->second->getWidth() != src->getWidth() ||
|
|
|
|
|
// iter->second->getHeight() != src->getHeight()) // bump not cached yet or has changed resolution
|
|
|
|
|
{
|
|
|
|
|
LLPointer<LLImageRaw> dst_image = new LLImageRaw(src->getWidth(), src->getHeight(), 1);
|
|
|
|
|
U8* dst_data = dst_image->getData();
|
|
|
|
|
@@ -1216,18 +1269,10 @@ void LLBumpImageList::onSourceLoaded( BOOL success, LLViewerTexture *src_vi, LLI
|
|
|
|
|
bump->setExplicitFormat(GL_RGBA, GL_RGBA);
|
|
|
|
|
bump->createGLTexture(0, nrm_image);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
iter->second = bump; // derefs (and deletes) old image
|
|
|
|
|
//---------------------------------------------------
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
// entry should have been added in LLBumpImageList::getImage().
|
|
|
|
|
|
|
|
|
|
// Not a legit assertion - the bump texture could have been flushed by the bump image manager
|
|
|
|
|
//llassert(0);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|