diff options
Diffstat (limited to 'linden/indra/newview/rcmoapradar.cpp')
-rw-r--r-- | linden/indra/newview/rcmoapradar.cpp | 440 |
1 files changed, 440 insertions, 0 deletions
diff --git a/linden/indra/newview/rcmoapradar.cpp b/linden/indra/newview/rcmoapradar.cpp new file mode 100644 index 0000000..f0593ef --- /dev/null +++ b/linden/indra/newview/rcmoapradar.cpp | |||
@@ -0,0 +1,440 @@ | |||
1 | // MOAP Radar | ||
2 | // Robin Cornelius | ||
3 | |||
4 | |||
5 | #include "llviewerprecompiledheaders.h" | ||
6 | |||
7 | #include "llavatarconstants.h" | ||
8 | #include "llfloateravatarlist.h" | ||
9 | |||
10 | #include "lluictrlfactory.h" | ||
11 | #include "llviewerwindow.h" | ||
12 | #include "llscrolllistctrl.h" | ||
13 | #include "llradiogroup.h" | ||
14 | #include "llviewercontrol.h" | ||
15 | #include "llbutton.h" | ||
16 | |||
17 | #include "llvoavatar.h" | ||
18 | #include "llimview.h" | ||
19 | #include "rcmoapradar.h" | ||
20 | #include "llregionflags.h" | ||
21 | #include "llfloaterreporter.h" | ||
22 | #include "llagent.h" | ||
23 | #include "llviewerregion.h" | ||
24 | #include "lltracker.h" | ||
25 | #include "llviewerstats.h" | ||
26 | #include "llerror.h" | ||
27 | #include "llchat.h" | ||
28 | #include "llfloaterchat.h" | ||
29 | #include "llviewermessage.h" | ||
30 | #include "llweb.h" | ||
31 | #include "llviewerobjectlist.h" | ||
32 | #include "llmutelist.h" | ||
33 | #include "llcallbacklist.h" | ||
34 | #include "llmediaentry.h" | ||
35 | |||
36 | #include <time.h> | ||
37 | #include <string.h> | ||
38 | |||
39 | #include <map> | ||
40 | |||
41 | #include "llworld.h" | ||
42 | |||
43 | #include "llsdutil.h" | ||
44 | |||
45 | LLFloaterMOAPRadar* LLFloaterMOAPRadar::sInstance = NULL; | ||
46 | |||
47 | LLFloaterMOAPRadar::LLFloaterMOAPRadar() : LLFloater(std::string("MOAPradar")) | ||
48 | { | ||
49 | llassert_always(sInstance == NULL); | ||
50 | sInstance = this; | ||
51 | mUpdateRate = gSavedSettings.getU32("MOAPRadarUpdateRate") * 3 + 3; | ||
52 | mTrackingRunning=false; | ||
53 | } | ||
54 | |||
55 | LLFloaterMOAPRadar::~LLFloaterMOAPRadar() | ||
56 | { | ||
57 | gIdleCallbacks.deleteFunction(LLFloaterMOAPRadar::callbackIdle); | ||
58 | sInstance = NULL; | ||
59 | } | ||
60 | |||
61 | //static | ||
62 | void LLFloaterMOAPRadar::toggle(void*) | ||
63 | { | ||
64 | if (sInstance) | ||
65 | { | ||
66 | if (sInstance->getVisible()) | ||
67 | { | ||
68 | sInstance->close(false); | ||
69 | } | ||
70 | else | ||
71 | { | ||
72 | sInstance->open(); | ||
73 | } | ||
74 | } | ||
75 | else | ||
76 | { | ||
77 | showInstance(); | ||
78 | } | ||
79 | } | ||
80 | |||
81 | //static | ||
82 | void LLFloaterMOAPRadar::showInstance() | ||
83 | { | ||
84 | if (sInstance) | ||
85 | { | ||
86 | if (!sInstance->getVisible()) | ||
87 | { | ||
88 | sInstance->open(); | ||
89 | } | ||
90 | } | ||
91 | else | ||
92 | { | ||
93 | sInstance = new LLFloaterMOAPRadar(); | ||
94 | LLUICtrlFactory::getInstance()->buildFloater(sInstance, "floater_moap_radar.xml"); | ||
95 | } | ||
96 | } | ||
97 | |||
98 | void LLFloaterMOAPRadar::draw() | ||
99 | { | ||
100 | LLFloater::draw(); | ||
101 | } | ||
102 | |||
103 | void LLFloaterMOAPRadar::onOpen() | ||
104 | { | ||
105 | gSavedSettings.setBOOL("ShowMOAPRadar", TRUE); | ||
106 | sInstance->setVisible(TRUE); | ||
107 | } | ||
108 | |||
109 | void LLFloaterMOAPRadar::onClose(bool app_quitting) | ||
110 | { | ||
111 | sInstance->setVisible(FALSE); | ||
112 | if (!app_quitting) | ||
113 | { | ||
114 | gSavedSettings.setBOOL("ShowMOAPRadar", FALSE); | ||
115 | } | ||
116 | if (!gSavedSettings.getBOOL("MOAPRadarKeepOpen") || app_quitting) | ||
117 | { | ||
118 | destroy(); | ||
119 | } | ||
120 | } | ||
121 | |||
122 | |||
123 | BOOL LLFloaterMOAPRadar::postBuild() | ||
124 | { | ||
125 | |||
126 | mMOAPList = getChild<LLScrollListCtrl>("moap_list"); | ||
127 | mMOAPList->sortByColumn("distance", TRUE); | ||
128 | |||
129 | mTrackBtn = getChild<LLButton>("track_btn"); | ||
130 | mTrackBtn->setLabel(LLStringExplicit("Track")); | ||
131 | |||
132 | childSetAction("open_btn", onClickOpen, this); | ||
133 | childSetAction("track_btn", onClickTrack, this); | ||
134 | childSetAction("copy_btn", onClickCopy, this); | ||
135 | |||
136 | mMOAPList->setCommitOnSelectionChange(TRUE); | ||
137 | childSetCommitCallback("moap_list", onSelectMOAP, this); | ||
138 | |||
139 | gIdleCallbacks.addFunction(LLFloaterMOAPRadar::callbackIdle); | ||
140 | |||
141 | return TRUE; | ||
142 | } | ||
143 | |||
144 | //static | ||
145 | void LLFloaterMOAPRadar::callbackIdle(void *userdata) { | ||
146 | if (LLFloaterMOAPRadar::sInstance != NULL) | ||
147 | { | ||
148 | // Do not update at every frame: this would be insane ! | ||
149 | if (gFrameCount % LLFloaterMOAPRadar::sInstance->mUpdateRate == 0) | ||
150 | { | ||
151 | LLFloaterMOAPRadar::sInstance->updateMOAPList(); | ||
152 | } | ||
153 | } | ||
154 | } | ||
155 | |||
156 | |||
157 | void LLFloaterMOAPRadar::updateMOAPList() | ||
158 | { | ||
159 | if (sInstance != this) return; | ||
160 | |||
161 | mMOAPList->deleteAllItems(); | ||
162 | |||
163 | S32 obj_count=gObjectList.getNumObjects(); | ||
164 | |||
165 | int count=0; | ||
166 | |||
167 | for(int objnum=0;objnum<obj_count;objnum++) | ||
168 | { | ||
169 | LLPointer<LLViewerObject> obj = gObjectList.getObject(objnum); | ||
170 | |||
171 | if(obj.isNull()) | ||
172 | continue; | ||
173 | |||
174 | if(obj->isDead() || obj->isOrphaned()) | ||
175 | continue; | ||
176 | |||
177 | if(obj->getMediaType() == LLViewerObject::MEDIA_TYPE_NONE) | ||
178 | continue; | ||
179 | |||
180 | LLSD element; | ||
181 | |||
182 | element["id"] = obj->getID(); | ||
183 | |||
184 | for(int face=0;face<obj->getNumTEs();face++) | ||
185 | { | ||
186 | const LLTextureEntry * te=obj->getTE(face); | ||
187 | if(te==NULL) | ||
188 | continue; | ||
189 | |||
190 | if(te->hasMedia()) | ||
191 | { | ||
192 | LLMediaEntry* media=te->getMediaData(); | ||
193 | |||
194 | if(media==NULL) | ||
195 | continue; | ||
196 | |||
197 | LLSD media_details; | ||
198 | media->asLLSD(media_details); | ||
199 | |||
200 | element["columns"][LIST_URL]["column"] = "URL"; | ||
201 | element["columns"][LIST_URL]["type"] = "text"; | ||
202 | std::string URL=media->getCurrentURL(); | ||
203 | if(URL=="") | ||
204 | URL="(Waiting....)"; | ||
205 | |||
206 | element["columns"][LIST_URL]["value"] = URL; | ||
207 | |||
208 | if(mTrackingRunning && mTrackedID==obj->getID() && mTrackedFace==face) | ||
209 | { | ||
210 | element["columns"][LIST_URL]["font-style"] = "BOLD"; | ||
211 | } | ||
212 | else | ||
213 | { | ||
214 | element["columns"][LIST_URL]["font-style"] = "NORMAL"; | ||
215 | } | ||
216 | |||
217 | element["columns"][LIST_FACE]["column"] = "face"; | ||
218 | element["columns"][LIST_FACE]["type"] = "text"; | ||
219 | std::stringstream face_buf; | ||
220 | face_buf << face; | ||
221 | element["columns"][LIST_FACE]["value"] = face_buf.str(); | ||
222 | |||
223 | LLVector3d offset = gAgent.getPositionGlobal()-obj->getPositionGlobal(); | ||
224 | S32 dist= offset.length(); | ||
225 | |||
226 | element["columns"][LIST_DISTANCE]["column"] = "distance"; | ||
227 | element["columns"][LIST_DISTANCE]["type"] = "text"; | ||
228 | std::stringstream dist_buf; | ||
229 | dist_buf << std::fixed << std::setprecision(2) << dist<<"m"; | ||
230 | element["columns"][LIST_DISTANCE]["value"] = dist_buf.str(); | ||
231 | |||
232 | if(dist<25) | ||
233 | element["columns"][LIST_DISTANCE]["color"] = LLColor4::green.getValue(); | ||
234 | else if(dist<50) | ||
235 | element["columns"][LIST_DISTANCE]["color"] = LLColor4::blue1.getValue(); | ||
236 | else if(dist<100) | ||
237 | element["columns"][LIST_DISTANCE]["color"] = LLColor4::black.getValue(); | ||
238 | else if(dist<256) | ||
239 | element["columns"][LIST_DISTANCE]["color"] = LLColor4::yellow.getValue(); | ||
240 | else | ||
241 | element["columns"][LIST_DISTANCE]["color"] = LLColor4::red.getValue(); | ||
242 | |||
243 | |||
244 | element["columns"][LIST_POSITION]["column"] = "position"; | ||
245 | element["columns"][LIST_POSITION]["type"] = "text"; | ||
246 | element["columns"][LIST_POSITION]["value"] = ""; | ||
247 | |||
248 | element["columns"][LIST_ALTITUDE]["column"] = "altitude"; | ||
249 | element["columns"][LIST_ALTITUDE]["type"] = "text"; | ||
250 | std::stringstream alt_buf; | ||
251 | alt_buf << std::fixed << std::setprecision(2) << obj->getPositionGlobal().mdV[2]<<"m"; | ||
252 | element["columns"][LIST_ALTITUDE]["value"] = alt_buf.str(); | ||
253 | |||
254 | element["columns"][LIST_POSITION]["column"]="position"; | ||
255 | element["columns"][LIST_POSITION]["type"] = "text"; | ||
256 | std::stringstream pos_buf; | ||
257 | |||
258 | S32 moap_x = (S32)offset.mdV[VX]; | ||
259 | S32 moap_y = (S32)offset.mdV[VY]; | ||
260 | if (moap_x >= -256 && moap_x <= 256 && moap_y >= -256 && moap_y <= 256) | ||
261 | { | ||
262 | pos_buf<< std::fixed << std::setprecision(2)<<obj->getPositionRegion().mV[VX]<<","<<obj->getPositionRegion().mV[VY]; | ||
263 | } | ||
264 | else | ||
265 | { | ||
266 | if (moap_y < 0) | ||
267 | pos_buf<<"S"; | ||
268 | else if (moap_y > 256) | ||
269 | pos_buf<<"N"; | ||
270 | |||
271 | if (moap_x < 0) | ||
272 | pos_buf<<"W"; | ||
273 | else if (moap_x > 256) | ||
274 | pos_buf<<"E"; | ||
275 | } | ||
276 | |||
277 | |||
278 | element["columns"][LIST_POSITION]["value"] = pos_buf.str(); | ||
279 | |||
280 | mMOAPList->addElement(element, ADD_BOTTOM); | ||
281 | |||
282 | if(mSelectedObjID==obj->getID() && mSelectedFace==face) | ||
283 | { | ||
284 | mMOAPList->selectNthItem(count); | ||
285 | } | ||
286 | |||
287 | count++; | ||
288 | } | ||
289 | } | ||
290 | } | ||
291 | |||
292 | updatetrackbtn(); | ||
293 | } | ||
294 | |||
295 | // static | ||
296 | void LLFloaterMOAPRadar::onClickOpen(void* userdata) | ||
297 | { | ||
298 | LLFloaterMOAPRadar *self = (LLFloaterMOAPRadar*)userdata; | ||
299 | |||
300 | LLDynamicArray<LLUUID> ids = self->mMOAPList->getSelectedIDs(); | ||
301 | |||
302 | if(ids.empty()) | ||
303 | { | ||
304 | return; | ||
305 | } | ||
306 | |||
307 | LLUUID id=ids.front(); | ||
308 | |||
309 | LLPointer<LLViewerObject> obj = gObjectList.findObject(id); | ||
310 | if(obj.notNull()) | ||
311 | { | ||
312 | |||
313 | const LLTextureEntry * te=obj->getTE(self->mSelectedFace); | ||
314 | if(te==NULL) | ||
315 | return; | ||
316 | |||
317 | if(te->hasMedia()) | ||
318 | { | ||
319 | LLMediaEntry* media=te->getMediaData(); | ||
320 | if(media) | ||
321 | { | ||
322 | //gViewerWindow->mWindow->copyTextToClipboard(utf8str_to_wstring(media->getCurrentURL())); | ||
323 | LLWeb::loadURL(media->getCurrentURL()); | ||
324 | } | ||
325 | } | ||
326 | } | ||
327 | |||
328 | } | ||
329 | |||
330 | // static | ||
331 | void LLFloaterMOAPRadar::onClickTrack(void* userdata) | ||
332 | { | ||
333 | LLFloaterMOAPRadar *self = (LLFloaterMOAPRadar*)userdata; | ||
334 | |||
335 | LLDynamicArray<LLUUID> ids = self->mMOAPList->getSelectedIDs(); | ||
336 | |||
337 | if(self->mTrackingRunning) | ||
338 | { | ||
339 | LLTracker::stopTracking(NULL); | ||
340 | self->mTrackingRunning=false; | ||
341 | } | ||
342 | |||
343 | if(ids.empty()) | ||
344 | { | ||
345 | self->mTrackedID=LLUUID::null; | ||
346 | self->mTrackingRunning=false; | ||
347 | return; | ||
348 | } | ||
349 | |||
350 | LLUUID id=ids.front(); | ||
351 | |||
352 | if(id==self->mTrackedID && self->mSelectedFace==self->mTrackedFace) | ||
353 | { | ||
354 | self->mTrackedID=LLUUID::null; | ||
355 | self->mTrackingRunning=false; | ||
356 | return; | ||
357 | } | ||
358 | |||
359 | self->mTrackedID=LLUUID::null; | ||
360 | |||
361 | LLPointer<LLViewerObject> obj = gObjectList.findObject(id); | ||
362 | if(obj.notNull()) | ||
363 | { | ||
364 | LLTracker::trackLocation(obj->getPositionGlobal(),"MOAP Tracking","",LLTracker::LOCATION_ITEM); | ||
365 | self->mTrackingRunning=true; | ||
366 | self->mTrackedID=id; | ||
367 | self->mTrackedFace=self->mSelectedFace; | ||
368 | } | ||
369 | } | ||
370 | |||
371 | // static | ||
372 | void LLFloaterMOAPRadar::onClickCopy(void* userdata) | ||
373 | { | ||
374 | LLFloaterMOAPRadar *self = (LLFloaterMOAPRadar*)userdata; | ||
375 | |||
376 | LLDynamicArray<LLUUID> ids = self->mMOAPList->getSelectedIDs(); | ||
377 | |||
378 | if(ids.empty()) | ||
379 | { | ||
380 | LLTracker::stopTracking(NULL); | ||
381 | return; | ||
382 | } | ||
383 | |||
384 | LLUUID id=ids.front(); | ||
385 | |||
386 | LLPointer<LLViewerObject> obj = gObjectList.findObject(id); | ||
387 | |||
388 | if(obj.notNull()) | ||
389 | { | ||
390 | |||
391 | const LLTextureEntry * te=obj->getTE(self->mSelectedFace); | ||
392 | if(te==NULL) | ||
393 | return; | ||
394 | |||
395 | if(te->hasMedia()) | ||
396 | { | ||
397 | LLMediaEntry* media=te->getMediaData(); | ||
398 | if(media) | ||
399 | { | ||
400 | gViewerWindow->mWindow->copyTextToClipboard(utf8str_to_wstring(media->getCurrentURL())); | ||
401 | } | ||
402 | } | ||
403 | } | ||
404 | |||
405 | } | ||
406 | |||
407 | //static | ||
408 | void LLFloaterMOAPRadar::onSelectMOAP(LLUICtrl*, void* userdata) | ||
409 | { | ||
410 | LLFloaterMOAPRadar *self = (LLFloaterMOAPRadar*)userdata; | ||
411 | |||
412 | LLScrollListItem *item = self->mMOAPList->getFirstSelected(); | ||
413 | if (item) | ||
414 | { | ||
415 | self->mSelectedObjID = item->getUUID(); | ||
416 | self->mSelectedFace = item->getColumn(LIST_FACE)->getValue().asInteger(); | ||
417 | } | ||
418 | |||
419 | self->updatetrackbtn(); | ||
420 | } | ||
421 | |||
422 | void LLFloaterMOAPRadar::updatetrackbtn() | ||
423 | { | ||
424 | if( mTrackingRunning) | ||
425 | { | ||
426 | if( mTrackedID==mSelectedObjID && mTrackedFace==mSelectedFace) | ||
427 | { | ||
428 | mTrackBtn->setLabel(LLStringExplicit("Untrack")); | ||
429 | } | ||
430 | else | ||
431 | { | ||
432 | mTrackBtn->setLabel(LLStringExplicit("New Track")); | ||
433 | } | ||
434 | } | ||
435 | else | ||
436 | { | ||
437 | mTrackBtn->setLabel(LLStringExplicit("Track")); | ||
438 | } | ||
439 | |||
440 | } \ No newline at end of file | ||