diff --git a/indra/llrender/llrender.cpp b/indra/llrender/llrender.cpp index 81e1eaf36ace0c678e049631350282c200037e8c..5d62ef03be632051d3423aef7939d2ea66c7ddec 100644 --- a/indra/llrender/llrender.cpp +++ b/indra/llrender/llrender.cpp @@ -1613,6 +1613,18 @@ void LLRender::scaleUI(F32 x, F32 y, F32 z) mUIScale.back().mul(scale); } +void LLRender::rotateUI(LLQuaternion& rot) +{ + if (mUIRotation.empty()) + { + mUIRotation.push_back(rot); + } + else + { + mUIRotation.push_back(mUIRotation.back()*rot); + } +} + void LLRender::pushUIMatrix() { if (mUIOffset.empty()) @@ -1632,6 +1644,10 @@ void LLRender::pushUIMatrix() { mUIScale.push_back(mUIScale.back()); } + if (!mUIRotation.empty()) + { + mUIRotation.push_back(mUIRotation.back()); + } } void LLRender::popUIMatrix() @@ -1643,6 +1659,10 @@ void LLRender::popUIMatrix() mUIOffset.pop_back(); mUIScale.pop_back(); + if (!mUIRotation.empty()) + { + mUIRotation.pop_back(); + } } LLVector3 LLRender::getUITranslation() @@ -1672,6 +1692,8 @@ void LLRender::loadUIIdentity() } mUIOffset.back().splat(0.f); mUIScale.back().splat(1.f); + if (!mUIRotation.empty()) + mUIRotation.push_back(LLQuaternion()); } void LLRender::setColorMask(bool writeColor, bool writeAlpha) @@ -2040,12 +2062,32 @@ void LLRender::vertex4a(const LLVector4a& vertex) if (mUIOffset.empty()) { + if (!mUIRotation.empty() && mUIRotation.back().isNotIdentity()) + { + LLVector4 vert(vertex.getF32ptr()); + mVerticesp[mCount].loadua((vert*mUIRotation.back()).mV); + } + else + { mVerticesp[mCount] = vertex; + } } else { - mVerticesp[mCount].setAdd(vertex, mUIOffset.back()); - mVerticesp[mCount].mul(mUIScale.back()); + if (!mUIRotation.empty() && mUIRotation.back().isNotIdentity()) + { + LLVector4 vert(vertex.getF32ptr()); + vert = vert * mUIRotation.back(); + LLVector4a postrot_vert; + postrot_vert.loadua(vert.mV); + mVerticesp[mCount].setAdd(postrot_vert, mUIOffset.back()); + mVerticesp[mCount].mul(mUIScale.back()); + } + else + { + mVerticesp[mCount].setAdd(vertex, mUIOffset.back()); + mVerticesp[mCount].mul(mUIScale.back()); + } } mCount++; diff --git a/indra/llrender/llrender.h b/indra/llrender/llrender.h index 6f158a2cb8d628ed084c057545abb3923934a96e..1ea8911320e8dac47f8b73cb5124ac9ec53dad1f 100644 --- a/indra/llrender/llrender.h +++ b/indra/llrender/llrender.h @@ -402,6 +402,8 @@ class LLRender void translateUI(F32 x, F32 y, F32 z); void scaleUI(F32 x, F32 y, F32 z); + // Rotates vertices, pre-translation/scale + void rotateUI(LLQuaternion& rot); void pushUIMatrix(); void popUIMatrix(); void loadUIIdentity(); @@ -412,6 +414,7 @@ class LLRender void begin(const GLuint& mode); void end(); + LL_FORCE_INLINE void vertex2i(const GLint& x, const GLint& y) { vertex4a(LLVector4a((GLfloat)x,(GLfloat)y,0.f)); } LL_FORCE_INLINE void vertex2f(const GLfloat& x, const GLfloat& y) { vertex4a(LLVector4a(x,y,0.f)); } LL_FORCE_INLINE void vertex3f(const GLfloat& x, const GLfloat& y, const GLfloat& z) { vertex4a(LLVector4a(x,y,z)); } @@ -518,6 +521,7 @@ class LLRender std::vector<LLVector4a, boost::alignment::aligned_allocator<LLVector4a, 64> > mUIOffset; std::vector<LLVector4a, boost::alignment::aligned_allocator<LLVector4a, 64> > mUIScale; + std::vector<LLQuaternion> mUIRotation; bool mPrimitiveReset; }; diff --git a/indra/newview/llnetmap.cpp b/indra/newview/llnetmap.cpp index 5fae601e2b98139688d7a8bdacf5d5c3697f2adb..aa395ffd334a6aa07a2d03b4e41927168320cb60 100644 --- a/indra/newview/llnetmap.cpp +++ b/indra/newview/llnetmap.cpp @@ -107,13 +107,13 @@ LLNetMap::LLNetMap (const Params & p) mToolTipMsg(), mPopupMenuHandle() { - mScale = gSavedSettings.getF32("MiniMapScale"); - mPixelsPerMeter = mScale / REGION_WIDTH_METERS; - mDotRadius = llmax(DOT_SCALE * mPixelsPerMeter, MIN_DOT_RADIUS); + setScale(gSavedSettings.getF32("MiniMapScale")); } LLNetMap::~LLNetMap() { + gSavedSettings.setF32("MiniMapScale", mScale); + auto menu = static_cast<LLMenuGL*>(mPopupMenuHandle.get()); if (menu) { @@ -158,7 +158,7 @@ void LLNetMap::setScale( F32 scale ) F32 height = (F32)(getRect().getHeight()); F32 diameter = sqrt(width * width + height * height); F32 region_widths = diameter / mScale; - F32 meters = region_widths * LLWorld::getInstanceFast()->getRegionWidthInMeters(); + F32 meters = region_widths * REGION_WIDTH_METERS; F32 num_pixels = (F32)mObjectImagep->getWidth(); mObjectMapTPM = num_pixels / meters; mObjectMapPixels = diameter; @@ -167,7 +167,6 @@ void LLNetMap::setScale( F32 scale ) mPixelsPerMeter = mScale / REGION_WIDTH_METERS; mDotRadius = llmax(DOT_SCALE * mPixelsPerMeter, MIN_DOT_RADIUS); - gSavedSettings.setF32("MiniMapScale", mScale); mUpdateObjectImage = true; mUpdateParcelImage = true; } @@ -217,27 +216,14 @@ void LLNetMap::draw() // Prepare a scissor region F32 rotation = 0.f; - gGL.pushMatrix(); gGL.pushUIMatrix(); - LLVector3 offset = gGL.getUITranslation(); - LLVector3 scale = gGL.getUIScale(); - - gGL.loadIdentity(); - gGL.loadUIIdentity(); - - gGL.scalef(scale.mV[0], scale.mV[1], scale.mV[2]); - gGL.translatef(offset.mV[0], offset.mV[1], offset.mV[2]); - auto& viewer_camera = LLViewerCamera::instanceFast(); - { LLLocalClipRect clip(getLocalRect()); { gGL.getTexUnit(0)->unbind(LLTexUnit::TT_TEXTURE); - gGL.matrixMode(LLRender::MM_MODELVIEW); - // Draw background rectangle const LLColor4& background_color = mBackgroundColor.get(); gGL.color4fv( background_color.mV ); @@ -248,22 +234,22 @@ void LLNetMap::draw() S32 center_sw_left = getRect().getWidth() / 2 + llfloor(mCurPan.mV[VX]); S32 center_sw_bottom = getRect().getHeight() / 2 + llfloor(mCurPan.mV[VY]); - gGL.pushMatrix(); - - gGL.translatef( (F32) center_sw_left, (F32) center_sw_bottom, 0.f); + gGL.pushUIMatrix(); + gGL.translateUI( (F32) center_sw_left, (F32) center_sw_bottom, 0.f); - static LLUICachedControl<bool> rotate_map("MiniMapRotate", true); + static LLCachedControl<bool> rotate_map(gSavedSettings, "MiniMapRotate", true); if( rotate_map ) { // rotate subsequent draws to agent rotation rotation = atan2(viewer_camera.getAtAxis().mV[VX], viewer_camera.getAtAxis().mV[VY] ); - gGL.rotatef( rotation * RAD_TO_DEG, 0.f, 0.f, 1.f); + LLQuaternion rot(rotation, LLVector3(0.f, 0.f, 1.f)); + gGL.rotateUI(rot); } auto& worldInst = LLWorld::instanceFast(); // figure out where agent is - S32 region_width = ll_round(REGION_WIDTH_METERS); + S32 region_width = REGION_WIDTH_UNITS; for (LLViewerRegion* regionp : worldInst.getRegionList()) { @@ -300,8 +286,7 @@ void LLNetMap::draw() if (use_world_map_image) { const LLViewerRegion::tex_matrix_t& tiles(regionp->getWorldMapTiles()); - for (S32 i(0), scaled_width(real_width / region_width), square_width(scaled_width * scaled_width); - i < square_width; ++i) + for (S32 i(0), scaled_width(real_width / region_width), square_width(scaled_width * scaled_width); i < square_width; ++i) { const F32 y(i / scaled_width); const F32 x(i - y * scaled_width); @@ -451,29 +436,24 @@ void LLNetMap::draw() map_center_agent.mV[VX] *= mScale / region_width; map_center_agent.mV[VY] *= mScale / region_width; - gGL.color4f(1.f, 1.f, 1.f, 1.f); gGL.getTexUnit(0)->bind(mParcelImagep); - gGL.begin(LLRender::TRIANGLES); + gGL.begin(LLRender::TRIANGLE_STRIP); { gGL.texCoord2f(0.f, 1.f); gGL.vertex2f(map_center_agent.mV[VX] - image_half_width, image_half_height + map_center_agent.mV[VY]); gGL.texCoord2f(0.f, 0.f); gGL.vertex2f(map_center_agent.mV[VX] - image_half_width, map_center_agent.mV[VY] - image_half_height); - gGL.texCoord2f(1.f, 0.f); - gGL.vertex2f(image_half_width + map_center_agent.mV[VX], map_center_agent.mV[VY] - image_half_height); + gGL.texCoord2f(1.f, 1.f); + gGL.vertex2f(image_half_width + map_center_agent.mV[VX], image_half_height + map_center_agent.mV[VY]); - gGL.texCoord2f(0.f, 1.f); - gGL.vertex2f(map_center_agent.mV[VX] - image_half_width, image_half_height + map_center_agent.mV[VY]); gGL.texCoord2f(1.f, 0.f); gGL.vertex2f(image_half_width + map_center_agent.mV[VX], map_center_agent.mV[VY] - image_half_height); - gGL.texCoord2f(1.f, 1.f); - gGL.vertex2f(image_half_width + map_center_agent.mV[VX], image_half_height + map_center_agent.mV[VY]); } gGL.end(); } } - gGL.popMatrix(); + gGL.popUIMatrix(); // Mouse pointer in local coordinates S32 local_mouse_x; @@ -608,6 +588,8 @@ void LLNetMap::draw() gGL.getTexUnit(0)->unbind(LLTexUnit::TT_TEXTURE); + LLColor4 frust_col = rotate_map ? map_frustum_color() : map_frustum_rotating_color(); + if (map_chat_ring) { const F32 chat_radius = curregionp->getChatRange() * mPixelsPerMeter; @@ -619,53 +601,37 @@ void LLNetMap::draw() gl_ring(shout_radius, 1.75f, map_shout_ring_color, map_shout_ring_color, 100, FALSE); gGL.popUIMatrix(); } - if( rotate_map ) - { - gGL.color4fv((map_frustum_color()).mV); + + gGL.pushUIMatrix(); - gGL.begin( LLRender::TRIANGLES ); - gGL.vertex2f( ctr_x, ctr_y ); - gGL.vertex2f( ctr_x + half_width_pixels, ctr_y + far_clip_pixels ); - gGL.vertex2f( ctr_x - half_width_pixels, ctr_y + far_clip_pixels ); - gGL.end(); + gGL.translateUI(ctr_x, ctr_y, 0); - if (render_guide_line) - { - gGL.begin(LLRender::LINES); - gGL.color4fv(map_line_color.get().mV); - gGL.vertex2f(ctr_x, ctr_y); - gGL.vertex2f(ctr_x, ctr_y + far_clip_pixels); - gGL.end(); - } + // If we don't rotate the map, we have to rotate the frustum. + if (!rotate_map) + { + LLQuaternion rot(atan2(viewer_camera.getAtAxis().mV[VX], viewer_camera.getAtAxis().mV[VY]), LLVector3(0.f, 0.f, -1.f)); + gGL.rotateUI(rot); } - else + + gGL.begin( LLRender::TRIANGLES ); + gGL.color4fv(frust_col.mV); + gGL.vertex2f( 0.f, 0.f ); + frust_col.mV[VW] *= .1f; + gGL.color4fv(frust_col.mV); + gGL.vertex2f( half_width_pixels, far_clip_pixels ); + gGL.vertex2f( -half_width_pixels, far_clip_pixels ); + gGL.end(); + if (render_guide_line) { - gGL.color4fv((map_frustum_rotating_color()).mV); - - // If we don't rotate the map, we have to rotate the frustum. - gGL.pushMatrix(); - { - gGL.translatef( ctr_x, ctr_y, 0 ); - gGL.rotatef( atan2(viewer_camera.getAtAxis().mV[VX], viewer_camera.getAtAxis().mV[VY] ) * RAD_TO_DEG, 0.f, 0.f, -1.f); - gGL.begin( LLRender::TRIANGLES ); - gGL.vertex2f( 0.f, 0.f ); - gGL.vertex2f( half_width_pixels, far_clip_pixels ); - gGL.vertex2f( -half_width_pixels, far_clip_pixels ); - gGL.end(); - if (render_guide_line) - { - gGL.begin(LLRender::LINES); - gGL.color4fv(map_line_color.get().mV); - gGL.vertex2f(0.f, 0.f); - gGL.vertex2f(0.f, far_clip_pixels); - gGL.end(); - } - } - gGL.popMatrix(); + gGL.begin(LLRender::LINES); + gGL.color4fv(map_line_color.get().mV); + gGL.vertex2f(0.f, 0.f); + gGL.vertex2f(0.f, far_clip_pixels); + gGL.end(); } + gGL.popUIMatrix(); } - - gGL.popMatrix(); + gGL.popUIMatrix(); LLUICtrl::draw();