Merge remote-tracking branch 'upstream/master' into pqihandlerOptim

This commit is contained in:
jolavillette 2020-06-04 07:39:59 +02:00
commit 752c997f24
57 changed files with 500 additions and 881 deletions

View File

@ -0,0 +1,37 @@
@echo off
setlocal
:: Initialize environment
call "%~dp0..\env.bat"
if errorlevel 1 goto error_env
call "%EnvPath%\env.bat"
if errorlevel 1 goto error_env
call "%EnvPath%\env.bat"
if errorlevel 1 goto error_env
call "%EnvPath%\env-msys2.bat"
if errorlevel 1 goto error_env
:: Initialize base environment
call "%~dp0env-base.bat" %*
if errorlevel 2 exit /B 2
if errorlevel 1 goto error_env
:: Initialize environment
call "%~dp0env.bat" %*
if errorlevel 2 exit /B 2
if errorlevel 1 goto error_env
call "%~dp0..\tools\webui.bat"
:error
title %COMSPEC%
if errorlevel 1 echo.& echo Webui generation failed& echo.
exit /B %ERRORLEVEL%
:error_env
echo Failed to initialize environment.
endlocal
exit /B 1

View File

@ -18,7 +18,7 @@ if errorlevel 2 exit /B 2
if errorlevel 1 goto error_env if errorlevel 1 goto error_env
:: Install needed things :: Install needed things
%EnvMSYS2Cmd% "pacman --noconfirm --needed -S make git mingw-w64-%RsMSYS2Architecture%-toolchain mingw-w64-%RsMSYS2Architecture%-qt5 mingw-w64-%RsMSYS2Architecture%-miniupnpc mingw-w64-%RsMSYS2Architecture%-sqlcipher mingw-w64-%RsMSYS2Architecture%-libmicrohttpd mingw-w64-%RsMSYS2Architecture%-xapian-core mingw-w64-%RsMSYS2Architecture%-cmake mingw-w64-%RsMSYS2Architecture%-rapidjson" %EnvMSYS2Cmd% "pacman --noconfirm --needed -S make git mingw-w64-%RsMSYS2Architecture%-toolchain mingw-w64-%RsMSYS2Architecture%-qt5 mingw-w64-%RsMSYS2Architecture%-miniupnpc mingw-w64-%RsMSYS2Architecture%-sqlcipher mingw-w64-%RsMSYS2Architecture%-xapian-core mingw-w64-%RsMSYS2Architecture%-cmake mingw-w64-%RsMSYS2Architecture%-rapidjson"
:: Plugins :: Plugins
if "%ParamPlugins%"=="1" %EnvMSYS2Cmd% "pacman --noconfirm --needed -S mingw-w64-%RsMSYS2Architecture%-speex mingw-w64-%RsMSYS2Architecture%-speexdsp mingw-w64-%RsMSYS2Architecture%-curl mingw-w64-%RsMSYS2Architecture%-libxslt mingw-w64-%RsMSYS2Architecture%-opencv mingw-w64-%RsMSYS2Architecture%-ffmpeg" if "%ParamPlugins%"=="1" %EnvMSYS2Cmd% "pacman --noconfirm --needed -S mingw-w64-%RsMSYS2Architecture%-speex mingw-w64-%RsMSYS2Architecture%-speexdsp mingw-w64-%RsMSYS2Architecture%-curl mingw-w64-%RsMSYS2Architecture%-libxslt mingw-w64-%RsMSYS2Architecture%-opencv mingw-w64-%RsMSYS2Architecture%-ffmpeg"
@ -52,6 +52,12 @@ set RS_QMAKE_CONFIG=%RS_QMAKE_CONFIG% "CONFIG+=%RsBuildConfig%"
if "%ParamAutologin%"=="1" set RS_QMAKE_CONFIG=%RS_QMAKE_CONFIG% "CONFIG+=rs_autologin" if "%ParamAutologin%"=="1" set RS_QMAKE_CONFIG=%RS_QMAKE_CONFIG% "CONFIG+=rs_autologin"
if "%ParamPlugins%"=="1" set RS_QMAKE_CONFIG=%RS_QMAKE_CONFIG% "CONFIG+=retroshare_plugins" if "%ParamPlugins%"=="1" set RS_QMAKE_CONFIG=%RS_QMAKE_CONFIG% "CONFIG+=retroshare_plugins"
:: Dump the active build config into a file
echo %RS_QMAKE_CONFIG% > buildinfo.txt
echo %RsBuildConfig% >> buildinfo.txt
echo %RsArchitecture% >> buildinfo.txt
echo Qt %QtVersion% >> buildinfo.txt
call "%ToolsPath%\msys2-path.bat" "%SourcePath%" MSYS2SourcePath call "%ToolsPath%\msys2-path.bat" "%SourcePath%" MSYS2SourcePath
call "%ToolsPath%\msys2-path.bat" "%EnvMSYS2Path%" MSYS2EnvMSYS2Path call "%ToolsPath%\msys2-path.bat" "%EnvMSYS2Path%" MSYS2EnvMSYS2Path
%EnvMSYS2Cmd% "qmake "%MSYS2SourcePath%/RetroShare.pro" -r -spec win32-g++ %RS_QMAKE_CONFIG%" %EnvMSYS2Cmd% "qmake "%MSYS2SourcePath%/RetroShare.pro" -r -spec win32-g++ %RS_QMAKE_CONFIG%"
@ -65,6 +71,11 @@ title Build - %SourceName%-%RsBuildConfig% [make]
%EnvMSYS2Cmd% "make -j %NUMBER_OF_PROCESSORS%" %EnvMSYS2Cmd% "make -j %NUMBER_OF_PROCESSORS%"
:: Webui
if "%ParamWebui%"=="1" (
call "%~dp0..\tools\webui.bat"
)
:error :error
popd popd

View File

@ -6,6 +6,7 @@ set ParamDebug=0
set ParamAutologin=0 set ParamAutologin=0
set ParamPlugins=0 set ParamPlugins=0
set ParamTor=0 set ParamTor=0
set ParamWebui=0
set RS_QMAKE_CONFIG= set RS_QMAKE_CONFIG=
:parameter_loop :parameter_loop
@ -25,6 +26,8 @@ if "%~1" NEQ "" (
set ParamPlugins=1 set ParamPlugins=1
) else if "%%~a"=="tor" ( ) else if "%%~a"=="tor" (
set ParamTor=1 set ParamTor=1
) else if "%%~a"=="webui" (
set ParamWebui=1
) else if "%%~a"=="CONFIG+" ( ) else if "%%~a"=="CONFIG+" (
set RS_QMAKE_CONFIG=%RS_QMAKE_CONFIG% %1 set RS_QMAKE_CONFIG=%RS_QMAKE_CONFIG% %1
) else ( ) else (
@ -75,12 +78,15 @@ if "%ParamTor%"=="1" (
set RsType= set RsType=
) )
if "%ParamWebui%"=="1" (
set RS_QMAKE_CONFIG=%RS_QMAKE_CONFIG% "CONFIG+=rs_jsonapi" "CONFIG+=rs_webui"
)
exit /B 0 exit /B 0
:usage :usage
echo. echo.
echo Usage: 32^|64 release^|debug [version autologin plugins] echo Usage: 32^|64 release^|debug [version autologin plugins webui]
echo. echo.
echo Mandatory parameter echo Mandatory parameter
echo 32^|64 32-bit or 64-bit Version echo 32^|64 32-bit or 64-bit Version
@ -89,6 +95,7 @@ echo.
echo Optional parameter (need clean when changed) echo Optional parameter (need clean when changed)
echo autologin Build with autologin echo autologin Build with autologin
echo plugins Build plugins echo plugins Build plugins
echo webui Enable JsonAPI and pack webui files
echo. echo.
echo Parameter for pack echo Parameter for pack
echo tor Pack tor version echo tor Pack tor version

View File

@ -20,6 +20,7 @@ set RsBuildPath=%BuildPath%\Qt-%QtVersion%-%RsArchitecture%-%RsBuildConfig%
set RsDeployPath=%DeployPath%\Qt-%QtVersion%%RsType%-%RsArchitecture%-%RsBuildConfig% set RsDeployPath=%DeployPath%\Qt-%QtVersion%%RsType%-%RsArchitecture%-%RsBuildConfig%
set RsPackPath=%DeployPath% set RsPackPath=%DeployPath%
set RsArchiveAdd= set RsArchiveAdd=
set RsWebuiPath=%RootPath%\%SourceName%-webui
if not exist "%~dp0env-mod.bat" goto no_mod if not exist "%~dp0env-mod.bat" goto no_mod
call "%~dp0env-mod.bat" call "%~dp0env-mod.bat"

View File

@ -23,7 +23,7 @@ call "%ToolsPath%\find-in-path.bat" GitPath git.exe
if "%GitPath%"=="" echo Git executable not found in PATH.& exit /B 1 if "%GitPath%"=="" echo Git executable not found in PATH.& exit /B 1
:: Get compiled revision :: Get compiled revision
set GetRsVersion=%SourcePath%\build_scripts\Windows\tools\get-rs-version.bat set GetRsVersion=%SourcePath%\build_scripts\Windows-msys2\tools\get-rs-version.bat
if not exist "%GetRsVersion%" ( if not exist "%GetRsVersion%" (
echo File not found echo File not found
echo %GetRsVersion% echo %GetRsVersion%

View File

@ -17,6 +17,9 @@ call "%~dp0env.bat" %*
if errorlevel 2 exit /B 2 if errorlevel 2 exit /B 2
if errorlevel 1 goto error_env if errorlevel 1 goto error_env
:: Install ntldd
%EnvMSYS2Cmd% "pacman --noconfirm --needed -S make git mingw-w64-%RsMSYS2Architecture%-ntldd-git"
:: Remove deploy path :: Remove deploy path
if exist "%RsDeployPath%" rmdir /S /Q "%RsDeployPath%" if exist "%RsDeployPath%" rmdir /S /Q "%RsDeployPath%"
@ -24,7 +27,7 @@ if exist "%RsDeployPath%" rmdir /S /Q "%RsDeployPath%"
if not exist "%RsBuildPath%\Makefile" echo Project is not compiled.& goto error if not exist "%RsBuildPath%\Makefile" echo Project is not compiled.& goto error
:: Get compiled revision :: Get compiled revision
set GetRsVersion=%SourcePath%\build_scripts\Windows\tools\get-rs-version.bat set GetRsVersion=%SourcePath%\build_scripts\Windows-msys2\tools\get-rs-version.bat
if not exist "%GetRsVersion%" ( if not exist "%GetRsVersion%" (
%cecho% error "File not found" %cecho% error "File not found"
echo %GetRsVersion% echo %GetRsVersion%
@ -100,16 +103,13 @@ echo copy binaries
copy "%RsBuildPath%\retroshare-gui\src\%RsBuildConfig%\RetroShare*.exe" "%RsDeployPath%" %Quite% copy "%RsBuildPath%\retroshare-gui\src\%RsBuildConfig%\RetroShare*.exe" "%RsDeployPath%" %Quite%
copy "%RsBuildPath%\retroshare-nogui\src\%RsBuildConfig%\retroshare*-nogui.exe" "%RsDeployPath%" %Quite% copy "%RsBuildPath%\retroshare-nogui\src\%RsBuildConfig%\retroshare*-nogui.exe" "%RsDeployPath%" %Quite%
copy "%RsBuildPath%\retroshare-service\src\%RsBuildConfig%\retroshare*-service.exe" "%RsDeployPath%" %Quite% copy "%RsBuildPath%\retroshare-service\src\%RsBuildConfig%\retroshare*-service.exe" "%RsDeployPath%" %Quite%
copy "%RsBuildPath%\supportlibs\cmark\build\src\libcmark.dll" "%RsDeployPath%" %Quite%
echo copy extensions echo copy extensions
for /D %%D in ("%RsBuildPath%\plugins\*") do ( for /D %%D in ("%RsBuildPath%\plugins\*") do (
call :copy_extension "%%D" "%RsDeployPath%\Data\%Extensions%" call :copy_extension "%%D" "%RsDeployPath%\Data\%Extensions%"
call :copy_dependencies "%RsDeployPath%\Data\%Extensions%\%%~nxD.dll" "%RsDeployPath%"
) )
echo copy dependencies
call :copy_dependencies "%RsDeployPath%\retroshare.exe" "%RsDeployPath%"
echo copy Qt DLL's echo copy Qt DLL's
copy "%RsMinGWPath%\bin\Qt%QtMainVersion1%Svg%QtMainVersion2%.dll" "%RsDeployPath%" %Quite% copy "%RsMinGWPath%\bin\Qt%QtMainVersion1%Svg%QtMainVersion2%.dll" "%RsDeployPath%" %Quite%
@ -128,7 +128,9 @@ if exist "%QtSharePath%\plugins\styles\qwindowsvistastyle.dll" (
copy "%QtSharePath%\plugins\imageformats\*.dll" "%RsDeployPath%\imageformats" %Quite% copy "%QtSharePath%\plugins\imageformats\*.dll" "%RsDeployPath%\imageformats" %Quite%
del /Q "%RsDeployPath%\imageformats\*d?.dll" %Quite% del /Q "%RsDeployPath%\imageformats\*d?.dll" %Quite%
for %%D in ("%RsDeployPath%\imageformats\*.dll") do (
echo copy dependencies
for /R "%RsDeployPath%" %%D in (*.dll, *.exe) do (
call :copy_dependencies "%%D" "%RsDeployPath%" call :copy_dependencies "%%D" "%RsDeployPath%"
) )
@ -161,10 +163,18 @@ copy "%SourcePath%\libbitdht\src\bitdht\bdboot.txt" "%RsDeployPath%" %Quite%
echo copy changelog.txt echo copy changelog.txt
copy "%SourcePath%\retroshare-gui\src\changelog.txt" "%RsDeployPath%" %Quite% copy "%SourcePath%\retroshare-gui\src\changelog.txt" "%RsDeployPath%" %Quite%
if exist "%SourcePath%\libresapi\src\webui" ( echo copy buildinfo.txt
copy "%RsBuildPath%\buildinfo.txt" "%RsDeployPath%" %Quite%
if "%ParamWebui%"=="1" (
if exist "%RsWebuiPath%\webui" (
echo copy webui echo copy webui
mkdir "%RsDeployPath%\webui" mkdir "%RsDeployPath%\webui"
xcopy /S "%SourcePath%\libresapi\src\webui" "%RsDeployPath%\webui" %Quite% xcopy /S "%RsWebuiPath%\webui" "%RsDeployPath%\webui" %Quite%
) else (
%cecho% error "Webui is enabled, but no webui data found at %RsWebuiPath%\webui"
goto error
)
) )
if "%ParamTor%"=="1" ( if "%ParamTor%"=="1" (
@ -204,14 +214,11 @@ if exist "%~1\%RsBuildConfig%\%~n1.dll" (
goto :EOF goto :EOF
:copy_dependencies :copy_dependencies
set CopyDependenciesCopiedSomething=0 for /F "usebackq" %%A in (`%ToolsPath%\depends.bat %1`) do (
for /F "usebackq" %%A in (`%ToolsPath%\depends.bat list %1`) do (
if not exist "%~2\%%A" ( if not exist "%~2\%%A" (
if exist "%RsMinGWPath%\bin\%%A" ( if exist "%RsMinGWPath%\bin\%%A" (
set CopyDependenciesCopiedSomething=1
copy "%RsMinGWPath%\bin\%%A" %2 %Quite% copy "%RsMinGWPath%\bin\%%A" %2 %Quite%
) )
) )
) )
if "%CopyDependenciesCopiedSomething%"=="1" goto copy_dependencies
goto :EOF goto :EOF

View File

@ -7,9 +7,7 @@ set EnvToolsPath=%EnvRootPath%\tools
set EnvTempPath=%EnvRootPath%\tmp set EnvTempPath=%EnvRootPath%\tmp
set EnvDownloadPath=%EnvRootPath%\download set EnvDownloadPath=%EnvRootPath%\download
set EnvWgetExe=%EnvToolsPath%\wget.exe
set EnvSevenZipExe=%EnvToolsPath%\7z.exe set EnvSevenZipExe=%EnvToolsPath%\7z.exe
set EnvDependsExe=%EnvToolsPath%\depends.exe
set EnvCEchoExe=%EnvToolsPath%\cecho.exe set EnvCEchoExe=%EnvToolsPath%\cecho.exe
set cecho=call "%ToolsPath%\cecho.bat" set cecho=call "%ToolsPath%\cecho.bat"

View File

@ -6,22 +6,6 @@ set CEchoUrl=https://github.com/lordmulder/cecho/releases/download/2015-10-10/ce
set CEchoInstall=cecho.2015-10-10.zip set CEchoInstall=cecho.2015-10-10.zip
set SevenZipUrl=https://sourceforge.net/projects/sevenzip/files/7-Zip/18.05/7z1805.msi/download set SevenZipUrl=https://sourceforge.net/projects/sevenzip/files/7-Zip/18.05/7z1805.msi/download
set SevenZipInstall=7z1805.msi set SevenZipInstall=7z1805.msi
set WgetUrl=https://eternallybored.org/misc/wget/1.19.4/32/wget.exe
set WgetInstall=wget.exe
set DependsUrl=http://www.dependencywalker.com/depends22_x86.zip
set DependsInstall=depends22_x86.zip
set SigcheckInstall=Sigcheck.zip
set SigcheckUrl=https://download.sysinternals.com/files/%SigcheckInstall%
if not exist "%EnvToolsPath%\wget.exe" (
echo Download Wget installation
if not exist "%EnvDownloadPath%\%WgetInstall%" call "%ToolsPath%\winhttpjs.bat" %WgetUrl% -saveTo "%EnvDownloadPath%\%WgetInstall%"
if not exist "%EnvDownloadPath%\%WgetInstall%" %cecho% error "Cannot download Wget installation" & goto error
echo Copy Wget
copy "%EnvDownloadPath%\wget.exe" "%EnvToolsPath%"
)
if not exist "%EnvToolsPath%\7z.exe" ( if not exist "%EnvToolsPath%\7z.exe" (
call "%ToolsPath%\remove-dir.bat" "%EnvTempPath%" call "%ToolsPath%\remove-dir.bat" "%EnvTempPath%"
@ -56,32 +40,6 @@ if not exist "%EnvToolsPath%\cecho.exe" (
call "%ToolsPath%\remove-dir.bat" "%EnvTempPath%" call "%ToolsPath%\remove-dir.bat" "%EnvTempPath%"
) )
if not exist "%EnvToolsPath%\depends.exe" (
call "%ToolsPath%\remove-dir.bat" "%EnvTempPath%"
mkdir "%EnvTempPath%"
%cecho% info "Download Dependency Walker installation"
if not exist "%EnvDownloadPath%\%DependsInstall%" call "%ToolsPath%\winhttpjs.bat" %DependsUrl% -saveTo "%EnvDownloadPath%\%DependsInstall%"
if not exist "%EnvDownloadPath%\%DependsInstall%" %cecho% error "Cannot download Dependendy Walker installation" & goto error
%cecho% info "Unpack Dependency Walker"
"%EnvSevenZipExe%" x -o"%EnvTempPath%" "%EnvDownloadPath%\%DependsInstall%"
copy "%EnvTempPath%\*" "%EnvToolsPath%"
call "%ToolsPath%\remove-dir.bat" "%EnvTempPath%"
)
if not exist "%EnvToolsPath%\sigcheck.exe" (
%cecho% info "Download Sigcheck installation"
if not exist "%EnvDownloadPath%\%SigcheckInstall%" call "%ToolsPath%\download-file.bat" "%SigcheckUrl%" "%EnvDownloadPath%\%SigcheckInstall%"
if not exist "%EnvDownloadPath%\%SigcheckInstall%" %cecho% error "Cannot download Sigcheck installation" & goto error
%cecho% info "Unpack Sigcheck"
"%EnvSevenZipExe%" x -o"%EnvToolsPath%" "%EnvDownloadPath%\%SigcheckInstall%" sigcheck.exe
)
:exit :exit
endlocal endlocal
exit /B 0 exit /B 0

View File

@ -1,40 +1,22 @@
:: Usage: :: Usage:
:: call depends.bat [list^|missing] file :: call depends.bat file
if "%2"=="" ( if "%1"=="" (
echo Usage: %~nx0 [list^|missing] File echo Usage: %~nx0 File
exit /B 1 exit /B 1
) )
setlocal setlocal
pushd %~dp1
if not exist "%EnvDependsExe%" echo depends.exe not found in %EnvToolsPath%.& exit /B 1 %EnvMSYS2Cmd% "ntldd --recursive $0 | cut -f1 -d"=" | awk '{$1=$1};1'" %~nx1 > %~sdp0depends.tmp
set CutPath= for /F %%A in (%~sdp0depends.tmp) do (
call "%ToolsPath%\find-in-path.bat" CutPath cut.exe
if "%CutPath%"=="" echo cut.exe not found in PATH.& exit /B 1
start /wait "" "%EnvDependsExe%" /c /oc:"%~dp0depends.tmp" %2
if "%1"=="missing" (
cut.exe --delimiter=, --fields=1,2 "%~dp0depends.tmp" >"%~dp0depends1.tmp"
for /F "tokens=1,2 delims=," %%A in (%~sdp0depends1.tmp) do (
if "%%A"=="?" (
echo %%~B
)
)
)
if "%1"=="list" (
cut.exe --delimiter=, --fields=2 "%~dp0depends.tmp" >"%~dp0depends1.tmp"
for /F "tokens=1 delims=," %%A in (%~sdp0depends1.tmp) do (
if "%%A" NEQ "Module" (
echo %%~A echo %%~A
)
)
) )
if exist "%~dp0depends.tmp" del /Q "%~dp0depends.tmp" if exist "%~dp0depends.tmp" del /Q "%~dp0depends.tmp"
if exist "%~dp0depends1.tmp" del /Q "%~dp0depends1.tmp"
popd
endlocal endlocal
exit /B 0 exit /B 0

View File

@ -7,7 +7,6 @@ if "%~2"=="" (
exit /B 1 exit /B 1
) )
::"%EnvCurlExe%" -L -k "%~1" -o "%~2" powershell -NoLogo -NoProfile -Command (New-Object System.Net.WebClient).DownloadFile(\""%~1\"", \""%~2\"")
"%EnvWgetExe%" --no-check-certificate --continue "%~1" --output-document="%~2"
exit /B %ERRORLEVEL% exit /B %ERRORLEVEL%

View File

@ -27,7 +27,7 @@ set VersionMinor=
set VersionMini= set VersionMini=
set VersionExtra= set VersionExtra=
for /F "tokens=1,2,3,* delims=.-" %%A in ('%EnvToolsPath%\sigcheck.exe -nobanner -n %Executable%') do ( for /F "USEBACKQ tokens=1,2,3,* delims=.-" %%A in (`powershell -NoLogo -NoProfile -Command ^(Get-Item "%Executable%"^).VersionInfo.FileVersion`) do (
set VersionMajor=%%A set VersionMajor=%%A
set VersionMinor=%%B set VersionMinor=%%B
set VersionMini=%%C set VersionMini=%%C

View File

@ -0,0 +1,20 @@
setlocal
echo.
echo === webui
echo.
title Build webui
if not exist "%RsWebuiPath%" (
echo Checking out webui source into %RsWebuiPath%
%EnvMSYS2Cmd% "pacman --noconfirm --needed -S git"
git clone https://github.com/RetroShare/RSNewWebUI.git "%RsWebuiPath%"
) else (
echo Webui source found at %RsWebuiPath%
)
pushd "%RsWebuiPath%\webui-src\make-src"
%EnvMSYS2Cmd% "sh build.sh"
popd
endlocal

View File

@ -1,584 +0,0 @@
@if (@X) == (@Y) @end /* JScript comment
@echo off
rem :: the first argument is the script name as it will be used for proper help message
cscript //E:JScript //nologo "%~f0" "%~nx0" %*
exit /b %errorlevel%
@if (@X)==(@Y) @end JScript comment */
// used resources
// update 12.10.15
// osvikvi(https://github.com/osvikvi) has nodited that the -password option is not set , so this is fixed
//https://msdn.microsoft.com/en-us/library/windows/desktop/aa384058(v=vs.85).aspx
//https://msdn.microsoft.com/en-us/library/windows/desktop/aa384055(v=vs.85).aspx
//https://msdn.microsoft.com/en-us/library/windows/desktop/aa384059(v=vs.85).aspx
// global variables and constants
// ----------------------------------
// -- asynch requests not included --
// ----------------------------------
//todo - save responceStream instead of responceBody !!
//todo - set all winthttp options ->//https://msdn.microsoft.com/en-us/library/windows/desktop/aa384108(v=vs.85).aspx
//todo - log all options
//todo - improve help message . eventual verbose option
var ARGS = WScript.Arguments;
var scriptName = ARGS.Item(0);
var url = "";
var saveTo = "";
var user = 0;
var pass = 0;
var proxy = 0;
var bypass = 0;
var proxy_user = 0;
var proxy_pass = 0;
var certificate = 0;
var force = true;
var body = "";
//ActiveX objects
var WinHTTPObj = new ActiveXObject("WinHttp.WinHttpRequest.5.1");
var FileSystemObj = new ActiveXObject("Scripting.FileSystemObject");
var AdoDBObj = new ActiveXObject("ADODB.Stream");
// HttpRequest SetCredentials flags.
var proxy_settings = 0;
//
HTTPREQUEST_SETCREDENTIALS_FOR_SERVER = 0;
HTTPREQUEST_SETCREDENTIALS_FOR_PROXY = 1;
//timeouts and their default values
var RESOLVE_TIMEOUT = 0;
var CONNECT_TIMEOUT = 90000;
var SEND_TIMEOUT = 90000;
var RECEIVE_TIMEOUT = 90000;
//HttpRequestMethod
var http_method = 'GET';
//header
var header_file = "";
//report
var reportfile = "";
//test-this:
var use_stream = false;
//autologon policy
var autologon_policy = 1; //0,1,2
//headers will be stored as multi-dimensional array
var headers = [];
//user-agent
var ua = "";
//escape URL
var escape = false;
function printHelp() {
WScript.Echo(scriptName + " - sends HTTP request and saves the request body as a file and/or a report of the sent request");
WScript.Echo(scriptName + " url [-force yes|no] [-user username -password password] [-proxy proxyserver:port] [-bypass bypass_list]");
WScript.Echo(" [-proxyuser proxy_username -proxypassword proxy_password] [-certificate certificateString]");
WScript.Echo(" [-method GET|POST|PATCH|DELETE|HEAD|OPTIONS|CONNECT]");
WScript.Echo(" [-saveTo file] - to print response to console use con");
WScript.Echo(" [-sendTimeout int(milliseconds)]");
WScript.Echo(" [-resolveTimeout int(milliseconds)]");
WScript.Echo(" [-connectTimeout int(milliseconds)]");
WScript.Echo(" [-receiveTimeout int(milliseconds)]");
WScript.Echo(" [-autologonPolicy 1|2|3]");
WScript.Echo(" [-proxySettings 1|2|3] (https://msdn.microsoft.com/en-us/library/windows/desktop/aa384059(v=vs.85).aspx)");
//header
WScript.Echo(" [-headers-file header_file]");
//reportfile
WScript.Echo(" [-reportfile reportfile]");
WScript.Echo(" [-ua user-agent]");
WScript.Echo(" [-ua-file user-agent-file]");
WScript.Echo(" [-escape yes|no]");
WScript.Echo(" [-body body-string]");
WScript.Echo(" [-body-file body-file]");
WScript.Echo("-force - decide to not or to overwrite if the local files exists");
WScript.Echo("proxyserver:port - the proxy server");
WScript.Echo("bypass- bypass list");
WScript.Echo("proxy_user , proxy_password - credentials for proxy server");
WScript.Echo("user , password - credentials for the server");
WScript.Echo("certificate - location of SSL certificate");
WScript.Echo("method - what HTTP method will be used.Default is GET");
WScript.Echo("saveTo - save the responce as binary file");
WScript.Echo(" ");
WScript.Echo("Header file should contain key:value pairs.Lines starting with \"#\" will be ignored.");
WScript.Echo("value should NOT be enclosed with quotes");
WScript.Echo(" ");
WScript.Echo("Examples:");
WScript.Echo(scriptName + " http://somelink.com/somefile.zip -saveTo c:\\somefile.zip -certificate \"LOCAL_MACHINE\\Personal\\My Middle-Tier Certificate\"");
WScript.Echo(scriptName + " http://somelink.com/something.html -method POST -certificate \"LOCAL_MACHINE\\Personal\\My Middle-Tier Certificate\" -header c:\\header_file -reportfile c:\\reportfile.txt");
WScript.Echo(scriptName + "\"http://somelink\" -method POST -header hdrs.txt -reportfile reportfile2.txt -saveTo responsefile2 -ua \"Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/41.0.2228.0 Safari/537.36\" -body-file some.json");
}
function parseArgs() {
//
if (ARGS.Length < 2) {
WScript.Echo("insufficient arguments");
printHelp();
WScript.Quit(43);
}
// !!!
url = ARGS.Item(1);
// !!!
if (ARGS.Length % 2 != 0) {
WScript.Echo("illegal arguments");
printHelp();
WScript.Quit(44);
}
for (var i = 2; i < ARGS.Length - 1; i = i + 2) {
var arg = ARGS.Item(i).toLowerCase();
var next = ARGS.Item(i + 1);
try {
switch (arg) { // the try-catch is set mainly because of the parseInts
case "-force":
if (next == "no") {
force = false;
}
break;
case "-escape":
if (next == "yes") {
escape = true;
}
break;
case "-saveto":
saveTo = next;
break;
case "-user":
case "-u":
user = next;
break;
case "-pass":
case "-password":
case "-p":
pass = next;
break;
case "-proxy":
proxy = next;
break;
case "-bypass":
bypass = next;
break;
case "-proxyuser":
case "-pu":
proxy_user = next;
break;
case "-proxypassword":
case "-pp":
proxy_pass = next;
break;
case "-ua":
ua = next;
break;
case "-ua-file":
ua = readFile(next);
break;
case "-body":
body = next;
break;
case "-usestream":
//WScript.Echo("~~");
if (next.toLowerCase() === "yes") {
use_stream = true
};
break;
case "-body-file":
body = readFile(next);
break;
case "-certificate":
certificate = next;
break;
case "-method":
switch (next.toLowerCase()) {
case "post":
http_method = 'POST';
break;
case "get":
http_method = 'GET';
break;
case "head":
http_method = 'HEAD';
break;
case "put":
http_method = 'PUT';
break;
case "options":
http_method = 'OPTIONS';
break;
case "connect":
http_method = 'CONNECT';
break;
case "patch":
http_method = 'PATCH';
break;
case "delete":
http_method = 'DELETE';
break;
default:
WScript.Echo("Invalid http method passed " + next);
WScript.Echo("possible values are GET,POST,DELETE,PUT,CONNECT,PATCH,HEAD,OPTIONS");
WScript.Quit(1326);
break;
}
break;
case "-headers-file":
case "-header":
headers = readPropFile(next);
break;
case "-reportfile":
reportfile = next;
break;
//timeouts
case "-sendtimeout":
SEND_TIMEOUT = parseInt(next);
break;
case "-connecttimeout":
CONNECT_TIMEOUT = parseint(next);
break;
case "-resolvetimeout":
RESOLVE_TIMEOUT = parseInt(next);
break;
case "-receivetimeout":
RECEIVE_TIMEOUT = parseInt(next);
break;
case "-autologonpolicy":
autologon_policy = parseInt(next);
if (autologon_policy > 2 || autologon_policy < 0) {
WScript.Echo("out of autologon policy range");
WScript.Quit(87);
};
break;
case "-proxysettings":
proxy_settings = parseInt(next);
if (proxy_settings > 2 || proxy_settings < 0) {
WScript.Echo("out of proxy settings range");
WScript.Quit(87);
};
break;
default:
WScript.Echo("Invalid command line switch: " + arg);
WScript.Quit(1405);
break;
}
} catch (err) {
WScript.Echo(err.message);
WScript.Quit(1348);
}
}
}
stripTrailingSlash = function(path) {
while (path.substr(path.length - 1, path.length) == '\\') {
path = path.substr(0, path.length - 1);
}
return path;
}
function existsItem(path) {
return FileSystemObj.FolderExists(path) || FileSystemObj.FileExists(path);
}
function deleteItem(path) {
if (FileSystemObj.FileExists(path)) {
FileSystemObj.DeleteFile(path);
return true;
} else if (FileSystemObj.FolderExists(path)) {
FileSystemObj.DeleteFolder(stripTrailingSlash(path));
return true;
} else {
return false;
}
}
//-------------------------------
//----------------------
//----------
//-----
//--
function request(url) {
try {
WinHTTPObj.Open(http_method, url, false);
if (proxy != 0 && bypass != 0) {
WinHTTPObj.SetProxy(proxy_settings, proxy, bypass);
}
if (proxy != 0) {
WinHTTPObj.SetProxy(proxy_settings, proxy);
}
if (user != 0 && pass != 0) {
WinHTTPObj.SetCredentials(user, pass, HTTPREQUEST_SETCREDENTIALS_FOR_SERVER);
}
if (proxy_user != 0 && proxy_pass != 0) {
WinHTTPObj.SetCredentials(proxy_user, proxy_pass, HTTPREQUEST_SETCREDENTIALS_FOR_PROXY);
}
if (certificate != 0) {
WinHTTPObj.SetClientCertificate(certificate);
}
//set autologin policy
WinHTTPObj.SetAutoLogonPolicy(autologon_policy);
//set timeouts
WinHTTPObj.SetTimeouts(RESOLVE_TIMEOUT, CONNECT_TIMEOUT, SEND_TIMEOUT, RECEIVE_TIMEOUT);
if (headers.length !== 0) {
WScript.Echo("Sending with headers:");
for (var i = 0; i < headers.length; i++) {
WinHTTPObj.SetRequestHeader(headers[i][0], headers[i][1]);
WScript.Echo(headers[i][0] + ":" + headers[i][1]);
}
WScript.Echo("");
}
if (ua !== "") {
//user-agent option from:
//WinHttpRequestOption enumeration
// other options can be added like bellow
//https://msdn.microsoft.com/en-us/library/windows/desktop/aa384108(v=vs.85).aspx
WinHTTPObj.Option(0) = ua;
}
if (escape) {
WinHTTPObj.Option(3) = true;
}
if (trim(body) === "") {
WinHTTPObj.Send();
} else {
WinHTTPObj.Send(body);
}
var status = WinHTTPObj.Status
} catch (err) {
WScript.Echo(err.message);
WScript.Quit(666);
}
////////////////////////
// report //
////////////////////////
if (reportfile != "") {
//var report_string="";
var n = "\r\n";
var report_string = "Status:" + n;
report_string = report_string + " " + WinHTTPObj.Status;
report_string = report_string + " " + WinHTTPObj.StatusText + n;
report_string = report_string + " " + n;
report_string = report_string + "Response:" + n;
report_string = report_string + WinHTTPObj.ResponseText + n;
report_string = report_string + " " + n;
report_string = report_string + "Headers:" + n;
report_string = report_string + WinHTTPObj.GetAllResponseHeaders() + n;
WinHttpRequestOption_UserAgentString = 0; // Name of the user agent
WinHttpRequestOption_URL = 1; // Current URL
WinHttpRequestOption_URLCodePage = 2; // Code page
WinHttpRequestOption_EscapePercentInURL = 3; // Convert percents
// in the URL
// rest of the options can be seen and eventually added using this as reference
// https://msdn.microsoft.com/en-us/library/windows/desktop/aa384108(v=vs.85).aspx
report_string = report_string + "URL:" + n;
report_string = report_string + WinHTTPObj.Option(WinHttpRequestOption_URL) + n;
report_string = report_string + "URL Code Page:" + n;
report_string = report_string + WinHTTPObj.Option(WinHttpRequestOption_URLCodePage) + n;
report_string = report_string + "User Agent:" + n;
report_string = report_string + WinHTTPObj.Option(WinHttpRequestOption_UserAgentString) + n;
report_string = report_string + "Escapped URL:" + n;
report_string = report_string + WinHTTPObj.Option(WinHttpRequestOption_EscapePercentInURL) + n;
prepareateFile(force, reportfile);
WScript.Echo("Writing report to " + reportfile);
writeFile(reportfile, report_string);
}
switch (status) {
case 200:
WScript.Echo("Status: 200 OK");
break;
default:
WScript.Echo("Status: " + status);
WScript.Echo("Status was not OK. More info -> https://en.wikipedia.org/wiki/List_of_HTTP_status_codes");
}
//if as binary
if (saveTo.toLowerCase() === "con") {
WScript.Echo(WinHTTPObj.ResponseText);
}
if (saveTo !== "" && saveTo.toLowerCase() !== "con") {
prepareateFile(force, saveTo);
try {
if (use_stream) {
writeBinFile(saveTo, WinHTTPObj.ResponseStream);
} else {
writeBinFile(saveTo, WinHTTPObj.ResponseBody);
}
} catch (err) {
WScript.Echo("Failed to save the file as binary.Attempt to save it as text");
AdoDBObj.Close();
prepareateFile(true, saveTo);
writeFile(saveTo, WinHTTPObj.ResponseText);
}
}
WScript.Quit(status);
}
//--
//-----
//----------
//----------------------
//-------------------------------
function prepareateFile(force, file) {
if (force && existsItem(file)) {
if (!deleteItem(file)) {
WScript.Echo("Unable to delete " + file);
WScript.Quit(8);
}
} else if (existsItem(file)) {
WScript.Echo("Item " + file + " already exist");
WScript.Quit(9);
}
}
function writeBinFile(fileName, data) {
AdoDBObj.Type = 1;
AdoDBObj.Open();
AdoDBObj.Position = 0;
AdoDBObj.Write(data);
AdoDBObj.SaveToFile(fileName, 2);
AdoDBObj.Close();
}
function writeFile(fileName, data) {
AdoDBObj.Type = 2;
AdoDBObj.CharSet = "iso-8859-1";
AdoDBObj.Open();
AdoDBObj.Position = 0;
AdoDBObj.WriteText(data);
AdoDBObj.SaveToFile(fileName, 2);
AdoDBObj.Close();
}
function readFile(fileName) {
//check existence
try {
if (!FileSystemObj.FileExists(fileName)) {
WScript.Echo("file " + fileName + " does not exist!");
WScript.Quit(13);
}
if (FileSystemObj.GetFile(fileName).Size === 0) {
return "";
}
var fileR = FileSystemObj.OpenTextFile(fileName, 1);
var content = fileR.ReadAll();
fileR.Close();
return content;
} catch (err) {
WScript.Echo("Error while reading file: " + fileName);
WScript.Echo(err.message);
WScript.Echo("Will return empty string");
return "";
}
}
function readPropFile(fileName) {
//check existence
resultArray = [];
if (!FileSystemObj.FileExists(fileName)) {
WScript.Echo("(headers)file " + fileName + " does not exist!");
WScript.Quit(15);
}
if (FileSystemObj.GetFile(fileName).Size === 0) {
return resultArray;
}
var fileR = FileSystemObj.OpenTextFile(fileName, 1);
var line = "";
var k = "";
var v = "";
var lineN = 0;
var index = 0;
try {
WScript.Echo("parsing headers form " + fileName + " property file ");
while (!fileR.AtEndOfStream) {
line = fileR.ReadLine();
lineN++;
index = line.indexOf(":");
if (line.indexOf("#") === 0 || trim(line) === "") {
continue;
}
if (index === -1 || index === line.length - 1 || index === 0) {
WScript.Echo("Invalid line " + lineN);
WScript.Quit(93);
}
k = trim(line.substring(0, index));
v = trim(line.substring(index + 1, line.length));
resultArray.push([k, v]);
}
fileR.Close();
return resultArray;
} catch (err) {
WScript.Echo("Error while reading headers file: " + fileName);
WScript.Echo(err.message);
WScript.Echo("Will return empty array");
return resultArray;
}
}
function trim(str) {
return str.replace(/^\s+/, '').replace(/\s+$/, '');
}
function main() {
parseArgs();
request(url);
}
main();

View File

@ -1424,9 +1424,15 @@ int p3FileDatabase::SearchBoolExp(RsRegularExpression::Expression *exp, std::lis
return !results.empty() ; return !results.empty() ;
} }
bool p3FileDatabase::search(const RsFileHash &hash, FileSearchFlags hintflags, FileInfo &info) const
bool p3FileDatabase::search(
const RsFileHash &hash, FileSearchFlags hintflags, FileInfo &info) const
{ {
RS_STACK_MUTEX(mFLSMtx) ; RS_STACK_MUTEX(mFLSMtx);
if( (hintflags & RS_FILE_HINTS_EXTRA) &&
mExtraFiles->search(hash, hintflags, info) )
return true;
if(hintflags & RS_FILE_HINTS_LOCAL) if(hintflags & RS_FILE_HINTS_LOCAL)
{ {

View File

@ -4,7 +4,7 @@
* libretroshare: retroshare core library * * libretroshare: retroshare core library *
* * * *
* Copyright (C) 2008 Robert Fernie <retroshare@lunamutt.com> * * Copyright (C) 2008 Robert Fernie <retroshare@lunamutt.com> *
* Copyright (C) 2018-2019 Gioacchino Mazzurco <gio@eigenlab.org> * * Copyright (C) 2018-2020 Gioacchino Mazzurco <gio@eigenlab.org> *
* * * *
* This program is free software: you can redistribute it and/or modify * * This program is free software: you can redistribute it and/or modify *
* it under the terms of the GNU Lesser General Public License as * * it under the terms of the GNU Lesser General Public License as *
@ -21,6 +21,9 @@
* * * *
*******************************************************************************/ *******************************************************************************/
#include <limits>
#include <system_error>
#ifdef WINDOWS_SYS #ifdef WINDOWS_SYS
#include "util/rswin.h" #include "util/rswin.h"
#endif #endif
@ -245,12 +248,8 @@ bool ftExtraList::cleanupOldFiles()
/* remove items */ /* remove items */
for(std::list<RsFileHash>::iterator rit = toRemove.begin(); rit != toRemove.end(); ++rit) for(std::list<RsFileHash>::iterator rit = toRemove.begin(); rit != toRemove.end(); ++rit)
{ {
if (mFiles.end() != (it = mFiles.find(*rit))) if (mFiles.end() != (it = mFiles.find(*rit))) mFiles.erase(it);
{ mHashOfHash.erase(makeEncryptedHash(*rit));
cleanupEntry(it->second.info.path, it->second.info.transfer_info_flags);
mFiles.erase(it);
}
mHashOfHash.erase(makeEncryptedHash(*rit)) ;
} }
IndicateConfigChanged(); IndicateConfigChanged();
@ -258,46 +257,39 @@ bool ftExtraList::cleanupOldFiles()
return true; return true;
} }
bool ftExtraList::cleanupEntry(std::string /*path*/, TransferRequestFlags /*flags*/)
{
// if (flags & RS_FILE_CONFIG_CLEANUP_DELETE)
// {
// /* Delete the file? - not yet! */
// }
return true;
}
/***
* Hash file, and add to the files,
* file is removed after period.
**/
bool ftExtraList::hashExtraFile( bool ftExtraList::hashExtraFile(
std::string path, uint32_t period, TransferRequestFlags flags ) std::string path, uint32_t period, TransferRequestFlags flags )
{ {
#ifdef DEBUG_ELIST constexpr rstime_t max_int = std::numeric_limits<int>::max();
std::cerr << "ftExtraList::hashExtraFile() path: " << path; const rstime_t now = time(nullptr);
std::cerr << " period: " << period; const rstime_t timeOut = now + period;
std::cerr << " flags: " << flags;
std::cerr << std::endl; if(timeOut > max_int)
#endif
auto failure = [](std::string errMsg)
{ {
RsErr() << __PRETTY_FUNCTION__ << " " << errMsg << std::endl; /* Under the hood period is stored as int FileInfo::age so we do this
* check here to detect 2038 year problem
* https://en.wikipedia.org/wiki/Year_2038_problem */
RsErr() << __PRETTY_FUNCTION__ << " period: " << period << " > "
<< max_int - now << std::errc::value_too_large << std::endl;
return false; return false;
}; }
if(!RsDirUtil::fileExists(path)) if(!RsDirUtil::fileExists(path))
return failure("file: " + path + "not found"); {
RsErr() << __PRETTY_FUNCTION__ << " path: " << path
<< std::errc::no_such_file_or_directory << std::endl;
return false;
}
if(RsDirUtil::checkDirectory(path)) if(RsDirUtil::checkDirectory(path))
return failure("Cannot add a directory: " + path + "as extra file"); {
RsErr() << __PRETTY_FUNCTION__ << " path: " << path
<< std::errc::is_a_directory << std::endl;
return false;
}
FileDetails details(path, period, flags); FileDetails details(path, period, flags);
details.info.age = static_cast<int>(time(nullptr) + period); details.info.age = static_cast<int>(timeOut);
{ {
RS_STACK_MUTEX(extMutex); RS_STACK_MUTEX(extMutex);
@ -492,8 +484,7 @@ bool ftExtraList::loadList(std::list<RsItem *>& load)
if (ts > (rstime_t)fi->file.age) if (ts > (rstime_t)fi->file.age)
{ {
/* to old */ /* too old */
cleanupEntry(fi->file.path, TransferRequestFlags(fi->flags));
delete (*it); delete (*it);
continue ; continue ;
} }

View File

@ -60,7 +60,7 @@
#include "pqi/p3cfgmgr.h" #include "pqi/p3cfgmgr.h"
#include "util/rstime.h" #include "util/rstime.h"
class FileDetails class RS_DEPRECATED_FOR(FileInfo) FileDetails
{ {
public: public:
FileDetails() FileDetails()
@ -130,7 +130,11 @@ public:
* file is removed after period. * file is removed after period.
**/ **/
bool hashExtraFile(std::string path, uint32_t period, TransferRequestFlags flags); /**
* Hash file, and add to the files, file is removed after period.
*/
bool hashExtraFile(
std::string path, uint32_t period, TransferRequestFlags flags );
bool hashExtraFileDone(std::string path, FileInfo &info); bool hashExtraFileDone(std::string path, FileInfo &info);
/*** /***
@ -165,7 +169,6 @@ private:
/* Worker Functions */ /* Worker Functions */
void hashAFile(); void hashAFile();
bool cleanupOldFiles(); bool cleanupOldFiles();
bool cleanupEntry(std::string path, TransferRequestFlags flags);
mutable RsMutex extMutex; mutable RsMutex extMutex;

View File

@ -22,6 +22,8 @@
#include <algorithm> #include <algorithm>
#include <iostream> #include <iostream>
#include <limits>
#include <system_error>
#include "crypto/chacha20.h" #include "crypto/chacha20.h"
//const int ftserverzone = 29539; //const int ftserverzone = 29539;
@ -293,7 +295,8 @@ bool ftServer::getFileData(const RsFileHash& hash, uint64_t offset, uint32_t& re
bool ftServer::alreadyHaveFile(const RsFileHash& hash, FileInfo &info) bool ftServer::alreadyHaveFile(const RsFileHash& hash, FileInfo &info)
{ {
return mFileDatabase->search(hash, RS_FILE_HINTS_LOCAL, info); return mFileDatabase->search(
hash, RS_FILE_HINTS_EXTRA | RS_FILE_HINTS_LOCAL, info );
} }
bool ftServer::FileRequest( bool ftServer::FileRequest(
@ -819,6 +822,14 @@ bool ftServer::ExtraFileRemove(const RsFileHash& hash)
bool ftServer::ExtraFileHash( bool ftServer::ExtraFileHash(
std::string localpath, rstime_t period, TransferRequestFlags flags ) std::string localpath, rstime_t period, TransferRequestFlags flags )
{ {
constexpr rstime_t uintmax = std::numeric_limits<uint32_t>::max();
if(period > uintmax)
{
RsErr() << __PRETTY_FUNCTION__ << " period: " << period << " > "
<< uintmax << std::errc::value_too_large << std::endl;
return false;
}
return mFtExtra->hashExtraFile( return mFtExtra->hashExtraFile(
localpath, static_cast<uint32_t>(period), flags ); localpath, static_cast<uint32_t>(period), flags );
} }

View File

@ -870,7 +870,7 @@ rs_jsonapi {
genrestbedheader.name = Generating restbed header. genrestbedheader.name = Generating restbed header.
genrestbedheader.input = genrestbedlib.output genrestbedheader.input = genrestbedlib.output
genrestbedheader.output = $${RESTBED_HEADER_FILE} genrestbedheader.output = $${RESTBED_HEADER_FILE}
genrestbedheader.CONFIG += target_predeps combine no_link genrestbedheader.CONFIG += target_predeps no_link
genrestbedheader.variable_out = HEADERS genrestbedheader.variable_out = HEADERS
genrestbedheader.commands = cd $${RESTBED_BUILD_PATH} && $(MAKE) install genrestbedheader.commands = cd $${RESTBED_BUILD_PATH} && $(MAKE) install
QMAKE_EXTRA_COMPILERS += genrestbedheader QMAKE_EXTRA_COMPILERS += genrestbedheader

View File

@ -658,7 +658,8 @@ public:
* @brief Get file details * @brief Get file details
* @jsonapi{development} * @jsonapi{development}
* @param[in] hash file identifier * @param[in] hash file identifier
* @param[in] hintflags filtering hint (RS_FILE_HINTS_EXTRA|...|RS_FILE_HINTS_LOCAL) * @param[in] hintflags filtering hint ( RS_FILE_HINTS_UPLOAD|...|
* RS_FILE_HINTS_EXTRA|RS_FILE_HINTS_LOCAL )
* @param[out] info storage for file information * @param[out] info storage for file information
* @return true if file found, false otherwise * @return true if file found, false otherwise
*/ */

View File

@ -310,6 +310,7 @@ public:
* @param[in] channelId id of the channel of which the content is requested * @param[in] channelId id of the channel of which the content is requested
* @param[out] posts storage for posts * @param[out] posts storage for posts
* @param[out] comments storage for the comments * @param[out] comments storage for the comments
* @param[out] votes storage for votes
* @return false if something failed, true otherwhise * @return false if something failed, true otherwhise
*/ */
virtual bool getChannelAllContent( const RsGxsGroupId& channelId, virtual bool getChannelAllContent( const RsGxsGroupId& channelId,

View File

@ -503,8 +503,16 @@ bool RsTypeSerializer::from_JSON( const std::string& /*memberName*/,
// Binary blocks // // Binary blocks //
//============================================================================// //============================================================================//
#if __cplusplus < 201703L
/* Solve weird undefined reference error with C++ < 17 see:
* https://stackoverflow.com/questions/8016780/undefined-reference-to-static-constexpr-char
*/
/*static*/ decltype(RsTypeSerializer::RawMemoryWrapper::base64_key) constexpr
RsTypeSerializer::RawMemoryWrapper::base64_key;
/*static*/ /* without this Android compilation breaks */ /*static*/ /* without this Android compilation breaks */
constexpr uint32_t RsTypeSerializer::RawMemoryWrapper::MAX_SERIALIZED_CHUNK_SIZE; constexpr uint32_t RsTypeSerializer::RawMemoryWrapper::MAX_SERIALIZED_CHUNK_SIZE;
#endif
/*static*/ /*static*/
void RsTypeSerializer::RawMemoryWrapper::serial_process( void RsTypeSerializer::RawMemoryWrapper::serial_process(
@ -542,18 +550,7 @@ void RsTypeSerializer::RawMemoryWrapper::serial_process(
ctx.mOffset += second; ctx.mOffset += second;
break; break;
case RsGenericSerializer::DESERIALIZE: case RsGenericSerializer::DESERIALIZE:
if(first || second) freshMemCheck();
{
/* Items are created anew before deserialization so buffer pointer
* must be null and size 0 at this point */
RsWarn() << __PRETTY_FUNCTION__ << " DESERIALIZE got uninitialized "
<< " or pre-allocated buffer! Buffer pointer: " << first
<< " must be null and size: " << second << " must be 0 at "
<< "this point. Does your item costructor initialize them "
<< "properly?" << std::endl;
print_stacktrace();
}
RS_SERIAL_PROCESS(second); RS_SERIAL_PROCESS(second);
if(!ctx.mOk) break; if(!ctx.mOk) break;
@ -597,44 +594,33 @@ void RsTypeSerializer::RawMemoryWrapper::serial_process(
if(!ctx.mOk) break; if(!ctx.mOk) break;
std::string encodedValue; std::string encodedValue;
RsBase64::encode(first, second, encodedValue, true, false); RsBase64::encode(first, second, encodedValue, true, false);
ctx.mJson.SetString( ctx.mOk = ctx.mOk &&
encodedValue.data(), RsTypeSerializer::to_JSON(base64_key, encodedValue, ctx.mJson);
static_cast<rapidjson::SizeType>(encodedValue.length()),
ctx.mJson.GetAllocator());
break; break;
} }
case RsGenericSerializer::FROM_JSON: case RsGenericSerializer::FROM_JSON:
{ {
const bool yelding = !!( freshMemCheck();
RsSerializationFlags::YIELDING & ctx.mFlags );
if(!(ctx.mOk || yelding))
{
clear();
break;
}
if(!ctx.mJson.IsString())
{
RsErr() << __PRETTY_FUNCTION__ << " "
<< std::errc::invalid_argument << std::endl;
print_stacktrace();
ctx.mOk = false; const auto failure = [&]() -> void { ctx.mOk = false; clear(); };
clear(); const bool yielding = !!(
break; RsSerializationFlags::YIELDING & ctx.mFlags );
} if(!(ctx.mOk || yielding)) return failure();
if( ctx.mJson.GetStringLength() >
std::string encodedValue;
if(!RsTypeSerializer::from_JSON(
base64_key, encodedValue, ctx.mJson )) return failure();
if( encodedValue.length() >
RsBase64::encodedSize(MAX_SERIALIZED_CHUNK_SIZE, true) ) RsBase64::encodedSize(MAX_SERIALIZED_CHUNK_SIZE, true) )
{ {
RsErr() << __PRETTY_FUNCTION__ << " " RsErr() << __PRETTY_FUNCTION__ << " "
<< std::errc::message_size << std::endl; << std::errc::message_size << std::endl;
print_stacktrace(); print_stacktrace();
ctx.mOk = false; return failure();
clear();
break;
} }
std::string encodedValue = ctx.mJson.GetString();
std::vector<uint8_t> decoded; std::vector<uint8_t> decoded;
auto ec = RsBase64::decode(encodedValue, decoded); auto ec = RsBase64::decode(encodedValue, decoded);
if(ec) if(ec)
@ -642,9 +628,7 @@ void RsTypeSerializer::RawMemoryWrapper::serial_process(
RsErr() << __PRETTY_FUNCTION__ << " " << ec << std::endl; RsErr() << __PRETTY_FUNCTION__ << " " << ec << std::endl;
print_stacktrace(); print_stacktrace();
ctx.mOk = false; return failure();
clear();
break;
} }
const auto decodedSize = decoded.size(); const auto decodedSize = decoded.size();
@ -655,11 +639,8 @@ void RsTypeSerializer::RawMemoryWrapper::serial_process(
break; break;
} }
if(decodedSize != second) first = reinterpret_cast<uint8_t*>(malloc(decodedSize));
{
first = reinterpret_cast<uint8_t*>(realloc(first, decodedSize));
second = static_cast<uint32_t>(decodedSize); second = static_cast<uint32_t>(decodedSize);
}
memcpy(first, decoded.data(), second); memcpy(first, decoded.data(), second);
break; break;
@ -675,6 +656,24 @@ void RsTypeSerializer::RawMemoryWrapper::clear()
second = 0; second = 0;
} }
bool RsTypeSerializer::RawMemoryWrapper::freshMemCheck()
{
if(first || second)
{
/* Items are created anew before deserialization so buffer pointer
* must be null and size 0 at this point */
RsWarn() << __PRETTY_FUNCTION__ << " got uninitialized "
<< " or pre-allocated buffer! Buffer pointer: " << first
<< " must be null and size: " << second << " must be 0 at "
<< "this point. Does your item costructor initialize them "
<< "properly?" << std::endl;
print_stacktrace();
return false;
}
return true;
}
//============================================================================// //============================================================================//
// std::error_condition // // std::error_condition //
//============================================================================// //============================================================================//

View File

@ -59,12 +59,17 @@ struct RsTypeSerializer
/// Maximum supported size 10MB /// Maximum supported size 10MB
static constexpr uint32_t MAX_SERIALIZED_CHUNK_SIZE = 10*1024*1024; static constexpr uint32_t MAX_SERIALIZED_CHUNK_SIZE = 10*1024*1024;
/** Key used for JSON serialization.
* @note Changing this value breaks JSON API retro-compatibility */
static constexpr char base64_key[] = "base64";
/// @see RsSerializable /// @see RsSerializable
void serial_process( void serial_process(
RsGenericSerializer::SerializeJob j, RsGenericSerializer::SerializeJob j,
RsGenericSerializer::SerializeContext& ctx ) override; RsGenericSerializer::SerializeContext& ctx ) override;
private: private:
void clear(); void clear();
bool freshMemCheck();
}; };
/// Most types are not valid sequence containers /// Most types are not valid sequence containers
@ -777,7 +782,7 @@ struct RsTypeSerializer
{ {
if(!yielding) if(!yielding)
{ {
std::cerr << __PRETTY_FUNCTION__ << " \"" << memberName RsErr() << __PRETTY_FUNCTION__ << " \"" << memberName
<< "\" not found in JSON:" << std::endl << "\" not found in JSON:" << std::endl
<< jDoc << std::endl << std::endl; << jDoc << std::endl << std::endl;
print_stacktrace(); print_stacktrace();
@ -790,7 +795,7 @@ struct RsTypeSerializer
if(!v.IsObject()) if(!v.IsObject())
{ {
std::cerr << __PRETTY_FUNCTION__ << " \"" << memberName RsErr() << __PRETTY_FUNCTION__ << " \"" << memberName
<< "\" has wrong type in JSON, object expected, got:" << "\" has wrong type in JSON, object expected, got:"
<< std::endl << jDoc << std::endl << std::endl; << std::endl << jDoc << std::endl << std::endl;
print_stacktrace(); print_stacktrace();

View File

@ -1192,6 +1192,10 @@ bool p3MsgService::MessageSend(MessageInfo &info)
imsg[msg->msgId] = msg; imsg[msg->msgId] = msg;
// Update info for caller
info.msgId = std::to_string(msg->msgId);
info .msgflags = msg->msgFlags;
RsServer::notify()->notifyListChange(NOTIFY_LIST_MESSAGELIST,NOTIFY_TYPE_ADD); RsServer::notify()->notifyListChange(NOTIFY_LIST_MESSAGELIST,NOTIFY_TYPE_ADD);
} }

View File

@ -117,11 +117,7 @@ void p3PhotoService::groupsChanged(std::list<RsGxsGroupId>& grpIds)
while(!mGroupChange.empty()) while(!mGroupChange.empty())
{ {
RsGxsGroupChange* gc = mGroupChange.back(); RsGxsGroupChange* gc = mGroupChange.back();
std::list<RsGxsGroupId>& gList = gc->mGrpIdList; grpIds.push_back(gc->mGroupId);
std::list<RsGxsGroupId>::iterator lit = gList.begin();
for(; lit != gList.end(); ++lit) {
grpIds.push_back(*lit);
}
mGroupChange.pop_back(); mGroupChange.pop_back();
delete gc; delete gc;
@ -136,7 +132,8 @@ void p3PhotoService::msgsChanged(GxsMsgIdResult& msgs)
while(!mMsgChange.empty()) while(!mMsgChange.empty())
{ {
RsGxsMsgChange* mc = mMsgChange.back(); RsGxsMsgChange* mc = mMsgChange.back();
msgs = mc->msgChangeMap;
msgs[mc->mGroupId].insert(mc->mMsgId);
mMsgChange.pop_back(); mMsgChange.pop_back();
delete mc; delete mc;
} }

View File

@ -21,8 +21,6 @@
* * * *
*******************************************************************************/ *******************************************************************************/
#include <cmath>
#include "util/rsbase64.h" #include "util/rsbase64.h"
#include "util/rsdebug.h" #include "util/rsdebug.h"
@ -40,6 +38,12 @@
rs_view_ptr<const uint8_t> data, size_t len, std::string& outString, rs_view_ptr<const uint8_t> data, size_t len, std::string& outString,
bool padding, bool urlSafe ) bool padding, bool urlSafe )
{ {
if(!data || !len)
{
outString.clear();
return;
}
const char* sDict = urlSafe ? uDict : bDict; const char* sDict = urlSafe ? uDict : bDict;
// Workaround if input and output are the same buffer. // Workaround if input and output are the same buffer.
@ -137,9 +141,11 @@
/*static*/ size_t RsBase64::encodedSize(size_t decodedSize, bool padding) /*static*/ size_t RsBase64::encodedSize(size_t decodedSize, bool padding)
{ {
if(padding) return 4 * (decodedSize + 2) / 3; if(!decodedSize) return 0;
return static_cast<size_t>(
std::ceil(4L * static_cast<double>(decodedSize) / 3L) ); // Thanks https://stackoverflow.com/a/45401395
if(padding) return ceilDivision(decodedSize, 3) * 4;
return ceilDivision(decodedSize * 8, 6);
} }
/*static*/ std::tuple<size_t, std::error_condition> RsBase64::decodedSize( /*static*/ std::tuple<size_t, std::error_condition> RsBase64::decodedSize(

View File

@ -137,4 +137,8 @@ private:
*/ */
static inline bool isBase64Char(char c) static inline bool isBase64Char(char c)
{ return rDict[static_cast<uint8_t>(c)] >= 0; } { return rDict[static_cast<uint8_t>(c)] >= 0; }
/** Perform ceil division without floating point operations */
static inline size_t ceilDivision(size_t dividend, size_t divisor)
{ return (dividend + divisor - 1) / divisor; }
}; };

View File

@ -32,6 +32,8 @@ std::ostream &operator<<(std::ostream& out, const std::error_condition& err);
# include <sstream> # include <sstream>
# include <string> # include <string>
# include "util/rsjson.h"
enum class RsLoggerCategories enum class RsLoggerCategories
{ {
DEBUG = ANDROID_LOG_DEBUG, DEBUG = ANDROID_LOG_DEBUG,
@ -46,6 +48,18 @@ struct t_RsLogger
{ {
inline t_RsLogger() = default; inline t_RsLogger() = default;
/** Offer variadic style too, as a benefit this has better atomicity then
* << style, but doesn't supports manipulators and things like std::endl
* @see https://stackoverflow.com/a/27375675 */
template <typename Arg, typename... Args>
inline t_RsLogger(Arg&& arg, Args&&... args)
{
ostr << std::forward<Arg>(arg);
using expander = int[];
(void)expander{0, (void(ostr << std::forward<Args>(args)), 0)...};
mFlush();
}
/** On other platforms expose the type of underlying stream. /** On other platforms expose the type of underlying stream.
* On Android it cannot work like that so return the class type itself * On Android it cannot work like that so return the class type itself
* just for code compatibility with other platforms */ * just for code compatibility with other platforms */
@ -55,17 +69,16 @@ struct t_RsLogger
inline stream_type& operator<<(const T& val) inline stream_type& operator<<(const T& val)
{ ostr << val; return *this; } { ostr << val; return *this; }
template<typename T>
inline stream_type& operator<<(const RsJson& val)
{ ostr << val; return *this; }
/// needed for manipulators and things like std::endl /// needed for manipulators and things like std::endl
stream_type& operator<<(std::ostream& (*pf)(std::ostream&)) stream_type& operator<<(std::ostream& (*pf)(std::ostream&))
{ {
if(pf == static_cast<std::ostream& (*)(std::ostream&)>( if(pf == static_cast<std::ostream& (*)(std::ostream&)>(
&std::endl< char, std::char_traits<char> > )) &std::endl< char, std::char_traits<char> > ))
{ mFlush();
__android_log_write(
static_cast<int>(CATEGORY),
"RetroShare", ostr.str().c_str() );
ostr.str() = "";
}
else ostr << pf; else ostr << pf;
return *this; return *this;
@ -78,6 +91,14 @@ struct t_RsLogger
private: private:
std::ostringstream ostr; std::ostringstream ostr;
void mFlush()
{
__android_log_write(
static_cast<int>(CATEGORY),
"RetroShare", ostr.str().c_str() );
ostr.str() = "";
}
}; };
#else // def __ANDROID__ #else // def __ANDROID__
@ -99,38 +120,56 @@ enum class RsLoggerCategories
template <RsLoggerCategories CATEGORY> template <RsLoggerCategories CATEGORY>
struct t_RsLogger struct t_RsLogger
{ {
inline t_RsLogger() = default;
/// Expose the type of underlying stream /// Expose the type of underlying stream
using stream_type = decltype(std::cerr); using stream_type = decltype(std::cerr);
/// Return underlying stream to write avoiding additional prefixes
static inline stream_type& uStream() { return std::cerr; }
inline t_RsLogger() = default;
/** Offer variadic style too, as a benefit this has better atomicity then
* << style, but doesn't supports manipulators and things like std::endl
* @see https://stackoverflow.com/a/27375675 */
template <typename Arg, typename... Args>
inline t_RsLogger(Arg&& arg, Args&&... args)
{
std::ostringstream ostr;
ostr << getPrefix() << std::forward<Arg>(arg);
using expander = int[];
(void)expander{0, (void(ostr << std::forward<Args>(args)), 0)...};
ostr << std::endl;
uStream() << ostr.str();
}
template<typename T> template<typename T>
inline stream_type& operator<<(const T& val) inline stream_type& operator<<(const T& val)
{ return uStream() << getPrefix() << val; }
/// needed for manipulators and things like std::endl
stream_type& operator<<(std::ostream& (*pf)(std::ostream&))
{ return uStream() << pf; }
private:
std::string getPrefix()
{ {
using namespace std::chrono; using namespace std::chrono;
const auto now = system_clock::now(); const auto now = system_clock::now();
const auto sec = time_point_cast<seconds>(now); const auto sec = time_point_cast<seconds>(now);
const auto msec = duration_cast<milliseconds>(now - sec); const auto msec = duration_cast<milliseconds>(now - sec);
std::stringstream tstream; std::ostringstream tstream;
tstream << static_cast<char>(CATEGORY) << " " tstream << static_cast<char>(CATEGORY) << " "
<< sec.time_since_epoch().count() << "." << sec.time_since_epoch().count() << "."
<< std::setfill('0') << std::setw(3) << msec.count() << std::setfill('0') << std::setw(3) << msec.count()
<< " " << val; << " ";
return std::cerr << tstream.str(); return tstream.str();
} }
/// needed for manipulators and things like std::endl
stream_type& operator<<(std::ostream& (*pf)(std::ostream&))
{ return std::cerr << pf; }
/// Return underlying stream to write avoiding additional prefixes
inline stream_type& uStream() const { return std::cerr; }
}; };
#endif // def __ANDROID__ #endif // def __ANDROID__
/** /**
* Comfortable debug message loggin, supports chaining like std::cerr but can * Comfortable debug message logging, supports chaining like std::cerr but can
* be easly and selectively disabled at compile time to reduce generated binary * be easly and selectively disabled at compile time to reduce generated binary
* size and performance impact without too many \#ifdef around. * size and performance impact without too many \#ifdef around.
* *
@ -190,6 +229,8 @@ struct RsNoDbg
{ {
inline RsNoDbg() = default; inline RsNoDbg() = default;
template <typename T, typename... Args> inline RsNoDbg(T, Args...) {}
/** Defined as the type itself just for code compatibility with other /** Defined as the type itself just for code compatibility with other
* logging classes */ * logging classes */
using stream_type = RsNoDbg; using stream_type = RsNoDbg;

View File

@ -29,7 +29,7 @@
typedef rapidjson::Document RsJson; typedef rapidjson::Document RsJson;
/** /**
* Print out RsJson to a stream, use std::stringstream to get the string * Print out RsJson to a stream, use std::ostringstream to get the string
* @param[out] out output stream * @param[out] out output stream
* @param[in] jDoc JSON document to print * @param[in] jDoc JSON document to print
* @return same output stream passed as out parameter * @return same output stream passed as out parameter

View File

@ -115,6 +115,7 @@ ChatWidget::ChatWidget(QWidget *parent)
//ui->sendButton->setFixedHeight(iconHeight); //ui->sendButton->setFixedHeight(iconHeight);
ui->sendButton->setIconSize(iconSize); ui->sendButton->setIconSize(iconSize);
ui->typingLabel->setMaximumHeight(QFontMetricsF(font()).height()*1.2); ui->typingLabel->setMaximumHeight(QFontMetricsF(font()).height()*1.2);
ui->fontcolorButton->setIconSize(iconSize);
//Initialize search //Initialize search
iCharToStartSearch=Settings->getChatSearchCharToStartSearch(); iCharToStartSearch=Settings->getChatSearchCharToStartSearch();
@ -189,7 +190,7 @@ ChatWidget::ChatWidget(QWidget *parent)
ui->hashBox->setDropWidget(this); ui->hashBox->setDropWidget(this);
ui->hashBox->setAutoHide(true); ui->hashBox->setAutoHide(true);
QMenu *fontmenu = new QMenu(tr("Set text font & color")); QMenu *fontmenu = new QMenu();
fontmenu->addAction(ui->actionChooseFont); fontmenu->addAction(ui->actionChooseFont);
fontmenu->addAction(ui->actionChooseColor); fontmenu->addAction(ui->actionChooseColor);
fontmenu->addAction(ui->actionResetFont); fontmenu->addAction(ui->actionResetFont);
@ -198,10 +199,10 @@ ChatWidget::ChatWidget(QWidget *parent)
#ifdef USE_CMARK #ifdef USE_CMARK
fontmenu->addAction(ui->actionSend_as_CommonMark); fontmenu->addAction(ui->actionSend_as_CommonMark);
#endif #endif
ui->fontcolorButton->setMenu(fontmenu);
QMenu *menu = new QMenu(); QMenu *menu = new QMenu();
menu->addAction(ui->actionMessageHistory); menu->addAction(ui->actionMessageHistory);
menu->addMenu(fontmenu);
menu->addSeparator(); menu->addSeparator();
menu->addAction(ui->actionSaveChatHistory); menu->addAction(ui->actionSaveChatHistory);
menu->addAction(ui->actionClearChatHistory); menu->addAction(ui->actionClearChatHistory);

View File

@ -455,13 +455,13 @@ border-image: url(:/images/closepressed.png)
</widget> </widget>
</item> </item>
<item> <item>
<widget class="QToolButton" name="notifyButton"> <widget class="QToolButton" name="fontcolorButton">
<property name="focusPolicy"> <property name="toolTip">
<enum>Qt::NoFocus</enum> <string>Set font &amp; color</string>
</property> </property>
<property name="icon"> <property name="icon">
<iconset resource="../icons.qrc"> <iconset resource="../icons.qrc">
<normaloff>:/icons/png/chat-bubble-notify.png</normaloff>:/icons/png/chat-bubble-notify.png</iconset> <normaloff>:/icons/png/font.png</normaloff>:/icons/png/font.png</iconset>
</property> </property>
<property name="iconSize"> <property name="iconSize">
<size> <size>
@ -469,6 +469,9 @@ border-image: url(:/images/closepressed.png)
<height>28</height> <height>28</height>
</size> </size>
</property> </property>
<property name="popupMode">
<enum>QToolButton::InstantPopup</enum>
</property>
<property name="autoRaise"> <property name="autoRaise">
<bool>true</bool> <bool>true</bool>
</property> </property>
@ -769,6 +772,26 @@ border-image: url(:/images/closepressed.png)
</property> </property>
</widget> </widget>
</item> </item>
<item>
<widget class="QToolButton" name="notifyButton">
<property name="focusPolicy">
<enum>Qt::NoFocus</enum>
</property>
<property name="icon">
<iconset resource="../icons.qrc">
<normaloff>:/icons/png/chat-bubble-notify.png</normaloff>:/icons/png/chat-bubble-notify.png</iconset>
</property>
<property name="iconSize">
<size>
<width>28</width>
<height>28</height>
</size>
</property>
<property name="autoRaise">
<bool>true</bool>
</property>
</widget>
</item>
<item> <item>
<widget class="QToolButton" name="pushtoolsButton"> <widget class="QToolButton" name="pushtoolsButton">
<property name="focusPolicy"> <property name="focusPolicy">

View File

@ -39,19 +39,19 @@
//#define DEBUG_EID_PAINT 1 //#define DEBUG_EID_PAINT 1
/* To test it you can make an empty.qss file with: /* To test it you can make an empty.qss file with:
QTreeView::item, QTreeWidget::item{ QTreeView::item, QTreeWidget::item, QListWidget::item{
color: #AB0000; color: #AB0000;
background-color: #00DC00; background-color: #00DC00;
} }
QTreeView::item:selected, QTreeWidget::item:selected{ QTreeView::item:selected, QTreeWidget::item:selected, QListWidget::item:selected{
color: #00CD00; color: #00CD00;
background-color: #0000BA; background-color: #0000BA;
} }
QTreeView::item:hover, QTreeWidget::item:hover{ QTreeView::item:hover, QTreeWidget::item:hover, QListWidget::item:hover{
color: #0000EF; color: #0000EF;
background-color: #FEDCBA; background-color: #FEDCBA;
} }
QQTreeView::item:selected:hover, TreeWidget::item:selected:hover{ QQTreeView::item:selected:hover, TreeWidget::item:selected:hover, QListWidget::item:selected:hover{
color: #ABCDEF; color: #ABCDEF;
background-color: #FE0000; background-color: #FE0000;
} }

View File

@ -23,6 +23,10 @@
#ifndef ELNODE_H #ifndef ELNODE_H
#define ELNODE_H #define ELNODE_H
#include "graphwidget.h"
#include <retroshare/rstypes.h>
#include <QApplication> #include <QApplication>
#if QT_VERSION >= 0x040600 #if QT_VERSION >= 0x040600
#include <QGraphicsObject> #include <QGraphicsObject>
@ -30,9 +34,7 @@
#include <QGraphicsItem> #include <QGraphicsItem>
#endif #endif
#include <QList> #include <QList>
#include <QPainterPath>
#include <retroshare/rstypes.h>
#include "graphwidget.h"
class Edge; class Edge;
QT_BEGIN_NAMESPACE QT_BEGIN_NAMESPACE

View File

@ -937,5 +937,7 @@
<file>emojione/1F1FF-1F1FC.png</file> <file>emojione/1F1FF-1F1FC.png</file>
<file>emojione/flags.png</file> <file>emojione/flags.png</file>
<file>emojione/flags2.png</file> <file>emojione/flags2.png</file>
<file>emojione/man-facepalming.png</file>
<file>emojione/woman-facepalming.png</file>
</qresource> </qresource>
</RCC> </RCC>

View File

@ -113,6 +113,8 @@
"emojione/people2.png"|":man_with_gua_pi_mao:":"emojione/1F472.png"; "emojione/people2.png"|":man_with_gua_pi_mao:":"emojione/1F472.png";
"emojione/people2.png"|":levitate:|:man_in_business_suit_levitating:":"emojione/1F574.png"; "emojione/people2.png"|":levitate:|:man_in_business_suit_levitating:":"emojione/1F574.png";
"emojione/people2.png"|":dancer:":"emojione/1F483.png"; "emojione/people2.png"|":dancer:":"emojione/1F483.png";
"emojione/people2.png"|":man_facepalming:":"emojione/man-facepalming.png";
"emojione/people2.png"|":woman_facepalming:":"emojione/woman-facepalming.png";
"emojione/people2.png"|":bust_in_silhouette:":"emojione/1F464.png"; "emojione/people2.png"|":bust_in_silhouette:":"emojione/1F464.png";
"emojione/people2.png"|":busts_in_silhouette:":"emojione/1F465.png"; "emojione/people2.png"|":busts_in_silhouette:":"emojione/1F465.png";
"emojione/people2.png"|":family:":"emojione/1F46A.png"; "emojione/people2.png"|":family:":"emojione/1F46A.png";

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

View File

@ -427,7 +427,7 @@ void GxsChannelPostItem::fill()
QString title; QString title;
float f = QFontMetricsF(font()).height()/14.0 ; //float f = QFontMetricsF(font()).height()/14.0 ;
if(mPost.mThumbnail.mData != NULL) if(mPost.mThumbnail.mData != NULL)
{ {
@ -629,14 +629,21 @@ QString GxsChannelPostItem::messageName()
void GxsChannelPostItem::setReadStatus(bool isNew, bool isUnread) void GxsChannelPostItem::setReadStatus(bool isNew, bool isUnread)
{ {
if (isNew)
mPost.mMeta.mMsgStatus |= GXS_SERV::GXS_MSG_STATUS_GUI_NEW;
else
mPost.mMeta.mMsgStatus &= ~GXS_SERV::GXS_MSG_STATUS_GUI_NEW;
if (isUnread) if (isUnread)
{ {
ui->readButton->setChecked(true); mPost.mMeta.mMsgStatus |= GXS_SERV::GXS_MSG_STATUS_GUI_UNREAD;
whileBlocking(ui->readButton)->setChecked(true);
ui->readButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/message-state-unread.png")); ui->readButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/message-state-unread.png"));
} }
else else
{ {
ui->readButton->setChecked(false); mPost.mMeta.mMsgStatus &= ~GXS_SERV::GXS_MSG_STATUS_GUI_UNREAD;
whileBlocking(ui->readButton)->setChecked(false);
ui->readButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/message-state-read.png")); ui->readButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/message-state-read.png"));
} }
@ -835,7 +842,7 @@ void GxsChannelPostItem::play()
} }
} }
void GxsChannelPostItem::readToggled(bool checked) void GxsChannelPostItem::readToggled(bool /*checked*/)
{ {
if (mInFill) { if (mInFill) {
return; return;
@ -845,10 +852,9 @@ void GxsChannelPostItem::readToggled(bool checked)
RsGxsGrpMsgIdPair msgPair = std::make_pair(groupId(), messageId()); RsGxsGrpMsgIdPair msgPair = std::make_pair(groupId(), messageId());
uint32_t token; rsGxsChannels->markRead(msgPair, isUnread());
rsGxsChannels->setMessageReadStatus(token, msgPair, !checked);
setReadStatus(false, checked); //setReadStatus(false, checked); // Updated by events
} }
void GxsChannelPostItem::makeDownVote() void GxsChannelPostItem::makeDownVote()

View File

@ -62,7 +62,10 @@ public:
QString getMsgLabel(); QString getMsgLabel();
const std::list<SubFileItem *> &getFileItems() {return mFileItems; } const std::list<SubFileItem *> &getFileItems() {return mFileItems; }
bool isLoaded() const {return mLoaded;};
bool isUnread() const ; bool isUnread() const ;
void setReadStatus(bool isNew, bool isUnread);
const std::set<RsGxsMessageId>& olderVersions() const { return mPost.mOlderVersions; } const std::set<RsGxsMessageId>& olderVersions() const { return mPost.mOlderVersions; }
static uint64_t computeIdentifier(const RsGxsMessageId& msgid) { return hash64("GxsChannelPostItem " + msgid.toStdString()) ; } static uint64_t computeIdentifier(const RsGxsMessageId& msgid) { return hash64("GxsChannelPostItem " + msgid.toStdString()) ; }
@ -112,7 +115,6 @@ private:
void setup(); void setup();
void fill(); void fill();
void fillExpandFrame(); void fillExpandFrame();
void setReadStatus(bool isNew, bool isUnread);
private: private:
bool mInFill; bool mInFill;

View File

@ -129,7 +129,7 @@ void GxsCircleItem::setup()
{ {
if(circleDetails.mAmIAdmin) if(circleDetails.mAmIAdmin)
{ {
ui->titleLabel->setText(idName + tr(" which you invited, has join this circle you're administrating.")); ui->titleLabel->setText(idName + tr(" which you invited, has joined this circle you're administrating."));
ui->inviteeButton->setHidden(false); ui->inviteeButton->setHidden(false);
ui->inviteeButton->setText(tr("Revoke membership")); ui->inviteeButton->setText(tr("Revoke membership"));
ui->inviteeButton->setToolTip(tr("Revoke membership for that identity")); ui->inviteeButton->setToolTip(tr("Revoke membership for that identity"));
@ -137,7 +137,7 @@ void GxsCircleItem::setup()
else else
{ {
ui->inviteeButton->setHidden(true); ui->inviteeButton->setHidden(true);
ui->titleLabel->setText(idName + tr(" has join this circle.")); ui->titleLabel->setText(idName + tr(" has joined this circle."));
} }
ui->iconLabel->setPixmap(pixmap); ui->iconLabel->setPixmap(pixmap);

View File

@ -18,6 +18,14 @@
* * * *
*******************************************************************************/ *******************************************************************************/
#include "GxsCommentTreeWidget.h"
#include "gui/common/FilesDefs.h"
#include "gui/common/RSElidedItemDelegate.h"
#include "gui/common/RSTreeWidgetItem.h"
#include "gui/gxs/GxsCreateCommentDialog.h"
#include "gui/gxs/GxsIdTreeWidgetItem.h"
#include <QAbstractTextDocumentLayout> #include <QAbstractTextDocumentLayout>
#include <QApplication> #include <QApplication>
#include <QClipboard> #include <QClipboard>
@ -25,15 +33,9 @@
#include <QMenu> #include <QMenu>
#include <QMimeData> #include <QMimeData>
#include <QPainter> #include <QPainter>
#include <QPainterPath>
#include <QTextDocument> #include <QTextDocument>
#include "gui/common/RSElidedItemDelegate.h"
#include "gui/common/FilesDefs.h"
#include "gui/gxs/GxsCommentTreeWidget.h"
#include "gui/gxs/GxsCreateCommentDialog.h"
#include "gui/gxs/GxsIdTreeWidgetItem.h"
#include "gui/common/RSTreeWidgetItem.h"
#include <iostream> #include <iostream>
#define PCITEM_COLUMN_COMMENT 0 #define PCITEM_COLUMN_COMMENT 0

View File

@ -18,21 +18,23 @@
* * * *
*******************************************************************************/ *******************************************************************************/
#include <QApplication>
#include <QThread>
#include <QTimerEvent>
#include <QMutexLocker>
#include <math.h>
#include <util/rsdir.h>
#include "gui/common/AvatarDialog.h"
#include "GxsIdDetails.h" #include "GxsIdDetails.h"
#include "gui/common/AvatarDialog.h"
#include "retroshare-gui/RsAutoUpdatePage.h" #include "retroshare-gui/RsAutoUpdatePage.h"
#include <retroshare/rspeers.h> #include <retroshare/rspeers.h>
#include <util/rsdir.h>
#include <QApplication>
#include <QMutexLocker>
#include <QPainter>
#include <QPainterPath>
#include <QThread>
#include <QTimerEvent>
#include <iostream> #include <iostream>
#include <QPainter> #include <cmath>
/* Images for tag icons */ /* Images for tag icons */
#define IMAGE_LOADING ":/images/folder-draft.png" #define IMAGE_LOADING ":/images/folder-draft.png"

View File

@ -146,13 +146,19 @@ void GxsChannelPostsWidget::handleEvent_main_thread(std::shared_ptr<const RsEven
switch(e->mChannelEventCode) switch(e->mChannelEventCode)
{ {
case RsChannelEventCode::UPDATED_CHANNEL: case RsChannelEventCode::NEW_CHANNEL: // [[fallthrough]];
case RsChannelEventCode::NEW_CHANNEL: case RsChannelEventCode::UPDATED_CHANNEL: // [[fallthrough]];
case RsChannelEventCode::NEW_MESSAGE: // [[fallthrough]];
case RsChannelEventCode::UPDATED_MESSAGE: case RsChannelEventCode::UPDATED_MESSAGE:
case RsChannelEventCode::NEW_MESSAGE:
if(e->mChannelGroupId == groupId()) if(e->mChannelGroupId == groupId())
updateDisplay(true); updateDisplay(true);
break; break;
case RsChannelEventCode::READ_STATUS_CHANGED:
if (FeedItem *feedItem = ui->feedWidget->findFeedItem(GxsChannelPostItem::computeIdentifier(e->mChannelMsgId)))
if (GxsChannelPostItem *channelPostItem = dynamic_cast<GxsChannelPostItem*>(feedItem))
channelPostItem->setReadStatus(false,!channelPostItem->isUnread());
//channelPostItem->setReadStatus(false,e->Don't get read status. Will be more easier and accurate);
break;
default: default:
break; break;
} }
@ -909,9 +915,9 @@ static void setAllMessagesReadCallback(FeedItem *feedItem, void *data)
} }
GxsChannelPostsReadData *readData = (GxsChannelPostsReadData*) data; GxsChannelPostsReadData *readData = (GxsChannelPostsReadData*) data;
bool is_not_new = !channelPostItem->isUnread() ; bool isRead = !channelPostItem->isUnread() ;
if(is_not_new == readData->mRead) if(channelPostItem->isLoaded() && (isRead == readData->mRead))
return ; return ;
RsGxsGrpMsgIdPair msgPair = std::make_pair(channelPostItem->groupId(), channelPostItem->messageId()); RsGxsGrpMsgIdPair msgPair = std::make_pair(channelPostItem->groupId(), channelPostItem->messageId());

View File

@ -301,6 +301,7 @@
<file>icons/png/arrow-left.png</file> <file>icons/png/arrow-left.png</file>
<file>icons/png/next-unread.png</file> <file>icons/png/next-unread.png</file>
<file>icons/mail/compose.png</file> <file>icons/mail/compose.png</file>
<file>icons/mail/downloadall.png</file>
<file>icons/mail/delete.png</file> <file>icons/mail/delete.png</file>
<file>icons/mail/tags.png</file> <file>icons/mail/tags.png</file>
<file>icons/mail/quote.png</file> <file>icons/mail/quote.png</file>

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 5.4 KiB

After

Width:  |  Height:  |  Size: 2.3 KiB

View File

@ -1206,6 +1206,12 @@ MessageComposer *MessageComposer::replyMsg(const std::string &msgId, bool all)
// needed to send system flags with reply // needed to send system flags with reply
msgComposer->msgFlags = (msgInfo.msgflags & RS_MSG_SYSTEM); msgComposer->msgFlags = (msgInfo.msgflags & RS_MSG_SYSTEM);
MsgTagInfo tagInfo;
rsMail->getMessageTag(msgId, tagInfo);
msgComposer->m_tagIds = tagInfo.tagIds;
msgComposer->showTagLabels();
msgComposer->calculateTitle(); msgComposer->calculateTitle();
/* window will destroy itself! */ /* window will destroy itself! */

View File

@ -36,6 +36,7 @@
#include "gui/common/TagDefs.h" #include "gui/common/TagDefs.h"
#include "gui/common/PeerDefs.h" #include "gui/common/PeerDefs.h"
#include "gui/common/Emoticons.h" #include "gui/common/Emoticons.h"
#include "gui/common/FilesDefs.h"
#include "gui/settings/rsharesettings.h" #include "gui/settings/rsharesettings.h"
#include "MessageComposer.h" #include "MessageComposer.h"
#include "MessageWidget.h" #include "MessageWidget.h"
@ -51,8 +52,8 @@
#include <retroshare/rsmsgs.h> #include <retroshare/rsmsgs.h>
/* Images for context menu icons */ /* Images for context menu icons */
#define IMAGE_DOWNLOAD ":/images/start.png" #define IMAGE_DOWNLOAD ":/icons/png/download.png"
#define IMAGE_DOWNLOADALL ":/images/startall.png" #define IMAGE_DOWNLOADALL ":/icons/mail/downloadall.png"
#define COLUMN_FILE_NAME 0 #define COLUMN_FILE_NAME 0
#define COLUMN_FILE_SIZE 1 #define COLUMN_FILE_SIZE 1
@ -555,6 +556,7 @@ void MessageWidget::fill(const std::string &msgId)
for (it = recList.begin(); it != recList.end(); ++it) { for (it = recList.begin(); it != recList.end(); ++it) {
QTreeWidgetItem *item = new QTreeWidgetItem; QTreeWidgetItem *item = new QTreeWidgetItem;
item->setText(COLUMN_FILE_NAME, QString::fromUtf8(it->fname.c_str())); item->setText(COLUMN_FILE_NAME, QString::fromUtf8(it->fname.c_str()));
item->setIcon(COLUMN_FILE_NAME, FilesDefs::getIconFromFileType(it->fname.c_str()));
item->setText(COLUMN_FILE_SIZE, misc::friendlyUnit(it->size)); item->setText(COLUMN_FILE_SIZE, misc::friendlyUnit(it->size));
item->setData(COLUMN_FILE_SIZE, Qt::UserRole, QVariant(qulonglong(it->size)) ); item->setData(COLUMN_FILE_SIZE, Qt::UserRole, QVariant(qulonglong(it->size)) );
item->setText(COLUMN_FILE_HASH, QString::fromStdString(it->hash.toStdString())); item->setText(COLUMN_FILE_HASH, QString::fromStdString(it->hash.toStdString()));
@ -668,9 +670,13 @@ void MessageWidget::fill(const std::string &msgId)
ui.subjectText->setText(QString::fromUtf8(msgInfo.title.c_str())); ui.subjectText->setText(QString::fromUtf8(msgInfo.title.c_str()));
// emoticons disabled because of crazy cost. unsigned int formatTextFlag = RSHTML_FORMATTEXT_EMBED_LINKS ;
//text = RsHtmlMsg(msgInfo.msgflags).formatText(ui.msgText->document(), QString::fromUtf8(msgInfo.msg.c_str()), RSHTML_FORMATTEXT_EMBED_SMILEYS | RSHTML_FORMATTEXT_EMBED_LINKS);
text = RsHtmlMsg(msgInfo.msgflags).formatText(ui.msgText->document(), QString::fromUtf8(msgInfo.msg.c_str()), RSHTML_FORMATTEXT_EMBED_LINKS); // embed smileys ?
if (Settings->valueFromGroup(QString("Messages"), QString::fromUtf8("Emoticons"), true).toBool()) {
formatTextFlag |= RSHTML_FORMATTEXT_EMBED_SMILEYS ;
}
text = RsHtmlMsg(msgInfo.msgflags).formatText(ui.msgText->document(), QString::fromUtf8(msgInfo.msg.c_str()), formatTextFlag);
ui.msgText->resetImagesStatus(Settings->getMsgLoadEmbeddedImages() || (msgInfo.msgflags & RS_MSG_LOAD_EMBEDDED_IMAGES)); ui.msgText->resetImagesStatus(Settings->getMsgLoadEmbeddedImages() || (msgInfo.msgflags & RS_MSG_LOAD_EMBEDDED_IMAGES));
ui.msgText->setHtml(text); ui.msgText->setHtml(text);

View File

@ -53,6 +53,7 @@
#include <algorithm> #include <algorithm>
/* Images for context menu icons */ /* Images for context menu icons */
#define IMAGE_MAIL ":/icons/png/message.png"
#define IMAGE_MESSAGE ":/icons/mail/compose.png" #define IMAGE_MESSAGE ":/icons/mail/compose.png"
#define IMAGE_MESSAGEREMOVE ":/icons/mail/delete.png" #define IMAGE_MESSAGEREMOVE ":/icons/mail/delete.png"
#define IMAGE_STAR_ON ":/images/star-on-16.png" #define IMAGE_STAR_ON ":/images/star-on-16.png"
@ -766,7 +767,7 @@ void MessagesDialog::openAsTab()
return; return;
} }
ui.tabWidget->addTab(msgWidget, msgWidget->subject(true)); ui.tabWidget->addTab(msgWidget,QIcon(IMAGE_MAIL), msgWidget->subject(true));
ui.tabWidget->setCurrentWidget(msgWidget); ui.tabWidget->setCurrentWidget(msgWidget);
connect(msgWidget, SIGNAL(messageRemoved()), this, SLOT(messageRemoved())); connect(msgWidget, SIGNAL(messageRemoved()), this, SLOT(messageRemoved()));
@ -1104,7 +1105,10 @@ void MessagesDialog::removemessage()
void MessagesDialog::messageRemoved() void MessagesDialog::messageRemoved()
{ {
if (lastSelectedIndex.isValid())
ui.messageTreeWidget->setCurrentIndex(lastSelectedIndex); ui.messageTreeWidget->setCurrentIndex(lastSelectedIndex);
else
insertMsgTxtAndFiles(QModelIndex());
} }
void MessagesDialog::undeletemessage() void MessagesDialog::undeletemessage()

View File

@ -904,6 +904,16 @@ MessagesDialog QWidget#messageTreeWidget::item {
padding: 2px; padding: 2px;
} }
MessagesDialog QWidget#messageTreeWidget::item:selected {
background-color: #cde8ff;
color: black;
}
MessagesDialog QWidget#messageTreeWidget::item:hover {
background-color: #e5f3ff;
color: black;
}
GxsForumThreadWidget QWidget#threadTreeWidget::item { GxsForumThreadWidget QWidget#threadTreeWidget::item {
padding: 2px; padding: 2px;
} }

View File

@ -39,7 +39,6 @@ MessagePage::MessagePage(QWidget * parent, Qt::WindowFlags flags)
connect (ui.editpushButton, SIGNAL(clicked(bool)), this, SLOT (editTag())); connect (ui.editpushButton, SIGNAL(clicked(bool)), this, SLOT (editTag()));
connect (ui.deletepushButton, SIGNAL(clicked(bool)), this, SLOT (deleteTag())); connect (ui.deletepushButton, SIGNAL(clicked(bool)), this, SLOT (deleteTag()));
connect (ui.defaultTagButton, SIGNAL(clicked(bool)), this, SLOT (defaultTag())); connect (ui.defaultTagButton, SIGNAL(clicked(bool)), this, SLOT (defaultTag()));
//connect (ui.encryptedMsgs_CB, SIGNAL(toggled(bool)), this, SLOT (toggleEnableEncryptedDistantMsgs(bool)));
connect (ui.tags_listWidget, SIGNAL(currentRowChanged(int)), this, SLOT(currentRowChangedTag(int))); connect (ui.tags_listWidget, SIGNAL(currentRowChanged(int)), this, SLOT(currentRowChangedTag(int)));
@ -54,6 +53,7 @@ MessagePage::MessagePage(QWidget * parent, Qt::WindowFlags flags)
connect(ui.setMsgToReadOnActivate,SIGNAL(toggled(bool)), this,SLOT(updateMsgToReadOnActivate())); connect(ui.setMsgToReadOnActivate,SIGNAL(toggled(bool)), this,SLOT(updateMsgToReadOnActivate()));
connect(ui.loadEmbeddedImages, SIGNAL(toggled(bool)), this,SLOT(updateLoadEmbededImages() )); connect(ui.loadEmbeddedImages, SIGNAL(toggled(bool)), this,SLOT(updateLoadEmbededImages() ));
connect(ui.openComboBox, SIGNAL(currentIndexChanged(int)),this,SLOT(updateMsgOpen() )); connect(ui.openComboBox, SIGNAL(currentIndexChanged(int)),this,SLOT(updateMsgOpen() ));
connect(ui.emoticonscheckBox, SIGNAL(toggled(bool)), this,SLOT(updateLoadEmoticons() ));
} }
MessagePage::~MessagePage() MessagePage::~MessagePage()
@ -84,6 +84,7 @@ void MessagePage::updateMsgToReadOnActivate() { Settings->setMsgSetToReadOnActiv
void MessagePage::updateLoadEmbededImages() { Settings->setMsgLoadEmbeddedImages(ui.loadEmbeddedImages->isChecked()); } void MessagePage::updateLoadEmbededImages() { Settings->setMsgLoadEmbeddedImages(ui.loadEmbeddedImages->isChecked()); }
void MessagePage::updateMsgOpen() { Settings->setMsgOpen( static_cast<RshareSettings::enumMsgOpen>(ui.openComboBox->itemData(ui.openComboBox->currentIndex()).toInt()) ); } void MessagePage::updateMsgOpen() { Settings->setMsgOpen( static_cast<RshareSettings::enumMsgOpen>(ui.openComboBox->itemData(ui.openComboBox->currentIndex()).toInt()) ); }
void MessagePage::updateDistantMsgs() { Settings->setValue("DistantMessages", ui.comboBox->currentIndex()); } void MessagePage::updateDistantMsgs() { Settings->setValue("DistantMessages", ui.comboBox->currentIndex()); }
void MessagePage::updateLoadEmoticons() { Settings->setValueToGroup("Messages", "Emoticons", ui.emoticonscheckBox->isChecked()); }
void MessagePage::updateMsgTags() void MessagePage::updateMsgTags()
{ {
@ -110,9 +111,12 @@ void MessagePage::updateMsgTags()
void void
MessagePage::load() MessagePage::load()
{ {
Settings->beginGroup(QString("Messages"));
whileBlocking(ui.setMsgToReadOnActivate)->setChecked(Settings->getMsgSetToReadOnActivate()); whileBlocking(ui.setMsgToReadOnActivate)->setChecked(Settings->getMsgSetToReadOnActivate());
whileBlocking(ui.loadEmbeddedImages)->setChecked(Settings->getMsgLoadEmbeddedImages()); whileBlocking(ui.loadEmbeddedImages)->setChecked(Settings->getMsgLoadEmbeddedImages());
whileBlocking(ui.openComboBox)->setCurrentIndex(ui.openComboBox->findData(Settings->getMsgOpen())); whileBlocking(ui.openComboBox)->setCurrentIndex(ui.openComboBox->findData(Settings->getMsgOpen()));
whileBlocking(ui.emoticonscheckBox)->setChecked(Settings->value("Emoticons", true).toBool());
Settings->endGroup();
// state of filter combobox // state of filter combobox
@ -267,3 +271,4 @@ void MessagePage::currentRowChangedTag(int row)
ui.editpushButton->setEnabled(bEditEnable); ui.editpushButton->setEnabled(bEditEnable);
ui.deletepushButton->setEnabled(bDeleteEnable); ui.deletepushButton->setEnabled(bDeleteEnable);
} }

View File

@ -58,6 +58,7 @@ private slots:
void updateMsgOpen() ; void updateMsgOpen() ;
void updateDistantMsgs() ; void updateDistantMsgs() ;
void updateMsgTags() ; void updateMsgTags() ;
void updateLoadEmoticons();
private: private:
void fillTags(); void fillTags();

View File

@ -65,14 +65,7 @@
</property> </property>
</widget> </widget>
</item> </item>
<item row="1" column="0"> <item row="3" column="0">
<widget class="QCheckBox" name="loadEmbeddedImages">
<property name="text">
<string>Load embedded images</string>
</property>
</widget>
</item>
<item row="2" column="0">
<layout class="QHBoxLayout" name="horizontalLayout"> <layout class="QHBoxLayout" name="horizontalLayout">
<item> <item>
<widget class="QLabel" name="openLabel"> <widget class="QLabel" name="openLabel">
@ -86,6 +79,20 @@
</item> </item>
</layout> </layout>
</item> </item>
<item row="1" column="0">
<widget class="QCheckBox" name="loadEmbeddedImages">
<property name="text">
<string>Load embedded images</string>
</property>
</widget>
</item>
<item row="2" column="0">
<widget class="QCheckBox" name="emoticonscheckBox">
<property name="text">
<string>Load Emoticons</string>
</property>
</widget>
</item>
</layout> </layout>
</widget> </widget>
</item> </item>

View File

@ -1157,7 +1157,7 @@ void RshareSettings::setWebinterfaceEnabled(bool enabled)
QString RshareSettings::getWebinterfaceFilesDirectory() QString RshareSettings::getWebinterfaceFilesDirectory()
{ {
#ifdef WINDOWS_SYS #ifdef WINDOWS_SYS
return valueFromGroup("Webinterface","directory","data/webui/").toString(); return valueFromGroup("Webinterface","directory","./webui/").toString();
#else #else
return valueFromGroup("Webinterface","directory","/usr/share/retroshare/webui/").toString(); return valueFromGroup("Webinterface","directory","/usr/share/retroshare/webui/").toString();
#endif #endif

View File

@ -51,6 +51,10 @@ background: black;
color: lightgray; color: lightgray;
border-color: transparent; border-color: transparent;
} }
QTreeView::item, QTreeWidget::item, QListWidget::item{
color: lightgray;
}
QDialog, QMainWindow{ QDialog, QMainWindow{
background-color: qlineargradient(spread:reflect, x1:0, y1:0, x2:0, y2:1, stop:0 rgb(25, 25, 25), stop:0.05 rgb(0, 0, 0), stop:0.95 rgb(0, 0, 0), stop:1 rgb(25, 25, 25)); background-color: qlineargradient(spread:reflect, x1:0, y1:0, x2:0, y2:1, stop:0 rgb(25, 25, 25), stop:0.05 rgb(0, 0, 0), stop:0.95 rgb(0, 0, 0), stop:1 rgb(25, 25, 25));
} }
@ -255,6 +259,12 @@ QTextEdit {
color: white; color: white;
} }
RSTextBrowser, MimeTextEdit
{
/*qproperty-textColorQuote: rgb(125, 125, 255);*/
qproperty-textColorQuotes: ColorList(#789922 #039bd5 #800000 #800080 #008080 #b10dc9 #85144b #3d9970);
}
/* OpModeStatus need to be at end to overload other values*/ /* OpModeStatus need to be at end to overload other values*/
OpModeStatus { OpModeStatus {
qproperty-opMode_Full_Color: #007000; qproperty-opMode_Full_Color: #007000;

View File

@ -51,6 +51,9 @@ QWidget {
selection-background-color: #1464A0; selection-background-color: #1464A0;
selection-color: #F0F0F0; selection-color: #F0F0F0;
} }
QTreeView::item, QTreeWidget::item, QListWidget::item{
color: #F0F0F0;
}
QWidget:disabled { QWidget:disabled {
background-color: #19232D; background-color: #19232D;
@ -2152,5 +2155,5 @@ GxsChannelDialog GroupTreeWidget QTreeWidget#treeWidget::item{
RSTextBrowser, MimeTextEdit RSTextBrowser, MimeTextEdit
{ {
/*qproperty-textColorQuote: rgb(125, 125, 255);*/ /*qproperty-textColorQuote: rgb(125, 125, 255);*/
qproperty-textColorQuotes: ColorList(#0000ff #00ff00 #00ffff #ff0000 #ff00ff #ffff00 #ffffff); qproperty-textColorQuotes: ColorList(#789922 #039bd5 #800000 #800080 #008080 #b10dc9 #85144b #3d9970);
} }

View File

@ -60,6 +60,9 @@ QWidget
border-image: none; border-image: none;
outline: 0; outline: 0;
} }
QTreeView::item, QTreeWidget::item, QListWidget::item{
color: silver;
}
QWidget:item:hover QWidget:item:hover
{ {
@ -1299,7 +1302,7 @@ WireGroupItem QFrame#frame{
RSTextBrowser, MimeTextEdit RSTextBrowser, MimeTextEdit
{ {
/*qproperty-textColorQuote: rgb(125, 125, 255);*/ /*qproperty-textColorQuote: rgb(125, 125, 255);*/
qproperty-textColorQuotes: ColorList(#0000ff #00ff00 #00ffff #ff0000 #ff00ff #ffff00 #ffffff); qproperty-textColorQuotes: ColorList(#789922 #039bd5 #800000 #800080 #008080 #b10dc9 #85144b #3d9970);
} }
ChatWidget QFrame#pluginTitleFrame ChatWidget QFrame#pluginTitleFrame

View File

@ -31,6 +31,8 @@
#include "gui/RetroShareLink.h" #include "gui/RetroShareLink.h"
#include "util/ObjectPainter.h" #include "util/ObjectPainter.h"
#include "util/imageutil.h" #include "util/imageutil.h"
#include "util/rsdebug.h"
#include "util/rstime.h" #include "util/rstime.h"
#ifdef USE_CMARK #ifdef USE_CMARK
@ -40,6 +42,8 @@
#include <iostream> #include <iostream>
//#define DEBUG_SAVESPACE 1
/** /**
* The type of embedding we'd like to do * The type of embedding we'd like to do
*/ */
@ -554,17 +558,23 @@ static QString saveSpace(const QString text)
if(cursChar==QLatin1Char('>')) { if(cursChar==QLatin1Char('>')) {
if(!echapChar && i>0) {outBrackets=true; firstOutBracket=true;} if(!echapChar && i>0) {outBrackets=true; firstOutBracket=true;}
} else if(cursChar==QLatin1Char('\t')) { } else if(cursChar==QLatin1Char('\t')) {
if(outBrackets && firstOutBracket && (keyName!="style")) savedSpaceText.replace(i, 1, "&nbsp;&nbsp;"); if(outBrackets && firstOutBracket && (keyName!="style")) { savedSpaceText.replace(i, 1, "&nbsp;&nbsp;"); i+= 11; }
} else if(cursChar==QLatin1Char(' ')) { } else if(cursChar==QLatin1Char(' ')) {
if(outBrackets && firstOutBracket && (keyName!="style")) savedSpaceText.replace(i, 1, "&nbsp;"); if(outBrackets && firstOutBracket && (keyName!="style")) { savedSpaceText.replace(i, 1, "&nbsp;"); i+= 5; }
} else if(cursChar==QChar(0xA0)) { } else if(cursChar==QChar(0xA0)) {
if(outBrackets && firstOutBracket && (keyName!="style")) savedSpaceText.replace(i, 1, "&nbsp;"); if(outBrackets && firstOutBracket && (keyName!="style")) { savedSpaceText.replace(i, 1, "&nbsp;"); i+= 5; }
} else if(cursChar==QLatin1Char('<')) { } else if(cursChar==QLatin1Char('<')) {
if(!echapChar) {outBrackets=false; getKeyName=true; keyName.clear();} if(!echapChar) {outBrackets=false; getKeyName=true; keyName.clear();}
} else firstOutBracket=false; } else firstOutBracket=false;
echapChar=(cursChar==QLatin1Char('\\')); echapChar=(cursChar==QLatin1Char('\\'));
} }
#ifdef DEBUG_SAVESPACE
RsDbg() << __PRETTY_FUNCTION__ << "Text to save:" << std::endl
<< text.toStdString() << std::endl
<< "---------------------- Saved Text:" << std::endl
<< savedSpaceText.toStdString() << std::endl;
#endif
return savedSpaceText; return savedSpaceText;
} }