Ansariel 2022-02-02 10:13:39 +01:00
commit abe4857fd3
68 changed files with 1322 additions and 1022 deletions

2
.gitignore vendored
View File

@ -111,3 +111,5 @@ compile_commands.json
# ignore tracy for now
indra/tracy
firestorm.code-workspace
.cache/clangd/index/

View File

@ -3,6 +3,62 @@
<map>
<key>installables</key>
<map>
<key>glib</key>
<map>
<key>copyright</key>
<string>Copyright (C) glib project</string>
<key>license</key>
<string>LGPL</string>
<key>license_file</key>
<string>LICENSES/glib.txt</string>
<key>name</key>
<string>glib</string>
<key>platforms</key>
<map>
<key>linux64</key>
<map>
<key>archive</key>
<map>
<key>hash</key>
<string>9c93ba8b8af97fc8379f77de77e1540a</string>
<key>url</key>
<string>http://3p.firestormviewer.org/glib-2.48.0.202301938-linux64-202301938.tar.bz2</string>
</map>
<key>name</key>
<string>linux</string>
</map>
</map>
<key>version</key>
<string>2.48.0</string>
</map>
<key>fltk</key>
<map>
<key>copyright</key>
<string>Copyright (C) fltk project</string>
<key>license</key>
<string>LGPL/fltk</string>
<key>license_file</key>
<string>LICENSES/fltk.txt</string>
<key>name</key>
<string>fltk</string>
<key>platforms</key>
<map>
<key>linux64</key>
<map>
<key>archive</key>
<map>
<key>hash</key>
<string>81fe1e927e4fe3c5e5f15ce6219ca883</string>
<key>url</key>
<string>http://3p.firestormviewer.org/fltk-1.3.5.202282121-linux64-202282121.tar.bz2</string>
</map>
<key>name</key>
<string>linux</string>
</map>
</map>
<key>version</key>
<string>1.3.5</string>
</map>
<key>jemalloc</key>
<map>
<key>copyright</key>
@ -787,48 +843,6 @@
<key>version</key>
<string>5.1.25</string>
</map>
<key>dbus_glib</key>
<map>
<key>copyright</key>
<string>Copyright (C) Red Hat Inc.</string>
<key>description</key>
<string>D-Bus bindings for glib</string>
<key>license</key>
<string>Academic Free License v. 2.1</string>
<key>license_file</key>
<string>LICENSES/dbus-glib.txt</string>
<key>name</key>
<string>dbus_glib</string>
<key>platforms</key>
<map>
<key>linux</key>
<map>
<key>archive</key>
<map>
<key>hash</key>
<string>9591dcb7efce2a770d77e907705e1492</string>
<key>url</key>
<string>http://3p.firestormviewer.org/dbus_glib-0.76-linux-180871236.tar.bz2</string>
</map>
<key>name</key>
<string>linux</string>
</map>
<key>linux64</key>
<map>
<key>archive</key>
<map>
<key>hash</key>
<string>5a685a65a7066937ef580dcd5a90f9dc</string>
<key>url</key>
<string>http://3p.firestormviewer.org/dbus_glib-0.76-linux64-180841549.tar.bz2</string>
</map>
<key>name</key>
<string>linux64</string>
</map>
</map>
<key>version</key>
<string>0.76</string>
</map>
<key>dictionaries</key>
<map>
<key>copyright</key>
@ -1058,11 +1072,11 @@
<key>archive</key>
<map>
<key>hash</key>
<string>bde9eb3e53001584edb1af44e3b265a2</string>
<string>2db00aa4126d4ee8152fc49b03bb3fe1</string>
<key>hash_algorithm</key>
<string>md5</string>
<key>url</key>
<string>file:///opt/firestorm/fmodstudio-2.02.04-darwin-213491614.tar.bz2</string>
<string>file:///opt/firestorm/fmodstudio-2.02.05-darwin-220160006.tar.bz2</string>
</map>
<key>name</key>
<string>darwin</string>
@ -1577,46 +1591,6 @@
<key>version</key>
<string>0.10.6.314267</string>
</map>
<key>gtk-atk-pango-glib</key>
<map>
<key>copyright</key>
<string>Copyright (various, see sources)</string>
<key>license</key>
<string>lgpl</string>
<key>license_file</key>
<string>LICENSES/gtk-atk-pango-glib.txt</string>
<key>name</key>
<string>gtk-atk-pango-glib</string>
<key>platforms</key>
<map>
<key>linux</key>
<map>
<key>archive</key>
<map>
<key>hash</key>
<string>fb047d496c32cc3b9f99793ee6ebb1e3</string>
<key>url</key>
<string>http://3p.firestormviewer.org/gtk_atk_pango_glib-2.1-linux-180871647.tar.bz2</string>
</map>
<key>name</key>
<string>linux</string>
</map>
<key>linux64</key>
<map>
<key>archive</key>
<map>
<key>hash</key>
<string>d918d894430c1d1d869b9f2e06570c65</string>
<key>url</key>
<string>http://3p.firestormviewer.org/gtk_atk_pango_glib-2.1-linux64-180841902.tar.bz2</string>
</map>
<key>name</key>
<string>linux64</string>
</map>
</map>
<key>version</key>
<string>2.1</string>
</map>
<key>havok-source</key>
<map>
<key>copyright</key>

View File

@ -20,7 +20,7 @@ set(cmake_SOURCE_FILES
ConfigurePkgConfig.cmake
CURL.cmake
Copy3rdPartyLibs.cmake
DBusGlib.cmake
GLIB.cmake
DeploySharedLibs.cmake
Discord.cmake # <FS:LO> Discord rich presence
DragDrop.cmake

View File

@ -245,16 +245,9 @@ elseif(LINUX)
# have to deal with
if (NOT USESYSTEMLIBS)
set(release_files
#libapr-1.so.0
#libaprutil-1.so.0
libatk-1.0.so
#libdb-5.1.so
${EXPAT_COPY}
#libfreetype.so.6.6.2
#libfreetype.so.6
#libGLOD.so
libgmodule-2.0.so
libgobject-2.0.so
libhunspell-1.3.so.0.0.0
libopenal.so
#libopenjpeg.so

View File

@ -1,29 +0,0 @@
# -*- cmake -*-
include(Prebuilt)
if (USESYSTEMLIBS)
include(FindPkgConfig)
pkg_check_modules(DBUSGLIB REQUIRED dbus-glib-1)
elseif (LINUX)
use_prebuilt_binary(dbus_glib)
set(DBUSGLIB_FOUND ON FORCE BOOL)
set(DBUSGLIB_INCLUDE_DIRS
${LIBS_PREBUILT_DIR}/include/dbus
)
# We don't need to explicitly link against dbus-glib itself, because
# the viewer probes for the system's copy at runtime.
set(DBUSGLIB_LIBRARIES
gobject-2.0
glib-2.0
)
endif (USESYSTEMLIBS)
if (DBUSGLIB_FOUND)
set(DBUSGLIB ON CACHE BOOL "Build with dbus-glib message bus support.")
endif (DBUSGLIB_FOUND)
if (DBUSGLIB)
add_definitions(-DLL_DBUS_ENABLED=1)
endif (DBUSGLIB)

View File

@ -9,7 +9,11 @@ else (USESYSTEMLIBS)
use_prebuilt_binary(freetype)
set(FREETYPE_INCLUDE_DIRS ${LIBS_PREBUILT_DIR}/include)
set(FREETYPE_INCLUDE_DIRS ${LIBS_PREBUILT_DIR}/include/freetype2) #<FS:ND/> Also add freetype2 to search dir, or some includes will fail.
set(FREETYPE_LIBRARIES freetype)
# <FS:ND> Linux links this via UI.cmake
if( NOT LINUX )
set(FREETYPE_LIBRARIES freetype)
endif()
# </FS:ND>
endif (USESYSTEMLIBS)
link_directories(${FREETYPE_LIBRARY_DIRS})

11
indra/cmake/GLIB.cmake Normal file
View File

@ -0,0 +1,11 @@
include(Prebuilt)
if( LINUX )
use_prebuilt_binary(glib)
set(GLIB_FOUND ON CACHE BOOL "Build against glib 2")
set(GLIB_INCLUDE_DIRS ${LIBS_PREBUILT_DIR}/include/glib-2.0 ${LIBS_PREBUILT_DIR}/lib/release/glib-2.0/include )
set(GLIB_LIBRARIES libgobject-2.0.a libglib-2.0.a libffi.a libpcre.a)
set(GIO_LIBRARIES libgio-2.0.a libgmodule-2.0.a -lresolv)
add_definitions(-DLL_GLIB=1)
endif()

View File

@ -13,7 +13,7 @@ else (USESYSTEMLIBS)
elseif(DARWIN)
set(HUNSPELL_LIBRARY hunspell-1.3)
elseif(LINUX)
set(HUNSPELL_LIBRARY hunspell-1.3)
set(HUNSPELL_LIBRARY libhunspell-1.3.a)
else()
message(FATAL_ERROR "Invalid platform")
endif()

View File

@ -1,5 +1,32 @@
# -*- cmake -*-
# <FS:ND> Try to find pulse header, if we got them we can use the linux volume catcher
if (LINUX)
include(GLIB)
include_directories( ${GLIB_INCLUDE_DIRS} )
set( PULSE_AUDIO True )
foreach( PULSE_FILE pulse/introspect.h pulse/context.h pulse/subscribe.h pulse/glib-mainloop.h )
find_path( PULSE_FILE_FOUND ${PULSE_FILE} NO_CACHE)
if( NOT PULSE_FILE_FOUND )
message( "Looking for ${PULSE_FILE} ... not found")
set( PULSE_AUDIO False )
else()
message( "Looking for ${PULSE_FILE} ... found")
endif()
endforeach()
if( NOT PULSE_AUDIO )
message( "Building without linux volume catcher" )
set(LINUX_VOLUME_CATCHER dummy_volume_catcher.cpp)
else()
message( "Building with linux volume catcher" )
set(LINUX_VOLUME_CATCHER linux_volume_catcher.cpp)
endif()
endif()
set(MEDIA_PLUGIN_BASE_INCLUDE_DIRS
${LIBS_OPEN_DIR}/media_plugins/base/

View File

@ -1,27 +1,34 @@
# -*- cmake -*-
include(Prebuilt)
include(FreeType)
include(GLIB)
if (USESYSTEMLIBS)
include(FindPkgConfig)
if( NOT GTK_VERSION )
set( GTK_VERSION 2.0 )
endif()
if (LINUX)
set(PKGCONFIG_PACKAGES
atk
cairo
gdk-2.0
gdk-${GTK_VERSION}
gdk-pixbuf-2.0
glib-2.0
gmodule-2.0
gtk+-2.0
gtk+-${GTK_VERSION}
gthread-2.0
libpng
pango
pangoft2
pangox
pangoxft
sdl
sdl2
)
if( GTK_VERSION LESS "3.0" )
LIST( APPEND PKGCONFIG_PACKAGES pangoxft )
else()
add_definitions( -DGTK_DISABLE_DEPRECATED)
endif()
endif (LINUX)
foreach(pkg ${PKGCONFIG_PACKAGES})
@ -31,29 +38,16 @@ if (USESYSTEMLIBS)
list(APPEND UI_LIBRARIES ${${pkg}_LIBRARIES})
add_definitions(${${pkg}_CFLAGS_OTHERS})
endforeach(pkg)
list(APPEND UI_LIBRARIES X11)
else (USESYSTEMLIBS)
if (LINUX)
use_prebuilt_binary(gtk-atk-pango-glib)
use_prebuilt_binary(fltk)
endif (LINUX)
if (LINUX)
set(UI_LIB_NAMES
freetype
atk-1.0
gdk-x11-2.0
gdk_pixbuf-2.0
glib-2.0
gmodule-2.0
gobject-2.0
gthread-2.0
gtk-x11-2.0
pango-1.0
pangoft2-1.0
pangox-1.0
#pangoxft-1.0
gio-2.0
pangocairo-1.0
ffi
libfltk.a
libfreetype.a
)
foreach(libname ${UI_LIB_NAMES})
@ -68,6 +62,7 @@ else (USESYSTEMLIBS)
endforeach(libname)
set(UI_LIBRARIES ${UI_LIBRARIES} Xinerama)
include_directories ( ${GLIB_INCLUDE_DIRS} )
endif (LINUX)
include_directories (
@ -80,5 +75,5 @@ else (USESYSTEMLIBS)
endif (USESYSTEMLIBS)
if (LINUX)
add_definitions(-DLL_GTK=1 -DLL_X11=1)
add_definitions(-DLL_X11=1 -DLL_FLTK=1)
endif (LINUX)

View File

@ -40,6 +40,7 @@
#if LL_GTK
# include "gtk/gtk.h"
#error "Direct use of GTK is deprecated"
#endif // LL_GTK
#define MAX_LOADSTRING 100

View File

@ -77,7 +77,8 @@ if (LINUX)
${LLXML_LIBRARIES}
${UI_LIBRARIES} # for GTK
${SDL_LIBRARY}
fontconfig # For FCInit and other FC* functions.
libfontconfig.a # For FCInit and other FC* functions.
libfreetype.a
)
list(APPEND viewer_SOURCE_FILES

View File

@ -43,10 +43,15 @@
#if LL_GTK
extern "C" {
# include "gtk/gtk.h"
#error "Direct use of GTK is deprecated"
}
#include <locale.h>
#endif // LL_GTK
#ifdef LL_GLIB
#include <glib.h>
#endif
extern "C" {
# include "fontconfig/fontconfig.h"
}
@ -186,6 +191,248 @@ Display* LLWindowSDL::get_SDL_Display(void)
}
#endif // LL_X11
#if LL_X11
// Clipboard handing via native X11, base on the implementation in Cool VL by Henri Beauchamp
namespace
{
std::array<Atom, 3> gSupportedAtoms;
Atom XA_CLIPBOARD;
Atom XA_TARGETS;
Atom PVT_PASTE_BUFFER;
long const MAX_PASTE_BUFFER_SIZE = 16383;
void filterSelectionRequest( XEvent aEvent )
{
auto *display = LLWindowSDL::getSDLDisplay();
auto &request = aEvent.xselectionrequest;
XSelectionEvent reply { SelectionNotify, aEvent.xany.serial, aEvent.xany.send_event, display,
request.requestor, request.selection, request.target,
request.property,request.time };
if (request.target == XA_TARGETS)
{
XChangeProperty(display, request.requestor, request.property,
XA_ATOM, 32, PropModeReplace,
(unsigned char *) &gSupportedAtoms.front(), gSupportedAtoms.size());
}
else if (std::find(gSupportedAtoms.begin(), gSupportedAtoms.end(), request.target) !=
gSupportedAtoms.end())
{
std::string utf8;
if (request.selection == XA_PRIMARY)
utf8 = wstring_to_utf8str(gWindowImplementation->getPrimaryText());
else
utf8 = wstring_to_utf8str(gWindowImplementation->getSecondaryText());
XChangeProperty(display, request.requestor, request.property,
request.target, 8, PropModeReplace,
(unsigned char *) utf8.c_str(), utf8.length());
}
else if (request.selection == XA_CLIPBOARD)
{
// Did not have what they wanted, so no property set
reply.property = None;
}
else
return;
XSendEvent(request.display, request.requestor, False, NoEventMask, (XEvent *) &reply);
XSync(display, False);
}
void filterSelectionClearRequest( XEvent aEvent )
{
auto &request = aEvent.xselectionrequest;
if (request.selection == XA_PRIMARY)
gWindowImplementation->clearPrimaryText();
else if (request.selection == XA_CLIPBOARD)
gWindowImplementation->clearSecondaryText();
}
int x11_clipboard_filter(const SDL_Event *evt)
{
Display *display = LLWindowSDL::getSDLDisplay();
if (!display)
return 1;
if (evt->type != SDL_SYSWMEVENT)
return 1;
auto xevent = evt->syswm.msg->event.xevent;
if (xevent.type == SelectionRequest)
filterSelectionRequest( xevent );
else if (xevent.type == SelectionClear)
filterSelectionClearRequest( xevent );
return 1;
}
bool grab_property(Display* display, Window window, Atom selection, Atom target)
{
if( !display )
return false;
maybe_lock_display();
XDeleteProperty(display, window, PVT_PASTE_BUFFER);
XFlush(display);
XConvertSelection(display, selection, target, PVT_PASTE_BUFFER, window, CurrentTime);
// Unlock the connection so that the SDL event loop may function
maybe_unlock_display();
const auto start{ SDL_GetTicks() };
const auto end{ start + 1000 };
XEvent xevent {};
bool response = false;
do
{
SDL_Event event {};
// Wait for an event
SDL_WaitEvent(&event);
// If the event is a window manager event
if (event.type == SDL_SYSWMEVENT)
{
xevent = event.syswm.msg->event.xevent;
if (xevent.type == SelectionNotify && xevent.xselection.requestor == window)
response = true;
}
} while (!response && SDL_GetTicks() < end );
return response && xevent.xselection.property != None;
}
}
void LLWindowSDL::initialiseX11Clipboard()
{
if (!mSDL_Display)
return;
SDL_EventState(SDL_SYSWMEVENT, SDL_ENABLE);
SDL_SetEventFilter(x11_clipboard_filter);
maybe_lock_display();
XA_CLIPBOARD = XInternAtom(mSDL_Display, "CLIPBOARD", False);
gSupportedAtoms[0] = XA_STRING;
gSupportedAtoms[1] = XInternAtom(mSDL_Display, "COMPOUND_TEXT", False);
gSupportedAtoms[2] = XInternAtom(mSDL_Display, "UTF8_STRING", False);
// TARGETS atom
XA_TARGETS = XInternAtom(mSDL_Display, "TARGETS", False);
// SL_PASTE_BUFFER atom
PVT_PASTE_BUFFER = XInternAtom(mSDL_Display, "FS_PASTE_BUFFER", False);
maybe_unlock_display();
}
bool LLWindowSDL::getSelectionText( Atom aSelection, Atom aType, LLWString &text )
{
if( !mSDL_Display )
return false;
if( !grab_property(mSDL_Display, mSDL_XWindowID, aSelection,aType ) )
return false;
maybe_lock_display();
Atom type;
int format{};
unsigned long len{},remaining {};
unsigned char* data = nullptr;
int res = XGetWindowProperty(mSDL_Display, mSDL_XWindowID,
PVT_PASTE_BUFFER, 0, MAX_PASTE_BUFFER_SIZE, False,
AnyPropertyType, &type, &format, &len,
&remaining, &data);
if (data && len)
{
text = LLWString(
utf8str_to_wstring(reinterpret_cast< char const *>( data ) )
);
XFree(data);
}
maybe_unlock_display();
return res == Success;
}
bool LLWindowSDL::getSelectionText(Atom selection, LLWString& text)
{
if (!mSDL_Display)
return false;
maybe_lock_display();
Window owner = XGetSelectionOwner(mSDL_Display, selection);
if (owner == None)
{
if (selection == XA_PRIMARY)
{
owner = DefaultRootWindow(mSDL_Display);
selection = XA_CUT_BUFFER0;
}
else
{
maybe_unlock_display();
return false;
}
}
maybe_unlock_display();
for( Atom atom : gSupportedAtoms )
{
if(getSelectionText(selection, atom, text ) )
return true;
}
return false;
}
bool LLWindowSDL::setSelectionText(Atom selection, const LLWString& text)
{
maybe_lock_display();
if (selection == XA_PRIMARY)
{
std::string utf8 = wstring_to_utf8str(text);
XStoreBytes(mSDL_Display, utf8.c_str(), utf8.length() + 1);
mPrimaryClipboard = text;
}
else
mSecondaryClipboard = text;
XSetSelectionOwner(mSDL_Display, selection, mSDL_XWindowID, CurrentTime);
auto owner = XGetSelectionOwner(mSDL_Display, selection);
maybe_unlock_display();
return owner == mSDL_XWindowID;
}
Display* LLWindowSDL::getSDLDisplay()
{
if (gWindowImplementation)
return gWindowImplementation->mSDL_Display;
return nullptr;
}
#endif
LLWindowSDL::LLWindowSDL(LLWindowCallbacks* callbacks,
const std::string& title, S32 x, S32 y, S32 width,
@ -253,6 +500,7 @@ LLWindowSDL::LLWindowSDL(LLWindowCallbacks* callbacks,
#if LL_X11
mFlashing = FALSE;
initialiseX11Clipboard();
#endif // LL_X11
mKeyScanCode = 0;
@ -1356,33 +1604,34 @@ BOOL LLWindowSDL::copyTextToPrimary(const LLWString &text)
#else
BOOL LLWindowSDL::isClipboardTextAvailable()
{
return FALSE; // unsupported
{
return mSDL_Display && XGetSelectionOwner(mSDL_Display, XA_CLIPBOARD) != None;
}
BOOL LLWindowSDL::pasteTextFromClipboard(LLWString &dst)
{
return FALSE; // unsupported
return getSelectionText(XA_CLIPBOARD, dst);
}
BOOL LLWindowSDL::copyTextToClipboard(const LLWString &s)
{
return FALSE; // unsupported
return setSelectionText(XA_CLIPBOARD, s);
}
BOOL LLWindowSDL::isPrimaryTextAvailable()
{
return FALSE; // unsupported
LLWString text;
return getSelectionText(XA_PRIMARY, text) && !text.empty();
}
BOOL LLWindowSDL::pasteTextFromPrimary(LLWString &dst)
{
return FALSE; // unsupported
return getSelectionText(XA_PRIMARY, dst);
}
BOOL LLWindowSDL::copyTextToPrimary(const LLWString &s)
{
return FALSE; // unsupported
return setSelectionText(XA_PRIMARY, s);
}
#endif // LL_GTK
@ -1747,7 +1996,18 @@ void LLWindowSDL::processMiscNativeEvents()
setlocale(LC_ALL, saved_locale.c_str() );
}
#endif // LL_GTK
#if LL_GLIB
// Pump until we've nothing left to do or passed 1/15th of a
// second pumping for this frame.
static LLTimer pump_timer;
pump_timer.reset();
pump_timer.setTimerExpirySec(1.0f / 15.0f);
do
{
g_main_context_iteration(g_main_context_default(), FALSE);
} while( g_main_context_pending(g_main_context_default()) && !pump_timer.hasExpired());
#endif
// hack - doesn't belong here - but this is just for debugging
if (getenv("LL_DEBUG_BLOAT"))
{
@ -2398,39 +2658,6 @@ static void color_changed_callback(GtkWidget *widget,
gtk_color_selection_get_current_color(colorsel, colorp);
}
/*
Make the raw keyboard data available - used to poke through to LLQtWebKit so
that Qt/Webkit has access to the virtual keycodes etc. that it needs
*/
LLSD LLWindowSDL::getNativeKeyData()
{
LLSD result = LLSD::emptyMap();
U32 modifiers = 0; // pretend-native modifiers... oh what a tangled web we weave!
// we go through so many levels of device abstraction that I can't really guess
// what a plugin under GDK under Qt under SL under SDL under X11 considers
// a 'native' modifier mask. this has been sort of reverse-engineered... they *appear*
// to match GDK consts, but that may be co-incidence.
modifiers |= (mKeyModifiers & KMOD_LSHIFT) ? 0x0001 : 0;
modifiers |= (mKeyModifiers & KMOD_RSHIFT) ? 0x0001 : 0;// munge these into the same shift
modifiers |= (mKeyModifiers & KMOD_CAPS) ? 0x0002 : 0;
modifiers |= (mKeyModifiers & KMOD_LCTRL) ? 0x0004 : 0;
modifiers |= (mKeyModifiers & KMOD_RCTRL) ? 0x0004 : 0;// munge these into the same ctrl
modifiers |= (mKeyModifiers & KMOD_LALT) ? 0x0008 : 0;// untested
modifiers |= (mKeyModifiers & KMOD_RALT) ? 0x0008 : 0;// untested
// *todo: test ALTs - I don't have a case for testing these. Do you?
// *todo: NUM? - I don't care enough right now (and it's not a GDK modifier).
result["scan_code"] = (S32)mKeyScanCode;
result["virtual_key"] = (S32)mKeyVirtualKey;
result["modifiers"] = (S32)modifiers;
result[ "sdl_sym" ] = (S32)mSDLSym; // <FS:ND/> Store the SDL Keysym too.
return result;
}
BOOL LLWindowSDL::dialogColorPicker( F32 *r, F32 *g, F32 *b)
{
BOOL rtn = FALSE;
@ -2515,6 +2742,37 @@ BOOL LLWindowSDL::dialogColorPicker( F32 *r, F32 *g, F32 *b)
}
#endif // LL_GTK
/*
Make the raw keyboard data available - used to poke through to LLQtWebKit so
that Qt/Webkit has access to the virtual keycodes etc. that it needs
*/
LLSD LLWindowSDL::getNativeKeyData()
{
LLSD result = LLSD::emptyMap();
U32 modifiers = 0; // pretend-native modifiers... oh what a tangled web we weave!
// we go through so many levels of device abstraction that I can't really guess
// what a plugin under GDK under Qt under SL under SDL under X11 considers
// a 'native' modifier mask. this has been sort of reverse-engineered... they *appear*
// to match GDK consts, but that may be co-incidence.
modifiers |= (mKeyModifiers & KMOD_LSHIFT) ? 0x0001 : 0;
modifiers |= (mKeyModifiers & KMOD_RSHIFT) ? 0x0001 : 0;// munge these into the same shift
modifiers |= (mKeyModifiers & KMOD_CAPS) ? 0x0002 : 0;
modifiers |= (mKeyModifiers & KMOD_LCTRL) ? 0x0004 : 0;
modifiers |= (mKeyModifiers & KMOD_RCTRL) ? 0x0004 : 0;// munge these into the same ctrl
modifiers |= (mKeyModifiers & KMOD_LALT) ? 0x0008 : 0;// untested
modifiers |= (mKeyModifiers & KMOD_RALT) ? 0x0008 : 0;// untested
// *todo: test ALTs - I don't have a case for testing these. Do you?
// *todo: NUM? - I don't care enough right now (and it's not a GDK modifier).
result["scan_code"] = (S32)mKeyScanCode;
result["virtual_key"] = (S32)mKeyVirtualKey;
result["modifiers"] = (S32)modifiers;
result[ "sdl_sym" ] = (S32)mSDLSym; // <FS:ND/> Store the SDL Keysym too.
return result;
}
#if LL_LINUX
// extracted from spawnWebBrowser for clarity and to eliminate
// compiler confusion regarding close(int fd) vs. LLWindow::close()

View File

@ -220,6 +220,24 @@ private:
U32 mSDLSym; // <FS:ND/> Store the SDL Keysym too.
BOOL mUseLegacyCursors; // <FS:LO> Legacy cursor setting from main program
public:
#if LL_X11
static Display* getSDLDisplay();
LLWString const& getPrimaryText() const { return mPrimaryClipboard; }
LLWString const& getSecondaryText() const { return mSecondaryClipboard; }
void clearPrimaryText() { mPrimaryClipboard.clear(); }
void clearSecondaryText() { mSecondaryClipboard.clear(); }
private:
void initialiseX11Clipboard();
bool getSelectionText(Atom selection, LLWString& text);
bool getSelectionText( Atom selection, Atom type, LLWString &text );
bool setSelectionText(Atom selection, const LLWString& text);
#endif
LLWString mPrimaryClipboard;
LLWString mSecondaryClipboard;
};

View File

@ -49,4 +49,3 @@ set(media_plugin_base_HEADER_FILES
add_library(media_plugin_base
${media_plugin_base_SOURCE_FILES}
)

View File

@ -58,7 +58,8 @@ set (media_plugin_cef_LINK_LIBRARIES
if (LINUX)
# message(FATAL_ERROR "CEF plugin has been enabled for a Linux compile.\n"
# " Please create a volume_catcher implementation for this platform.")
list(APPEND media_plugin_cef_SOURCE_FILES dummy_volume_catcher.cpp)
list(APPEND media_plugin_cef_SOURCE_FILES ${LINUX_VOLUME_CATCHER})
set(CMAKE_SHARED_LINKER_FLAGS "-Wl,--build-id -Wl,-rpath,'$ORIGIN:$ORIGIN/../../lib'")
elseif (DARWIN)
list(APPEND media_plugin_cef_SOURCE_FILES mac_volume_catcher_null.cpp)

View File

@ -53,6 +53,7 @@ extern "C" {
#include "apr_dso.h"
}
////////////////////////////////////////////////////
#define DEBUGMSG(...) do {} while(0)
@ -81,7 +82,7 @@ bool grab_pa_syms(std::string pulse_dso_name)
apr_status_t rv;
apr_dso_handle_t *sSymPADSOHandle = NULL;
#define LL_PA_SYM(REQUIRED, PASYM, RTN, ...) do{rv = apr_dso_sym((apr_dso_handle_sym_t*)&ll##PASYM, sSymPADSOHandle, #PASYM); if (rv != APR_SUCCESS) {INFOMSG("Failed to grab symbol: %s", #PASYM); if (REQUIRED) sym_error = true;} else DEBUGMSG("grabbed symbol: %s from %p", #PASYM, (void*)ll##PASYM);}while(0)
#define LL_PA_SYM(REQUIRED, PASYM, RTN, ...) do{rv = apr_dso_sym((apr_dso_handle_sym_t*)&ll##PASYM, sSymPADSOHandle, #PASYM); if (rv != APR_SUCCESS) { if (REQUIRED) sym_error = true;} } while(0);
//attempt to load the shared library
apr_pool_create(&sSymPADSOMemoryPool, NULL);
@ -216,17 +217,16 @@ void VolumeCatcherImpl::init()
mGotSyms = loadsyms("libpulse-mainloop-glib.so.0");
if (!mGotSyms) return;
// better make double-sure glib itself is initialized properly.
if (!g_thread_supported ()) g_thread_init (NULL);
g_type_init();
mMainloop = llpa_glib_mainloop_new(g_main_context_default());
if (mMainloop)
{
pa_mainloop_api *api = llpa_glib_mainloop_get_api(mMainloop);
if (api)
{
pa_proplist *proplist = llpa_proplist_new();
if (proplist)
{
llpa_proplist_sets(proplist, PA_PROP_APPLICATION_ICON_NAME, "multimedia-player");
@ -236,6 +236,7 @@ void VolumeCatcherImpl::init()
// plain old pa_context_new() is broken!
mPAContext = llpa_context_new_with_proplist(api, NULL, proplist);
llpa_proplist_free(proplist);
}
}
@ -350,6 +351,51 @@ void VolumeCatcherImpl::update_index_volume(U32 index, F32 volume)
}
}
pid_t getParentPid( pid_t aPid )
{
std::stringstream strm;
strm << "/proc/" << aPid << "/status";
std::ifstream in{ strm.str() };
if( !in.is_open() )
return 0;
pid_t res {0};
while( !in.eof() && res == 0 )
{
std::string line;
line.resize( 1024, 0 );
in.getline( &line[0], line.length() );
auto i = line.find( "PPid:" );
if( i == std::string::npos )
continue;
char const *pIn = line.c_str() + 5; // Skip over pid;
while( *pIn != 0 && isspace( *pIn ) )
++pIn;
if( *pIn )
res = atoll( pIn );
}
return res;
}
bool isPluginPid( pid_t aPid )
{
auto myPid = getpid();
do
{
if( aPid == myPid )
return true;
aPid = getParentPid( aPid );
} while( aPid > 1 );
return false;
}
void callback_discovered_sinkinput(pa_context *context, const pa_sink_input_info *sii, int eol, void *userdata)
{
@ -360,11 +406,10 @@ void callback_discovered_sinkinput(pa_context *context, const pa_sink_input_info
{
pa_proplist *proplist = sii->proplist;
pid_t sinkpid = atoll(llpa_proplist_gets(proplist, PA_PROP_APPLICATION_PROCESS_ID));
if (sinkpid == getpid()) // does the discovered sinkinput belong to this process?
if (isPluginPid( sinkpid )) // does the discovered sinkinput belong to this process?
{
bool is_new = (impl->mSinkInputIndices.find(sii->index) ==
impl->mSinkInputIndices.end());
bool is_new = (impl->mSinkInputIndices.find(sii->index) == impl->mSinkInputIndices.end());
impl->mSinkInputIndices.insert(sii->index);
impl->mSinkInputNumChannels[sii->index] = sii->channel_map.channels;
@ -387,32 +432,31 @@ void callback_subscription_alert(pa_context *context, pa_subscription_event_type
VolumeCatcherImpl *impl = dynamic_cast<VolumeCatcherImpl*>((VolumeCatcherImpl*)userdata);
llassert(impl);
switch (t & PA_SUBSCRIPTION_EVENT_FACILITY_MASK) {
switch (t & PA_SUBSCRIPTION_EVENT_FACILITY_MASK)
{
case PA_SUBSCRIPTION_EVENT_SINK_INPUT:
if ((t & PA_SUBSCRIPTION_EVENT_TYPE_MASK) ==
PA_SUBSCRIPTION_EVENT_REMOVE)
{
// forget this sinkinput, if we were caring about it
impl->mSinkInputIndices.erase(index);
impl->mSinkInputNumChannels.erase(index);
}
else if ((t & PA_SUBSCRIPTION_EVENT_TYPE_MASK) ==
PA_SUBSCRIPTION_EVENT_NEW)
{
// ask for more info about this new sinkinput
pa_operation *op;
if ((op = llpa_context_get_sink_input_info(impl->mPAContext, index, callback_discovered_sinkinput, impl)))
if ((t & PA_SUBSCRIPTION_EVENT_TYPE_MASK) == PA_SUBSCRIPTION_EVENT_REMOVE)
{
llpa_operation_unref(op);
// forget this sinkinput, if we were caring about it
impl->mSinkInputIndices.erase(index);
impl->mSinkInputNumChannels.erase(index);
}
}
else
{
// property change on this sinkinput - we don't care.
}
break;
else if ((t & PA_SUBSCRIPTION_EVENT_TYPE_MASK) == PA_SUBSCRIPTION_EVENT_NEW)
{
// ask for more info about this new sinkinput
pa_operation *op;
if ((op = llpa_context_get_sink_input_info(impl->mPAContext, index, callback_discovered_sinkinput, impl)))
{
llpa_operation_unref(op);
}
}
else
{
// property change on this sinkinput - we don't care.
}
break;
default:;
default:;
}
}

View File

@ -13,7 +13,7 @@ include(BuildPackagesInfo)
include(BuildVersion)
include(CMakeCopyIfDifferent)
include(CubemapToEquirectangularJS)
include(DBusGlib)
include(GLIB)
include(DragDrop)
include(EXPAT)
include(FMODSTUDIO)
@ -1797,7 +1797,6 @@ if (LINUX)
# fsversionstrings.h with the right numbers in it.
# COMPILE_DEFINITIONS "${VIEWER_CHANNEL_VERSION_DEFINES}"
)
LIST(APPEND viewer_SOURCE_FILES llappviewerlinux_api_dbus.cpp)
# [FS] Growl support
LIST(APPEND viewer_HEADER_FILES desktopnotifierlinux.h growlmanager.h)
LIST(APPEND viewer_SOURCE_FILES desktopnotifierlinux.cpp growlmanager.cpp)
@ -2518,7 +2517,7 @@ target_link_libraries(${VIEWER_BINARY_NAME}
${BOOST_WAVE_LIBRARY} #FS specific
${BOOST_THREAD_LIBRARY} #FS specific
${BOOST_CONTEXT_LIBRARY}
${DBUSGLIB_LIBRARIES}
${GLIB_LIBRARIES}
${OPENGL_LIBRARIES}
${FMODWRAPPER_LIBRARY} # must come after LLAudio
${OPENAL_LIBRARIES}
@ -2538,6 +2537,7 @@ target_link_libraries(${VIEWER_BINARY_NAME}
${LLPHYSICSEXTENSIONS_LIBRARIES}
${LLAPPEARANCE_LIBRARIES}
${GROWL_LIBRARY}
${GIO_LIBRARIES}
)
target_link_libraries(${VIEWER_BINARY_NAME} ${DISCORD_LIBRARY} )

View File

@ -1 +1 @@
6.5.2
6.5.4

View File

@ -139,7 +139,7 @@ BOOL FSFloaterPerformance::postBuild()
mObjectList->setHoverIconName("StopReload_Off");
mObjectList->setIconClickedCallback(boost::bind(&FSFloaterPerformance::detachItem, this, _1));
mSettingsPanel->getChild<LLRadioGroup>("graphics_quality")->setCommitCallback(boost::bind(&FSFloaterPerformance::onChangeQuality, this, _2));
mSettingsPanel->getChild<LLSliderCtrl>("quality_vs_perf_selection")->setCommitCallback(boost::bind(&FSFloaterPerformance::onChangeQuality, this, _2));
mNearbyPanel->getChild<LLButton>("exceptions_btn")->setCommitCallback(boost::bind(&FSFloaterPerformance::onClickExceptions, this));
mNearbyPanel->getChild<LLCheckBoxCtrl>("hide_avatars")->setCommitCallback(boost::bind(&FSFloaterPerformance::onClickHideAvatars, this));
@ -240,104 +240,106 @@ void FSFloaterPerformance::draw()
// tot_frame_time_ns -= tot_limit_time_ns;
// tot_frame_time_ns -= tot_sleep_time_ns;
if(tot_frame_time_ns == 0)
if(tot_frame_time_ns != 0)
{
LL_WARNS("performance") << "things went wrong, quit while we can." << LL_ENDL;
return;
}
auto pct_avatar_time = (tot_avatar_time_ns * 100)/tot_frame_time_ns;
auto pct_huds_time = (tot_huds_time_ns * 100)/tot_frame_time_ns;
auto pct_ui_time = (tot_ui_time_ns * 100)/tot_frame_time_ns;
auto pct_idle_time = (tot_idle_time_ns * 100)/tot_frame_time_ns;
auto pct_swap_time = (tot_swap_time_ns * 100)/tot_frame_time_ns;
auto pct_scene_render_time = (tot_scene_time_ns * 100)/tot_frame_time_ns;
pct_avatar_time = llclamp(pct_avatar_time,0.,100.);
pct_huds_time = llclamp(pct_huds_time,0.,100.);
pct_ui_time = llclamp(pct_ui_time,0.,100.);
pct_idle_time = llclamp(pct_idle_time,0.,100.);
pct_swap_time = llclamp(pct_swap_time,0.,100.);
pct_scene_render_time = llclamp(pct_scene_render_time,0.,100.);
auto pct_avatar_time = (tot_avatar_time_ns * 100)/tot_frame_time_ns;
auto pct_huds_time = (tot_huds_time_ns * 100)/tot_frame_time_ns;
auto pct_ui_time = (tot_ui_time_ns * 100)/tot_frame_time_ns;
auto pct_idle_time = (tot_idle_time_ns * 100)/tot_frame_time_ns;
auto pct_swap_time = (tot_swap_time_ns * 100)/tot_frame_time_ns;
auto pct_scene_render_time = (tot_scene_time_ns * 100)/tot_frame_time_ns;
pct_avatar_time = llclamp(pct_avatar_time,0.,100.);
pct_huds_time = llclamp(pct_huds_time,0.,100.);
pct_ui_time = llclamp(pct_ui_time,0.,100.);
pct_idle_time = llclamp(pct_idle_time,0.,100.);
pct_swap_time = llclamp(pct_swap_time,0.,100.);
pct_scene_render_time = llclamp(pct_scene_render_time,0.,100.);
args["AV_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_avatar_time));
args["HUDS_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_huds_time));
args["UI_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_ui_time));
args["IDLE_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_idle_time));
args["SWAP_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_swap_time));
args["SCENERY_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_scene_render_time));
args["TOT_FRAME_TIME"] = llformat("%02u", (U32)llround(tot_frame_time_ns/1000000));
args["FPSCAP"] = llformat("%02u", (U32)fpsCap);
args["FPSTARGET"] = llformat("%02u", (U32)targetFPS);
args["AV_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_avatar_time));
args["HUDS_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_huds_time));
args["UI_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_ui_time));
args["IDLE_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_idle_time));
args["SWAP_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_swap_time));
args["SCENERY_FRAME_PCT"] = llformat("%02u", (U32)llround(pct_scene_render_time));
args["TOT_FRAME_TIME"] = llformat("%02u", (U32)llround(tot_frame_time_ns/1000000));
args["FPSCAP"] = llformat("%02u", (U32)fpsCap);
args["FPSTARGET"] = llformat("%02u", (U32)targetFPS);
getChild<LLTextBox>("av_frame_stats")->setText(getString("av_frame_pct", args));
getChild<LLTextBox>("huds_frame_stats")->setText(getString("huds_frame_pct", args));
getChild<LLTextBox>("frame_breakdown")->setText(getString("frame_stats", args));
auto textbox = getChild<LLTextBox>("fps_warning");
if (tot_sleep_time_raw > 0) // We are sleeping because view is not focussed
{
textbox->setVisible(true);
textbox->setText(getString("focus_fps"));
textbox->setColor(LLUIColorTable::instance().getColor("DrYellow"));
unreliable = true;
}
else if (tot_limit_time_raw > 0)
{
textbox->setVisible(true);
textbox->setText(getString("limit_fps", args));
textbox->setColor(LLUIColorTable::instance().getColor("DrYellow"));
unreliable = true;
}
else if (FSPerfStats::autoTune)
{
textbox->setVisible(true);
textbox->setText(getString("tuning_fps", args));
textbox->setColor(LLUIColorTable::instance().getColor("green"));
getChild<LLTextBox>("av_frame_stats")->setText(getString("av_frame_pct", args));
getChild<LLTextBox>("huds_frame_stats")->setText(getString("huds_frame_pct", args));
getChild<LLTextBox>("frame_breakdown")->setText(getString("frame_stats", args));
auto textbox = getChild<LLTextBox>("fps_warning");
if (tot_sleep_time_raw > 0) // We are sleeping because view is not focussed
{
textbox->setVisible(true);
textbox->setText(getString("focus_fps"));
textbox->setColor(LLUIColorTable::instance().getColor("DrYellow"));
unreliable = true;
}
else if (tot_limit_time_raw > 0)
{
textbox->setVisible(true);
textbox->setText(getString("limit_fps", args));
textbox->setColor(LLUIColorTable::instance().getColor("DrYellow"));
unreliable = true;
}
else if (FSPerfStats::autoTune)
{
textbox->setVisible(true);
textbox->setText(getString("tuning_fps", args));
textbox->setColor(LLUIColorTable::instance().getColor("green"));
}
else
{
textbox->setVisible(false);
}
if (FSPerfStats::autoTune && !unreliable )
{
// the tuning itself is managed from another thread but we can report progress here
// Is our target frame time lower than current? If so we need to take action to reduce draw overheads.
if (target_frame_time_ns <= tot_frame_time_ns)
{
U32 non_avatar_time_ns = tot_frame_time_ns - tot_avatar_time_ns;
// If the target frame time < non avatar frame time then we can pototentially reach it.
if (non_avatar_time_ns < target_frame_time_ns)
{
textbox->setColor(LLUIColorTable::instance().getColor("orange"));
}
else
{
// TODO(Beq): Set advisory text for further actions
textbox->setColor(LLUIColorTable::instance().getColor("red"));
}
}
else if (target_frame_time_ns > (tot_frame_time_ns + FSPerfStats::renderAvatarMaxART_ns))
{
// if we have more time to spare. Display this (the service will update things)
textbox->setColor(LLUIColorTable::instance().getColor("green"));
}
}
if (mHUDsPanel->getVisible())
{
populateHUDList();
}
else if (mNearbyPanel->getVisible())
{
populateNearbyList();
mNearbyPanel->getChild<LLCheckBoxCtrl>("hide_avatars")->set(!LLPipeline::hasRenderTypeControl(LLPipeline::RENDER_TYPE_AVATAR));
}
else if (mComplexityPanel->getVisible())
{
populateObjectList();
}
}
else
{
textbox->setVisible(false);
LL_WARNS("performance") << "Scene time 0. Skipping til we have data." << LL_ENDL;
}
if (FSPerfStats::autoTune && !unreliable )
{
// the tuning itself is managed from another thread but we can report progress here
// Is our target frame time lower than current? If so we need to take action to reduce draw overheads.
if (target_frame_time_ns <= tot_frame_time_ns)
{
U32 non_avatar_time_ns = tot_frame_time_ns - tot_avatar_time_ns;
// If the target frame time < non avatar frame time then we can pototentially reach it.
if (non_avatar_time_ns < target_frame_time_ns)
{
textbox->setColor(LLUIColorTable::instance().getColor("orange"));
}
else
{
// TODO(Beq): Set advisory text for further actions
textbox->setColor(LLUIColorTable::instance().getColor("red"));
}
}
else if (target_frame_time_ns > (tot_frame_time_ns + FSPerfStats::renderAvatarMaxART_ns))
{
// if we have more time to spare. Display this (the service will update things)
textbox->setColor(LLUIColorTable::instance().getColor("green"));
}
}
if (mHUDsPanel->getVisible())
{
populateHUDList();
}
else if (mNearbyPanel->getVisible())
{
populateNearbyList();
mNearbyPanel->getChild<LLCheckBoxCtrl>("hide_avatars")->set(!LLPipeline::hasRenderTypeControl(LLPipeline::RENDER_TYPE_AVATAR));
}
else if (mComplexityPanel->getVisible())
{
populateObjectList();
}
mUpdateTimer->setTimerExpirySec(REFRESH_INTERVAL);
}
LLFloater::draw();
@ -732,11 +734,9 @@ void FSFloaterPerformance::detachItem(const LLUUID& item_id)
void FSFloaterPerformance::onChangeQuality(const LLSD& data)
{
LLFloaterPreference* instance = LLFloaterReg::getTypedInstance<LLFloaterPreference>("preferences");
if (instance)
{
instance->onChangeQuality(data);
}
U32 level = (U32)(data.asReal());
LLFeatureManager::getInstance()->setGraphicsLevel(level, true);
refresh();
}
void FSFloaterPerformance::onClickHideAvatars()

View File

@ -49,11 +49,12 @@ namespace FSPerfStats
std::atomic<int64_t> tunedAvatars{0};
U32 targetFPS; // desired FPS
U64 renderAvatarMaxART_ns{(U64)(ART_UNLIMITED_NANOS)}; // highest render time we'll allow without culling features
U32 fpsTuningStrategy{0}; // linked to FSTuningFPSStrategy
U32 lastGlobalPrefChange{0};
std::mutex bufferToggleLock{};
bool autoTune{false};
Tunables tunables;
std::atomic<int> StatsRecorder::writeBuffer{0};
bool StatsRecorder::collectionEnabled{true};
LLUUID StatsRecorder::focusAv{LLUUID::null};
@ -61,6 +62,14 @@ namespace FSPerfStats
std::array<StatsRecorder::StatsSummaryArray,2> StatsRecorder::max{ {} };
std::array<StatsRecorder::StatsSummaryArray,2> StatsRecorder::sum{ {} };
void Tunables::applyUpdates()
{
assert_main_thread();
if( tuningFlag & NonImposters ){ gSavedSettings.setU32("IndirectMaxNonImpostors", nonImposters); };
if( tuningFlag & ReflectionDetail ){ gSavedSettings.setS32("RenderReflectionDetail", reflectionDetail); };
if( tuningFlag & FarClip ){ gSavedSettings.setF32("RenderFarClip", farClip); };
resetChanges();
}
StatsRecorder::StatsRecorder():q(1024*16),t(&StatsRecorder::run)
{
@ -109,6 +118,7 @@ namespace FSPerfStats
unreliable = true;
lastStats[static_cast<size_t>(StatType_t::RENDER_FPSLIMIT)] = sceneStats[static_cast<size_t>(StatType_t::RENDER_FPSLIMIT)];
lastStats[static_cast<size_t>(StatType_t::RENDER_SLEEP)] = sceneStats[static_cast<size_t>(StatType_t::RENDER_SLEEP)];
lastStats[static_cast<size_t>(StatType_t::RENDER_FRAME)] = sceneStats[static_cast<size_t>(StatType_t::RENDER_FRAME)]; // bring over the total frame render time to deal with region crossing overlap issues
}
if(!unreliable)
@ -174,7 +184,7 @@ namespace FSPerfStats
sum[writeBuffer][i].fill(0);
}
// and now adjust the visuals.
// and now adjust the proxy vars so that the main thread can adjust the visuals.
if(autoTune)
{
updateAvatarParams();
@ -279,6 +289,7 @@ namespace FSPerfStats
static LLCachedControl<F32> impostorDistance(gSavedSettings, "FSAutoTuneImpostorFarAwayDistance");
static LLCachedControl<bool> impostorDistanceTuning(gSavedSettings, "FSAutoTuneImpostorByDistEnabled");
static LLCachedControl<U32> maxNonImpostors (gSavedSettings, "IndirectMaxNonImpostors");
static LLCachedControl<U32> fpsTuningStrategy (gSavedSettings, "FSTuningFPSStrategy");
if(impostorDistanceTuning)
{
@ -287,7 +298,7 @@ namespace FSPerfStats
auto count = countNearbyAvatars(std::min(drawDistance, impostorDistance));
if( count != maxNonImpostors )
{
gSavedSettings.setU32("IndirectMaxNonImpostors", (count < LLVOAvatar::NON_IMPOSTORS_MAX_SLIDER)?count : LLVOAvatar::NON_IMPOSTORS_MAX_SLIDER);
tunables.updateNonImposters( (count < LLVOAvatar::NON_IMPOSTORS_MAX_SLIDER)?count : LLVOAvatar::NON_IMPOSTORS_MAX_SLIDER );
LL_DEBUGS("AutoTune") << "There are " << count << "avatars within " << std::min(drawDistance, impostorDistance) << "m of the camera" << LL_ENDL;
}
}
@ -338,13 +349,13 @@ namespace FSPerfStats
// we cannnot do this by avatar adjustment alone.
if((gFrameCount - FSPerfStats::lastGlobalPrefChange) > 10) // give changes a short time to take effect.
{
if(FSPerfStats::fpsTuningStrategy == 1)
if(fpsTuningStrategy == 1)
{
// 1 - hack the water to opaque. all non opaque have a significant hit, this is a big boost for (arguably) a minor visual hit.
// the other reflection options make comparatively little change and iof this overshoots we'll be stepping back up later
if(LLPipeline::RenderReflectionDetail != -2)
{
gSavedSettings.setS32("RenderReflectionDetail", -2);
FSPerfStats::tunables.updateReflectionDetail(-2);
FSPerfStats::lastGlobalPrefChange = gFrameCount;
return;
}
@ -354,7 +365,7 @@ namespace FSPerfStats
auto new_dd = (drawDistance-10>userMinDrawDistance)?(drawDistance - 10) : userMinDrawDistance;
if(new_dd != drawDistance)
{
gSavedSettings.setF32("RenderFarClip", new_dd);
FSPerfStats::tunables.updateFarClip( new_dd );
FSPerfStats::lastGlobalPrefChange = gFrameCount;
return;
}
@ -403,15 +414,14 @@ namespace FSPerfStats
}
if( drawDistance < userTargetDrawDistance )
{
gSavedSettings.setF32("RenderFarClip", drawDistance + 10.);
FSPerfStats::tunables.updateFarClip( drawDistance + 10. );
}
if( (target_frame_time_raw * 1.5) > tot_frame_time_raw &&
FSPerfStats::tunedAvatars == 0 &&
drawDistance >= userTargetDrawDistance)
{
// if everything else is "max" and we have 50% headroom let's knock the water quality up a notch at a time.
auto water = gSavedSettings.getS32("RenderReflectionDetail");
gSavedSettings.setS32("RenderReflectionDetail", water+1);
FSPerfStats::tunables.updateReflectionDetail( gSavedSettings.getS32("RenderReflectionDetail") + 1 );
}
}
updateSettingsFromRenderCostLimit();

View File

@ -74,7 +74,6 @@ namespace FSPerfStats
extern std::atomic<int64_t> tunedAvatars;
extern U32 targetFPS; // desired FPS
extern U64 renderAvatarMaxART_ns;
extern U32 fpsTuningStrategy;
extern U32 lastGlobalPrefChange;
extern std::mutex bufferToggleLock;
extern bool autoTune;
@ -116,6 +115,28 @@ namespace FSPerfStats
bool isHUD;
};
struct Tunables
{
static constexpr U32 Nothing{0};
static constexpr U32 NonImposters{1};
static constexpr U32 ReflectionDetail{2};
static constexpr U32 FarClip{4};
U32 tuningFlag{0};
U32 nonImposters;
S32 reflectionDetail;
F32 farClip;
void updateFarClip(F32 nv){farClip=nv; tuningFlag |= FarClip;};
void updateNonImposters(U32 nv){nonImposters=nv; tuningFlag |= NonImposters;};
void updateReflectionDetail(S32 nv){reflectionDetail=nv; tuningFlag |= ReflectionDetail;};
void applyUpdates();
void resetChanges(){tuningFlag=Nothing;};
};
extern Tunables tunables;
class StatsRecorder{
using Queue = moodycamel::BlockingConcurrentQueue<StatsRecord>;
public:

View File

@ -16,8 +16,9 @@ if [ -f "$CONFIG_FILE" ]; then
--password $PASSWORD \
--asc-provider $ASC_PROVIDER \
--file "$zip_file" 2>&1)
echo $res
requestUUID=$(echo $res | awk '/RequestUUID/ { print $NF; }')
echo "Apple Notarization RequestUUID: $requestUUID"
if [[ -n $requestUUID ]]; then

View File

@ -0,0 +1,47 @@
#!/bin/bash
SCRIPT_PATH=`readlink -f $0`
SCRIPT_PATH=`dirname $SCRIPT_PATH`
# All hope is lost if there is no lsb_release command
command -v lsb_release >/dev/null 2>/dev/null || exit 0
if [ `lsb_release -is` != "Ubuntu" ]
then
echo "Distribution is not Ubuntu, skipping AppImage creation"
exit 0
fi
set -e
cd $1
pushd packaged
wget -q https://github.com/AppImage/AppImages/raw/master/functions.sh -O ./functions.sh
. ./functions.sh
rm functions.sh
cp firestorm AppRun
cp ${SCRIPT_PATH}/firestorm.desktop firestorm.desktop
copy_deps
copy_deps
copy_deps
delete_blacklisted
# Now copy everything to ./lib. The viewer binaries got build with a rpath pointing to ./lib so all so will be magically found there.
#find ./usr/lib/ -type f -print0 | xargs -0 -Ifile cp file ./lib/
#find ./lib/x86_64-linux-gnu/ -type f -print0 | xargs -0 -Ifile cp file ./lib/
#rm -rf ./usr/lib/
#rm -rf ./lib/x86_64-linux-gnu/
find . -empty -type d -delete
popd
wget "https://github.com/AppImage/AppImageKit/releases/download/continuous/appimagetool-x86_64.AppImage"
chmod a+x appimagetool-x86_64.AppImage
./appimagetool-x86_64.AppImage --appimage-extract
rm appimagetool-x86_64.AppImage
ARCH=x86_64 squashfs-root/AppRun packaged

View File

@ -0,0 +1,8 @@
[Desktop Entry]
Type=Application
Name=Firestorm
Exec=firestorm
Comment=Client for virtual worlds
Icon=firestorm_icon
Categories=Development;
Terminal=true

View File

@ -1645,6 +1645,12 @@ bool LLAppViewer::doFrame()
{
// <FS:Beq> Perfstats collection Frame boundary
{
// and now adjust the visuals from previous frame.
if(FSPerfStats::autoTune && FSPerfStats::tunables.tuningFlag != FSPerfStats::Tunables::Nothing)
{
FSPerfStats::tunables.applyUpdates();
}
FSPerfStats::RecordSceneTime T (FSPerfStats::StatType_t::RENDER_FRAME);
LLEventPump& mainloop(LLEventPumps::instance().obtain("mainloop"));
@ -1702,7 +1708,7 @@ bool LLAppViewer::doFrame()
}
// Check if we need to temporarily enable rendering.
//F32 periodic_rendering = gSavedSettings.getF32("ForcePeriodicRenderingTime");
static LLCachedControl<F32> periodic_rendering(gSavedSettings, "ForcePeriodicRenderingTime");
static LLCachedControl<F32> periodic_rendering(gSavedSettings, "ForcePeriodicRenderingTime", -1.f);
if (periodic_rendering > F_APPROXIMATELY_ZERO && periodicRenderingTimer.getElapsedTimeF64() > periodic_rendering)
{
periodicRenderingTimer.reset();

View File

@ -42,16 +42,27 @@
#include "json/reader.h" // <FS:ND/> To parse manifest.json from pepperflash
#if LL_DBUS_ENABLED
# include "llappviewerlinux_api_dbus.h"
// regrettable hacks to give us better runtime compatibility with older systems inside llappviewerlinux_api.h:
#define llg_return_if_fail(COND) do{if (!(COND)) return;}while(0)
#undef g_return_if_fail
#define g_return_if_fail(COND) llg_return_if_fail(COND)
// The generated API
# include "llappviewerlinux_api.h"
#endif
#include <gio/gio.h>
#define VIEWERAPI_SERVICE "com.secondlife.ViewerAppAPIService"
#define VIEWERAPI_PATH "/com/secondlife/ViewerAppAPI"
#define VIEWERAPI_INTERFACE "com.secondlife.ViewerAppAPI"
static const char * DBUS_SERVER = "<node name=\"/com/secondlife/ViewerAppAPI\">\n"
" <interface name=\"com.secondlife.ViewerAppAPI\">\n"
" <annotation name=\"org.freedesktop.DBus.GLib.CSymbol\" value=\"viewer_app_api\"/>\n"
" <method name=\"GoSLURL\">\n"
" <annotation name=\"org.freedesktop.DBus.GLib.CSymbol\" value=\"dispatchSLURL\"/>\n"
" <arg type=\"s\" name=\"slurl\" direction=\"in\" />\n"
" </method>\n"
" </interface>\n"
"</node>";
typedef struct
{
GObject parent;
} ViewerAppAPI;
namespace
{
@ -127,10 +138,6 @@ bool LLAppViewerLinux::init()
// libraries likes to use glib functions; in short, do this here
// really early in app startup!
#if ( !defined(GLIB_MAJOR_VERSION) && !defined(GLIB_MINOR_VERSION) ) || ( GLIB_MAJOR_VERSION < 2 ) || ( GLIB_MAJOR_VERSION == 2 && GLIB_MINOR_VERSION < 32 )
if (!g_thread_supported ()) g_thread_init (NULL);
#endif
bool success = LLAppViewer::init();
#if LL_SEND_CRASH_REPORTS
@ -152,40 +159,17 @@ bool LLAppViewerLinux::restoreErrorTrap()
}
/////////////////////////////////////////
#if LL_DBUS_ENABLED
#if LL_GLIB
typedef struct
{
GObjectClass parent_class;
} ViewerAppAPIClass;
static void viewerappapi_init(ViewerAppAPI *server);
static void viewerappapi_class_init(ViewerAppAPIClass *klass);
///
// regrettable hacks to give us better runtime compatibility with older systems in general
static GType llg_type_register_static_simple_ONCE(GType parent_type,
const gchar *type_name,
guint class_size,
GClassInitFunc class_init,
guint instance_size,
GInstanceInitFunc instance_init,
GTypeFlags flags)
{
static GTypeInfo type_info;
memset(&type_info, 0, sizeof(type_info));
type_info.class_size = class_size;
type_info.class_init = class_init;
type_info.instance_size = instance_size;
type_info.instance_init = instance_init;
return g_type_register_static(parent_type, type_name, &type_info, flags);
}
#define llg_intern_static_string(S) (S)
#define g_intern_static_string(S) llg_intern_static_string(S)
#define g_type_register_static_simple(parent_type, type_name, class_size, class_init, instance_size, instance_init, flags) llg_type_register_static_simple_ONCE(parent_type, type_name, class_size, class_init, instance_size, instance_init, flags)
static void viewerappapi_init(ViewerAppAPI *server);
static void viewerappapi_class_init(ViewerAppAPIClass *klass);
G_DEFINE_TYPE(ViewerAppAPI, viewerappapi, G_TYPE_OBJECT);
@ -193,79 +177,71 @@ void viewerappapi_class_init(ViewerAppAPIClass *klass)
{
}
static bool dbus_server_init = false;
void viewerappapi_init(ViewerAppAPI *server)
static void dispatchSLURL(gchar const *slurl)
{
// Connect to the default DBUS, register our service/API.
LL_INFOS() << "Was asked to go to slurl: " << slurl << LL_ENDL;
if (!dbus_server_init)
{
GError *error = NULL;
server->connection = lldbus_g_bus_get(DBUS_BUS_SESSION, &error);
if (server->connection)
{
lldbus_g_object_type_install_info(viewerappapi_get_type(), &dbus_glib_viewerapp_object_info);
lldbus_g_connection_register_g_object(server->connection, VIEWERAPI_PATH, G_OBJECT(server));
DBusGProxy *serverproxy = lldbus_g_proxy_new_for_name(server->connection, DBUS_SERVICE_DBUS, DBUS_PATH_DBUS, DBUS_INTERFACE_DBUS);
guint request_name_ret_unused;
// akin to org_freedesktop_DBus_request_name
if (lldbus_g_proxy_call(serverproxy, "RequestName", &error, G_TYPE_STRING, VIEWERAPI_SERVICE, G_TYPE_UINT, 0, G_TYPE_INVALID, G_TYPE_UINT, &request_name_ret_unused, G_TYPE_INVALID))
{
// total success.
dbus_server_init = true;
}
else
{
LL_WARNS() << "Unable to register service name: " << error->message << LL_ENDL;
}
g_object_unref(serverproxy);
}
else
{
g_warning("Unable to connect to dbus: %s", error->message);
}
if (error)
g_error_free(error);
}
std::string url = slurl;
LLMediaCtrl* web = NULL;
const bool trusted_browser = false;
LLURLDispatcher::dispatch(url, "", web, trusted_browser);
}
// <FS:ND> FIRE-5417; The xml manifest for dbus claims success_rtn is a boolean, not a boolean array
//gboolean viewer_app_api_GoSLURL(ViewerAppAPI *obj, gchar *slurl, gboolean **success_rtn, GError **error)
gboolean viewer_app_api_GoSLURL(ViewerAppAPI *obj, gchar *slurl, gboolean *success_rtn, GError **error)
// </FS:ND>
static void DoMethodeCall (GDBusConnection *connection,
const gchar *sender,
const gchar *object_path,
const gchar *interface_name,
const gchar *method_name,
GVariant *parameters,
GDBusMethodInvocation *invocation,
gpointer user_data)
{
bool success = false;
LL_INFOS() << "DBUS message " << method_name << " from: " << sender << " interface: " << interface_name << LL_ENDL;
const gchar *slurl;
LL_INFOS() << "Was asked to go to slurl: " << slurl << LL_ENDL;
g_variant_get (parameters, "(&s)", &slurl);
dispatchSLURL(slurl);
}
std::string url = slurl;
LLMediaCtrl* web = NULL;
const bool trusted_browser = false;
if (LLURLDispatcher::dispatch(url, "", web, trusted_browser))
{
// bring window to foreground, as it has just been "launched" from a URL
// todo: hmm, how to get there from here?
//xxx->mWindow->bringToFront();
success = true;
}
GDBusNodeInfo *gBusNodeInfo = nullptr;
static const GDBusInterfaceVTable interface_vtable =
{
DoMethodeCall
};
static void busAcquired(GDBusConnection *connection, const gchar *name, gpointer user_data)
{
auto id = g_dbus_connection_register_object(connection,
VIEWERAPI_PATH,
gBusNodeInfo->interfaces[0],
&interface_vtable,
NULL, /* user_data */
NULL, /* user_data_free_func */
NULL); /* GError** */
g_assert (id > 0);
}
// <FS:ND> FIRE-5417; The xml manifest for dbus claims success_rtn is a boolean, not a boolean array
static void nameAcquired(GDBusConnection *connection, const gchar *name, gpointer user_data)
{
}
// *success_rtn = g_new (gboolean, 1);
// (*success_rtn)[0] = (gboolean)success;
static void nameLost(GDBusConnection *connection, const gchar *name, gpointer user_data)
{
*success_rtn = (gboolean)success;
}
void viewerappapi_init(ViewerAppAPI *server)
{
gBusNodeInfo = g_dbus_node_info_new_for_xml (DBUS_SERVER, NULL);
g_assert (gBusNodeInfo != NULL);
// </FS:ND>
auto owner_id = g_bus_own_name(G_BUS_TYPE_SESSION,
VIEWERAPI_SERVICE,
G_BUS_NAME_OWNER_FLAGS_NONE,
busAcquired,
nameAcquired,
nameLost,
NULL,
NULL);
return TRUE; // the invokation succeeded, even if the actual dispatch didn't.
}
///
@ -273,15 +249,6 @@ gboolean viewer_app_api_GoSLURL(ViewerAppAPI *obj, gchar *slurl, gboolean *succe
//virtual
bool LLAppViewerLinux::initSLURLHandler()
{
if (!grab_dbus_syms(DBUSGLIB_DYLIB_DEFAULT_NAME))
{
return false; // failed
}
#if ( !defined(GLIB_MAJOR_VERSION) && !defined(GLIB_MINOR_VERSION) ) || ( GLIB_MAJOR_VERSION < 2 ) || ( GLIB_MAJOR_VERSION == 2 && GLIB_MINOR_VERSION < 35 )
g_type_init();
#endif
//ViewerAppAPI *api_server = (ViewerAppAPI*)
g_object_new(viewerappapi_get_type(), NULL);
@ -291,51 +258,51 @@ bool LLAppViewerLinux::initSLURLHandler()
//virtual
bool LLAppViewerLinux::sendURLToOtherInstance(const std::string& url)
{
if (!grab_dbus_syms(DBUSGLIB_DYLIB_DEFAULT_NAME))
{
return false; // failed
}
bool success = false;
bool success = false;
DBusGConnection *bus;
GError *error = NULL;
auto *pBus = g_bus_get_sync(G_BUS_TYPE_SESSION, NULL, nullptr);
#if ( !defined(GLIB_MAJOR_VERSION) && !defined(GLIB_MINOR_VERSION) ) || ( GLIB_MAJOR_VERSION < 2 ) || ( GLIB_MAJOR_VERSION == 2 && GLIB_MINOR_VERSION < 35 )
g_type_init();
#endif
bus = lldbus_g_bus_get (DBUS_BUS_SESSION, &error);
if (bus)
{
gboolean rtn = FALSE;
DBusGProxy *remote_object =
lldbus_g_proxy_new_for_name(bus, VIEWERAPI_SERVICE, VIEWERAPI_PATH, VIEWERAPI_INTERFACE);
if( !pBus )
{
LL_WARNS() << "Getting dbus failed." << LL_ENDL;
return false;
}
if (lldbus_g_proxy_call(remote_object, "GoSLURL", &error,
G_TYPE_STRING, url.c_str(), G_TYPE_INVALID,
G_TYPE_BOOLEAN, &rtn, G_TYPE_INVALID))
{
success = rtn;
}
else
{
LL_INFOS() << "Call-out to other instance failed (perhaps not running): " << error->message << LL_ENDL;
}
auto pProxy = g_dbus_proxy_new_sync(pBus, G_DBUS_PROXY_FLAGS_NONE, nullptr,
VIEWERAPI_SERVICE, VIEWERAPI_PATH,
VIEWERAPI_INTERFACE, nullptr, nullptr);
g_object_unref(G_OBJECT(remote_object));
}
else
{
LL_WARNS() << "Couldn't connect to session bus: " << error->message << LL_ENDL;
}
if( !pProxy )
{
LL_WARNS() << "Cannot create new dbus proxy." << LL_ENDL;
g_object_unref( pBus );
return false;
}
if (error)
g_error_free(error);
return success;
auto *pArgs = g_variant_new( "(s)", url.c_str() );
if( !pArgs )
{
LL_WARNS() << "Cannot create new variant." << LL_ENDL;
g_object_unref( pBus );
return false;
}
auto pRes = g_dbus_proxy_call_sync(pProxy,
"GoSLURL",
pArgs,
G_DBUS_CALL_FLAGS_NONE,
-1, nullptr, nullptr);
if( pRes )
g_variant_unref( pRes );
g_object_unref( pProxy );
g_object_unref( pBus );
return true;
}
#else // LL_DBUS_ENABLED
#else // LL_GLIB
bool LLAppViewerLinux::initSLURLHandler()
{
return false; // not implemented without dbus
@ -344,7 +311,7 @@ bool LLAppViewerLinux::sendURLToOtherInstance(const std::string& url)
{
return false; // not implemented without dbus
}
#endif // LL_DBUS_ENABLED
#endif // LL_GLIB
void LLAppViewerLinux::initCrashReporting(bool reportFreeze)
{

View File

@ -27,17 +27,6 @@
#ifndef LL_LLAPPVIEWERLINUX_H
#define LL_LLAPPVIEWERLINUX_H
extern "C" {
# include <glib.h>
}
#if LL_DBUS_ENABLED
extern "C" {
# include <glib-object.h>
# include <dbus/dbus-glib.h>
}
#endif
#ifndef LL_LLAPPVIEWER_H
#include "llappviewer.h"
#endif
@ -70,26 +59,4 @@ protected:
virtual bool sendURLToOtherInstance(const std::string& url);
};
#if LL_DBUS_ENABLED
typedef struct
{
GObject parent;
DBusGConnection *connection;
} ViewerAppAPI;
extern "C" {
// <FS:ND> FIRE-5417; The xml manifest for dbus claims success_rtn is a boolean, not a boolean array
// gboolean viewer_app_api_GoSLURL(ViewerAppAPI *obj, gchar *slurl, gboolean **success_rtn, GError **error);
gboolean viewer_app_api_GoSLURL(ViewerAppAPI *obj, gchar *slurl, gboolean *success_rtn, GError **error);
// <FS:ND>
}
#define VIEWERAPI_SERVICE "com.secondlife.ViewerAppAPIService"
#define VIEWERAPI_PATH "/com/secondlife/ViewerAppAPI"
#define VIEWERAPI_INTERFACE "com.secondlife.ViewerAppAPI"
#endif // LL_DBUS_ENABLED
#endif // LL_LLAPPVIEWERLINUX_H

View File

@ -1,143 +0,0 @@
/* Generated by dbus-binding-tool; do not edit! */
/**
* $LicenseInfo:firstyear=2008&license=viewerlgpl$
* Second Life Viewer Source Code
* Copyright (C) 2010, Linden Research, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation;
* version 2.1 of the License only.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
* $/LicenseInfo$
*/
#ifndef __dbus_glib_marshal_viewerapp_MARSHAL_H__
#define __dbus_glib_marshal_viewerapp_MARSHAL_H__
#include <glib-object.h>
G_BEGIN_DECLS
#ifdef G_ENABLE_DEBUG
#define g_marshal_value_peek_boolean(v) g_value_get_boolean (v)
#define g_marshal_value_peek_char(v) g_value_get_char (v)
#define g_marshal_value_peek_uchar(v) g_value_get_uchar (v)
#define g_marshal_value_peek_int(v) g_value_get_int (v)
#define g_marshal_value_peek_uint(v) g_value_get_uint (v)
#define g_marshal_value_peek_long(v) g_value_get_long (v)
#define g_marshal_value_peek_ulong(v) g_value_get_ulong (v)
#define g_marshal_value_peek_int64(v) g_value_get_int64 (v)
#define g_marshal_value_peek_uint64(v) g_value_get_uint64 (v)
#define g_marshal_value_peek_enum(v) g_value_get_enum (v)
#define g_marshal_value_peek_flags(v) g_value_get_flags (v)
#define g_marshal_value_peek_float(v) g_value_get_float (v)
#define g_marshal_value_peek_double(v) g_value_get_double (v)
#define g_marshal_value_peek_string(v) (char*) g_value_get_string (v)
#define g_marshal_value_peek_param(v) g_value_get_param (v)
#define g_marshal_value_peek_boxed(v) g_value_get_boxed (v)
#define g_marshal_value_peek_pointer(v) g_value_get_pointer (v)
#define g_marshal_value_peek_object(v) g_value_get_object (v)
#else /* !G_ENABLE_DEBUG */
/* WARNING: This code accesses GValues directly, which is UNSUPPORTED API.
* Do not access GValues directly in your code. Instead, use the
* g_value_get_*() functions
*/
#define g_marshal_value_peek_boolean(v) (v)->data[0].v_int
#define g_marshal_value_peek_char(v) (v)->data[0].v_int
#define g_marshal_value_peek_uchar(v) (v)->data[0].v_uint
#define g_marshal_value_peek_int(v) (v)->data[0].v_int
#define g_marshal_value_peek_uint(v) (v)->data[0].v_uint
#define g_marshal_value_peek_long(v) (v)->data[0].v_long
#define g_marshal_value_peek_ulong(v) (v)->data[0].v_ulong
#define g_marshal_value_peek_int64(v) (v)->data[0].v_int64
#define g_marshal_value_peek_uint64(v) (v)->data[0].v_uint64
#define g_marshal_value_peek_enum(v) (v)->data[0].v_long
#define g_marshal_value_peek_flags(v) (v)->data[0].v_ulong
#define g_marshal_value_peek_float(v) (v)->data[0].v_float
#define g_marshal_value_peek_double(v) (v)->data[0].v_double
#define g_marshal_value_peek_string(v) (v)->data[0].v_pointer
#define g_marshal_value_peek_param(v) (v)->data[0].v_pointer
#define g_marshal_value_peek_boxed(v) (v)->data[0].v_pointer
#define g_marshal_value_peek_pointer(v) (v)->data[0].v_pointer
#define g_marshal_value_peek_object(v) (v)->data[0].v_pointer
#endif /* !G_ENABLE_DEBUG */
/* BOOLEAN:STRING,POINTER,POINTER (/tmp/dbus-binding-tool-c-marshallers.5XXD8T:1) */
extern void dbus_glib_marshal_viewerapp_BOOLEAN__STRING_POINTER_POINTER (GClosure *closure,
GValue *return_value,
guint n_param_values,
const GValue *param_values,
gpointer invocation_hint,
gpointer marshal_data);
void
dbus_glib_marshal_viewerapp_BOOLEAN__STRING_POINTER_POINTER (GClosure *closure,
GValue *return_value,
guint n_param_values,
const GValue *param_values,
gpointer invocation_hint,
gpointer marshal_data)
{
typedef gboolean (*GMarshalFunc_BOOLEAN__STRING_POINTER_POINTER) (gpointer data1,
gpointer arg_1,
gpointer arg_2,
gpointer arg_3,
gpointer data2);
register GMarshalFunc_BOOLEAN__STRING_POINTER_POINTER callback;
register GCClosure *cc = (GCClosure*) closure;
register gpointer data1, data2;
gboolean v_return;
g_return_if_fail (return_value != NULL);
g_return_if_fail (n_param_values == 4);
if (G_CCLOSURE_SWAP_DATA (closure))
{
data1 = closure->data;
data2 = g_value_peek_pointer (param_values + 0);
}
else
{
data1 = g_value_peek_pointer (param_values + 0);
data2 = closure->data;
}
callback = (GMarshalFunc_BOOLEAN__STRING_POINTER_POINTER) (marshal_data ? marshal_data : cc->callback);
v_return = callback (data1,
g_marshal_value_peek_string (param_values + 1),
g_marshal_value_peek_pointer (param_values + 2),
g_marshal_value_peek_pointer (param_values + 3),
data2);
g_value_set_boolean (return_value, v_return);
}
G_END_DECLS
#endif /* __dbus_glib_marshal_viewerapp_MARSHAL_H__ */
#include <dbus/dbus-glib.h>
static const DBusGMethodInfo dbus_glib_viewerapp_methods[] = {
{ (GCallback) viewer_app_api_GoSLURL, dbus_glib_marshal_viewerapp_BOOLEAN__STRING_POINTER_POINTER, 0 },
};
const DBusGObjectInfo dbus_glib_viewerapp_object_info = {
0,
dbus_glib_viewerapp_methods,
1,
"com.secondlife.ViewerAppAPI\0GoSLURL\0S\0slurl\0I\0s\0success_ret\0O\0F\0N\0b\0\0\0",
"\0",
"\0"
};

View File

@ -1,14 +0,0 @@
<?xml version="1.0" encoding="UTF-8" ?>
<!-- dbus-binding-tool -mode=glib-server llappviewerlinux_api.xml -prefix=viewerapp -output=llappviewerlinux_api.h -->
<node name="/com/secondlife/ViewerAppAPI">
<interface name="com.secondlife.ViewerAppAPI">
<annotation name="org.freedesktop.DBus.GLib.CSymbol" value="viewer_app_api"/>
<method name="GoSLURL">
<annotation name="org.freedesktop.DBus.GLib.CSymbol" value="viewer_app_api_GoSLURL"/>
<arg type="s" name="slurl" direction="in" />
<arg type="b" name="success_ret" direction="out" />
</method>
</interface>
</node>

View File

@ -1,126 +0,0 @@
/**
* @file llappviewerlinux_api_dbus.cpp
* @brief dynamic DBus symbol-grabbing code
*
* $LicenseInfo:firstyear=2008&license=viewerlgpl$
* Second Life Viewer Source Code
* Copyright (C) 2010, Linden Research, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation;
* version 2.1 of the License only.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
* $/LicenseInfo$
*/
#if LL_DBUS_ENABLED
#include "linden_common.h"
extern "C" {
#include <dbus/dbus-glib.h>
#include "apr_pools.h"
#include "apr_dso.h"
}
#define DEBUGMSG(...) do { LL_DEBUGS() << llformat(__VA_ARGS__) << LL_ENDL; } while(0)
#define INFOMSG(...) do { LL_INFOS() << llformat(__VA_ARGS__) << LL_ENDL; } while(0)
#define WARNMSG(...) do { LL_WARNS() << llformat(__VA_ARGS__) << LL_ENDL; } while(0)
#define LL_DBUS_SYM(REQUIRED, DBUSSYM, RTN, ...) RTN (*ll##DBUSSYM)(__VA_ARGS__) = NULL
#include "llappviewerlinux_api_dbus_syms_raw.inc"
#undef LL_DBUS_SYM
static bool sSymsGrabbed = false;
static apr_pool_t *sSymDBUSDSOMemoryPool = NULL;
static apr_dso_handle_t *sSymDBUSDSOHandleG = NULL;
bool grab_dbus_syms(std::string dbus_dso_name)
{
if (sSymsGrabbed)
{
// already have grabbed good syms
return TRUE;
}
bool sym_error = false;
bool rtn = false;
apr_status_t rv;
apr_dso_handle_t *sSymDBUSDSOHandle = NULL;
#define LL_DBUS_SYM(REQUIRED, DBUSSYM, RTN, ...) do{rv = apr_dso_sym((apr_dso_handle_sym_t*)&ll##DBUSSYM, sSymDBUSDSOHandle, #DBUSSYM); if (rv != APR_SUCCESS) {INFOMSG("Failed to grab symbol: %s", #DBUSSYM); if (REQUIRED) sym_error = true;} else DEBUGMSG("grabbed symbol: %s from %p", #DBUSSYM, (void*)ll##DBUSSYM);}while(0)
//attempt to load the shared library
apr_pool_create(&sSymDBUSDSOMemoryPool, NULL);
if ( APR_SUCCESS == (rv = apr_dso_load(&sSymDBUSDSOHandle,
dbus_dso_name.c_str(),
sSymDBUSDSOMemoryPool) ))
{
INFOMSG("Found DSO: %s", dbus_dso_name.c_str());
#include "llappviewerlinux_api_dbus_syms_raw.inc"
if ( sSymDBUSDSOHandle )
{
sSymDBUSDSOHandleG = sSymDBUSDSOHandle;
sSymDBUSDSOHandle = NULL;
}
rtn = !sym_error;
}
else
{
INFOMSG("Couldn't load DSO: %s", dbus_dso_name.c_str());
rtn = false; // failure
}
if (sym_error)
{
WARNMSG("Failed to find necessary symbols in DBUS-GLIB libraries.");
}
#undef LL_DBUS_SYM
sSymsGrabbed = rtn;
return rtn;
}
void ungrab_dbus_syms()
{
// should be safe to call regardless of whether we've
// actually grabbed syms.
if ( sSymDBUSDSOHandleG )
{
apr_dso_unload(sSymDBUSDSOHandleG);
sSymDBUSDSOHandleG = NULL;
}
if ( sSymDBUSDSOMemoryPool )
{
apr_pool_destroy(sSymDBUSDSOMemoryPool);
sSymDBUSDSOMemoryPool = NULL;
}
// NULL-out all of the symbols we'd grabbed
#define LL_DBUS_SYM(REQUIRED, DBUSSYM, RTN, ...) do{ll##DBUSSYM = NULL;}while(0)
#include "llappviewerlinux_api_dbus_syms_raw.inc"
#undef LL_DBUS_SYM
sSymsGrabbed = false;
}
#endif // LL_DBUS_ENABLED

View File

@ -1,44 +0,0 @@
/**
* @file llappviewerlinux_api_dbus.h
* @brief DBus-glib symbol handling
*
* $LicenseInfo:firstyear=2008&license=viewerlgpl$
* Second Life Viewer Source Code
* Copyright (C) 2010, Linden Research, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation;
* version 2.1 of the License only.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
* $/LicenseInfo$
*/
#include "linden_common.h"
#if LL_DBUS_ENABLED
extern "C" {
#include <dbus/dbus-glib.h>
}
#define DBUSGLIB_DYLIB_DEFAULT_NAME "libdbus-glib-1.so.2"
bool grab_dbus_syms(std::string dbus_dso_name);
void ungrab_dbus_syms();
#define LL_DBUS_SYM(REQUIRED, DBUSSYM, RTN, ...) extern RTN (*ll##DBUSSYM)(__VA_ARGS__)
#include "llappviewerlinux_api_dbus_syms_raw.inc"
#undef LL_DBUS_SYM
#endif // LL_DBUS_ENABLED

View File

@ -1,9 +0,0 @@
// required symbols to grab
LL_DBUS_SYM(true, dbus_g_bus_get, DBusGConnection*, DBusBusType, GError**);
LL_DBUS_SYM(true, dbus_g_proxy_new_for_name, DBusGProxy*, DBusGConnection*, const char *, const char*, const char*);
LL_DBUS_SYM(true, dbus_g_proxy_call, gboolean, DBusGProxy*, const char*, GError**, GType, ...);
LL_DBUS_SYM(true, dbus_g_object_type_install_info, void, GType, const DBusGObjectInfo*);
LL_DBUS_SYM(true, dbus_g_connection_register_g_object, void, DBusGConnection*, const char*, GObject*);
// optional symbols to grab

View File

@ -885,6 +885,7 @@ static void on_avatar_name_cache_notify(const LLUUID& agent_id,
}
else
{
args["ONLINE_STATUS"] = true;
LLNotificationsUI::LLNotificationManager::instance().onChat(chat, args);
}

View File

@ -41,6 +41,11 @@
# include "llfilepicker.h"
#endif
#ifdef LL_FLTK
#include "FL/Fl.H"
#include "FL/Fl_Native_File_Chooser.H"
#endif
//
// Globals
//
@ -193,32 +198,41 @@ LLDirPicker::LLDirPicker() :
mFileName(NULL),
mLocked(false)
{
#ifndef LL_FLTK
mFilePicker = new LLFilePicker();
#endif
reset();
}
LLDirPicker::~LLDirPicker()
{
#ifndef LL_FLTK
delete mFilePicker;
#endif
}
void LLDirPicker::reset()
{
#ifndef LL_FLTK
if (mFilePicker)
mFilePicker->reset();
mFilePicker->reset();
#else
mDir = "";
#endif
}
BOOL LLDirPicker::getDir(std::string* filename, bool blocking)
{
reset();
// if local file browsing is turned off, return without opening dialog
if ( check_local_file_access_enabled() == false )
{
return FALSE;
}
#ifndef LL_FLTK
#if !LL_MESA_HEADLESS
if (mFilePicker)
@ -237,15 +251,42 @@ BOOL LLDirPicker::getDir(std::string* filename, bool blocking)
#endif // !LL_MESA_HEADLESS
return FALSE;
#else
gViewerWindow->getWindow()->beforeDialog();
Fl_Native_File_Chooser flDlg;
flDlg.title(LLTrans::getString("choose_the_directory").c_str());
flDlg.type(Fl_Native_File_Chooser::BROWSE_DIRECTORY );
int res = flDlg.show();
gViewerWindow->getWindow()->afterDialog();
if( res == 0 )
{
char const *pDir = flDlg.filename(0);
if( pDir )
mDir = pDir;
}
else if( res == -1 )
{
LL_WARNS() << "FLTK failed: " << flDlg.errmsg() << LL_ENDL;
}
return !mDir.empty();
#endif
}
std::string LLDirPicker::getDirName()
{
#ifndef LL_FLTK
if (mFilePicker)
{
return mFilePicker->getFirstFile();
}
return "";
#else
return mDir;
#endif
}
#else // not implemented

View File

@ -79,9 +79,12 @@ private:
bool check_local_file_access_enabled();
#if LL_LINUX || LL_DARWIN
// On Linux we just implement LLDirPicker on top of LLFilePicker
// On Linux we just implement LLDirPicker on top of LLFilePicker
// <FS:ND> Seems like on OSX too ... Unless FLTK is used, then nope
#ifndef LL_FLTK
LLFilePicker *mFilePicker;
#endif
#endif
std::string* mFileName;

View File

@ -36,10 +36,16 @@
#include "llviewercontrol.h"
#include "llwindow.h" // beforeDialog()
#undef LL_GTK
#if LL_SDL
#include "llwindowsdl.h" // for some X/GTK utils to help with filepickers
#endif // LL_SDL
#ifdef LL_FLTK
#include "FL/Fl.H"
#include "FL/Fl_Native_File_Chooser.H"
#endif
#if LL_LINUX
#include "llhttpconstants.h" // file picker uses some of thes constants on Linux
#endif
@ -1566,12 +1572,243 @@ BOOL LLFilePicker::getMultipleOpenFiles( ELoadFilter filter, bool blocking)
return rtn;
}
#elif LL_FLTK
BOOL LLFilePicker::getSaveFile( ESaveFilter filter, const std::string& filename, bool blocking )
{
return openFileDialog( filter, blocking, eSaveFile );
}
BOOL LLFilePicker::getOpenFile( ELoadFilter filter, bool blocking )
{
return openFileDialog( filter, blocking, eOpenFile );
}
BOOL LLFilePicker::getMultipleOpenFiles( ELoadFilter filter, bool blocking)
{
return openFileDialog( filter, blocking, eOpenMultiple );
}
bool LLFilePicker::openFileDialog( int32_t filter, bool blocking, EType aType )
{
if ( check_local_file_access_enabled() == false )
return false;
gViewerWindow->getWindow()->beforeDialog();
reset();
Fl_Native_File_Chooser::Type flType = Fl_Native_File_Chooser::BROWSE_FILE;
if( aType == eOpenMultiple )
flType = Fl_Native_File_Chooser::BROWSE_MULTI_FILE;
else if( aType == eSaveFile )
flType = Fl_Native_File_Chooser::BROWSE_SAVE_FILE;
Fl_Native_File_Chooser flDlg;
std::string file_dialog_title;
std::string file_dialog_filter;
if (aType == EType::eSaveFile)
{
std::string file_type("all_files");
switch ((ESaveFilter) filter)
{
case FFSAVE_ALL:
break;
case FFSAVE_TGA:
file_type = "targa_image_files";
file_dialog_filter = "*.tga";
break;
case FFSAVE_BMP:
file_type = "bitmap_image_files";
file_dialog_filter = "*.bmp";
break;
case FFSAVE_AVI:
file_type = "avi_movie_file";
file_dialog_filter = "*.avi";
break;
case FFSAVE_ANIM:
file_type = "xaf_animation_file";
file_dialog_filter = "*.xaf";
break;
case FFSAVE_XML:
file_type = "xml_file";
file_dialog_filter = "*.xml";
break;
case FFSAVE_COLLADA:
file_type = "collada_files";
file_dialog_filter = "*.dae";
break;
case FFSAVE_RAW:
file_type = "raw_file";
file_dialog_filter = "*.raw";
break;
case FFSAVE_J2C:
file_type = "compressed_image_files";
file_dialog_filter = "*.j2c";
break;
case FFSAVE_PNG:
file_type = "png_image_files";
file_dialog_filter = "*.png";
break;
case FFSAVE_JPEG:
file_type = "jpeg_image_files";
file_dialog_filter = "*.{jpg,jpeg}";
break;
case FFSAVE_SCRIPT:
file_type = "script_files";
file_dialog_filter = "*.lsl";
break;
case FFSAVE_TGAPNG:
file_type = "save_texture_image_files";
file_dialog_filter = "*.{tga,png}";
break;
case FFSAVE_WAV:
file_type = "sound_files";
file_dialog_filter = "*.wav";
break;
// Firestorm additions
case FFSAVE_BEAM:
file_type = "xml_file";
file_dialog_filter = "*.xml";
break;
case FFSAVE_EXPORT:
file_type = "backup_files";
file_dialog_filter = "*.oxp";
break;
case FFSAVE_CSV:
file_type = "csv_files";
file_dialog_filter = "*.csv";
break;
#ifdef _CORY_TESTING
case FFSAVE_GEOMETRY:
// no file type translation for this, so using the default "all_files" for now
file_dialog_filter = "*.slg";
break;
#endif
}
// can't say I like this combining of verb+type, it might not work too well in all languages -Zi
file_dialog_title = LLTrans::getString("save_file_verb") + " " + LLTrans::getString(file_type);
file_dialog_filter = LLTrans::getString(file_type) + " \t" + file_dialog_filter;
}
else
{
std::string file_type("all_files");
switch ((ELoadFilter) filter)
{
case FFLOAD_ALL:
break;
case FFLOAD_WAV:
file_type = "sound_files";
file_dialog_filter = "*.wav";
break;
case FFLOAD_IMAGE:
file_type = "image_files";
file_dialog_filter = "*.{tga,bmp,jpg,jpeg,png}";
break;
case FFLOAD_ANIM:
file_type = "animation_files";
file_dialog_filter = "*.{bvh,anim}";
break;
case FFLOAD_XML:
file_type = "xml_file";
file_dialog_filter = "*.xml";
break;
case FFLOAD_SLOBJECT:
file_type = "xml_file";
file_dialog_filter = "*.slobject";
break;
case FFLOAD_RAW:
file_type = "raw_file";
file_dialog_filter = "*.raw";
break;
case FFLOAD_MODEL:
case FFLOAD_COLLADA:
file_type = "collada_files";
file_dialog_filter = "*.dae";
break;
case FFLOAD_SCRIPT:
file_type = "script_files";
file_dialog_filter = "*.lsl";
break;
case FFLOAD_DICTIONARY:
file_type = "dictionary_files";
file_dialog_filter = "*.{dic,xcu}";
break;
case FFLOAD_DIRECTORY:
file_type = "choose_the_directory";
break;
case FFLOAD_EXE:
file_type = "executable_files";
break;
// Firestorm additions
case FFLOAD_IMPORT:
file_type = "backup_files";
file_dialog_filter = "*.oxp";
break;
#ifdef _CORY_TESTING
case FFLOAD_GEOMETRY:
// no file type translation for this, so using the default "all_files" for now
file_dialog_filter = "*.slg";
break;
#endif
}
if (aType == EType::eOpenMultiple)
{
file_dialog_title = LLTrans::getString("load_files");
}
else
{
// can't say I like this combining of verb+type, it might not work too well in all languages -Zi
file_dialog_title = LLTrans::getString("load_file_verb") + " " + LLTrans::getString(file_type);
file_dialog_filter = LLTrans::getString(file_type) + " \t" + file_dialog_filter;
}
}
flDlg.title(file_dialog_title.c_str());
flDlg.type(flType);
if (!file_dialog_filter.empty())
{
flDlg.filter(file_dialog_filter.c_str());
}
int res = flDlg.show();
gViewerWindow->getWindow()->afterDialog();
if( res == 0 )
{
int32_t count = flDlg.count();
if( count < 0 )
count = 0;
for( int32_t i = 0; i < count; ++i )
{
char const *pFile = flDlg.filename(i);
if( pFile && strlen(pFile) > 0 )
mFiles.push_back( pFile );
}
}
else if( res == -1 )
{
LL_WARNS() << "FLTK failed: " << flDlg.errmsg() << LL_ENDL;
}
return mFiles.empty()?FALSE:TRUE;
}
# else // LL_GTK
// Hacky stubs designed to facilitate fake getSaveFile and getOpenFile with
// static results, when we don't have a real filepicker.
BOOL LLFilePicker::getSaveFile( ESaveFilter filter, const std::string& filename )
BOOL LLFilePicker::getSaveFile( ESaveFilter filter, const std::string& filename, bool blocking )
{
// if local file browsing is turned off, return without opening dialog
// (Even though this is a stub, I think we still should not return anything at all)
@ -1634,7 +1871,7 @@ BOOL LLFilePicker::getMultipleOpenFiles( ELoadFilter filter, bool blocking)
#else // not implemented
BOOL LLFilePicker::getSaveFile( ESaveFilter filter, const std::string& filename )
BOOL LLFilePicker::getSaveFile( ESaveFilter filter, const std::string& filename, bool blockin )
{
reset();
return FALSE;

View File

@ -33,6 +33,12 @@
#ifndef LL_LLFILEPICKER_H
#define LL_LLFILEPICKER_H
#if LL_FLTK
#if LL_GTK
#undef LL_GTK
#endif
#endif
#include "stdtypes.h"
#if LL_DARWIN
@ -58,12 +64,13 @@ extern "C" {
// mostly for Linux, possible on others
#if LL_GTK
# include "gtk/gtk.h"
#error "Direct use of GTK is deprecated"
#endif // LL_GTK
}
class LLFilePicker
{
#ifdef LL_GTK
#if LL_GTK
friend class LLDirPicker;
friend void chooser_responder(GtkWidget *, gint, gpointer);
#endif // LL_GTK
@ -187,7 +194,14 @@ private:
// we also remember the extension of the last added file.
std::string mCurrentExtension;
#endif
#if LL_FLTK
enum EType
{
eSaveFile, eOpenFile, eOpenMultiple
};
bool openFileDialog( int32_t filter, bool blocking, EType aType );
#endif
std::vector<std::string> mFiles;
S32 mCurrentFile;
bool mLocked;

View File

@ -569,7 +569,7 @@ void LLFloaterIMNearbyChatHandler::processChat(const LLChat& chat_msg,
RlvUtil::filterLocation(tmp_chat.mText);
tmp_chat.mRlvLocFiltered = TRUE;
}
if ( (!RlvActions::canShowName(RlvActions::SNC_DEFAULT)) && (!tmp_chat.mRlvNamesFiltered) && (CHAT_SOURCE_AGENT != tmp_chat.mSourceType) )
if ( (!RlvActions::canShowName(RlvActions::SNC_DEFAULT)) && (!tmp_chat.mRlvNamesFiltered) && (CHAT_SOURCE_AGENT != tmp_chat.mSourceType) && (!args.has("ONLINE_STATUS") || !args["ONLINE_STATUS"].asBoolean()) )
{
RlvUtil::filterNames(tmp_chat.mText);
tmp_chat.mRlvNamesFiltered = TRUE;

View File

@ -3139,6 +3139,16 @@ void LLFloaterPreference::updateUISoundsControls()
getChild<LLComboBox>("PlayModeUISndNewIncomingGroupIMSession")->setValue((int)gSavedSettings.getU32("PlayModeUISndNewIncomingGroupIMSession")); // 0, 1, 2, 3. Shared with Chat > Notifications > "When receiving Group Instant Messages"
getChild<LLComboBox>("PlayModeUISndNewIncomingConfIMSession")->setValue((int)gSavedSettings.getU32("PlayModeUISndNewIncomingConfIMSession")); // 0, 1, 2, 3. Shared with Chat > Notifications > "When receiving AdHoc Instant Messages"
#ifdef OPENSIM
// <FS:Beq> OpenSim has option to not attenuate nearby local voice by distance
auto earPosGroup = findChild<LLRadioGroup>("ear_location");
if (earPosGroup)
{
// It seems there is no better way to do this than with magic numbers short of importing the enums in vivoxvoice (which aren't necessarily the same thing).
// Index 2 here is the opensim only option to hear nearby chat without attenuation.
constexpr int hearNearbyVoiceFullVolume{2};
earPosGroup->setIndexEnabled(hearNearbyVoiceFullVolume, LLGridManager::instance().isInOpenSim());
}
// <FS:Beq>
getChild<LLTextBox>("textFSRestartOpenSim")->setVisible(TRUE);
getChild<LLLineEditor>("UISndRestartOpenSim")->setVisible(TRUE);
getChild<LLButton>("Prev_UISndRestartOpenSim")->setVisible(TRUE);

View File

@ -334,15 +334,15 @@ BOOL LLFloaterTools::postBuild()
sShowObjectCost = gSavedSettings.getBOOL("ShowObjectRenderingCost");
// <FS:KC> Added back more/less button
LLButton* btnExpand = getChild<LLButton>("btnExpand");
LLButton* btnExpand = findChild<LLButton>("btnExpand");
if (btnExpand && mTab)
{
mExpandedHeight = getRect().getHeight();
mCollapsedHeight = mExpandedHeight - mTab->getRect().getHeight() + btnExpand->getRect().getHeight();
if(!gSavedSettings.getBOOL("FSToolboxExpanded"))
if (!gSavedSettings.getBOOL("FSToolboxExpanded"))
{
mTab->setVisible(FALSE);
reshape( getRect().getWidth(), mCollapsedHeight);
reshape(getRect().getWidth(), mCollapsedHeight);
btnExpand->setImageOverlay("Arrow_Down", btnExpand->getImageOverlayHAlign());
}
}

View File

@ -1112,11 +1112,7 @@ void handleRenderAvatarMaxARTChanged(const LLSD& newValue)
{
FSPerfStats::StatsRecorder::updateRenderCostLimitFromSettings();
}
void handleFPSTuningStrategyChanged(const LLSD& newValue)
{
const auto newval = gSavedSettings.getU32("FSTuningFPSStrategy");
FSPerfStats::fpsTuningStrategy = newval;
}
void handlePerformanceStatsEnabledChanged(const LLSD& newValue)
{
const auto newval = gSavedSettings.getBOOL("FSPerfStatsCaptureEnabled");
@ -1383,7 +1379,6 @@ void settings_setup_listeners()
gSavedSettings.getControl("FSTargetFPS")->getSignal()->connect(boost::bind(&handleTargetFPSChanged, _2));
gSavedSettings.getControl("FSAutoTuneFPS")->getSignal()->connect(boost::bind(&handleAutoTuneFPSChanged, _2));
gSavedSettings.getControl("FSRenderAvatarMaxART")->getSignal()->connect(boost::bind(&handleRenderAvatarMaxARTChanged, _2));
gSavedSettings.getControl("FSTuningFPSStrategy")->getSignal()->connect(boost::bind(&handleFPSTuningStrategyChanged, _2));
gSavedSettings.getControl("FSPerfStatsCaptureEnabled")->getSignal()->connect(boost::bind(&handlePerformanceStatsEnabledChanged, _2));
// </FS:Beq>
}

View File

@ -6839,7 +6839,7 @@ void mean_name_callback(const LLUUID &id, const LLAvatarName& av_name)
LLMeanCollisionData *mcd = *iter;
if (mcd->mPerp == id)
{
mcd->mFullName = av_name.getUserName();
mcd->mFullName = gRlvHandler.hasBehaviour(RLV_BHVR_SHOWNAMES) ? RlvStrings::getAnonym(av_name) : av_name.getUserName();
}
}
// <FS:Ansariel> Instant bump list floater update
@ -6886,7 +6886,14 @@ void process_mean_collision_alert_message(LLMessageSystem *msgsystem, void **use
{
std::string action;
LLStringUtil::format_map_t args;
args["NAME"] = llformat("secondlife:///app/agent/%s/inspect", perp.asString().c_str());
if (!gRlvHandler.hasBehaviour(RLV_BHVR_SHOWNAMES))
{
args["NAME"] = llformat("secondlife:///app/agent/%s/inspect", perp.asString().c_str());
}
else
{
args["NAME"] = llformat("secondlife:///app/agent/%s/rlvanonym", perp.asString().c_str());
}
switch (type)
{
@ -6920,10 +6927,10 @@ void process_mean_collision_alert_message(LLMessageSystem *msgsystem, void **use
LLMessageSystem* msgs = gMessageSystem;
msgs->newMessage(_PREHASH_ScriptDialogReply);
msgs->nextBlock(_PREHASH_AgentData);
msgs->addUUID(_PREHASH_AgentID, gAgent.getID());
msgs->addUUID(_PREHASH_SessionID, gAgent.getSessionID());
msgs->addUUID(_PREHASH_AgentID, gAgentID);
msgs->addUUID(_PREHASH_SessionID, gAgentSessionID);
msgs->nextBlock(_PREHASH_Data);
msgs->addUUID(_PREHASH_ObjectID, gAgent.getID());
msgs->addUUID(_PREHASH_ObjectID, gAgentID);
msgs->addS32(_PREHASH_ChatChannel, gSavedSettings.getS32("FSReportCollisionMessagesChannel"));
msgs->addS32(_PREHASH_ButtonIndex, 1);
msgs->addString(_PREHASH_ButtonLabel, collision_data.c_str());

View File

@ -614,7 +614,8 @@ void LLViewerObjectList::processObjectUpdate(LLMessageSystem *mesgsys,
if(update_cache)
{
objectp = regionp->updateCacheEntry(local_id, objectp, update_type);
//update object cache if the object receives a full-update or terse update
objectp = regionp->updateCacheEntry(local_id, objectp);
}
// This looks like it will break if the local_id of the object doesn't change

View File

@ -1862,13 +1862,8 @@ LLViewerObject* LLViewerRegion::addNewObject(LLVOCacheEntry* entry)
//update object cache if the object receives a full-update or terse update
//update_type == EObjectUpdateType::OUT_TERSE_IMPROVED or EObjectUpdateType::OUT_FULL
LLViewerObject* LLViewerRegion::updateCacheEntry(U32 local_id, LLViewerObject* objectp, U32 update_type)
LLViewerObject* LLViewerRegion::updateCacheEntry(U32 local_id, LLViewerObject* objectp)
{
if(objectp && update_type != (U32)OUT_TERSE_IMPROVED)
{
return objectp; //no need to access cache
}
LLVOCacheEntry* entry = getCacheEntry(local_id);
if (!entry)
{
@ -1880,11 +1875,8 @@ LLViewerObject* LLViewerRegion::updateCacheEntry(U32 local_id, LLViewerObject* o
objectp = addNewObject(entry);
}
//remove from cache if terse update
if(update_type == (U32)OUT_TERSE_IMPROVED)
{
killCacheEntry(entry, true);
}
//remove from cache.
killCacheEntry(entry, true);
return objectp;
}

View File

@ -380,7 +380,7 @@ public:
void requestCacheMisses();
void addCacheMissFull(const U32 local_id);
//update object cache if the object receives a full-update or terse update
LLViewerObject* updateCacheEntry(U32 local_id, LLViewerObject* objectp, U32 update_type);
LLViewerObject* updateCacheEntry(U32 local_id, LLViewerObject* objectp);
void findOrphans(U32 parent_id);
void clearCachedVisibleObjects();
void dumpCache();

View File

@ -3397,17 +3397,31 @@ void LLVivoxVoiceClient::sendPositionAndVolumeUpdate(void)
earVelocity = mAvatarVelocity;
earRot = mCameraRot;
break;
// <FS:Beq> reimplement hear voice equally
case earLocSpeaker:
// we leave EarPos/Vel/Rot as empty
LL_DEBUGS("Voice") << "EarLoc Speaker in use" << LL_ENDL;
break;
// </FS:Beq>
}
// <FS:Beq> reimplement hear voice equally
if(mEarLocation != earLocSpeaker)
{
// for all spatial sources we need to do the transform
// </FS:Beq>
l = earRot.getLeftRow();
u = earRot.getUpRow();
a = earRot.getFwdRow();
pos = earPosition;
vel = earVelocity;
oldSDKTransform(l, u, a, pos, vel);
// <FS:Beq> reimplement hear voice equally
}
// </FS:Beq>
if (mHidden)
{

View File

@ -803,6 +803,7 @@ private:
{
earLocCamera = 0, // ear at camera
earLocAvatar, // ear at avatar
earLocSpeaker, // <FS:Beq> re-add equal voice based loosely on original patch from Tigh MacFanatic
earLocMixed // ear at avatar location/camera direction
};

View File

@ -48,7 +48,7 @@
<combo_box.item label="Nur Avatar-Einstellungen" name="av_only" />
<combo_box.item label="Avatar und Szenerie" name="av_and_scene" />
</combo_box>
<spinner name="target_fps" tooltip="Ziel-FPS - Der Viewer wird automatisch versuchen, die gewünschte FPS durch Anpassung der Einstellungen zu erreichen." />
<spinner name="target_fps" tool_tip="Ziel-FPS - Der Viewer wird automatisch versuchen, die gewünschte FPS durch Anpassung der Einstellungen zu erreichen." />
</panel>
</panel>
<panel name="panel_performance_main">

View File

@ -233,6 +233,7 @@
<check_box label="Zeige Toasts im Vordergrund" name="FSShowToastsInFront"/>
<check_box label="Neue Regions-Neustart-Meldung verwenden" name="FSUseNewRegionRestartNotification"/>
<check_box label="Bei Regions-Neustart-Meldung Bildschirm nicht wackeln" name="FSNoScreenShakeOnRegionRestart"/>
<check_box label="Regions-Neustart-Meldung an Kanal senden:" width="265" name="FSReportRegionRestartToChat" />
</panel>
<!--Font-->
<panel label="Schrift" name="UI-font-tab">

View File

@ -10,8 +10,8 @@
Maustaste 5
</panel.string>
<tab_container label="Firestorm Prefs" name="tabs">
<!-- Sounds -->
<panel label="Klänge" name="Media Sounds Panel">
<!-- Sounds -->
<panel label="Klänge" name="Media Sounds Panel">
<slider label="Master-Lautstärke" name="System Volume"/>
<check_box name="mute_when_minimized" label="Stummschalten, wenn minimiert"/>
<slider label="Schaltflächen" name="UI Volume"/>
@ -57,7 +57,7 @@
</panel>
</panel>
<!-- Media -->
<panel label="Medien" name="Media Media Panel">
<text width="190" name="media_autoplay_label">
@ -72,23 +72,23 @@
<check_box label="Medien, die an andere Avatare angehängt sind, wiedergeben." name="media_show_on_others_btn" tool_tip="Diese Option deaktivieren, um Medien für andere Avataren, die sich in der Nähe befinden, auszublenden."/>
<check_box name="media_filter" tool_tip="Aktiviert den Medienfilter, der abhängig der Medien-URL die Wiedergabe erlaubt oder verbietet." label="Medienfilter aktivieren (erhöhte Sicherheit)"/>
<button label="Listen bearbeiten..." name="edit_media_lists_button"/>
<text name="Media Rolloff">
Lautstärkeabfall-Distanz für Medien-Quellen:
</text>
<slider label="Wird leiser ab:" name="MediaRollOffMin" tool_tip="Minimale Distanz von der Soundquelle, ab der die Lautstärke abzufallen beginnt."/>
<text name="MinMeters">
Meter
</text>
<slider label="Wird lauter ab:" name="MediaRollOffMax" tool_tip="Maximale Distanz von der Soundquelle, ab der sie stummgeschaltet wird."/>
<text name="MaxMeters">
Meter
</text>
</panel>
<text name="Media Rolloff">
Lautstärkeabfall-Distanz für Medien-Quellen:
</text>
<slider label="Wird leiser ab:" name="MediaRollOffMin" tool_tip="Minimale Distanz von der Soundquelle, ab der die Lautstärke abzufallen beginnt."/>
<text name="MinMeters">
Meter
</text>
<slider label="Wird lauter ab:" name="MediaRollOffMax" tool_tip="Maximale Distanz von der Soundquelle, ab der sie stummgeschaltet wird."/>
<text name="MaxMeters">
Meter
</text>
</panel>
<!-- Music -->
<panel label="Musik" name="Media Music Panel">
<check_box label="Automatische Audio-Wiedergabe zulassen" name="audio_auto_play_btn" tool_tip="Hier aktivieren, um Audio-Streams automatisch wiederzugeben."/>
<check_box name="FSFadeAudioStream" tool_tip="Aktiviert Fading, wenn sich der Parzellen-Audiostream ändert" label="Parzellen-Audiostream-Fading aktivieren:"/>
<check_box name="FSFadeAudioStream" tool_tip="Aktiviert Fading, wenn sich der Parzellen-Audiostream ändert" label="Parzellen-Audiostream-Fading aktivieren:"/>
<slider label="Einblenden:" width="270" label_width="70" name="FSAudioMusicFadeIn" tool_tip="Einblenddauer für Parzellen-Audiostream."/>
<text left_delta="275" name="FSAudioMusicFadeInSeconds">
Sekunden
@ -105,8 +105,8 @@
<radio_item label="Toasts" name="radio_toasts"/>
<radio_item label="Chat in der Nähe" name="radio_chat"/>
</radio_group>
<check_box name="StreamMetadataAnnounceToChat" label="Stream-Titel an diesen Kanal senden:" width="230"/>
</panel>
<check_box name="StreamMetadataAnnounceToChat" label="Stream-Titel an diesen Kanal senden:" width="230"/>
</panel>
<!-- Voice -->
<panel label="Voice-Chat" name="Media Voice tab">
@ -116,6 +116,7 @@
<radio_group name="ear_location">
<radio_item label="Voice-Chat von Kameraposition aus hören" name="0"/>
<radio_item label="Voice-Chat von Avatarposition aus hören" name="1"/>
<radio_item label="Voice-Chat in der Nähe in gleicher Lautstärke hören (nur OpenSim)" name="2"/>
</radio_group>
<check_box label="Avatarlippen beim Sprechen bewegen" name="enable_lip_sync"/>
<check_box label="Zeige Voice-Indikator über Avataren" name="FSShowVoiceVisualizer" tool_tip="Wenn diese Option aktiviert ist, wird der Voice-Indikator (weißer Punkt) über Avataren angezeigt."/>
@ -153,7 +154,7 @@
</text>
</panel>
</panel>
<!-- UI Sounds 1 -->
<panel label="UI-Klänge 1" name="UI Sounds tab 1">
<text name="textFSExplanation_tab1">
@ -182,7 +183,7 @@ Der jeweilige Standardwert wird im Hovertip des UUID-Feldes angezeigt.
<check_box label="Abspielen" name="PlayModeUISndClick"/>
<text tool_tip="UUID des Klangs beim Loslassen eines Mausknopfs." name="textFSClickRelease">
Loslassen Mausknopf:
Loslassen Mausknopf:
</text>
<button label="V" name="Prev_UISndClickRelease" tool_tip="Vorschau zu diesem Klang."/>
<button label="S" name="Def_UISndClickRelease" tool_tip="Auf Standardwert zurücksetzen."/>
@ -217,7 +218,7 @@ Der jeweilige Standardwert wird im Hovertip des UUID-Feldes angezeigt.
<check_box label="Abspielen" name="PlayModeUISndMoneyChangeUp"/>
<text tool_tip="UUID des Klangs bei eingehenden Instant Messages. Diese Einstellung ist gekoppelt mit Chat &gt; Benachrichtigungen &gt; 'Beim Eintreffen von Instant Messages:'." name="textFSNewIncomingIMSession">
Eingeh. Instant Messages:
Eingeh. Instant Messages:
</text>
<button label="V" name="Prev_UISndNewIncomingIMSession" tool_tip="Vorschau zu diesem Klang."/>
<button label="S" name="Def_UISndNewIncomingIMSession" tool_tip="Auf Standardwert zurücksetzen."/>
@ -229,7 +230,7 @@ Der jeweilige Standardwert wird im Hovertip des UUID-Feldes angezeigt.
</combo_box>
<text tool_tip="UUID des Klangs bei eingehenden Gruppenchats. Diese Einstellung ist gekoppelt mit Chat &gt; Benachrichtigungen &gt; 'Beim Eintreffen von Gruppenchats:'." name="textFSNewGroupIncomingIMSession">
Eingeh. Gruppenchats:
Eingeh. Gruppenchats:
</text>
<button label="V" name="Prev_UISndNewIncomingGroupIMSession" tool_tip="Vorschau zu diesem Klang."/>
<button label="S" name="Def_UISndNewIncomingGroupIMSession" tool_tip="Auf Standardwert zurücksetzen."/>
@ -274,7 +275,7 @@ Der jeweilige Standardwert wird im Hovertip des UUID-Feldes angezeigt.
<check_box label="Abspielen" name="PlayModeUISndObjectDelete"/>
<text tool_tip="UUID des Klangs beim Rezzen eines Objektes." name="textFSObjectRezIn">
Objekt rezzen:
Objekt rezzen:
</text>
<button label="V" name="Prev_UISndObjectRezIn" tool_tip="Vorschau zu diesem Klang."/>
<button label="S" name="Def_UISndObjectRezIn" tool_tip="Auf Standardwert zurücksetzen."/>
@ -288,7 +289,7 @@ Der jeweilige Standardwert wird im Hovertip des UUID-Feldes angezeigt.
<check_box label="Abspielen" name="PlayModeUISndObjectRezOut"/>
<text tool_tip="UUID des Klangs beim Erzeugen eines Fotos. Diese Einstellung ist gekoppelt an die Option 'Fotos leise speichern' im 'Erweitert'-Menü." name="textFSSnapshot">
Erstellen Schnappschuß:
Erstellen Schnappschuß:
</text>
<button label="V" name="Prev_UISndSnapshot" tool_tip="Vorschau zu diesem Klang."/>
<button label="S" name="Def_UISndSnapshot" tool_tip="Auf Standardwert zurücksetzen."/>
@ -311,14 +312,14 @@ Der jeweilige Standardwert wird im Hovertip des UUID-Feldes angezeigt.
</text>
<text tool_tip="UUID des Klangs beim Öffnen des Pie-Menüs." name="textFSPieMenuAppear">
Öffnen Pie-Menü:
Öffnen Pie-Menü:
</text>
<button label="V" name="Prev_UISndPieMenuAppear" tool_tip="Vorschau zu diesem Klang."/>
<button label="S" name="Def_UISndPieMenuAppear" tool_tip="Auf Standardwert zurücksetzen."/>
<check_box label="Abspielen" name="PlayModeUISndPieMenuAppear"/>
<text tool_tip="UUID des Klangs beim Schließen des Pie-Menüs." name="textFSPieMenuHide">
Schließen Pie-Menü:
Schließen Pie-Menü:
</text>
<button label="V" name="Prev_UISndPieMenuHide" tool_tip="Vorschau zu diesem Klang."/>
<button label="S" name="Def_UISndPieMenuHide" tool_tip="Auf Standardwert zurücksetzen."/>
@ -435,7 +436,7 @@ Der jeweilige Standardwert wird im Hovertip des UUID-Feldes angezeigt.
<button label="V" name="Prev_UISndTeleportOffer" tool_tip="Vorschau zu diesem Klang."/>
<button label="S" name="Def_UISndTeleportOffer" tool_tip="Auf Standardwert zurücksetzen."/>
<check_box label="Abspielen" name="PlayModeUISndTeleportOffer"/>
</panel>
</panel>
<!-- UI Sounds 3 -->
<panel label="UI-Klänge 3" name="UI Sounds tab 3">
@ -520,7 +521,6 @@ Der jeweilige Standardwert wird im Hovertip des UUID-Feldes angezeigt.
<button label="V" name="Prev_UISndRestartOpenSim" tool_tip="Vorschau zu diesem Klang."/>
<button label="S" name="Def_UISndRestartOpenSim" tool_tip="Auf Standardwert zurücksetzen."/>
<check_box label="Abspielen" name="PlayModeUISndRestartOpenSim"/>
</panel>
</panel>
</tab_container>
</panel>

View File

@ -1448,6 +1448,12 @@ https://www.firestormviewer.org/support für Hilfe zum Lösen des Problems.
<string name="csv_files">
Komma-separierte Werte
</string>
<string name="jpeg_image_files">
JPEG-Bilder
</string>
<string name="executable_files">
Ausführbare Programmdateien
</string>
<string name="recompile_script_verb">
Rekompilieren
</string>

View File

@ -7,8 +7,6 @@
save_rect="true"
title="Improve Graphics Speed (Experimental)"
can_resize="false"
min_height="652"
max_height="652"
min_width="580"
width="580">
<floater.string name="frame_stats">
@ -172,7 +170,6 @@ Target [FPSTARGET] fps
<combo_box
follows="top|right"
font="SansSerif"
text_color="White"
height="20"
layout="topleft"
left_pad="5"
@ -193,7 +190,7 @@ Target [FPSTARGET] fps
name="target_fps"
control_name="FSTargetFPS"
font="SansSerifLarge"
tooltip="Target FPS - The desired FPS level. The viewer will attempt to achieve this by adjusting your graphics settings."
tool_tip="Target FPS - The desired FPS level. The viewer will attempt to achieve this by adjusting your graphics settings."
layout="topleft"
follows="right|top"
right="-55"

View File

@ -75,8 +75,7 @@ Distant Avatars
name="FSAutoTuneImpostorByDistEnabled"
tool_tip="When enabled the viewer will adjust the MaxNonImpostors setting to limit fully rendered avatars to those within the defined radius."
top_delta="0"
width="190"
label_wrap="true" />
width="190" />
<spinner
control_name="FSAutoTuneImpostorFarAwayDistance"
height="20"
@ -200,8 +199,7 @@ left_pad="40"
name="alow_self_impostor"
tool_tip="When enabled the viewer may render your own avatar as an impostor."
top_delta="0"
width="190"
label_wrap="true" />
width="190" />
<check_box
control_name="FSShowTunedART"
height="19"
@ -212,8 +210,7 @@ left_delta="0"
name="show_tuned_art"
tool_tip="When enabled the Time column shows the current render time not the pre-tuning render time."
top_pad="0"
width="190"
label_wrap="true" />
width="190" />
<text
follows="left|top"
font="SansSerifSmall"

View File

@ -162,12 +162,10 @@ Faster
layout="topleft"
left_delta="-285"
max_val="6"
name="QualityPerformanceSelection"
name="quality_vs_perf_selection"
show_text="false"
top_delta="-1"
width="275">
<slider.commit_callback
function="Pref.QualityPerformance"/>
</slider>
<text
type="string"

View File

@ -939,7 +939,7 @@
layout="topleft"
left="25"
width="400"
height="40"
height="60"
top_pad="0"
name="ear_location">
<radio_item
@ -949,7 +949,7 @@
layout="topleft"
name="0"
width="150"/>
<radio_item
<radio_item
height="19"
follows="left|top"
label="Hear Voice from Avatar position"
@ -957,6 +957,15 @@
name="1"
top_pad="-2"
width="150" />
<radio_item
enabled="false"
height="19"
follows="left|top"
label="Hear Nearby Voices at full volume (Open Sim Only)"
layout="topleft"
name="2"
top_pad="-2"
width="150" />
</radio_group>
<check_box

View File

@ -655,6 +655,10 @@ https://www.firestormviewer.org/support for help fixing this problem.
<string name="csv_files">Comma separated values</string>
<string name="recompile_script_verb">Recompile</string>
<!-- FS:Zi: add missing file picker translations -->
<string name="jpeg_image_files">JPEG Images</string>
<string name="executable_files">Executable Program Files</string>
<!-- LSL Usage Hover Tips -->
<string name="LSLTipSleepTime" translate="false">Sleeps script for [SLEEP_TIME] seconds.</string>
<!-- (FS:CR) LSL Hover Tips have been moved into scriptlibrary_*.xml so they can be dynamically updated -->

View File

@ -42,7 +42,7 @@
<combo_box.item label="Dostrój tylko awatary" name="av_only" />
<combo_box.item label="Awatary i scena" name="av_and_scene" />
</combo_box>
<spinner name="target_fps" tooltip="Docelowa liczba FPS — żądany poziom klatek na sekundę. Przeglądarka spróbuje go osiągnąć dostosowując ustawienia grafiki." />
<spinner name="target_fps" tool_tip="Docelowa liczba FPS — żądany poziom klatek na sekundę. Przeglądarka spróbuje go osiągnąć dostosowując ustawienia grafiki." />
</panel>
</panel>
<panel name="panel_performance_main">

View File

@ -107,6 +107,7 @@
<radio_group name="ear_location">
<radio_item label="Odtwarzaj głos z pozycji kamery" name="0"/>
<radio_item label="Odtwarzaj głos z pozycji mojego awatara" name="1"/>
<radio_item label="Odtwarzaj głos z pełną głośnością (tylko OpenSim)" name="2" />
</radio_group>
<check_box label="Poruszaj ustami awatara podczas mówienia" name="enable_lip_sync"/>
<check_box label="Pokazuj wskaźniki dźwięku ponad awatarami" tool_tip="Pokazuj wskaźniki dźwięku (białe kropki) ponad awatarami" name="FSShowVoiceVisualizer"/>

View File

@ -1365,6 +1365,12 @@ https://www.firestormviewer.org/support aby uzyskać pomoc.
<string name="recompile_script_verb">
Rekompiluj
</string>
<string name="jpeg_image_files">
Obrazy JPEG
</string>
<string name="executable_files">
Pliki wykonywalne
</string>
<string name="shape">
Kształt
</string>

View File

@ -38,7 +38,7 @@
<combo_box.item label="Только аватары" name="av_only"/>
<combo_box.item label="Аватары и сцена" name="av_and_scene"/>
</combo_box>
<spinner name="target_fps" tooltip="Цель FPS - Желаемый уровень FPS. Программа просмотра попытается добиться этого, изменив настройки графики."/>
<spinner name="target_fps" tool_tip="Цель FPS - Желаемый уровень FPS. Программа просмотра попытается добиться этого, изменив настройки графики."/>
</panel>
</panel>

View File

@ -225,6 +225,7 @@
<check_box label="Показывать тоасты над другими окнами" name="FSShowToastsInFront" />
<check_box label="Использовать новое уведомление перезагрузки региона" name="FSUseNewRegionRestartNotification" />
<check_box label="Не встряхивать мой экран, при получении уведомления о перезагрузке региона" name="FSNoScreenShakeOnRegionRestart" />
<check_box label="Сообщать о рестарте региона в канал:" width="245" name="FSReportRegionRestartToChat" />
</panel>
<panel label="Шрифт" name="UI-font-tab">
<text name="tooltip_textbox1">

View File

@ -102,6 +102,7 @@
<radio_group name="ear_location">
<radio_item label="Слышать голос из положения камеры" name="0"/>
<radio_item label="Слышать голос из положения аватара" name="1"/>
<radio_item label="Слышать все голоса громко (только Open Sim)" name="2"/>
</radio_group>
<check_box label="Двигать губами аватара во время разговора" name="enable_lip_sync"/>
<check_box label="Показать голосовой индикатор над аватарами" tool_tip="Показывает голосовой индикатор (белую точку) над аватарами" name="FSShowVoiceVisualizer"/>

View File

@ -1421,6 +1421,12 @@ https://www.firestormviewer.org/support за помощь в решении эт
<string name="recompile_script_verb">
Перекомпиляция
</string>
<string name="jpeg_image_files">
Изображения в формате JPEG
</string>
<string name="executable_files">
Исполняемые файлы программы
</string>
<string name="LSLTipSleepTime">
Пауза скрипта на [SLEEP_TIME] секунд.
</string>

View File

@ -1799,8 +1799,15 @@ class LinuxManifest(ViewerManifest):
build_data_json_platform = 'lnx'
def construct(self):
# <FS:ND> HACK! Force parent to always copy XML/... even when not having configured with --package.
# This allows build result to be started without always having to --package and thus waiting for the length tar ball generation --package incurs
savedActions = self.args['actions']
self.args["actions"].append("package")
super(LinuxManifest, self).construct()
self.args["actions"] = savedActions # Restore old actions
pkgdir = os.path.join(self.args['build'], os.pardir, 'packages')
relpkgdir = os.path.join(pkgdir, "lib", "release")
debpkgdir = os.path.join(pkgdir, "lib", "debug")
@ -1877,11 +1884,9 @@ class LinuxManifest(ViewerManifest):
with self.prefix(src=os.path.join(pkgdir, 'bin', 'release'), dst="bin"):
self.path( "chrome-sandbox" )
self.path( "dullahan_host" )
self.fs_try_path( "natives_blob.bin" )
self.path( "snapshot_blob.bin" )
self.path( "v8_context_snapshot.bin" )
with self.prefix(src=os.path.join(pkgdir, 'bin', 'release'), dst="lib"):
self.fs_try_path( "natives_blob.bin" )
self.path( "snapshot_blob.bin" )
self.path( "v8_context_snapshot.bin" )
@ -1960,8 +1965,7 @@ class LinuxManifest(ViewerManifest):
with self.prefix(src=pkgdir, dst="bin"):
self.path("ca-bundle.crt")
if self.is_packaging_viewer():
with self.prefix(src=os.path.join(pkgdir, 'lib', 'release'), dst="lib"):
with self.prefix(src=os.path.join(pkgdir, 'lib', 'release'), dst="lib"):
self.path("libapr-1.so*")
self.path("libaprutil-1.so*")
#self.path("libboost_context-mt.so*")
@ -1995,7 +1999,7 @@ class LinuxManifest(ViewerManifest):
self.path("libopenal.so", "libopenal.so.1") # Install as versioned file in case it's missing from the 3p- and won't get copied below
self.path("libopenal.so*")
#self.path("libnotify.so.1.1.2", "libnotify.so.1") # LO - uncomment when testing libnotify(growl) on linux
self.path("libpangox-1.0.so*")
#self.path("libpangox-1.0.so*")
# KLUDGE: As of 2012-04-11, the 'fontconfig' package installs
# libfontconfig.so.1.4.4, along with symlinks libfontconfig.so.1
# and libfontconfig.so. Before we added support for library-file
@ -2013,24 +2017,24 @@ class LinuxManifest(ViewerManifest):
# particular wildcard specification gets us exactly what the
# previous call did, without having to explicitly state the
# version number.
self.path("libfontconfig.so.*.*")
#self.path("libfontconfig.so.*.*")
self.fs_try_path("libjemalloc.so*")
# Vivox runtimes
# Currentelly, the 32-bit ones will work with a 64-bit client.
with self.prefix(src=os.path.join(pkgdir, 'lib', 'release'), dst="bin"):
self.path("SLVoice")
self.path("win32")
self.path("win64")
# Vivox runtimes
# Currentelly, the 32-bit ones will work with a 64-bit client.
with self.prefix(src=os.path.join(pkgdir, 'lib', 'release'), dst="bin"):
self.path("SLVoice")
self.path("win32")
self.path("win64")
with self.prefix(src=os.path.join(pkgdir, 'lib', 'release'), dst="lib"):
self.path("libortp.so")
self.path("libsndfile.so.1")
# <FS:TS> Vivox wants this library even if it's present already in the viewer
self.path("libvivoxoal.so.1")
self.path("libvivoxsdk.so")
self.path("libvivoxplatform.so")
with self.prefix(src=os.path.join(pkgdir, 'lib', 'release'), dst="lib"):
self.path("libortp.so")
self.path("libsndfile.so.1")
# <FS:TS> Vivox wants this library even if it's present already in the viewer
self.path("libvivoxoal.so.1")
self.path("libvivoxsdk.so")
self.path("libvivoxplatform.so")
def package_finish(self):
@ -2056,6 +2060,7 @@ class LinuxManifest(ViewerManifest):
# name in the tarfile
realname = self.get_dst_prefix()
tempname = self.build_path_of(installer_name)
self.run_command([self.args["source"] + "/installers/linux/appimage.sh", self.args["build"]] )
self.run_command(["mv", realname, tempname])
try:
# only create tarball if it's a release build.
@ -2080,7 +2085,7 @@ class LinuxManifest(ViewerManifest):
[os.path.join(self.get_dst_prefix(), dir) for dir in ('bin', 'lib')] +
# <FS:Ansariel> Remove VMP
# ['-type', 'f', '!', '-name', '*.py',
['-type', 'f', "!", "-name", "*.dat", "!", "-name", "*.pak", "!", "-name", "*.bin",
['-type', 'f', "!", "-name", "*.dat", "!", "-name", "*.pak", "!", "-name", "*.bin", "!", "-name", "*.lib", "!", "-name", "*.pdb",
# </FS:Ansariel> Remove VMP
'!', '-name', 'update_install', '-exec', 'strip', '-S', '{}', ';'])
@ -2182,9 +2187,8 @@ class Linux_x86_64_Manifest(LinuxManifest):
relpkgdir = os.path.join(pkgdir, "lib", "release")
debpkgdir = os.path.join(pkgdir, "lib", "debug")
if self.is_packaging_viewer():
with self.prefix(src=os.path.join(pkgdir, 'lib', 'release'), dst="lib"):
self.path("libffi*.so*")
with self.prefix(src=os.path.join(pkgdir, 'lib', 'release'), dst="lib"):
#self.path("libffi*.so*")
# vivox 32-bit hack.
# one has to extract libopenal.so from the 32-bit openal package, or official LL viewer, and rename it to libopenal32.so
# and place it in the prebuilt lib/release directory

View File

@ -42,6 +42,7 @@ WANTS_TESTBUILD=$FALSE
WANTS_TRACY=$FALSE
WANTS_BUILD=$FALSE
WANTS_CRASHREPORTING=$FALSE
WANTS_CACHE=$FALSE
TARGET_PLATFORM="darwin" # darwin, windows, linux
BTYPE="Release"
CHANNEL="" # will be overwritten later with platform-specific values unless manually specified.
@ -83,8 +84,9 @@ showUsage()
echo " --testbuild <days> : Create time-limited test build (build date + <days>)"
echo " --platform <platform> : Build for specified platform (darwin | windows | linux)"
echo " --jobs <num> : Build with <num> jobs in parallel (Linux and Darwin only)"
echo " --ninja : Build using Ninja (Linux only)"
echo " --ninja : Build using Ninja"
echo " --vscode : Exports compile commands for VSCode (Linux only)"
echo " --compiler-cache : Try to detect and use compiler cache (needs also --ninja for OSX and Windows)"
echo
echo "All arguments not in the above list will be passed through to LL's configure/build."
echo
@ -94,7 +96,7 @@ getArgs()
# $* = the options passed in from main
{
if [ $# -gt 0 ]; then
while getoptex "clean build config version package no-package fmodstudio openal ninja vscode jobs: platform: kdu opensim no-opensim singlegrid: avx avx2 tracy crashreporting testbuild: help chan: btype:" "$@" ; do
while getoptex "clean build config version package no-package fmodstudio openal ninja vscode compiler-cache jobs: platform: kdu opensim no-opensim singlegrid: avx avx2 tracy crashreporting testbuild: help chan: btype:" "$@" ; do
#ensure options are valid
if [ -z "$OPTOPT" ] ; then
@ -133,6 +135,7 @@ getArgs()
jobs) JOBS="$OPTARG";;
ninja) WANTS_NINJA=$TRUE;;
vscode) WANTS_VSCODE=$TRUE;;
compiler-cache) WANTS_CACHE=$TRUE;;
help) showUsage && exit 0;;
@ -324,6 +327,7 @@ echo -e " BUILD: `b2a $WANTS_BUILD`" |
echo -e " CONFIG: `b2a $WANTS_CONFIG`" | tee -a $LOG
echo -e " NINJA: `b2a $WANTS_NINJA`" | tee -a $LOG
echo -e " VSCODE: `b2a $WANTS_VSCODE`" | tee -a $LOG
echo -e " COMPILER CACHE: `b2a $WANTS_CACHE`" | tee -a $LOG
echo -e " PASSTHRU: $LL_ARGS_PASSTHRU" | tee -a $LOG
echo -e " BTYPE: $BTYPE" | tee -a $LOG
if [ $TARGET_PLATFORM == "linux" -o $TARGET_PLATFORM == "darwin" ] ; then
@ -525,11 +529,7 @@ if [ $WANTS_CONFIG -eq $TRUE ] ; then
TARGET="Xcode"
elif [ \( $TARGET_PLATFORM == "linux" \) ] ; then
OPENAL="-DOPENAL:BOOL=ON"
if [ $WANTS_NINJA -eq $TRUE ] ; then
TARGET="Ninja"
else
TARGET="Unix Makefiles"
fi
TARGET="Unix Makefiles"
if [ $WANTS_VSCODE -eq $TRUE ] ; then
VSCODE_FLAGS="-DCMAKE_EXPORT_COMPILE_COMMANDS=On"
ROOT_DIR=$(dirname $(dirname $(readlink -f $0)))
@ -545,8 +545,28 @@ if [ $WANTS_CONFIG -eq $TRUE ] ; then
UNATTENDED="-DUNATTENDED=ON"
fi
if [ $WANTS_NINJA -eq $TRUE ] ; then
TARGET="Ninja"
fi
CACHE_OPT=""
if [ $WANTS_CACHE -eq $TRUE ]
then
if [ `which ccache 2>/dev/null` ]
then
echo "Found ccache"
CACHE_OPT="-DCMAKE_C_COMPILER_LAUNCHER=ccache -DCMAKE_CXX_COMPILER_LAUNCHER=ccache"
fi
if [ `which buildcache 2>/dev/null` ]
then
echo "Found buildcache"
CACHE_OPT="-DCMAKE_C_COMPILER_LAUNCHER=buildcache -DCMAKE_CXX_COMPILER_LAUNCHER=buildcache"
fi
fi
cmake -G "$TARGET" ../indra $CHANNEL ${GITHASH} $FMODSTUDIO $OPENAL $KDU $OPENSIM $SINGLEGRID $AVX_OPTIMIZATION $AVX2_OPTIMIZATION $TRACY_PROFILER $TESTBUILD $PACKAGE \
$UNATTENDED -DLL_TESTS:BOOL=OFF -DADDRESS_SIZE:STRING=$AUTOBUILD_ADDRSIZE -DCMAKE_BUILD_TYPE:STRING=$BTYPE \
$UNATTENDED -DLL_TESTS:BOOL=OFF -DADDRESS_SIZE:STRING=$AUTOBUILD_ADDRSIZE -DCMAKE_BUILD_TYPE:STRING=$BTYPE $CACHE_OPT \
$CRASH_REPORTING -DVIEWER_SYMBOL_FILE:STRING="${VIEWER_SYMBOL_FILE:-}" -DROOT_PROJECT_NAME:STRING=Firestorm $LL_ARGS_PASSTHRU ${VSCODE_FLAGS:-} | tee $LOG
if [ $TARGET_PLATFORM == "windows" ] ; then

View File

@ -1,11 +0,0 @@
if [ -d exp/ ]
then
rm exp/*.diff
else
mkdir exp
fi
for i in $(cat exp.txt)
do
hg export -o exp/$i.diff -r $i
done

View File

@ -1,46 +0,0 @@
#!/bin/sh
read -p "Calling hg revert and purge on indra/. Then importing changes. Continue? " ANSWER
case "$ANSWER" in
y|Y)echo "Carrying on"
;;
*) echo "Exit"
exit 0
;;
esac
if [ ! -d indra/ ]
then
echo "Indra directory not found"
exit 1
fi
hg revert indra/
hg revert autobuild.xml
hg purge indra/
for i in $(cat exp.txt|sort -n)
do
echo "Importing change $i"
hg import --no-commit -f exp/$i.diff || exit 1
done
read -p "All patches applied without errors. Apply them again and commit? " ANSWER
case "$ANSWER" in
y|Y)echo "Carrying on"
;;
*) echo "Exit"
exit 0
;;
esac
hg revert indra/
hg revert autobuild.xml
hg purge indra/
for i in $(cat exp.txt|sort -n)
do
echo "Importing change $i"
hg import exp/$i.diff || exit 1
done