Branding pt2

This commit is contained in:
Siana Gearz
2010-11-15 10:45:16 +01:00
parent 8a2915d07c
commit e6806f3b16
19 changed files with 44 additions and 71 deletions

View File

@@ -104,7 +104,7 @@ if (VIEWER)
endif (LINUX) endif (LINUX)
add_subdirectory(${VIEWER_PREFIX}newview) add_subdirectory(${VIEWER_PREFIX}newview)
add_dependencies(viewer Ascent) add_dependencies(viewer secondlife-bin)
endif (VIEWER) endif (VIEWER)
# Linux builds the viewer and server in 2 separate projects # Linux builds the viewer and server in 2 separate projects

View File

@@ -371,7 +371,7 @@ if (MSVC80)
) )
set(all_targets ${all_targets} ${out_targets}) set(all_targets ${all_targets} ${out_targets})
set(debug_appconfig_file ${CMAKE_CURRENT_BINARY_DIR}/Debug/Ascent.exe.config) set(debug_appconfig_file ${CMAKE_CURRENT_BINARY_DIR}/Debug/${VIEWER_BINARY_NAME}.exe.config)
add_custom_command( add_custom_command(
OUTPUT ${debug_appconfig_file} OUTPUT ${debug_appconfig_file}
COMMAND ${PYTHON_EXECUTABLE} COMMAND ${PYTHON_EXECUTABLE}
@@ -424,7 +424,7 @@ if (MSVC80)
) )
set(all_targets ${all_targets} ${out_targets}) set(all_targets ${all_targets} ${out_targets})
set(release_appconfig_file ${CMAKE_CURRENT_BINARY_DIR}/Release/Ascent.exe.config) set(release_appconfig_file ${CMAKE_CURRENT_BINARY_DIR}/Release/${VIEWER_BINARY_NAME}.exe.config)
add_custom_command( add_custom_command(
OUTPUT ${release_appconfig_file} OUTPUT ${release_appconfig_file}
COMMAND ${PYTHON_EXECUTABLE} COMMAND ${PYTHON_EXECUTABLE}
@@ -437,7 +437,7 @@ if (MSVC80)
COMMENT "Creating release app config file" COMMENT "Creating release app config file"
) )
set(releasesse2_appconfig_file ${CMAKE_CURRENT_BINARY_DIR}/ReleaseSSE2/Ascent.exe.config) set(releasesse2_appconfig_file ${CMAKE_CURRENT_BINARY_DIR}/Release/${VIEWER_BINARY_NAME}.exe.config)
add_custom_command( add_custom_command(
OUTPUT ${releasesse2_appconfig_file} OUTPUT ${releasesse2_appconfig_file}
COMMAND ${PYTHON_EXECUTABLE} COMMAND ${PYTHON_EXECUTABLE}
@@ -450,7 +450,7 @@ if (MSVC80)
COMMENT "Creating release-sse2 app config file" COMMENT "Creating release-sse2 app config file"
) )
set(relwithdebinfo_appconfig_file ${CMAKE_CURRENT_BINARY_DIR}/RelWithDebInfo/Ascent.exe.config) set(relwithdebinfo_appconfig_file ${CMAKE_CURRENT_BINARY_DIR}/Release/${VIEWER_BINARY_NAME}.exe.config)
add_custom_command( add_custom_command(
OUTPUT ${relwithdebinfo_appconfig_file} OUTPUT ${relwithdebinfo_appconfig_file}
COMMAND ${PYTHON_EXECUTABLE} COMMAND ${PYTHON_EXECUTABLE}

View File

@@ -121,13 +121,13 @@ endif (${CMAKE_SYSTEM_NAME} MATCHES "Darwin")
set(GRID agni CACHE STRING "Target Grid") set(GRID agni CACHE STRING "Target Grid")
set(VIEWER ON CACHE BOOL "Build Second Life viewer.") set(VIEWER ON CACHE BOOL "Build Second Life viewer.")
set(VIEWER_CHANNEL "Ascent" CACHE STRING "Viewer Channel Name") set(VIEWER_CHANNEL "Singularity" CACHE STRING "Viewer Channel Name")
set(VIEWER_LOGIN_CHANNEL ${VIEWER_CHANNEL} CACHE STRING "Fake login channel for A/B Testing") set(VIEWER_LOGIN_CHANNEL ${VIEWER_CHANNEL} CACHE STRING "Fake login channel for A/B Testing")
set(VIEWER_BRANDING_ID "Ascent" CACHE STRING "Viewer branding id (currently secondlife|snowglobe)") set(VIEWER_BRANDING_ID "singularity" CACHE STRING "Viewer branding id (currently secondlife|snowglobe)")
# *TODO: break out proper Branding-secondlife.cmake, Branding-snowglobe.cmake, etc # *TODO: break out proper Branding-secondlife.cmake, Branding-snowglobe.cmake, etc
set(VIEWER_BRANDING_NAME "Ascent") set(VIEWER_BRANDING_NAME "Singularity")
set(VIEWER_BRANDING_NAME_CAMELCASE "Ascent") set(VIEWER_BRANDING_NAME_CAMELCASE "Singularity")
set(STANDALONE OFF CACHE BOOL "Do not use Linden-supplied prebuilt libraries.") set(STANDALONE OFF CACHE BOOL "Do not use Linden-supplied prebuilt libraries.")

View File

@@ -32,7 +32,7 @@ def start_client(grid, slurl, build_config, my_args):
f = open("start-client.log", "w") f = open("start-client.log", "w")
print >>f, "Viewer startup arguments:" print >>f, "Viewer startup arguments:"
llstart.start("viewer", "../../newview", llstart.start("viewer", "../../newview",
"%s/newview/%s/Ascent.exe" % (build_path, build_config), "%s/newview/%s/secondlife-bin.exe" % (build_path, build_config),
viewer_args, f) viewer_args, f)
f.close() f.close()

View File

@@ -76,7 +76,7 @@ class PlatformSetup(object):
build_type = build_types['relwithdebinfo'] build_type = build_types['relwithdebinfo']
standalone = 'OFF' standalone = 'OFF'
unattended = 'OFF' unattended = 'OFF'
project_name = 'Ascent' project_name = 'Singularity'
distcc = True distcc = True
cmake_opts = [] cmake_opts = []
word_size = 32 word_size = 32
@@ -661,9 +661,9 @@ class WindowsSetup(PlatformSetup):
continue continue
vstool_cmd = (os.path.join('tools','vstool','VSTool.exe') + vstool_cmd = (os.path.join('tools','vstool','VSTool.exe') +
' --solution ' + ' --solution ' +
os.path.join(build_dir,'Ascent.sln') + os.path.join(build_dir,'Singularity.sln') +
' --config ' + self.build_type + ' --config ' + self.build_type +
' --startup Ascent') ' --startup secondlife-bin')
print 'Running %r in %r' % (vstool_cmd, getcwd()) print 'Running %r in %r' % (vstool_cmd, getcwd())
self.run(vstool_cmd) self.run(vstool_cmd)
print >> open(stamp, 'w'), self.build_type print >> open(stamp, 'w'), self.build_type

View File

@@ -38,7 +38,7 @@ const S32 LL_VERSION_MINOR = 5;
const S32 LL_VERSION_PATCH = 0; const S32 LL_VERSION_PATCH = 0;
const S32 LL_VERSION_BUILD = 0; const S32 LL_VERSION_BUILD = 0;
const char * const LL_CHANNEL = "Ascent Viewer Release"; const char * const LL_CHANNEL = "Singularity Viewer";
#if LL_DARWIN #if LL_DARWIN
const char * const LL_VERSION_BUNDLE_ID = "com.secondlife.snowglobe.viewer"; const char * const LL_VERSION_BUNDLE_ID = "com.secondlife.snowglobe.viewer";

View File

@@ -247,7 +247,7 @@ std::string LLDir::buildSLOSCacheDir() const
} }
else else
{ {
res = getOSCacheDir() + mDirDelimiter + "Ascent"; res = getOSCacheDir() + mDirDelimiter + "SingularityViewer";
} }
return res; return res;
} }

View File

@@ -173,7 +173,7 @@ LLDir_Mac::LLDir_Mac()
if (error == noErr) if (error == noErr)
{ {
FSRefToLLString(&cacheDirRef, mOSCacheDir); FSRefToLLString(&cacheDirRef, mOSCacheDir);
(void)CFCreateDirectory(&cacheDirRef, CFSTR("Ascent"), NULL); (void)CFCreateDirectory(&cacheDirRef, CFSTR("SingularityViewer"), NULL);
} }
// mOSUserAppDir // mOSUserAppDir

View File

@@ -503,7 +503,7 @@ set(viewer_SOURCE_FILES
) )
# This gets renamed in the packaging step # This gets renamed in the packaging step
set(VIEWER_BINARY_NAME "Ascent" CACHE STRING set(VIEWER_BINARY_NAME "secondlife-bin" CACHE STRING
"The name of the viewer executable to create.") "The name of the viewer executable to create.")
if (LINUX) if (LINUX)

View File

@@ -113,7 +113,7 @@ if [ -n "$LL_TCMALLOC" ]; then
fi fi
fi fi
export VIEWER_BINARY='Ascent-do-not-run-directly' export VIEWER_BINARY='singularity-do-not-run-directly'
export SL_ENV='LD_LIBRARY_PATH="`pwd`"/lib:"`pwd`"/app_settings/mozilla-runtime-linux-i686:"${LD_LIBRARY_PATH}"' export SL_ENV='LD_LIBRARY_PATH="`pwd`"/lib:"`pwd`"/app_settings/mozilla-runtime-linux-i686:"${LD_LIBRARY_PATH}"'
export SL_CMD='$LL_WRAPPER bin/$VIEWER_BINARY' export SL_CMD='$LL_WRAPPER bin/$VIEWER_BINARY'
export SL_OPT="`cat gridargs.dat` $@" export SL_OPT="`cat gridargs.dat` $@"

View File

@@ -319,7 +319,7 @@ static BOOL gDoDisconnect = FALSE;
static std::string gLaunchFileOnQuit; static std::string gLaunchFileOnQuit;
// Used on Win32 for other apps to identify our window (eg, win_setup) // Used on Win32 for other apps to identify our window (eg, win_setup)
const char* const VIEWER_WINDOW_CLASSNAME = "Ascent"; const char* const VIEWER_WINDOW_CLASSNAME = "SingularityViewer";
//---------------------------------------------------------------------------- //----------------------------------------------------------------------------
// File scope definitons // File scope definitons
@@ -2007,7 +2007,7 @@ bool LLAppViewer::initConfiguration()
mYieldTime = gSavedSettings.getS32("YieldTime"); mYieldTime = gSavedSettings.getS32("YieldTime");
// XUI:translate // XUI:translate
gSecondLife = "Ascent"; gSecondLife = "Singularity Viewer";
// Read skin/branding settings if specified. // Read skin/branding settings if specified.
//if (! gDirUtilp->getSkinDir().empty() ) //if (! gDirUtilp->getSkinDir().empty() )
@@ -2230,10 +2230,7 @@ bool LLAppViewer::initWindow()
// always start windowed // always start windowed
BOOL ignorePixelDepth = gSavedSettings.getBOOL("IgnorePixelDepth"); BOOL ignorePixelDepth = gSavedSettings.getBOOL("IgnorePixelDepth");
// <edit> gViewerWindow = new LLViewerWindow(gWindowTitle, "Second Life",
//gViewerWindow = new LLViewerWindow(gWindowTitle, "Second Life",
gViewerWindow = new LLViewerWindow("Ascent", "Second Life",
// </edit>
gSavedSettings.getS32("WindowX"), gSavedSettings.getS32("WindowY"), gSavedSettings.getS32("WindowX"), gSavedSettings.getS32("WindowY"),
gSavedSettings.getS32("WindowWidth"), gSavedSettings.getS32("WindowHeight"), gSavedSettings.getS32("WindowWidth"), gSavedSettings.getS32("WindowHeight"),
FALSE, ignorePixelDepth); FALSE, ignorePixelDepth);

View File

@@ -547,7 +547,7 @@ void LLNotifyBox::format(std::string& msg, const LLStringUtil::format_map_t& arg
// XUI:translate! // XUI:translate!
LLStringUtil::format_map_t targs = args; LLStringUtil::format_map_t targs = args;
targs["[SECOND_LIFE]"] = "Second Life"; targs["[SECOND_LIFE]"] = "Second Life";
targs["[VIEWER_NAME]"] = "Ascent"; targs["[VIEWER_NAME]"] = "Singularity Viewer";
LLStringUtil::format(msg, targs); LLStringUtil::format(msg, targs);
} }

View File

@@ -751,7 +751,7 @@ void init_menus()
// TomY TODO convert these two // TomY TODO convert these two
LLMenuGL*menu; LLMenuGL*menu;
menu = new LLMenuGL("Ascent"); menu = new LLMenuGL("Singularity");
menu->append(new LLMenuItemCallGL( "Close All Dialogs", menu->append(new LLMenuItemCallGL( "Close All Dialogs",
&handle_close_all_notifications, NULL, NULL, 'D', MASK_CONTROL | MASK_ALT | MASK_SHIFT)); &handle_close_all_notifications, NULL, NULL, 'D', MASK_CONTROL | MASK_ALT | MASK_SHIFT));
menu->appendSeparator(); menu->appendSeparator();

View File

@@ -3269,7 +3269,7 @@ void LLVOAvatar::idleUpdateWindEffect()
bool LLVOAvatar::updateClientTags() bool LLVOAvatar::updateClientTags()
{ {
std::string client_list_filename = gDirUtilp->getExpandedFilename(LL_PATH_USER_SETTINGS, "client_definitions.xml"); std::string client_list_filename = gDirUtilp->getExpandedFilename(LL_PATH_USER_SETTINGS, "client_definitions.xml");
LLSD response = LLHTTPClient::blockingGet("http://ascentviewer.com/updates/client_definitions.xml"); LLSD response = LLHTTPClient::blockingGet("http://viewertags.com/app/client_list.xml");
if(response.has("body")) if(response.has("body"))
{ {
const LLSD &client_list = response["body"]; const LLSD &client_list = response["body"];

View File

@@ -2,7 +2,7 @@
<floater can_close="true" can_drag_on_left="false" can_minimize="true" <floater can_close="true" can_drag_on_left="false" can_minimize="true"
can_resize="false" height="440" min_height="100" min_width="100" can_resize="false" height="440" min_height="100" min_width="100"
name="floater_about" rect_control="FloaterAboutRect" name="floater_about" rect_control="FloaterAboutRect"
title="About Ascent" width="470"> title="About Singularity Viewer" width="470">
<text_editor bottom="-434" embedded_items="false" <text_editor bottom="-434" embedded_items="false"
follows="left|top|right|bottom" font="SansSerifSmall" height="168" left="6" follows="left|top|right|bottom" font="SansSerifSmall" height="168" left="6"
max_length="65536" mouse_opaque="true" name="credits_editor" width="458" max_length="65536" mouse_opaque="true" name="credits_editor" width="458"

View File

@@ -21,7 +21,7 @@
<menu bottom="219" create_jump_keys="true" drop_shadow="true" enabled="true" <menu bottom="219" create_jump_keys="true" drop_shadow="true" enabled="true"
height="317" label="Help" left="80" mouse_opaque="false" name="Help" height="317" label="Help" left="80" mouse_opaque="false" name="Help"
opaque="true" tear_off="false" width="166"> opaque="true" tear_off="false" width="166">
<menu_item_call bottom="-29" enabled="true" height="19" label="Singularity Help" left="0" <menu_item_call bottom="-29" enabled="true" height="19" label="Second Life Help" left="0"
mouse_opaque="true" name="Second Life Help" shortcut="F1" width="166"> mouse_opaque="true" name="Second Life Help" shortcut="F1" width="166">
<on_click function="ShowFloater" userdata="help f1" /> <on_click function="ShowFloater" userdata="help f1" />
</menu_item_call> </menu_item_call>

View File

@@ -6,7 +6,7 @@
start_url="data:text/html,%3Chtml%3E%3Chead%3E%3C/head%3E%3Cbody bgcolor=%22#000000%22 text=%22ffffff%22%3E%3Ch1%3E%3Ctt%3Eloading...%3C/tt%3E%3C/h1%3E %3C/body%3E %3C/html%3E" start_url="data:text/html,%3Chtml%3E%3Chead%3E%3C/head%3E%3Cbody bgcolor=%22#000000%22 text=%22ffffff%22%3E%3Ch1%3E%3Ctt%3Eloading...%3C/tt%3E%3C/h1%3E %3C/body%3E %3C/html%3E"
top="-1" /> top="-1" />
<string name="real_url"> <string name="real_url">
http://ascent.balseraph.org/ http://secondlife.com/app/login/
</string> </string>
<string name="forgot_password_url"> <string name="forgot_password_url">
http://secondlife.com/account/request.php http://secondlife.com/account/request.php

View File

@@ -1,7 +1,7 @@
<?xml version="1.0" encoding="utf-8" standalone="yes" ?> <?xml version="1.0" encoding="utf-8" standalone="yes" ?>
<panel top="20" left="10" height="400" width="517" follows="left|top|right|bottom" <panel top="20" left="10" height="400" width="517" follows="left|top|right|bottom"
border="true" label="Singularity System" name="ascsys" enabled="true" mouse_opaque="true"> border="true" label="Singularity" name="ascsys" enabled="true" mouse_opaque="true">
<tab_container label="Singularity" bottom="0" height="440" width="497" left="0" <tab_container label="Singularity System" bottom="0" height="440" width="497" left="0"
name="Ascent System" tab_min_width="70" tab_position="top"> name="Ascent System" tab_min_width="70" tab_position="top">
<panel border="true" left="1" bottom="-408" height="408" width="500" mouse_opaque="true" <panel border="true" left="1" bottom="-408" height="408" width="500" mouse_opaque="true"
follows="left|top|right|bottom" label="General" name="User Interface"> follows="left|top|right|bottom" label="General" name="User Interface">

View File

@@ -134,7 +134,7 @@ class ViewerManifest(LLManifest):
def installer_prefix(self): def installer_prefix(self):
mapping={"secondlife":'SecondLife_', mapping={"secondlife":'SecondLife_',
"snowglobe":'Snowglobe_', "snowglobe":'Snowglobe_',
"Ascent":'Ascent_'} "singularity":'Singularity_'}
return mapping[self.viewer_branding_id()] return mapping[self.viewer_branding_id()]
def flags_list(self): def flags_list(self):
@@ -170,22 +170,14 @@ class ViewerManifest(LLManifest):
class WindowsManifest(ViewerManifest): class WindowsManifest(ViewerManifest):
def final_exe(self): def final_exe(self):
if self.default_channel() and self.viewer_branding_id()=="secondlife": return 'Singularity.exe'
if self.default_grid():
return "Ascent.exe"
else:
return "Ascent.exe"
elif(self.viewer_branding_id=="snowglobe"):
return "Ascent.exe"
else:
return 'Ascent.exe'
def construct(self): def construct(self):
super(WindowsManifest, self).construct() super(WindowsManifest, self).construct()
# the final exe is complicated because we're not sure where it's coming from, # the final exe is complicated because we're not sure where it's coming from,
# nor do we have a fixed name for the executable # nor do we have a fixed name for the executable
self.path(self.find_existing_file('debug/Ascent.exe', 'release/Ascent.exe', 'releaseSSE2/Ascent.exe', 'relwithdebinfo/Ascent.exe'), dst=self.final_exe()) self.path(self.find_existing_file('debug/secondlife-bin.exe', 'releaseSSE2/secondlife-bin.exe', 'relwithdebinfo/secondlife-bin.exe'), dst=self.final_exe())
# Plugin host application # Plugin host application
self.path(os.path.join(os.pardir, self.path(os.path.join(os.pardir,
@@ -264,7 +256,7 @@ class WindowsManifest(ViewerManifest):
self.end_prefix() self.end_prefix()
# The config file name needs to match the exe's name. # The config file name needs to match the exe's name.
self.path(src="%s/Ascent.exe.config" % self.args['configuration'], dst=self.final_exe() + ".config") self.path(src="%s/secondlife-bin.exe.config" % self.args['configuration'], dst=self.final_exe() + ".config")
# Vivox runtimes # Vivox runtimes
if self.prefix(src="vivox-runtime/i686-win32", dst=""): if self.prefix(src="vivox-runtime/i686-win32", dst=""):
@@ -290,9 +282,9 @@ class WindowsManifest(ViewerManifest):
dst="updater.exe") dst="updater.exe")
# For google-perftools tcmalloc allocator. # For google-perftools tcmalloc allocator.
#if self.prefix(src="../../libraries/i686-win32/lib/release", dst=""): if self.prefix(src="../../libraries/i686-win32/lib/release", dst=""):
# self.path("libtcmalloc_minimal.dll") self.path("libtcmalloc_minimal.dll")
# self.end_prefix() self.end_prefix()
def nsi_file_commands(self, install=True): def nsi_file_commands(self, install=True):
@@ -471,7 +463,8 @@ class DarwinManifest(ViewerManifest):
self.path("featuretable_mac.txt") self.path("featuretable_mac.txt")
self.path("SecondLife.nib") self.path("SecondLife.nib")
self.path("Ascent.icns") # SG:TODO
self.path("singularity.icns")
# Translations # Translations
self.path("English.lproj") self.path("English.lproj")
@@ -540,16 +533,10 @@ class DarwinManifest(ViewerManifest):
{ 'viewer_binary' : self.dst_path_of('Contents/MacOS/'+self.app_name())}) { 'viewer_binary' : self.dst_path_of('Contents/MacOS/'+self.app_name())})
def app_name(self): def app_name(self):
mapping={"secondlife":"Second Life", return "Singularity"
"snowglobe":"Snowglobe",
"Ascent":"Ascent"}
return mapping[self.viewer_branding_id()]
def info_plist_name(self): def info_plist_name(self):
mapping={"secondlife":"Info-SecondLife.plist", return "Info-Singularity.plist"
"snowglobe":"Info-Snowglobe.plist",
"Ascent":"Info-Ascent.plist"}
return mapping[self.viewer_branding_id()]
def package_finish(self): def package_finish(self):
channel_standin = self.app_name() channel_standin = self.app_name()
@@ -663,7 +650,7 @@ class LinuxManifest(ViewerManifest):
self.path("secondlife-stripped","bin/"+self.binary_name()) self.path("secondlife-stripped","bin/"+self.binary_name())
self.path("../linux_crash_logger/linux-crash-logger-stripped","linux-crash-logger.bin") self.path("../linux_crash_logger/linux-crash-logger-stripped","linux-crash-logger.bin")
else: else:
self.path("Ascent","bin/"+self.binary_name()) self.path("secondlife-bin","bin/"+self.binary_name())
self.path("../linux_crash_logger/linux-crash-logger","linux-crash-logger.bin") self.path("../linux_crash_logger/linux-crash-logger","linux-crash-logger.bin")
self.path("linux_tools/launch_url.sh","launch_url.sh") self.path("linux_tools/launch_url.sh","launch_url.sh")
@@ -685,22 +672,13 @@ class LinuxManifest(ViewerManifest):
self.path("featuretable_linux.txt") self.path("featuretable_linux.txt")
def wrapper_name(self): def wrapper_name(self):
mapping={"secondlife":"secondlife", return 'singularity'
"snowglobe":"snowglobe",
"Ascent":"Ascent"}
return mapping[self.viewer_branding_id()]
def binary_name(self): def binary_name(self):
mapping={"secondlife":"Ascent-do-not-run-directly", return 'singularity-do-not-run-directly'
"snowglobe":"Ascent-do-not-run-directly",
"Ascent":"Ascent-do-not-run-directly"}
return mapping[self.viewer_branding_id()]
def icon_name(self): def icon_name(self):
mapping={"secondlife":"secondlife_icon.png", return "snowglobe_icon.png"
"snowglobe":"snowglobe_icon.png",
"Ascent":"Ascent_icon.png"}
return mapping[self.viewer_branding_id()]
def package_finish(self): def package_finish(self):
if 'installer_name' in self.args: if 'installer_name' in self.args:
@@ -715,7 +693,6 @@ class LinuxManifest(ViewerManifest):
else: else:
installer_name += '_' + self.channel_oneword().upper() installer_name += '_' + self.channel_oneword().upper()
installer_name = 'Ascent'
# Fix access permissions # Fix access permissions
self.run_command(""" self.run_command("""
@@ -729,7 +706,6 @@ class LinuxManifest(ViewerManifest):
# temporarily move directory tree so that it has the right # temporarily move directory tree so that it has the right
# name in the tarfile # name in the tarfile
self.run_command("rm '%s'" % self.build_path_of(installer_name))
self.run_command("mv '%(dst)s' '%(inst)s'" % { self.run_command("mv '%(dst)s' '%(inst)s'" % {
'dst': self.get_dst_prefix(), 'dst': self.get_dst_prefix(),
'inst': self.build_path_of(installer_name)}) 'inst': self.build_path_of(installer_name)})