00001
00032 #include "llviewerprecompiledheaders.h"
00033
00034
00035 #include "llpanelobject.h"
00036
00037
00038 #include "lleconomy.h"
00039 #include "llerror.h"
00040 #include "llfontgl.h"
00041 #include "llpermissionsflags.h"
00042 #include "llstring.h"
00043 #include "llvolume.h"
00044 #include "m3math.h"
00045
00046
00047 #include "llagent.h"
00048 #include "llbutton.h"
00049 #include "llcheckboxctrl.h"
00050 #include "llcolorswatch.h"
00051 #include "llcombobox.h"
00052 #include "llfocusmgr.h"
00053 #include "llmanipscale.h"
00054 #include "llpanelinventory.h"
00055 #include "llpreviewscript.h"
00056 #include "llresmgr.h"
00057 #include "llselectmgr.h"
00058 #include "llspinctrl.h"
00059 #include "lltexturectrl.h"
00060 #include "lltextbox.h"
00061 #include "lltool.h"
00062 #include "lltoolcomp.h"
00063 #include "lltoolmgr.h"
00064 #include "llui.h"
00065 #include "llviewerobject.h"
00066 #include "llviewerregion.h"
00067 #include "llviewerwindow.h"
00068 #include "llvovolume.h"
00069 #include "llworld.h"
00070 #include "pipeline.h"
00071 #include "llviewercontrol.h"
00072 #include "lluictrlfactory.h"
00073 #include "llfirstuse.h"
00074
00075 #include "lldrawpool.h"
00076
00077
00078
00079
00080 enum {
00081 MI_BOX,
00082 MI_CYLINDER,
00083 MI_PRISM,
00084 MI_SPHERE,
00085 MI_TORUS,
00086 MI_TUBE,
00087 MI_RING,
00088 MI_SCULPT,
00089 MI_NONE,
00090 MI_VOLUME_COUNT
00091 };
00092
00093 enum {
00094 MI_HOLE_SAME,
00095 MI_HOLE_CIRCLE,
00096 MI_HOLE_SQUARE,
00097 MI_HOLE_TRIANGLE,
00098 MI_HOLE_COUNT
00099 };
00100
00101
00102 static const LLString LEGACY_FULLBRIGHT_DESC("Fullbright (Legacy)");
00103
00104 BOOL LLPanelObject::postBuild()
00105 {
00106 setMouseOpaque(FALSE);
00107
00108
00109
00110
00111
00112
00113 mCheckLock = getChild<LLCheckBoxCtrl>("checkbox locked");
00114 childSetCommitCallback("checkbox locked",onCommitLock,this);
00115
00116
00117 mCheckPhysics = getChild<LLCheckBoxCtrl>("Physical Checkbox Ctrl");
00118 childSetCommitCallback("Physical Checkbox Ctrl",onCommitPhysics,this);
00119
00120
00121 mCheckTemporary = getChild<LLCheckBoxCtrl>("Temporary Checkbox Ctrl");
00122 childSetCommitCallback("Temporary Checkbox Ctrl",onCommitTemporary,this);
00123
00124
00125 mCheckPhantom = getChild<LLCheckBoxCtrl>("Phantom Checkbox Ctrl");
00126 childSetCommitCallback("Phantom Checkbox Ctrl",onCommitPhantom,this);
00127
00128
00129 mLabelPosition = getChild<LLTextBox>("label position");
00130 mCtrlPosX = getChild<LLSpinCtrl>("Pos X");
00131 childSetCommitCallback("Pos X",onCommitPosition,this);
00132 mCtrlPosY = getChild<LLSpinCtrl>("Pos Y");
00133 childSetCommitCallback("Pos Y",onCommitPosition,this);
00134 mCtrlPosZ = getChild<LLSpinCtrl>("Pos Z");
00135 childSetCommitCallback("Pos Z",onCommitPosition,this);
00136
00137
00138 mLabelSize = getChild<LLTextBox>("label size");
00139 mCtrlScaleX = getChild<LLSpinCtrl>("Scale X");
00140 childSetCommitCallback("Scale X",onCommitScale,this);
00141
00142
00143 mCtrlScaleY = getChild<LLSpinCtrl>("Scale Y");
00144 childSetCommitCallback("Scale Y",onCommitScale,this);
00145
00146
00147 mCtrlScaleZ = getChild<LLSpinCtrl>("Scale Z");
00148 childSetCommitCallback("Scale Z",onCommitScale,this);
00149
00150
00151 mLabelRotation = getChild<LLTextBox>("label rotation");
00152 mCtrlRotX = getChild<LLSpinCtrl>("Rot X");
00153 childSetCommitCallback("Rot X",onCommitRotation,this);
00154 mCtrlRotY = getChild<LLSpinCtrl>("Rot Y");
00155 childSetCommitCallback("Rot Y",onCommitRotation,this);
00156 mCtrlRotZ = getChild<LLSpinCtrl>("Rot Z");
00157 childSetCommitCallback("Rot Z",onCommitRotation,this);
00158
00159
00160
00161
00162 mLabelMaterial = getChild<LLTextBox>("label material");
00163 mComboMaterial = getChild<LLComboBox>("material");
00164 childSetCommitCallback("material",onCommitMaterial,this);
00165 mComboMaterial->removeall();
00166
00167 for (LLMaterialTable::info_list_t::iterator iter = LLMaterialTable::basic.mMaterialInfoList.begin();
00168 iter != LLMaterialTable::basic.mMaterialInfoList.end(); ++iter)
00169 {
00170 LLMaterialInfo* minfop = *iter;
00171 if (minfop->mMCode != LL_MCODE_LIGHT)
00172 {
00173 mComboMaterial->add(minfop->mName);
00174 }
00175 }
00176 mComboMaterialItemCount = mComboMaterial->getItemCount();
00177
00178
00179 mLabelBaseType = getChild<LLTextBox>("label basetype");
00180 mComboBaseType = getChild<LLComboBox>("comboBaseType");
00181 childSetCommitCallback("comboBaseType",onCommitParametric,this);
00182
00183
00184 mLabelCut = getChild<LLTextBox>("text cut");
00185 mSpinCutBegin = getChild<LLSpinCtrl>("cut begin");
00186 childSetCommitCallback("cut begin",onCommitParametric,this);
00187 mSpinCutBegin->setValidateBeforeCommit( precommitValidate );
00188 mSpinCutEnd = getChild<LLSpinCtrl>("cut end");
00189 childSetCommitCallback("cut end",onCommitParametric,this);
00190 mSpinCutEnd->setValidateBeforeCommit( &precommitValidate );
00191
00192
00193 mLabelHollow = getChild<LLTextBox>("text hollow");
00194 mLabelSkew = getChild<LLTextBox>("text skew");
00195 mSpinHollow = getChild<LLSpinCtrl>("Scale 1");
00196 childSetCommitCallback("Scale 1",onCommitParametric,this);
00197 mSpinHollow->setValidateBeforeCommit( &precommitValidate );
00198 mSpinSkew = getChild<LLSpinCtrl>("Skew");
00199 childSetCommitCallback("Skew",onCommitParametric,this);
00200 mSpinSkew->setValidateBeforeCommit( &precommitValidate );
00201 mLabelHoleType = getChild<LLTextBox>("Hollow Shape");
00202
00203
00204 mComboHoleType = getChild<LLComboBox>("hole");
00205 childSetCommitCallback("hole",onCommitParametric,this);
00206
00207
00208 mLabelTwist = getChild<LLTextBox>("text twist");
00209 mSpinTwistBegin = getChild<LLSpinCtrl>("Twist Begin");
00210 childSetCommitCallback("Twist Begin",onCommitParametric,this);
00211 mSpinTwistBegin->setValidateBeforeCommit( precommitValidate );
00212 mSpinTwist = getChild<LLSpinCtrl>("Twist End");
00213 childSetCommitCallback("Twist End",onCommitParametric,this);
00214 mSpinTwist->setValidateBeforeCommit( &precommitValidate );
00215
00216
00217 mSpinScaleX = getChild<LLSpinCtrl>("Taper Scale X");
00218 childSetCommitCallback("Taper Scale X",onCommitParametric,this);
00219 mSpinScaleX->setValidateBeforeCommit( &precommitValidate );
00220 mSpinScaleY = getChild<LLSpinCtrl>("Taper Scale Y");
00221 childSetCommitCallback("Taper Scale Y",onCommitParametric,this);
00222 mSpinScaleY->setValidateBeforeCommit( &precommitValidate );
00223
00224
00225 mLabelShear = getChild<LLTextBox>("text topshear");
00226 mSpinShearX = getChild<LLSpinCtrl>("Shear X");
00227 childSetCommitCallback("Shear X",onCommitParametric,this);
00228 mSpinShearX->setValidateBeforeCommit( &precommitValidate );
00229 mSpinShearY = getChild<LLSpinCtrl>("Shear Y");
00230 childSetCommitCallback("Shear Y",onCommitParametric,this);
00231 mSpinShearY->setValidateBeforeCommit( &precommitValidate );
00232
00233
00234 mCtrlPathBegin = getChild<LLSpinCtrl>("Path Limit Begin");
00235 childSetCommitCallback("Path Limit Begin",onCommitParametric,this);
00236 mCtrlPathBegin->setValidateBeforeCommit( &precommitValidate );
00237 mCtrlPathEnd = getChild<LLSpinCtrl>("Path Limit End");
00238 childSetCommitCallback("Path Limit End",onCommitParametric,this);
00239 mCtrlPathEnd->setValidateBeforeCommit( &precommitValidate );
00240
00241
00242 mLabelTaper = getChild<LLTextBox>("text taper2");
00243 mSpinTaperX = getChild<LLSpinCtrl>("Taper X");
00244 childSetCommitCallback("Taper X",onCommitParametric,this);
00245 mSpinTaperX->setValidateBeforeCommit( precommitValidate );
00246 mSpinTaperY = getChild<LLSpinCtrl>("Taper Y");
00247 childSetCommitCallback("Taper Y",onCommitParametric,this);
00248 mSpinTaperY->setValidateBeforeCommit( precommitValidate );
00249
00250
00251 mLabelRadiusOffset = getChild<LLTextBox>("text radius delta");
00252 mLabelRevolutions = getChild<LLTextBox>("text revolutions");
00253 mSpinRadiusOffset = getChild<LLSpinCtrl>("Radius Offset");
00254 childSetCommitCallback("Radius Offset",onCommitParametric,this);
00255 mSpinRadiusOffset->setValidateBeforeCommit( &precommitValidate );
00256 mSpinRevolutions = getChild<LLSpinCtrl>("Revolutions");
00257 childSetCommitCallback("Revolutions",onCommitParametric,this);
00258 mSpinRevolutions->setValidateBeforeCommit( &precommitValidate );
00259
00260
00261 mCtrlSculptTexture = getChild<LLTextureCtrl>("sculpt texture control");
00262 if (mCtrlSculptTexture)
00263 {
00264 mCtrlSculptTexture->setDefaultImageAssetID(LLUUID(SCULPT_DEFAULT_TEXTURE));
00265 mCtrlSculptTexture->setCommitCallback( LLPanelObject::onCommitSculpt );
00266 mCtrlSculptTexture->setOnCancelCallback( LLPanelObject::onCancelSculpt );
00267 mCtrlSculptTexture->setOnSelectCallback( LLPanelObject::onSelectSculpt );
00268 mCtrlSculptTexture->setDropCallback(LLPanelObject::onDropSculpt);
00269 mCtrlSculptTexture->setCallbackUserData( this );
00270
00271 mCtrlSculptTexture->setImmediateFilterPermMask(PERM_COPY | PERM_TRANSFER);
00272
00273 mCtrlSculptTexture->setNonImmediateFilterPermMask(PERM_NONE);
00274 LLAggregatePermissions texture_perms;
00275 if (LLSelectMgr::getInstance()->selectGetAggregateTexturePermissions(texture_perms))
00276 {
00277 BOOL can_copy =
00278 texture_perms.getValue(PERM_COPY) == LLAggregatePermissions::AP_EMPTY ||
00279 texture_perms.getValue(PERM_COPY) == LLAggregatePermissions::AP_ALL;
00280 BOOL can_transfer =
00281 texture_perms.getValue(PERM_TRANSFER) == LLAggregatePermissions::AP_EMPTY ||
00282 texture_perms.getValue(PERM_TRANSFER) == LLAggregatePermissions::AP_ALL;
00283 mCtrlSculptTexture->setCanApplyImmediately(can_copy && can_transfer);
00284 }
00285 else
00286 {
00287 mCtrlSculptTexture->setCanApplyImmediately(FALSE);
00288 }
00289 }
00290
00291 mLabelSculptType = getChild<LLTextBox>("label sculpt type");
00292 mCtrlSculptType = getChild<LLComboBox>( "sculpt type control");
00293 childSetCommitCallback("sculpt type control", onCommitSculptType, this);
00294
00295
00296
00297 clearCtrls();
00298
00299 return TRUE;
00300 }
00301
00302 LLPanelObject::LLPanelObject(const std::string& name)
00303 : LLPanel(name),
00304 mIsPhysical(FALSE),
00305 mIsTemporary(FALSE),
00306 mIsPhantom(FALSE),
00307 mCastShadows(TRUE),
00308 mSelectedType(MI_BOX)
00309 {
00310 }
00311
00312
00313 LLPanelObject::~LLPanelObject()
00314 {
00315
00316 }
00317
00318 void LLPanelObject::getState( )
00319 {
00320 LLViewerObject* objectp = LLSelectMgr::getInstance()->getSelection()->getFirstRootObject();
00321 LLViewerObject* root_objectp = objectp;
00322 if(!objectp)
00323 {
00324 objectp = LLSelectMgr::getInstance()->getSelection()->getFirstObject();
00325
00326 if (objectp)
00327 {
00328 LLViewerObject* parentp = objectp->getSubParent();
00329
00330 if (parentp)
00331 {
00332 root_objectp = parentp;
00333 }
00334 else
00335 {
00336 root_objectp = objectp;
00337 }
00338 }
00339 }
00340
00341 LLVOVolume *volobjp = NULL;
00342 if ( objectp && (objectp->getPCode() == LL_PCODE_VOLUME))
00343 {
00344 volobjp = (LLVOVolume *)objectp;
00345 }
00346
00347 if( !objectp )
00348 {
00349
00350 if (gFocusMgr.childHasKeyboardFocus(this))
00351 {
00352 gFocusMgr.setKeyboardFocus(NULL);
00353 }
00354
00355
00356 clearCtrls();
00357 return;
00358 }
00359
00360
00361 BOOL enable_move = objectp->permMove() && !objectp->isAttachment() && (objectp->permModify() || !gSavedSettings.getBOOL("EditLinkedParts"));
00362 BOOL enable_scale = objectp->permMove() && objectp->permModify();
00363 BOOL enable_rotate = objectp->permMove() && ( (objectp->permModify() && !objectp->isAttachment()) || !gSavedSettings.getBOOL("EditLinkedParts"));
00364
00365 LLVector3 vec;
00366 if (enable_move)
00367 {
00368 vec = objectp->getPositionEdit();
00369 mCtrlPosX->set( vec.mV[VX] );
00370 mCtrlPosY->set( vec.mV[VY] );
00371 mCtrlPosZ->set( vec.mV[VZ] );
00372 }
00373 else
00374 {
00375 mCtrlPosX->clear();
00376 mCtrlPosY->clear();
00377 mCtrlPosZ->clear();
00378 }
00379
00380
00381 mLabelPosition->setEnabled( enable_move );
00382 mCtrlPosX->setEnabled(enable_move);
00383 mCtrlPosY->setEnabled(enable_move);
00384 mCtrlPosZ->setEnabled(enable_move);
00385
00386 if (enable_scale)
00387 {
00388 vec = objectp->getScale();
00389 mCtrlScaleX->set( vec.mV[VX] );
00390 mCtrlScaleY->set( vec.mV[VY] );
00391 mCtrlScaleZ->set( vec.mV[VZ] );
00392 }
00393 else
00394 {
00395 mCtrlScaleX->clear();
00396 mCtrlScaleY->clear();
00397 mCtrlScaleZ->clear();
00398 }
00399
00400 mLabelSize->setEnabled( enable_scale );
00401 mCtrlScaleX->setEnabled( enable_scale );
00402 mCtrlScaleY->setEnabled( enable_scale );
00403 mCtrlScaleZ->setEnabled( enable_scale );
00404
00405 LLQuaternion object_rot = objectp->getRotationEdit();
00406 object_rot.getEulerAngles(&(mCurEulerDegrees.mV[VX]), &(mCurEulerDegrees.mV[VY]), &(mCurEulerDegrees.mV[VZ]));
00407 mCurEulerDegrees *= RAD_TO_DEG;
00408 mCurEulerDegrees.mV[VX] = fmod(llround(mCurEulerDegrees.mV[VX], OBJECT_ROTATION_PRECISION) + 360.f, 360.f);
00409 mCurEulerDegrees.mV[VY] = fmod(llround(mCurEulerDegrees.mV[VY], OBJECT_ROTATION_PRECISION) + 360.f, 360.f);
00410 mCurEulerDegrees.mV[VZ] = fmod(llround(mCurEulerDegrees.mV[VZ], OBJECT_ROTATION_PRECISION) + 360.f, 360.f);
00411
00412 if (enable_rotate)
00413 {
00414 mCtrlRotX->set( mCurEulerDegrees.mV[VX] );
00415 mCtrlRotY->set( mCurEulerDegrees.mV[VY] );
00416 mCtrlRotZ->set( mCurEulerDegrees.mV[VZ] );
00417 }
00418 else
00419 {
00420 mCtrlRotX->clear();
00421 mCtrlRotY->clear();
00422 mCtrlRotZ->clear();
00423 }
00424
00425 mLabelRotation->setEnabled( enable_rotate );
00426 mCtrlRotX->setEnabled( enable_rotate );
00427 mCtrlRotY->setEnabled( enable_rotate );
00428 mCtrlRotZ->setEnabled( enable_rotate );
00429
00430 BOOL owners_identical;
00431 LLUUID owner_id;
00432 LLString owner_name;
00433 owners_identical = LLSelectMgr::getInstance()->selectGetOwner(owner_id, owner_name);
00434
00435
00436 S32 roots_selected = LLSelectMgr::getInstance()->getSelection()->getRootObjectCount();
00437 BOOL editable = root_objectp->permModify();
00438 S32 selected_count = LLSelectMgr::getInstance()->getSelection()->getObjectCount();
00439 BOOL single_volume = (LLSelectMgr::getInstance()->selectionAllPCode( LL_PCODE_VOLUME ))
00440 && (selected_count == 1);
00441
00442
00443 childSetVisible("select_single", FALSE);
00444 childSetVisible("edit_object", FALSE);
00445 if (!editable || single_volume || selected_count <= 1)
00446 {
00447 childSetVisible("edit_object", TRUE);
00448 childSetEnabled("edit_object", TRUE);
00449 }
00450 else
00451 {
00452 childSetVisible("select_single", TRUE);
00453 childSetEnabled("select_single", TRUE);
00454 }
00455
00456 BOOL self_owned = (gAgent.getID() == owner_id);
00457 mCheckLock->setEnabled( roots_selected > 0 && self_owned );
00458
00459
00460 BOOL valid;
00461 U32 owner_mask_on;
00462 U32 owner_mask_off;
00463 valid = LLSelectMgr::getInstance()->selectGetPerm(PERM_OWNER, &owner_mask_on, &owner_mask_off);
00464
00465 if(valid)
00466 {
00467 if(owner_mask_on & PERM_MOVE)
00468 {
00469
00470 mCheckLock->set(FALSE);
00471 mCheckLock->setTentative(FALSE);
00472 }
00473 else if(owner_mask_off & PERM_MOVE)
00474 {
00475
00476 mCheckLock->set(TRUE);
00477 mCheckLock->setTentative(FALSE);
00478 }
00479 else
00480 {
00481
00482 mCheckLock->set(FALSE);
00483 mCheckLock->setTentative(TRUE);
00484 }
00485 }
00486
00487 BOOL is_flexible = volobjp && volobjp->isFlexible();
00488
00489
00490 mIsPhysical = root_objectp->usePhysics();
00491 mCheckPhysics->set( mIsPhysical );
00492 mCheckPhysics->setEnabled( roots_selected>0
00493 && (editable || gAgent.isGodlike())
00494 && !is_flexible);
00495
00496 mIsTemporary = root_objectp->flagTemporaryOnRez();
00497 mCheckTemporary->set( mIsTemporary );
00498 mCheckTemporary->setEnabled( roots_selected>0 && editable );
00499
00500 mIsPhantom = root_objectp->flagPhantom();
00501 mCheckPhantom->set( mIsPhantom );
00502 mCheckPhantom->setEnabled( roots_selected>0 && editable && !is_flexible );
00503
00504 #if 0 // 1.9.2
00505 mCastShadows = root_objectp->flagCastShadows();
00506 mCheckCastShadows->set( mCastShadows );
00507 mCheckCastShadows->setEnabled( roots_selected==1 && editable );
00508 #endif
00509
00510
00511
00512 U8 material_code = 0;
00513 struct f : public LLSelectedTEGetFunctor<U8>
00514 {
00515 U8 get(LLViewerObject* object, S32 te)
00516 {
00517 return object->getMaterial();
00518 }
00519 } func;
00520 bool material_same = LLSelectMgr::getInstance()->getSelection()->getSelectedTEValue( &func, material_code );
00521
00522 if (editable && single_volume && material_same)
00523 {
00524 mComboMaterial->setEnabled( TRUE );
00525 mLabelMaterial->setEnabled( TRUE );
00526 if (material_code == LL_MCODE_LIGHT)
00527 {
00528 if (mComboMaterial->getItemCount() == mComboMaterialItemCount)
00529 {
00530 mComboMaterial->add(LEGACY_FULLBRIGHT_DESC);
00531 }
00532 mComboMaterial->setSimple(LEGACY_FULLBRIGHT_DESC);
00533 }
00534 else
00535 {
00536 if (mComboMaterial->getItemCount() != mComboMaterialItemCount)
00537 {
00538 mComboMaterial->remove(LEGACY_FULLBRIGHT_DESC);
00539 }
00540
00541 mComboMaterial->setSimple(LLString(LLMaterialTable::basic.getName(material_code)));
00542 }
00543 }
00544 else
00545 {
00546 mComboMaterial->setEnabled( FALSE );
00547 mLabelMaterial->setEnabled( FALSE );
00548 }
00549
00550
00551 S32 selected_item = MI_BOX;
00552 S32 selected_hole = MI_HOLE_SAME;
00553 BOOL enabled = FALSE;
00554 BOOL hole_enabled = FALSE;
00555 F32 scale_x=1.f, scale_y=1.f;
00556
00557 if( !objectp || !objectp->getVolume() || !editable || !single_volume)
00558 {
00559
00560 mComboBaseType->clear();
00561 mSpinHollow->clear();
00562 mSpinCutBegin->clear();
00563 mSpinCutEnd->clear();
00564 mCtrlPathBegin->clear();
00565 mCtrlPathEnd->clear();
00566 mSpinScaleX->clear();
00567 mSpinScaleY->clear();
00568 mSpinTwist->clear();
00569 mSpinTwistBegin->clear();
00570 mComboHoleType->clear();
00571 mSpinShearX->clear();
00572 mSpinShearY->clear();
00573 mSpinTaperX->clear();
00574 mSpinTaperY->clear();
00575 mSpinRadiusOffset->clear();
00576 mSpinRevolutions->clear();
00577 mSpinSkew->clear();
00578
00579 mSelectedType = MI_NONE;
00580 }
00581 else
00582 {
00583
00584
00585 enabled = root_objectp->permModify();
00586
00587 const LLVolumeParams &volume_params = objectp->getVolume()->getParams();
00588
00589
00590 U8 path = volume_params.getPathParams().getCurveType();
00591 U8 profile_and_hole = volume_params.getProfileParams().getCurveType();
00592 U8 profile = profile_and_hole & LL_PCODE_PROFILE_MASK;
00593 U8 hole = profile_and_hole & LL_PCODE_HOLE_MASK;
00594
00595
00596
00597
00598
00599 scale_x = volume_params.getRatioX();
00600 scale_y = volume_params.getRatioY();
00601
00602 BOOL linear_path = (path == LL_PCODE_PATH_LINE) || (path == LL_PCODE_PATH_FLEXIBLE);
00603 if ( linear_path && profile == LL_PCODE_PROFILE_CIRCLE )
00604 {
00605 selected_item = MI_CYLINDER;
00606 }
00607 else if ( linear_path && profile == LL_PCODE_PROFILE_SQUARE )
00608 {
00609 selected_item = MI_BOX;
00610 }
00611 else if ( linear_path && profile == LL_PCODE_PROFILE_ISOTRI )
00612 {
00613 selected_item = MI_PRISM;
00614 }
00615 else if ( linear_path && profile == LL_PCODE_PROFILE_EQUALTRI )
00616 {
00617 selected_item = MI_PRISM;
00618 }
00619 else if ( linear_path && profile == LL_PCODE_PROFILE_RIGHTTRI )
00620 {
00621 selected_item = MI_PRISM;
00622 }
00623 else if (path == LL_PCODE_PATH_FLEXIBLE)
00624 {
00625 selected_item = MI_CYLINDER;
00626 }
00627 else if ( path == LL_PCODE_PATH_CIRCLE && profile == LL_PCODE_PROFILE_CIRCLE && scale_y > 0.75f)
00628 {
00629 selected_item = MI_SPHERE;
00630 }
00631 else if ( path == LL_PCODE_PATH_CIRCLE && profile == LL_PCODE_PROFILE_CIRCLE && scale_y <= 0.75f)
00632 {
00633 selected_item = MI_TORUS;
00634 }
00635 else if ( path == LL_PCODE_PATH_CIRCLE && profile == LL_PCODE_PROFILE_CIRCLE_HALF)
00636 {
00637 selected_item = MI_SPHERE;
00638 }
00639 else if ( path == LL_PCODE_PATH_CIRCLE2 && profile == LL_PCODE_PROFILE_CIRCLE )
00640 {
00641
00642 selected_item = MI_SPHERE;
00643 }
00644 else if ( path == LL_PCODE_PATH_CIRCLE && profile == LL_PCODE_PROFILE_EQUALTRI )
00645 {
00646 selected_item = MI_RING;
00647 }
00648 else if ( path == LL_PCODE_PATH_CIRCLE && profile == LL_PCODE_PROFILE_SQUARE && scale_y <= 0.75f)
00649 {
00650 selected_item = MI_TUBE;
00651 }
00652 else
00653 {
00654 llinfos << "Unknown path " << (S32) path << " profile " << (S32) profile << " in getState" << llendl;
00655 selected_item = MI_BOX;
00656 }
00657
00658
00659 if (objectp->getParameterEntryInUse(LLNetworkData::PARAMS_SCULPT))
00660 {
00661 selected_item = MI_SCULPT;
00662 LLFirstUse::useSculptedPrim();
00663 }
00664
00665
00666 mComboBaseType ->setCurrentByIndex( selected_item );
00667 mSelectedType = selected_item;
00668
00669
00670 F32 begin_s = volume_params.getBeginS();
00671 F32 end_s = volume_params.getEndS();
00672
00673
00674 F32 begin_t = volume_params.getBeginT();
00675 F32 end_t = volume_params.getEndT();
00676
00677
00678 F32 hollow = volume_params.getHollow();
00679 mSpinHollow->set( 100.f * hollow );
00680
00681
00682 if (hollow > 0.f)
00683 {
00684 switch (hole)
00685 {
00686 case LL_PCODE_HOLE_CIRCLE:
00687 selected_hole = MI_HOLE_CIRCLE;
00688 break;
00689 case LL_PCODE_HOLE_SQUARE:
00690 selected_hole = MI_HOLE_SQUARE;
00691 break;
00692 case LL_PCODE_HOLE_TRIANGLE:
00693 selected_hole = MI_HOLE_TRIANGLE;
00694 break;
00695 case LL_PCODE_HOLE_SAME:
00696 default:
00697 selected_hole = MI_HOLE_SAME;
00698 break;
00699 }
00700 mComboHoleType->setCurrentByIndex( selected_hole );
00701 hole_enabled = enabled;
00702 }
00703 else
00704 {
00705 mComboHoleType->setCurrentByIndex( MI_HOLE_SAME );
00706 hole_enabled = FALSE;
00707 }
00708
00709
00710 F32 cut_begin, cut_end, adv_cut_begin, adv_cut_end;
00711
00712 if ( selected_item == MI_SPHERE || selected_item == MI_TORUS ||
00713 selected_item == MI_TUBE || selected_item == MI_RING )
00714 {
00715 cut_begin = begin_t;
00716 cut_end = end_t;
00717 adv_cut_begin = begin_s;
00718 adv_cut_end = end_s;
00719 }
00720 else
00721 {
00722 cut_begin = begin_s;
00723 cut_end = end_s;
00724 adv_cut_begin = begin_t;
00725 adv_cut_end = end_t;
00726 }
00727
00728 mSpinCutBegin ->set( cut_begin );
00729 mSpinCutEnd ->set( cut_end );
00730 mCtrlPathBegin ->set( adv_cut_begin );
00731 mCtrlPathEnd ->set( adv_cut_end );
00732
00733
00734 F32 twist = volume_params.getTwist();
00735 F32 twist_begin = volume_params.getTwistBegin();
00736
00737 if (path == LL_PCODE_PATH_LINE || path == LL_PCODE_PATH_FLEXIBLE)
00738 {
00739 twist *= OBJECT_TWIST_LINEAR_MAX;
00740 twist_begin *= OBJECT_TWIST_LINEAR_MAX;
00741 }
00742 else
00743 {
00744 twist *= OBJECT_TWIST_MAX;
00745 twist_begin *= OBJECT_TWIST_MAX;
00746 }
00747
00748 mSpinTwist ->set( twist );
00749 mSpinTwistBegin ->set( twist_begin );
00750
00751
00752 F32 shear_x = volume_params.getShearX();
00753 F32 shear_y = volume_params.getShearY();
00754 mSpinShearX->set( shear_x );
00755 mSpinShearY->set( shear_y );
00756
00757
00758 F32 taper_x = volume_params.getTaperX();
00759 F32 taper_y = volume_params.getTaperY();
00760 mSpinTaperX->set( taper_x );
00761 mSpinTaperY->set( taper_y );
00762
00763
00764 F32 radius_offset = volume_params.getRadiusOffset();
00765
00766 F32 radius_mag = fabs(radius_offset);
00767 F32 hole_y_mag = fabs(scale_y);
00768 F32 taper_y_mag = fabs(taper_y);
00769
00770 if ( (radius_offset > 0.f && taper_y < 0.f) ||
00771 (radius_offset < 0.f && taper_y > 0.f) )
00772 {
00773
00774 taper_y_mag = 0.f;
00775 }
00776 F32 max_radius_mag = 1.f - hole_y_mag * (1.f - taper_y_mag) / (1.f - hole_y_mag);
00777
00778 if (radius_mag > max_radius_mag)
00779 {
00780
00781 if (radius_offset < 0.f)
00782 {
00783 radius_offset = -max_radius_mag;
00784 }
00785 else
00786 {
00787 radius_offset = max_radius_mag;
00788 }
00789 }
00790 mSpinRadiusOffset->set( radius_offset);
00791
00792
00793 F32 revolutions = volume_params.getRevolutions();
00794 mSpinRevolutions->set( revolutions );
00795
00796
00797 F32 skew = volume_params.getSkew();
00798
00799 F32 skew_mag= fabs(skew);
00800 F32 min_skew_mag = 1.0f - 1.0f / (revolutions * scale_x + 1.0f);
00801
00802 if ( fabs(revolutions - 1.0f) < 0.001)
00803 min_skew_mag = 0.0f;
00804
00805
00806 if (skew_mag < min_skew_mag)
00807 {
00808
00809 if (skew < 0.0f)
00810 {
00811 skew = -min_skew_mag;
00812 }
00813 else
00814 {
00815 skew = min_skew_mag;
00816 }
00817 }
00818 mSpinSkew->set( skew );
00819 }
00820
00821
00822
00823 BOOL cut_visible = TRUE;
00824 BOOL hollow_visible = TRUE;
00825 BOOL top_size_x_visible = TRUE;
00826 BOOL top_size_y_visible = TRUE;
00827 BOOL top_shear_x_visible = TRUE;
00828 BOOL top_shear_y_visible = TRUE;
00829 BOOL twist_visible = TRUE;
00830 BOOL advanced_cut_visible = FALSE;
00831 BOOL taper_visible = FALSE;
00832 BOOL skew_visible = FALSE;
00833 BOOL radius_offset_visible = FALSE;
00834 BOOL revolutions_visible = FALSE;
00835 BOOL sculpt_texture_visible = FALSE;
00836 F32 twist_min = OBJECT_TWIST_LINEAR_MIN;
00837 F32 twist_max = OBJECT_TWIST_LINEAR_MAX;
00838 F32 twist_inc = OBJECT_TWIST_LINEAR_INC;
00839
00840 BOOL advanced_is_dimple = FALSE;
00841 BOOL size_is_hole = FALSE;
00842
00843
00844 switch (selected_item)
00845 {
00846 case MI_SPHERE:
00847 top_size_x_visible = FALSE;
00848 top_size_y_visible = FALSE;
00849 top_shear_x_visible = FALSE;
00850 top_shear_y_visible = FALSE;
00851
00852 advanced_cut_visible = TRUE;
00853 advanced_is_dimple = TRUE;
00854 twist_min = OBJECT_TWIST_MIN;
00855 twist_max = OBJECT_TWIST_MAX;
00856 twist_inc = OBJECT_TWIST_INC;
00857 break;
00858
00859 case MI_TORUS:
00860 case MI_TUBE:
00861 case MI_RING:
00862
00863
00864 size_is_hole = TRUE;
00865 skew_visible = TRUE;
00866 advanced_cut_visible = TRUE;
00867 taper_visible = TRUE;
00868 radius_offset_visible = TRUE;
00869 revolutions_visible = TRUE;
00870 twist_min = OBJECT_TWIST_MIN;
00871 twist_max = OBJECT_TWIST_MAX;
00872 twist_inc = OBJECT_TWIST_INC;
00873
00874 break;
00875
00876 case MI_SCULPT:
00877 cut_visible = FALSE;
00878 hollow_visible = FALSE;
00879 twist_visible = FALSE;
00880 top_size_x_visible = FALSE;
00881 top_size_y_visible = FALSE;
00882 top_shear_x_visible = FALSE;
00883 top_shear_y_visible = FALSE;
00884 skew_visible = FALSE;
00885 advanced_cut_visible = FALSE;
00886 taper_visible = FALSE;
00887 radius_offset_visible = FALSE;
00888 revolutions_visible = FALSE;
00889 sculpt_texture_visible = TRUE;
00890
00891 break;
00892
00893 case MI_BOX:
00894 case MI_CYLINDER:
00895 case MI_PRISM:
00896 default:
00897 break;
00898 }
00899
00900
00901 switch (selected_item)
00902 {
00903 case MI_SPHERE:
00904 case MI_TORUS:
00905 case MI_TUBE:
00906 case MI_RING:
00907 mSpinScaleX->set( scale_x );
00908 mSpinScaleY->set( scale_y );
00909 mSpinScaleX->setMinValue(OBJECT_MIN_HOLE_SIZE);
00910 mSpinScaleX->setMaxValue(OBJECT_MAX_HOLE_SIZE_X);
00911 mSpinScaleY->setMinValue(OBJECT_MIN_HOLE_SIZE);
00912 mSpinScaleY->setMaxValue(OBJECT_MAX_HOLE_SIZE_Y);
00913 break;
00914 default:
00915 if (editable)
00916 {
00917 mSpinScaleX->set( 1.f - scale_x );
00918 mSpinScaleY->set( 1.f - scale_y );
00919 mSpinScaleX->setMinValue(-1.f);
00920 mSpinScaleX->setMaxValue(1.f);
00921 mSpinScaleY->setMinValue(-1.f);
00922 mSpinScaleY->setMaxValue(1.f);
00923 }
00924 break;
00925 }
00926
00927
00928 if ( selected_hole == MI_HOLE_SQUARE &&
00929 ( selected_item == MI_CYLINDER || selected_item == MI_TORUS ||
00930 selected_item == MI_PRISM || selected_item == MI_RING ||
00931 selected_item == MI_SPHERE ) )
00932 {
00933 mSpinHollow->setMinValue(0.f);
00934 mSpinHollow->setMaxValue(70.f);
00935 }
00936 else
00937 {
00938 mSpinHollow->setMinValue(0.f);
00939 mSpinHollow->setMaxValue(95.f);
00940 }
00941
00942
00943 mLabelBaseType ->setEnabled( enabled );
00944 mComboBaseType ->setEnabled( enabled );
00945
00946 mLabelCut ->setEnabled( enabled );
00947 mSpinCutBegin ->setEnabled( enabled );
00948 mSpinCutEnd ->setEnabled( enabled );
00949
00950 mLabelHollow ->setEnabled( enabled );
00951 mSpinHollow ->setEnabled( enabled );
00952 mLabelHoleType ->setEnabled( hole_enabled );
00953 mComboHoleType ->setEnabled( hole_enabled );
00954
00955 mLabelTwist ->setEnabled( enabled );
00956 mSpinTwist ->setEnabled( enabled );
00957 mSpinTwistBegin ->setEnabled( enabled );
00958
00959 mLabelSkew ->setEnabled( enabled );
00960 mSpinSkew ->setEnabled( enabled );
00961
00962 childSetVisible("scale_hole", FALSE);
00963 childSetVisible("scale_taper", FALSE);
00964 if (top_size_x_visible || top_size_y_visible)
00965 {
00966 if (size_is_hole)
00967 {
00968 childSetVisible("scale_hole", TRUE);
00969 childSetEnabled("scale_hole", enabled);
00970 }
00971 else
00972 {
00973 childSetVisible("scale_taper", TRUE);
00974 childSetEnabled("scale_taper", enabled);
00975 }
00976 }
00977
00978 mSpinScaleX ->setEnabled( enabled );
00979 mSpinScaleY ->setEnabled( enabled );
00980
00981 mLabelShear ->setEnabled( enabled );
00982 mSpinShearX ->setEnabled( enabled );
00983 mSpinShearY ->setEnabled( enabled );
00984
00985 childSetVisible("advanced_cut", FALSE);
00986 childSetVisible("advanced_dimple", FALSE);
00987 if (advanced_cut_visible)
00988 {
00989 if (advanced_is_dimple)
00990 {
00991 childSetVisible("advanced_dimple", TRUE);
00992 childSetEnabled("advanced_dimple", enabled);
00993 }
00994 else
00995 {
00996 childSetVisible("advanced_cut", TRUE);
00997 childSetEnabled("advanced_cut", enabled);
00998 }
00999 }
01000
01001 mCtrlPathBegin ->setEnabled( enabled );
01002 mCtrlPathEnd ->setEnabled( enabled );
01003
01004 mLabelTaper ->setEnabled( enabled );
01005 mSpinTaperX ->setEnabled( enabled );
01006 mSpinTaperY ->setEnabled( enabled );
01007
01008 mLabelRadiusOffset->setEnabled( enabled );
01009 mSpinRadiusOffset ->setEnabled( enabled );
01010
01011 mLabelRevolutions->setEnabled( enabled );
01012 mSpinRevolutions ->setEnabled( enabled );
01013
01014
01015 mLabelCut ->setVisible( cut_visible );
01016 mSpinCutBegin ->setVisible( cut_visible );
01017 mSpinCutEnd ->setVisible( cut_visible );
01018
01019 mLabelHollow ->setVisible( hollow_visible );
01020 mSpinHollow ->setVisible( hollow_visible );
01021 mLabelHoleType ->setVisible( hollow_visible );
01022 mComboHoleType ->setVisible( hollow_visible );
01023
01024 mLabelTwist ->setVisible( twist_visible );
01025 mSpinTwist ->setVisible( twist_visible );
01026 mSpinTwistBegin ->setVisible( twist_visible );
01027 mSpinTwist ->setMinValue( twist_min );
01028 mSpinTwist ->setMaxValue( twist_max );
01029 mSpinTwist ->setIncrement( twist_inc );
01030 mSpinTwistBegin ->setMinValue( twist_min );
01031 mSpinTwistBegin ->setMaxValue( twist_max );
01032 mSpinTwistBegin ->setIncrement( twist_inc );
01033
01034 mSpinScaleX ->setVisible( top_size_x_visible );
01035 mSpinScaleY ->setVisible( top_size_y_visible );
01036
01037 mLabelSkew ->setVisible( skew_visible );
01038 mSpinSkew ->setVisible( skew_visible );
01039
01040 mLabelShear ->setVisible( top_shear_x_visible || top_shear_y_visible );
01041 mSpinShearX ->setVisible( top_shear_x_visible );
01042 mSpinShearY ->setVisible( top_shear_y_visible );
01043
01044 mCtrlPathBegin ->setVisible( advanced_cut_visible );
01045 mCtrlPathEnd ->setVisible( advanced_cut_visible );
01046
01047 mLabelTaper ->setVisible( taper_visible );
01048 mSpinTaperX ->setVisible( taper_visible );
01049 mSpinTaperY ->setVisible( taper_visible );
01050
01051 mLabelRadiusOffset->setVisible( radius_offset_visible );
01052 mSpinRadiusOffset ->setVisible( radius_offset_visible );
01053
01054 mLabelRevolutions->setVisible( revolutions_visible );
01055 mSpinRevolutions ->setVisible( revolutions_visible );
01056
01057 mCtrlSculptTexture->setVisible(sculpt_texture_visible);
01058 mLabelSculptType->setVisible(sculpt_texture_visible);
01059 mCtrlSculptType->setVisible(sculpt_texture_visible);
01060
01061
01062
01063
01064 if (selected_item == MI_SCULPT)
01065 {
01066 LLUUID id;
01067 LLSculptParams *sculpt_params = (LLSculptParams *)objectp->getParameterEntry(LLNetworkData::PARAMS_SCULPT);
01068
01069
01070 if (sculpt_params)
01071 {
01072 if (mObject != objectp)
01073 {
01074 mSculptTextureRevert = sculpt_params->getSculptTexture();
01075 mSculptTypeRevert = sculpt_params->getSculptType();
01076 }
01077
01078 LLTextureCtrl* mTextureCtrl = getChild<LLTextureCtrl>("sculpt texture control");
01079 if(mTextureCtrl)
01080 {
01081 mTextureCtrl->setTentative(FALSE);
01082 mTextureCtrl->setEnabled(editable);
01083 if (editable)
01084 mTextureCtrl->setImageAssetID(sculpt_params->getSculptTexture());
01085 else
01086 mTextureCtrl->setImageAssetID(LLUUID::null);
01087 }
01088
01089 if (mCtrlSculptType)
01090 {
01091 mCtrlSculptType->setCurrentByIndex(sculpt_params->getSculptType());
01092 mCtrlSculptType->setEnabled(editable);
01093 }
01094
01095 if (mLabelSculptType)
01096 {
01097 mLabelSculptType->setEnabled(TRUE);
01098 }
01099 }
01100 }
01101 else
01102 {
01103 mSculptTextureRevert = LLUUID::null;
01104 }
01105
01106
01107
01108
01109 mObject = objectp;
01110 mRootObject = root_objectp;
01111 }
01112
01113
01114 BOOL LLPanelObject::precommitValidate( LLUICtrl* ctrl, void* userdata )
01115 {
01116
01117 return TRUE;
01118 }
01119
01120 void LLPanelObject::sendIsPhysical()
01121 {
01122 BOOL value = mCheckPhysics->get();
01123 if( mIsPhysical != value )
01124 {
01125 LLSelectMgr::getInstance()->selectionUpdatePhysics(value);
01126 mIsPhysical = value;
01127
01128 llinfos << "update physics sent" << llendl;
01129 }
01130 else
01131 {
01132 llinfos << "update physics not changed" << llendl;
01133 }
01134 }
01135
01136 void LLPanelObject::sendIsTemporary()
01137 {
01138 BOOL value = mCheckTemporary->get();
01139 if( mIsTemporary != value )
01140 {
01141 LLSelectMgr::getInstance()->selectionUpdateTemporary(value);
01142 mIsTemporary = value;
01143
01144 llinfos << "update temporary sent" << llendl;
01145 }
01146 else
01147 {
01148 llinfos << "update temporary not changed" << llendl;
01149 }
01150 }
01151
01152
01153 void LLPanelObject::sendIsPhantom()
01154 {
01155 BOOL value = mCheckPhantom->get();
01156 if( mIsPhantom != value )
01157 {
01158 LLSelectMgr::getInstance()->selectionUpdatePhantom(value);
01159 mIsPhantom = value;
01160
01161 llinfos << "update phantom sent" << llendl;
01162 }
01163 else
01164 {
01165 llinfos << "update phantom not changed" << llendl;
01166 }
01167 }
01168
01169 void LLPanelObject::sendCastShadows()
01170 {
01171 BOOL value = mCheckCastShadows->get();
01172 if( mCastShadows != value )
01173 {
01174 LLSelectMgr::getInstance()->selectionUpdateCastShadows(value);
01175 mCastShadows = value;
01176
01177 llinfos << "update cast shadows sent" << llendl;
01178 }
01179 else
01180 {
01181 llinfos << "update cast shadows not changed" << llendl;
01182 }
01183 }
01184
01185
01186 void LLPanelObject::onCommitMaterial( LLUICtrl* ctrl, void* userdata )
01187 {
01188
01189 LLComboBox* box = (LLComboBox*) ctrl;
01190
01191 if (box)
01192 {
01193
01194 const LLString& material_name = box->getSimple();
01195 if (material_name != LEGACY_FULLBRIGHT_DESC)
01196 {
01197 U8 material_code = LLMaterialTable::basic.getMCode(material_name.c_str());
01198 LLSelectMgr::getInstance()->selectionSetMaterial(material_code);
01199 }
01200 }
01201 }
01202
01203
01204 void LLPanelObject::onCommitParametric( LLUICtrl* ctrl, void* userdata )
01205 {
01206 LLPanelObject* self = (LLPanelObject*) userdata;
01207
01208 if (self->mObject.isNull())
01209 {
01210 return;
01211 }
01212
01213 if (self->mObject->getPCode() != LL_PCODE_VOLUME)
01214 {
01215
01216 return;
01217 }
01218
01219 LLVolume *volume = self->mObject->getVolume();
01220 if (!volume)
01221 {
01222 return;
01223 }
01224
01225 LLVolumeParams volume_params;
01226 self->getVolumeParams(volume_params);
01227
01228
01229
01230
01231 S32 selected_type = self->mComboBaseType->getCurrentIndex();
01232
01233 if (selected_type == MI_SCULPT)
01234 {
01235 self->mObject->setParameterEntryInUse(LLNetworkData::PARAMS_SCULPT, TRUE, TRUE);
01236 LLSculptParams *sculpt_params = (LLSculptParams *)self->mObject->getParameterEntry(LLNetworkData::PARAMS_SCULPT);
01237 if (sculpt_params)
01238 volume_params.setSculptID(sculpt_params->getSculptTexture(), sculpt_params->getSculptType());
01239 }
01240 else
01241 {
01242 LLSculptParams *sculpt_params = (LLSculptParams *)self->mObject->getParameterEntry(LLNetworkData::PARAMS_SCULPT);
01243 if (sculpt_params)
01244 self->mObject->setParameterEntryInUse(LLNetworkData::PARAMS_SCULPT, FALSE, TRUE);
01245 }
01246
01247
01248 self->mObject->updateVolume(volume_params);
01249
01250
01251
01252
01253
01254
01255 self->refresh();
01256
01257 }
01258
01259 void LLPanelObject::getVolumeParams(LLVolumeParams& volume_params)
01260 {
01261
01262 S32 was_selected_type = mSelectedType;
01263 S32 selected_type = mComboBaseType->getCurrentIndex();
01264 U8 profile;
01265 U8 path;
01266 switch ( selected_type )
01267 {
01268 case MI_CYLINDER:
01269 profile = LL_PCODE_PROFILE_CIRCLE;
01270 path = LL_PCODE_PATH_LINE;
01271 break;
01272
01273 case MI_BOX:
01274 profile = LL_PCODE_PROFILE_SQUARE;
01275 path = LL_PCODE_PATH_LINE;
01276 break;
01277
01278 case MI_PRISM:
01279 profile = LL_PCODE_PROFILE_EQUALTRI;
01280 path = LL_PCODE_PATH_LINE;
01281 break;
01282
01283 case MI_SPHERE:
01284 profile = LL_PCODE_PROFILE_CIRCLE_HALF;
01285 path = LL_PCODE_PATH_CIRCLE;
01286 break;
01287
01288 case MI_TORUS:
01289 profile = LL_PCODE_PROFILE_CIRCLE;
01290 path = LL_PCODE_PATH_CIRCLE;
01291 break;
01292
01293 case MI_TUBE:
01294 profile = LL_PCODE_PROFILE_SQUARE;
01295 path = LL_PCODE_PATH_CIRCLE;
01296 break;
01297
01298 case MI_RING:
01299 profile = LL_PCODE_PROFILE_EQUALTRI;
01300 path = LL_PCODE_PATH_CIRCLE;
01301 break;
01302
01303 case MI_SCULPT:
01304 profile = LL_PCODE_PROFILE_CIRCLE;
01305 path = LL_PCODE_PATH_CIRCLE;
01306 break;
01307
01308 default:
01309 llwarns << "Unknown base type " << selected_type
01310 << " in getVolumeParams()" << llendl;
01311
01312 selected_type = MI_BOX;
01313 profile = LL_PCODE_PROFILE_SQUARE;
01314 path = LL_PCODE_PATH_LINE;
01315 break;
01316 }
01317
01318
01319 if (path == LL_PCODE_PATH_LINE)
01320 {
01321 LLVOVolume *volobjp = (LLVOVolume *)(LLViewerObject*)(mObject);
01322 if (volobjp->isFlexible())
01323 {
01324 path = LL_PCODE_PATH_FLEXIBLE;
01325 }
01326 }
01327
01328 S32 selected_hole = mComboHoleType->getCurrentIndex();
01329 U8 hole;
01330 switch (selected_hole)
01331 {
01332 case MI_HOLE_CIRCLE:
01333 hole = LL_PCODE_HOLE_CIRCLE;
01334 break;
01335 case MI_HOLE_SQUARE:
01336 hole = LL_PCODE_HOLE_SQUARE;
01337 break;
01338 case MI_HOLE_TRIANGLE:
01339 hole = LL_PCODE_HOLE_TRIANGLE;
01340 break;
01341 case MI_HOLE_SAME:
01342 default:
01343 hole = LL_PCODE_HOLE_SAME;
01344 break;
01345 }
01346
01347 volume_params.setType(profile | hole, path);
01348 mSelectedType = selected_type;
01349
01350
01351 F32 cut_begin = mSpinCutBegin->get();
01352 F32 cut_end = mSpinCutEnd->get();
01353
01354
01355 if (cut_begin > cut_end - OBJECT_MIN_CUT_INC)
01356 {
01357 cut_begin = cut_end - OBJECT_MIN_CUT_INC;
01358 mSpinCutBegin->set(cut_begin);
01359 }
01360
01361 F32 adv_cut_begin = mCtrlPathBegin->get();
01362 F32 adv_cut_end = mCtrlPathEnd->get();
01363
01364
01365 if (adv_cut_begin > adv_cut_end - OBJECT_MIN_CUT_INC)
01366 {
01367 adv_cut_begin = adv_cut_end - OBJECT_MIN_CUT_INC;
01368 mCtrlPathBegin->set(adv_cut_begin);
01369 }
01370
01371 F32 begin_s, end_s;
01372 F32 begin_t, end_t;
01373
01374 if (selected_type == MI_SPHERE || selected_type == MI_TORUS ||
01375 selected_type == MI_TUBE || selected_type == MI_RING)
01376 {
01377 begin_s = adv_cut_begin;
01378 end_s = adv_cut_end;
01379
01380 begin_t = cut_begin;
01381 end_t = cut_end;
01382 }
01383 else
01384 {
01385 begin_s = cut_begin;
01386 end_s = cut_end;
01387
01388 begin_t = adv_cut_begin;
01389 end_t = adv_cut_end;
01390 }
01391
01392 volume_params.setBeginAndEndS(begin_s, end_s);
01393 volume_params.setBeginAndEndT(begin_t, end_t);
01394
01395
01396 F32 hollow = mSpinHollow->get() / 100.f;
01397
01398 if ( selected_hole == MI_HOLE_SQUARE &&
01399 ( selected_type == MI_CYLINDER || selected_type == MI_TORUS ||
01400 selected_type == MI_PRISM || selected_type == MI_RING ||
01401 selected_type == MI_SPHERE ) )
01402 {
01403 if (hollow > 0.7f) hollow = 0.7f;
01404 }
01405
01406 volume_params.setHollow( hollow );
01407
01408
01409 F32 twist_begin = mSpinTwistBegin->get();
01410 F32 twist = mSpinTwist->get();
01411
01412 if (path == LL_PCODE_PATH_LINE || path == LL_PCODE_PATH_FLEXIBLE)
01413 {
01414 twist_begin /= OBJECT_TWIST_LINEAR_MAX;
01415 twist /= OBJECT_TWIST_LINEAR_MAX;
01416 }
01417 else
01418 {
01419 twist_begin /= OBJECT_TWIST_MAX;
01420 twist /= OBJECT_TWIST_MAX;
01421 }
01422
01423 volume_params.setTwistBegin(twist_begin);
01424 volume_params.setTwist(twist);
01425
01426
01427 F32 scale_x = mSpinScaleX->get();
01428 F32 scale_y = mSpinScaleY->get();
01429 if ( was_selected_type == MI_BOX || was_selected_type == MI_CYLINDER || was_selected_type == MI_PRISM)
01430 {
01431 scale_x = 1.f - scale_x;
01432 scale_y = 1.f - scale_y;
01433 }
01434
01435
01436 F32 skew = mSpinSkew->get();
01437
01438
01439 F32 taper_x = mSpinTaperX->get();
01440 F32 taper_y = mSpinTaperY->get();
01441
01442
01443 F32 radius_offset = mSpinRadiusOffset->get();
01444
01445
01446 F32 revolutions = mSpinRevolutions->get();
01447
01448 if ( selected_type == MI_SPHERE )
01449 {
01450
01451 scale_x = 1.0f;
01452 scale_y = 1.0f;
01453 skew = 0.0f;
01454 taper_x = 0.0f;
01455 taper_y = 0.0f;
01456 radius_offset = 0.0f;
01457 revolutions = 1.0f;
01458 }
01459 else if ( selected_type == MI_TORUS || selected_type == MI_TUBE ||
01460 selected_type == MI_RING )
01461 {
01462 scale_x = llclamp(
01463 scale_x,
01464 OBJECT_MIN_HOLE_SIZE,
01465 OBJECT_MAX_HOLE_SIZE_X);
01466 scale_y = llclamp(
01467 scale_y,
01468 OBJECT_MIN_HOLE_SIZE,
01469 OBJECT_MAX_HOLE_SIZE_Y);
01470
01471
01472 F32 radius_mag = fabs(radius_offset);
01473 F32 hole_y_mag = fabs(scale_y);
01474 F32 taper_y_mag = fabs(taper_y);
01475
01476 if ( (radius_offset > 0.f && taper_y < 0.f) ||
01477 (radius_offset < 0.f && taper_y > 0.f) )
01478 {
01479
01480 taper_y_mag = 0.f;
01481 }
01482 F32 max_radius_mag = 1.f - hole_y_mag * (1.f - taper_y_mag) / (1.f - hole_y_mag);
01483
01484 if (radius_mag > max_radius_mag)
01485 {
01486
01487 if (radius_offset < 0.f)
01488 {
01489 radius_offset = -max_radius_mag;
01490 }
01491 else
01492 {
01493 radius_offset = max_radius_mag;
01494 }
01495 }
01496
01497
01498 F32 skew_mag= fabs(skew);
01499 F32 min_skew_mag = 1.0f - 1.0f / (revolutions * scale_x + 1.0f);
01500
01501 if ( fabs(revolutions - 1.0f) < 0.001)
01502 min_skew_mag = 0.0f;
01503
01504
01505 if (skew_mag < min_skew_mag)
01506 {
01507
01508 if (skew < 0.0f)
01509 {
01510 skew = -min_skew_mag;
01511 }
01512 else
01513 {
01514 skew = min_skew_mag;
01515 }
01516 }
01517 }
01518
01519 volume_params.setRatio( scale_x, scale_y );
01520 volume_params.setSkew(skew);
01521 volume_params.setTaper( taper_x, taper_y );
01522 volume_params.setRadiusOffset(radius_offset);
01523 volume_params.setRevolutions(revolutions);
01524
01525
01526 F32 shear_x = mSpinShearX->get();
01527 F32 shear_y = mSpinShearY->get();
01528 volume_params.setShear( shear_x, shear_y );
01529
01530 if (selected_type == MI_SCULPT)
01531 {
01532 volume_params.setSculptID(LLUUID::null, 0);
01533 volume_params.setBeginAndEndT (0, 1);
01534 volume_params.setBeginAndEndS (0, 1);
01535 volume_params.setHollow (0);
01536 volume_params.setTwistBegin (0);
01537 volume_params.setTwistEnd (0);
01538 volume_params.setRatio (1, 0.5);
01539 volume_params.setShear (0, 0);
01540 volume_params.setTaper (0, 0);
01541 volume_params.setRevolutions (1);
01542 volume_params.setRadiusOffset (0);
01543 volume_params.setSkew (0);
01544 }
01545
01546 }
01547
01548
01549 void LLPanelObject::sendRotation()
01550 {
01551 if (mObject.isNull()) return;
01552
01553 LLVector3 new_rot(mCtrlRotX->get(), mCtrlRotY->get(), mCtrlRotZ->get());
01554 new_rot.mV[VX] = llround(new_rot.mV[VX], OBJECT_ROTATION_PRECISION);
01555 new_rot.mV[VY] = llround(new_rot.mV[VY], OBJECT_ROTATION_PRECISION);
01556 new_rot.mV[VZ] = llround(new_rot.mV[VZ], OBJECT_ROTATION_PRECISION);
01557
01558
01559 LLVector3 delta = new_rot - mCurEulerDegrees;
01560
01561 if (delta.magVec() >= 0.0005f)
01562 {
01563 mCurEulerDegrees = new_rot;
01564 new_rot *= DEG_TO_RAD;
01565
01566 LLQuaternion rotation;
01567 rotation.setQuat(new_rot.mV[VX], new_rot.mV[VY], new_rot.mV[VZ]);
01568
01569 if (mRootObject != mObject)
01570 {
01571 rotation = rotation * ~mRootObject->getRotationRegion();
01572 }
01573
01574 mObject->setRotation(rotation, TRUE );
01575
01576 LLSelectMgr::getInstance()->sendMultipleUpdate(UPD_ROTATION);
01577 }
01578 }
01579
01580
01581
01582 void LLPanelObject::sendScale()
01583 {
01584 if (mObject.isNull()) return;
01585
01586 LLVector3 newscale(mCtrlScaleX->get(), mCtrlScaleY->get(), mCtrlScaleZ->get());
01587
01588 LLVector3 delta = newscale - mObject->getScale();
01589 if (delta.magVec() >= 0.0005f)
01590 {
01591
01592
01593
01594
01595 BOOL dont_stretch_textures = !LLManipScale::getStretchTextures();
01596 if (dont_stretch_textures)
01597 {
01598 LLSelectMgr::getInstance()->saveSelectedObjectTransform(SELECT_ACTION_TYPE_SCALE);
01599 }
01600
01601 mObject->setScale(newscale, TRUE);
01602 LLSelectMgr::getInstance()->sendMultipleUpdate(UPD_SCALE | UPD_POSITION);
01603
01604 LLSelectMgr::getInstance()->adjustTexturesByScale(TRUE, !dont_stretch_textures);
01605
01606 }
01607 else
01608 {
01609
01610 }
01611 }
01612
01613
01614 void LLPanelObject::sendPosition()
01615 {
01616 if (mObject.isNull()) return;
01617
01618 LLVector3 newpos(mCtrlPosX->get(), mCtrlPosY->get(), mCtrlPosZ->get());
01619 LLViewerRegion* regionp = mObject->getRegion();
01620
01621
01622 const F32 height = newpos.mV[VZ];
01623 const F32 min_height = LLWorld::getInstance()->getMinAllowedZ(mObject);
01624 const F32 max_height = LLWorld::getInstance()->getRegionMaxHeight();
01625
01626 if (!mObject->isAttachment())
01627 {
01628 if ( height < min_height)
01629 {
01630 newpos.mV[VZ] = min_height;
01631 mCtrlPosZ->set( min_height );
01632 }
01633 else if ( height > max_height )
01634 {
01635 newpos.mV[VZ] = max_height;
01636 mCtrlPosZ->set( max_height );
01637 }
01638
01639
01640 if (mObject->getPCode() == LL_PCODE_LEGACY_GRASS)
01641 {
01642 mCtrlPosZ->set(LLWorld::getInstance()->resolveLandHeightAgent(newpos) + 1.f);
01643 }
01644 }
01645
01646
01647
01648 LLVector3d new_pos_global = regionp->getPosGlobalFromRegion(newpos);
01649
01650 if ( LLWorld::getInstance()->positionRegionValidGlobal(new_pos_global) )
01651 {
01652
01653 LLVector3d old_pos_global = mObject->getPositionGlobal();
01654 LLVector3d delta = new_pos_global - old_pos_global;
01655
01656 if (delta.magVec() >= 0.0005f)
01657 {
01658 if (mRootObject != mObject)
01659 {
01660 newpos = newpos - mRootObject->getPositionRegion();
01661 newpos = newpos * ~mRootObject->getRotationRegion();
01662 mObject->setPositionParent(newpos);
01663 }
01664 else
01665 {
01666 mObject->setPositionEdit(newpos);
01667 }
01668 LLSelectMgr::getInstance()->sendMultipleUpdate(UPD_POSITION);
01669
01670 LLSelectMgr::getInstance()->updateSelectionCenter();
01671 }
01672 }
01673 else
01674 {
01675
01676 LLVector3 vec = mRootObject->getPositionRegion();
01677 mCtrlPosX->set(vec.mV[VX]);
01678 mCtrlPosY->set(vec.mV[VY]);
01679 mCtrlPosZ->set(vec.mV[VZ]);
01680 }
01681 }
01682
01683 void LLPanelObject::sendSculpt()
01684 {
01685 if (mObject.isNull())
01686 return;
01687
01688 LLSculptParams sculpt_params;
01689
01690 if (mCtrlSculptTexture)
01691 sculpt_params.setSculptTexture(mCtrlSculptTexture->getImageAssetID());
01692
01693 if (mCtrlSculptType)
01694 sculpt_params.setSculptType(mCtrlSculptType->getCurrentIndex());
01695
01696 mObject->setParameterEntry(LLNetworkData::PARAMS_SCULPT, sculpt_params, TRUE);
01697 }
01698
01699 void LLPanelObject::refresh()
01700 {
01701 getState();
01702 if (mObject.notNull() && mObject->isDead())
01703 {
01704 mObject = NULL;
01705 }
01706
01707 if (mRootObject.notNull() && mRootObject->isDead())
01708 {
01709 mRootObject = NULL;
01710 }
01711 }
01712
01713
01714 void LLPanelObject::draw()
01715 {
01716 const LLColor4 white( 1.0f, 1.0f, 1.0f, 1);
01717 const LLColor4 red( 1.0f, 0.25f, 0.f, 1);
01718 const LLColor4 green( 0.f, 1.0f, 0.f, 1);
01719 const LLColor4 blue( 0.f, 0.5f, 1.0f, 1);
01720
01721
01722 LLTool* tool = LLToolMgr::getInstance()->getCurrentTool();
01723
01724 if (tool == LLToolCompTranslate::getInstance())
01725 {
01726 mCtrlPosX ->setLabelColor(red);
01727 mCtrlPosY ->setLabelColor(green);
01728 mCtrlPosZ ->setLabelColor(blue);
01729
01730 mCtrlScaleX ->setLabelColor(white);
01731 mCtrlScaleY ->setLabelColor(white);
01732 mCtrlScaleZ ->setLabelColor(white);
01733
01734 mCtrlRotX ->setLabelColor(white);
01735 mCtrlRotY ->setLabelColor(white);
01736 mCtrlRotZ ->setLabelColor(white);
01737 }
01738 else if ( tool == LLToolCompScale::getInstance() )
01739 {
01740 mCtrlPosX ->setLabelColor(white);
01741 mCtrlPosY ->setLabelColor(white);
01742 mCtrlPosZ ->setLabelColor(white);
01743
01744 mCtrlScaleX ->setLabelColor(red);
01745 mCtrlScaleY ->setLabelColor(green);
01746 mCtrlScaleZ ->setLabelColor(blue);
01747
01748 mCtrlRotX ->setLabelColor(white);
01749 mCtrlRotY ->setLabelColor(white);
01750 mCtrlRotZ ->setLabelColor(white);
01751 }
01752 else if ( tool == LLToolCompRotate::getInstance() )
01753 {
01754 mCtrlPosX ->setLabelColor(white);
01755 mCtrlPosY ->setLabelColor(white);
01756 mCtrlPosZ ->setLabelColor(white);
01757
01758 mCtrlScaleX ->setLabelColor(white);
01759 mCtrlScaleY ->setLabelColor(white);
01760 mCtrlScaleZ ->setLabelColor(white);
01761
01762 mCtrlRotX ->setLabelColor(red);
01763 mCtrlRotY ->setLabelColor(green);
01764 mCtrlRotZ ->setLabelColor(blue);
01765 }
01766 else
01767 {
01768 mCtrlPosX ->setLabelColor(white);
01769 mCtrlPosY ->setLabelColor(white);
01770 mCtrlPosZ ->setLabelColor(white);
01771
01772 mCtrlScaleX ->setLabelColor(white);
01773 mCtrlScaleY ->setLabelColor(white);
01774 mCtrlScaleZ ->setLabelColor(white);
01775
01776 mCtrlRotX ->setLabelColor(white);
01777 mCtrlRotY ->setLabelColor(white);
01778 mCtrlRotZ ->setLabelColor(white);
01779 }
01780
01781 LLPanel::draw();
01782 }
01783
01784
01785 void LLPanelObject::clearCtrls()
01786 {
01787 LLPanel::clearCtrls();
01788
01789 mCheckLock ->set(FALSE);
01790 mCheckLock ->setEnabled( FALSE );
01791 mCheckPhysics ->set(FALSE);
01792 mCheckPhysics ->setEnabled( FALSE );
01793 mCheckTemporary ->set(FALSE);
01794 mCheckTemporary ->setEnabled( FALSE );
01795 mCheckPhantom ->set(FALSE);
01796 mCheckPhantom ->setEnabled( FALSE );
01797 #if 0 // 1.9.2
01798 mCheckCastShadows->set(FALSE);
01799 mCheckCastShadows->setEnabled( FALSE );
01800 #endif
01801 mComboMaterial ->setEnabled( FALSE );
01802 mLabelMaterial ->setEnabled( FALSE );
01803
01804 mLabelPosition ->setEnabled( FALSE );
01805 mLabelSize ->setEnabled( FALSE );
01806 mLabelRotation ->setEnabled( FALSE );
01807 mLabelBaseType ->setEnabled( FALSE );
01808 mLabelCut ->setEnabled( FALSE );
01809 mLabelHollow ->setEnabled( FALSE );
01810 mLabelHoleType ->setEnabled( FALSE );
01811 mLabelTwist ->setEnabled( FALSE );
01812 mLabelSkew ->setEnabled( FALSE );
01813 mLabelShear ->setEnabled( FALSE );
01814 mLabelTaper ->setEnabled( FALSE );
01815 mLabelRadiusOffset->setEnabled( FALSE );
01816 mLabelRevolutions->setEnabled( FALSE );
01817
01818 childSetVisible("select_single", FALSE);
01819 childSetVisible("edit_object", TRUE);
01820 childSetEnabled("edit_object", FALSE);
01821
01822 childSetEnabled("scale_hole", FALSE);
01823 childSetEnabled("scale_taper", FALSE);
01824 childSetEnabled( "advanced_cut", FALSE );
01825 childSetEnabled( "advanced_dimple", FALSE );
01826 }
01827
01828
01829
01830
01831
01832
01833 void LLPanelObject::onCommitLock(LLUICtrl *ctrl, void *data)
01834 {
01835
01836 LLPanelObject *self = (LLPanelObject *)data;
01837
01838 if(self->mRootObject.isNull()) return;
01839
01840 BOOL new_state = self->mCheckLock->get();
01841
01842 LLSelectMgr::getInstance()->selectionSetObjectPermissions(PERM_OWNER, !new_state, PERM_MOVE | PERM_MODIFY);
01843 }
01844
01845
01846 void LLPanelObject::onCommitPosition( LLUICtrl* ctrl, void* userdata )
01847 {
01848 LLPanelObject* self = (LLPanelObject*) userdata;
01849 self->sendPosition();
01850 }
01851
01852
01853 void LLPanelObject::onCommitScale( LLUICtrl* ctrl, void* userdata )
01854 {
01855 LLPanelObject* self = (LLPanelObject*) userdata;
01856 self->sendScale();
01857 }
01858
01859
01860 void LLPanelObject::onCommitRotation( LLUICtrl* ctrl, void* userdata )
01861 {
01862 LLPanelObject* self = (LLPanelObject*) userdata;
01863 self->sendRotation();
01864 }
01865
01866
01867 void LLPanelObject::onCommitPhysics( LLUICtrl* ctrl, void* userdata )
01868 {
01869 LLPanelObject* self = (LLPanelObject*) userdata;
01870 self->sendIsPhysical();
01871 }
01872
01873
01874 void LLPanelObject::onCommitTemporary( LLUICtrl* ctrl, void* userdata )
01875 {
01876 LLPanelObject* self = (LLPanelObject*) userdata;
01877 self->sendIsTemporary();
01878 }
01879
01880
01881 void LLPanelObject::onCommitPhantom( LLUICtrl* ctrl, void* userdata )
01882 {
01883 LLPanelObject* self = (LLPanelObject*) userdata;
01884 self->sendIsPhantom();
01885 }
01886
01887
01888 void LLPanelObject::onCommitCastShadows( LLUICtrl* ctrl, void* userdata )
01889 {
01890 LLPanelObject* self = (LLPanelObject*) userdata;
01891 self->sendCastShadows();
01892 }
01893
01894
01895
01896 void LLPanelObject::onSelectSculpt(LLUICtrl* ctrl, void* userdata)
01897 {
01898 LLPanelObject* self = (LLPanelObject*) userdata;
01899
01900 LLTextureCtrl* mTextureCtrl = self->getChild<LLTextureCtrl>("sculpt texture control");
01901
01902 if (mTextureCtrl)
01903 {
01904 self->mSculptTextureRevert = mTextureCtrl->getImageAssetID();
01905 }
01906
01907 self->sendSculpt();
01908 }
01909
01910
01911 void LLPanelObject::onCommitSculpt( LLUICtrl* ctrl, void* userdata )
01912 {
01913 LLPanelObject* self = (LLPanelObject*) userdata;
01914
01915 self->sendSculpt();
01916 }
01917
01918
01919 BOOL LLPanelObject::onDropSculpt(LLUICtrl*, LLInventoryItem* item, void* userdata)
01920 {
01921 LLPanelObject* self = (LLPanelObject*) userdata;
01922
01923 LLTextureCtrl* mTextureCtrl = self->getChild<LLTextureCtrl>("sculpt texture control");
01924
01925 if (mTextureCtrl)
01926 {
01927 LLUUID asset = item->getAssetUUID();
01928
01929 mTextureCtrl->setImageAssetID(asset);
01930 self->mSculptTextureRevert = asset;
01931 }
01932
01933 return TRUE;
01934 }
01935
01936
01937
01938 void LLPanelObject::onCancelSculpt(LLUICtrl* ctrl, void* userdata)
01939 {
01940 LLPanelObject* self = (LLPanelObject*) userdata;
01941
01942 LLTextureCtrl* mTextureCtrl = self->getChild<LLTextureCtrl>("sculpt texture control");
01943 if(!mTextureCtrl)
01944 return;
01945
01946 mTextureCtrl->setImageAssetID(self->mSculptTextureRevert);
01947
01948 self->sendSculpt();
01949 }
01950
01951
01952 void LLPanelObject::onCommitSculptType(LLUICtrl *ctrl, void* userdata)
01953 {
01954 LLPanelObject* self = (LLPanelObject*) userdata;
01955
01956 self->sendSculpt();
01957 }