diff --git a/.github/workflows/dockerimage.yml b/.github/workflows/dockerimage.yml
index b10a0bfb65..70f0d00889 100644
--- a/.github/workflows/dockerimage.yml
+++ b/.github/workflows/dockerimage.yml
@@ -21,3 +21,12 @@ jobs:
with:
name: Scopy.flatpak
path: ${{ github.workspace }}/Scopy.flatpak
+ - name: Upload master flatpak build to continous prerelease
+ if: ${{ github.event_name == 'push' && github.ref == 'refs/heads/master' }}
+ run: |
+ wget https://github.com/tcnksm/ghr/releases/download/v0.13.0/ghr_v0.13.0_linux_amd64.tar.gz
+ tar xvf ghr_v0.13.0_linux_amd64.tar.gz
+ ghr_v0.13.0_linux_amd64/ghr -u ${{ github.repository_owner }} -r scopy -name "Continuous build" -b "Latest succesful master build " -prerelease -debug -replace continous ${{ github.workspace }}/Scopy.flatpak
+ env:
+ GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
+
diff --git a/CI/appveyor/build_appveyor_macos.sh b/CI/appveyor/build_appveyor_macos.sh
index 32bf443188..09f7a3c71f 100755
--- a/CI/appveyor/build_appveyor_macos.sh
+++ b/CI/appveyor/build_appveyor_macos.sh
@@ -21,8 +21,13 @@ mkdir -p build
cd build
if [ "$APPVEYOR" == "true" ] ; then
+ MACOS_VERSION=$(/usr/libexec/PlistBuddy -c "Print:ProductVersion" /System/Library/CoreServices/SystemVersion.plist)
+ if [[ "$MACOS_VERSION" == "10.14."* ]] ; then
+ export MACOSX_DEPLOYMENT_TARGET=10.13
+ fi
cmake ..
make -j${NUM_JOBS}
+ otool -l ./Scopy.app/Contents/MacOS/Scopy # for debugging
else
cmake -DCMAKE_PREFIX_PATH="$STAGINGDIR;${QT_PATH}/lib/cmake" -DCMAKE_INSTALL_PREFIX="$STAGINGDIR" \
-DCMAKE_EXE_LINKER_FLAGS="-L${STAGINGDIR}/lib" ..
diff --git a/CI/appveyor/build_appveyor_mingw.sh b/CI/appveyor/build_appveyor_mingw.sh
index e3617fc66e..c5fa0efa8e 100755
--- a/CI/appveyor/build_appveyor_mingw.sh
+++ b/CI/appveyor/build_appveyor_mingw.sh
@@ -11,17 +11,25 @@ WORKDIR=${PWD}
echo BUILD_NO $BUILD_NO
JOBS=$(nproc)
+
wget http://swdownloads.analog.com/cse/m1k/drivers/dpinst.zip
wget http://swdownloads.analog.com/cse/m1k/drivers/dfu-util.zip
7z x -y "dpinst.zip" -o"/c/dpinst"
7z x -y "dfu-util.zip" -o"/c/dfu-util"
+# github release upload tool install
+wget https://github.com/tcnksm/ghr/releases/download/v0.13.0/ghr_v0.13.0_windows_amd64.zip
+7z x -y ghr_v0.13.0_windows_amd64.zip -o"/c/ghr"
+UPLOAD_TOOL=/c/ghr/ghr_v0.13.0_windows_amd64/ghr.exe
+
+
CC=/${MINGW_VERSION}/bin/${ARCH}-w64-mingw32-gcc.exe
CXX=/${MINGW_VERSION}/bin/${ARCH}-w64-mingw32-g++.exe
CMAKE_OPTS="\
-DCMAKE_C_COMPILER:FILEPATH=${CC} \
-DCMAKE_CXX_COMPILER:FILEPATH=${CXX} \
-DPKG_CONFIG_EXECUTABLE=/$MINGW_VERSION/bin/pkg-config.exe \
+ -DCMAKE_CXX_FLAGS="-fno-omit-frame-pointer" \
-DCMAKE_PREFIX_PATH=/c/msys64/$MINGW_VERSION/lib/cmake \
-DCMAKE_BUILD_TYPE=RelWithDebInfo \
"
@@ -33,8 +41,9 @@ SCOPY_CMAKE_OPTS="\
-DPYTHON_EXECUTABLE=/$MINGW_VERSION/bin/python3.exe \
"
-PYTHON_LOCATION=/$MINGW_VERSION/lib/python3.8
-PYTHON_FILES="${PYTHON_LOCATION}/*.py ${PYTHON_LOCATION}/asyncio ${PYTHON_LOCATION}/collections ${PYTHON_LOCATION}/concurrent ${PYTHON_LOCATION}/config-3.* ${PYTHON_LOCATION}/ctypes ${PYTHON_LOCATION}/distutils ${PYTHON_LOCATION}/encodings ${PYTHON_LOCATION}/lib-dynload ${PYTHON_LOCATION}/site-packages"
+#PYTHON_LOCATION=/$MINGW_VERSION/lib/python3.8
+#PYTHON_FILES="${PYTHON_LOCATION}/*.py ${PYTHON_LOCATION}/asyncio ${PYTHON_LOCATION}/collections ${PYTHON_LOCATION}/concurrent ${PYTHON_LOCATION}/config-3.* ${PYTHON_LOCATION}/ctypes ${PYTHON_LOCATION}/distutils ${PYTHON_LOCATION}/encodings ${PYTHON_LOCATION}/lib-dynload ${PYTHON_LOCATION}/site-packages"
+PYTHON_FILES=/$MINGW_VERSION/lib/python3.*
DLL_DEPS=$(cat ${WORKDIR}/CI/appveyor/mingw_dll_deps)
DLL_DEPS="$DLL_DEPS $PYTHON_FILES"
@@ -106,6 +115,13 @@ dump_syms -r /c/$DEST_FOLDER/Scopy.exe > /c/$DEST_FOLDER/Scopy.exe.sym
mkdir /c/$DEBUG_FOLDER
mv /c/$DEST_FOLDER/Scopy.exe.sym /c/$DEBUG_FOLDER
mv /c/$DEST_FOLDER/.debug /c/$DEBUG_FOLDER
+/c/cv2pdb/cv2pdb /c/$DEST_FOLDER/Scopy.exe
+/c/cv2pdb/cv2pdb /c/$DEST_FOLDER/libm2k.dll
+/c/cv2pdb/cv2pdb /c/$DEST_FOLDER/libiio.dll
+/c/cv2pdb/cv2pdb /c/$DEST_FOLDER/libgnuradio-m2k.dll
+/c/cv2pdb/cv2pdb /c/$DEST_FOLDER/libgnuradio-scopy.dll
+cp -R /c/projects/scopy /c/$DEBUG_FOLDER/scopy
+mv /c/$DEST_FOLDER/*.pdb /c/$DEBUG_FOLDER
cp -r /c/projects/scopy/drivers /c/$DEST_FOLDER
if [[ $ARCH_BIT == "64" ]]; then
@@ -128,3 +144,16 @@ appveyor AddMessage "11. Creating installer"
iscc //Qp /c/$BUILD_FOLDER/scopy-$ARCH_BIT.iss
appveyor PushArtifact $DEPLOY_FILE
appveyor AddMessage "12. Job complete"
+
+if [ "$APPVEYOR_REPO_BRANCH" = "master" ]; then
+ echo Identified master branch
+ if [ -z "$APPVEYOR_PULL_REQUEST_NUMBER" ]; then
+ echo Not a pull request
+ mkdir /c/to_deploy
+ cp /c/scopy-${ARCH_BIT}bit.zip /c/to_deploy
+ cp /c/debug-${ARCH_BIT}bit.zip /c/to_deploy
+ cp $DEPLOY_FILE /c/to_deploy
+ $UPLOAD_TOOL -u $APPVEYOR_ACCOUNT_NAME -r $APPVEYOR_PROJECT_NAME -name "Continuous build" -b "Latest succesful master build " -prerelease -debug -replace continous /c/to_deploy
+ fi
+fi
+
diff --git a/CI/appveyor/data b/CI/appveyor/data
new file mode 100644
index 0000000000..2c37c2a94b
--- /dev/null
+++ b/CI/appveyor/data
@@ -0,0 +1 @@
+vineri 26 martie 2021, 13:48:33 +0200
diff --git a/CI/appveyor/install_macos_deps.sh b/CI/appveyor/install_macos_deps.sh
index 2b28d6e834..fa7ccc56e3 100755
--- a/CI/appveyor/install_macos_deps.sh
+++ b/CI/appveyor/install_macos_deps.sh
@@ -1,6 +1,6 @@
#!/bin/bash
-LIBIIO_BRANCH=master
+LIBIIO_VERSION=v0.21
LIBAD9361_BRANCH=master
LIBM2K_BRANCH=master
GRIIO_BRANCH=upgrade-3.8
@@ -11,20 +11,22 @@ GRM2K_BRANCH=master
QWT_BRANCH=qwt-6.1-multiaxes
QWTPOLAR_BRANCH=master # not used
LIBSIGROK_BRANCH=master
-LIBSIGROKDECODE_BRANCH=master #not used
+LIBSIGROKDECODE_BRANCH=master
BOOST_VERSION_FILE=1_73_0
BOOST_VERSION=1.73.0
LIBTINYIIOD_BRANCH=master
PYTHON="python3"
PACKAGES=" ${QT_FORMULAE} pkg-config cmake fftw bison gettext autoconf automake libtool libzip glib libusb glog $PYTHON"
-PACKAGES="$PACKAGES doxygen wget gnu-sed libmatio dylibbundler libxml2"
+PACKAGES="$PACKAGES doxygen wget gnu-sed libmatio dylibbundler libxml2 ghr"
set -e
cd ~
WORKDIR=${PWD}
NUM_JOBS=4
+brew update
+brew search ${QT_FORMULAE}
brew_install_or_upgrade() {
brew install $1 || \
brew upgrade $1 || \
@@ -63,10 +65,12 @@ QMAKE="$(command -v qmake)"
CMAKE_OPTS="-DCMAKE_PREFIX_PATH=$STAGINGDIR -DCMAKE_INSTALL_PREFIX=$STAGINGDIR"
build_libiio() {
- echo "### Building libiio - branch $LIBIIO_BRANCH"
+ echo "### Building libiio - version $LIBIIO_VERSION"
cd ~
- git clone --depth 1 https://github.com/analogdevicesinc/libiio.git -b $LIBIIO_BRANCH ${WORKDIR}/libiio
+ git clone https://github.com/analogdevicesinc/libiio.git ${WORKDIR}/libiio
+ cd ${WORKDIR}/libiio
+ git checkout $LIBIIO_VERSION
mkdir ${WORKDIR}/libiio/build-${ARCH}
cd ${WORKDIR}/libiio/build-${ARCH}
@@ -137,7 +141,7 @@ build_boost() {
echo "### Building boost - version $BOOST_VERSION_FILE"
cd ~
- wget https://dl.bintray.com/boostorg/release/$BOOST_VERSION/source/boost_$BOOST_VERSION_FILE.tar.gz
+ wget https://boostorg.jfrog.io/artifactory/main/release/$BOOST_VERSION/source/boost_$BOOST_VERSION_FILE.tar.gz
tar -xzf boost_$BOOST_VERSION_FILE.tar.gz
cd boost_$BOOST_VERSION_FILE
patch -p1 < ${WORKDIR}/projects/scopy/CI/appveyor/patches/boost-darwin.patch
@@ -240,11 +244,11 @@ build_libsigrokdecode() {
echo "### Building libsigrokdecode - branch $LIBSIGROKDECODE_BRANCH"
git clone --depth 1 https://github.com/sigrokproject/libsigrokdecode.git -b $LIBSIGROKDECODE_BRANCH ${WORKDIR}/libsigrokdecode
- mkdir -p ${WORKDIR}/libsigrokdecode/build-${ARCH}
cd ${WORKDIR}/libsigrokdecode
./autogen.sh
./configure
+
sudo make $JOBS install
}
@@ -257,14 +261,14 @@ patch_qwtpolar_mac() {
+++ b/qwtpolarconfig.pri
@@ -16,7 +16,9 @@ QWT_POLAR_VER_PAT = 1
QWT_POLAR_VERSION = \$\${QWT_POLAR_VER_MAJ}.\$\${QWT_POLAR_VER_MIN}.\$\${QWT_POLAR_VER_PAT}
-
+
unix {
- QWT_POLAR_INSTALL_PREFIX = /usr/local/qwtpolar-\$\$QWT_POLAR_VERSION
+ QWT_POLAR_INSTALL_PREFIX = $STAGINGDIR
+ QMAKE_CXXFLAGS = -I${STAGINGDIR}/include
+ QMAKE_LFLAGS = ${STAGINGDIR}/lib/libqwt*dylib
}
-
+
win32 {
EOF
}
diff --git a/CI/appveyor/install_msys_deps.sh b/CI/appveyor/install_msys_deps.sh
index 2154fd9102..a7c66f6450 100644
--- a/CI/appveyor/install_msys_deps.sh
+++ b/CI/appveyor/install_msys_deps.sh
@@ -7,7 +7,15 @@ echo "Download and install pre-compiled libraries ... "
wget "https://ci.appveyor.com/api/projects/$SCOPY_MINGW_BUILD_DEPS_FORK/scopy-mingw-build-deps/artifacts/scopy-$MINGW_VERSION-build-deps-pacman.txt?branch=$SCOPY_MINGW_BUILD_DEPS_BRANCH&job=Environment: MINGW_VERSION=$MINGW_VERSION, ARCH=$ARCH" -O /tmp/scopy-$MINGW_VERSION-build-deps-pacman.txt
wget "https://ci.appveyor.com/api/projects/$SCOPY_MINGW_BUILD_DEPS_FORK/scopy-mingw-build-deps/artifacts/scopy-$MINGW_VERSION-build-deps.tar.xz?branch=$SCOPY_MINGW_BUILD_DEPS_BRANCH&job=Environment: MINGW_VERSION=$MINGW_VERSION, ARCH=$ARCH" -O /tmp/scopy-$MINGW_VERSION-build-deps.tar.xz
wget "https://ci.appveyor.com/api/projects/$SCOPY_MINGW_BUILD_DEPS_FORK/scopy-mingw-build-deps/artifacts/scopy-mingw-build-status?branch=$SCOPY_MINGW_BUILD_DEPS_BRANCH&job=Environment: MINGW_VERSION=$MINGW_VERSION, ARCH=$ARCH" -O /tmp/scopy-mingw-build-status
+
+
cd /c
+
+pacman -S --noconfirm unzip
+wget https://swdownloads.analog.com/cse/scopydeps/cv2pdb.zip
+unzip cv2pdb.zip
+#/c/cv2pdb/cv2pdb.exe
+
tar xJf /tmp/scopy-$MINGW_VERSION-build-deps.tar.xz
cat /tmp/scopy-mingw-build-status
@@ -16,6 +24,7 @@ SCOPY_MINGW_BUILD_DEPS_PACMAN=$(
Qt |
-License |
+License |
Homepage |
@@ -51,7 +51,7 @@ table, th, td {
PulseView |
-License |
+License |
Homepage |
diff --git a/resources/scopy.html b/resources/scopy.html
index 43bce635a5..517d3737ba 100644
--- a/resources/scopy.html
+++ b/resources/scopy.html
@@ -11,7 +11,7 @@
Welcome to Scopy!
Scopy is a powerful toolbox for signal analysis and generation.
Please visit our wiki for more information about Scopy.
-If you need help, drop a message on our Engineer Zone.
+If you need help, drop a message on our Engineer Zone.
diff --git a/resources/stylesheets/light.qss b/resources/stylesheets/light.qss
index 4aa40cb6d8..77a251b5f9 100644
--- a/resources/stylesheets/light.qss
+++ b/resources/stylesheets/light.qss
@@ -139,15 +139,14 @@ QComboBox QAbstractItemView {
border: none;
background-color: white;
text-align: left;
- color: #bebebe;
+ color: black;
outline: none;
border-bottom: 1px solid #bebebe;
border-top: 1px solid #bebebe;
-}
-/* This only works on Windows */
-QComboBox QAbstractItemView {
+ /* This only works on Windows */
+ selection-color: black;
selection-background-color: #EDEDED;
}
diff --git a/scopy-32.iss.cmakein b/scopy-32.iss.cmakein
index 828f614a06..39e573b98c 100644
--- a/scopy-32.iss.cmakein
+++ b/scopy-32.iss.cmakein
@@ -21,7 +21,7 @@ AllowNoIcons=yes
Compression=lzma
SolidCompression=yes
ArchitecturesInstallIn64BitMode=x64
-DefaultDirName={#AppDev}\{#AppName}
+DefaultDirName={pf}\{#AppDev}\{#AppName}
DefaultGroupName={#AppName}
AlwaysRestart=yes
DisableDirPage=no
@@ -59,10 +59,192 @@ begin
end;
end;
+var
+ UninstallPage: TNewNotebookPage;
+ UninstallButton: TNewButton;
+ UninstallDriverCheckBox: TNewCheckBox;
+
+procedure UpdateUninstallWizard;
+begin
+ if UninstallProgressForm.InnerNotebook.ActivePage = UninstallPage then
+ begin
+ UninstallProgressForm.PageNameLabel.Caption := 'Uninstall Scopy';
+ UninstallProgressForm.PageDescriptionLabel.Caption := '';
+ end;
+ UninstallButton.Caption := 'Uninstall';
+ UninstallButton.ModalResult := mrOK;
+end;
+
+procedure UninstallButtonClick(Sender: TObject);
+begin
+ UninstallButton.Visible := False;
+end;
+
+procedure InitializeUninstallProgressForm();
+var
+ PageNameLabel: string;
+ PageDescriptionLabel: string;
+ CancelButtonEnabled: Boolean;
+ CancelButtonModalResult: Integer;
+ ResultCode : Integer;
+ PageCaption: TNewStaticText;
+begin
+ if not UninstallSilent then
+ begin
+ { Create the first page and make it active }
+ UninstallPage := TNewNotebookPage.Create(UninstallProgressForm);
+ UninstallPage.Notebook := UninstallProgressForm.InnerNotebook;
+ UninstallPage.Parent := UninstallProgressForm.InnerNotebook;
+ UninstallPage.Align := alClient;
+
+ PageCaption := TNewStaticText.Create(UninstallProgressForm);
+ PageCaption.Parent := UninstallPage;
+ PageCaption.Top := UninstallProgressForm.StatusLabel.Top;
+ PageCaption.Left := UninstallProgressForm.StatusLabel.Left;
+ PageCaption.Width := UninstallProgressForm.StatusLabel.Width;
+ PageCaption.Height := UninstallProgressForm.StatusLabel.Height;
+ PageCaption.AutoSize := False;
+ PageCaption.ShowAccelChar := False;
+ PageCaption.Caption := 'Press Uninstall to proceeed with uninstallation.';
+
+ UninstallDriverCheckBox := TNewCheckBox.Create(UninstallProgressForm);
+ UninstallDriverCheckBox.Parent := UninstallPage;
+ UninstallDriverCheckBox.Top := PageCaption.Top;
+ UninstallDriverCheckBox.Left := PageCaption.Left;
+ UninstallDriverCheckBox.Width := PageCaption.Width;
+ UninstallDriverCheckBox.Height := PageCaption.Height;
+ UninstallDriverCheckBox.Caption := 'Uninstall ADALM2000/ADALM-PLUTO drivers.';
+ UninstallProgressForm.InnerNotebook.ActivePage := UninstallPage;
+
+ PageNameLabel := UninstallProgressForm.PageNameLabel.Caption;
+ PageDescriptionLabel := UninstallProgressForm.PageDescriptionLabel.Caption;
+
+
+ UninstallButton := TNewButton.Create(UninstallProgressForm);
+ UninstallButton.Parent := UninstallProgressForm;
+ UninstallButton.Left :=
+ UninstallProgressForm.CancelButton.Left -
+ UninstallProgressForm.CancelButton.Width -
+ ScaleX(10);
+ UninstallButton.Top := UninstallProgressForm.CancelButton.Top;
+ UninstallButton.Width := UninstallProgressForm.CancelButton.Width;
+ UninstallButton.Height := UninstallProgressForm.CancelButton.Height;
+ UninstallButton.OnClick := @UninstallButtonClick;
+ UninstallProgressForm.CancelButton.TabOrder := UninstallButton.TabOrder + 1;
+
+ { Run the wizard }
+ UpdateUninstallWizard;
+ CancelButtonEnabled := UninstallProgressForm.CancelButton.Enabled
+ UninstallProgressForm.CancelButton.Enabled := True;
+ CancelButtonModalResult := UninstallProgressForm.CancelButton.ModalResult;
+ UninstallProgressForm.CancelButton.ModalResult := mrCancel;
+
+ { Display the First uninstaller page }
+ if UninstallProgressForm.ShowModal = mrCancel then Abort;
+
+ if UninstallDriverCheckBox.Checked = True then
+ begin
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-cdc-acm.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-rndis.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-usbd.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-dfu.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not RegDeleteKeyIncludingSubkeys(HKEY_LOCAL_MACHINE, 'Software\Analog Devices\Scopy') then
+ begin
+ MsgBox('Failed to remove registry key: Scopy.', mbInformation, MB_OK);
+ end;
+ end;
+ UninstallProgressForm.CancelButton.Enabled := CancelButtonEnabled;
+ UninstallProgressForm.CancelButton.ModalResult := CancelButtonModalResult;
+ UninstallProgressForm.PageNameLabel.Caption := PageNameLabel;
+ UninstallProgressForm.PageDescriptionLabel.Caption := PageDescriptionLabel;
+ UninstallProgressForm.InnerNotebook.ActivePage := UninstallProgressForm.InstallingPage;
+ end;
+end;
+
+function GetInstallLocation(): String;
+var
+ regPath: String;
+ installLocationString: String;
+begin
+ regPath := ExpandConstant('Software\Microsoft\Windows\CurrentVersion\Uninstall\{#SetupSetting("AppId")}_is1');
+ installLocationString := '';
+ if not RegQueryStringValue(HKLM, regPath, 'InstallLocation', installLocationString) then
+ RegQueryStringValue(HKCU, regPath, 'InstallLocation', installLocationString);
+ Result := installLocationString;
+end;
+
+function GetUninstallerString(): String;
+var
+ regPath: String;
+ uninstallerString: String;
+begin
+ regPath := ExpandConstant('Software\Microsoft\Windows\CurrentVersion\Uninstall\{#SetupSetting("AppId")}_is1');
+ uninstallerString := '';
+ if not RegQueryStringValue(HKLM, regPath, 'UninstallString', uninstallerString) then
+ RegQueryStringValue(HKCU, regPath, 'UninstallString', uninstallerString);
+ Result := uninstallerString;
+end;
+
+
+function IsUpgrade(): Boolean;
+begin
+ Result := (GetInstallLocation() = ExpandConstant('{app}\'));
+end;
+
+
+procedure RemoveOldVersion();
+var
+ installLocationString: String;
+ uninstallerString: String;
+ resultCode: Integer;
+begin
+ installLocationString := GetInstallLocation();
+ uninstallerString := GetUninstallerString();
+ if installLocationString <> '' then begin
+ uninstallerString := RemoveQuotes(uninstallerString);
+ if not Exec(uninstallerString, '/SILENT /NORESTART /SUPPRESSMSGBOXES','', SW_HIDE, ewWaitUntilTerminated, resultCode) then
+ begin
+ MsgBox('Failed to uninstall previous version!', mbInformation, MB_OK);
+ end;
+ end;
+end;
+
+procedure CurStepChanged(CurStep: TSetupStep);
+begin
+ if (CurStep=ssInstall) then
+ begin
+ if (isUpgrade()) then
+ begin
+ if MsgBox('A different Scopy version was found at this location. Remove before installing?', mbConfirmation, MB_YESNO or MB_DEFBUTTON2) = IDYES then
+ begin
+ RemoveOldVersion();
+ end;
+ end;
+ end;
+end;
+
[Tasks]
Name: "desktopicon"; Description: "{cm:CreateDesktopIcon}"; GroupDescription: "{cm:AdditionalIcons}"
Name: "deleteini"; Description: Delete previous settings (Scopy.ini)
+Name: "deletepreferences"; Description: Delete previous application preferences (Preferences.ini)
Name: "drivers"; Description: Install drivers for ADALM2000; Check: not isDriverInstalled;
+Name: "drivers_overwrite"; Description: Install drivers for ADALM2000; Check: isDriverInstalled; Flags: unchecked
[Files]
Source: "c:\scopy_32\*"; DestDir: "{app}"; Check: not Is64BitInstallMode; Flags: ignoreversion recursesubdirs createallsubdirs
@@ -74,18 +256,13 @@ Name: "{commondesktop}\{#AppName}"; Filename: "{app}\{#AppExeName}"; Tasks: desk
[InstallDelete]
Type: files; Name: "{userappdata}\ADI\Scopy.ini"; Tasks: deleteini
+Type: files; Name: "{userappdata}\ADI\Preferences.ini"; Tasks: deletepreferences
[Run]
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/PATH ""{app}\drivers"" {param:dpinstflags|/F}" ; Flags: waituntilterminated; Tasks: drivers
-
-[UninstallRun]
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-cdc-acm.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-rndis.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-usbd.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-dfu.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
+Filename: "{app}\drivers\dpinst.exe"; Parameters: "/PATH ""{app}\drivers"" {param:dpinstflags|/F}" ; Flags: waituntilterminated; Tasks: drivers drivers_overwrite
[Registry]
-Root: HKLM; Subkey: "Software\Analog Devices"; Flags: uninsdeletekeyifempty
-Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}"; Flags: uninsdeletekey
+Root: HKLM; Subkey: "Software\Analog Devices"
+Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}"
Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}\Settings"; ValueType: string; ValueName: "InstallPath"; ValueData: "{app}"
Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}\Settings"; ValueType: string; ValueName: "InstallVersion"; ValueData: {#DriverVersion}
diff --git a/scopy-64.iss.cmakein b/scopy-64.iss.cmakein
index 500d281a36..ddaf9f0de1 100644
--- a/scopy-64.iss.cmakein
+++ b/scopy-64.iss.cmakein
@@ -21,7 +21,7 @@ AllowNoIcons=yes
Compression=lzma
SolidCompression=yes
ArchitecturesInstallIn64BitMode=x64
-DefaultDirName={#AppDev}\{#AppName}
+DefaultDirName={pf}\{#AppDev}\{#AppName}
DefaultGroupName={#AppName}
AlwaysRestart=yes
DisableDirPage=no
@@ -59,10 +59,194 @@ begin
end;
end;
+var
+ UninstallPage: TNewNotebookPage;
+ UninstallButton: TNewButton;
+ UninstallDriverCheckBox: TNewCheckBox;
+
+procedure UpdateUninstallWizard;
+begin
+ if UninstallProgressForm.InnerNotebook.ActivePage = UninstallPage then
+ begin
+ UninstallProgressForm.PageNameLabel.Caption := 'Uninstall Scopy';
+ UninstallProgressForm.PageDescriptionLabel.Caption := '';
+ end;
+ UninstallButton.Caption := 'Uninstall';
+ UninstallButton.ModalResult := mrOK;
+end;
+
+procedure UninstallButtonClick(Sender: TObject);
+begin
+ UninstallButton.Visible := False;
+end;
+
+procedure InitializeUninstallProgressForm();
+var
+ PageNameLabel: string;
+ PageDescriptionLabel: string;
+ CancelButtonEnabled: Boolean;
+ CancelButtonModalResult: Integer;
+ ResultCode : Integer;
+ PageCaption: TNewStaticText;
+begin
+ if not UninstallSilent then
+ begin
+ { Create the first page and make it active }
+ UninstallPage := TNewNotebookPage.Create(UninstallProgressForm);
+ UninstallPage.Notebook := UninstallProgressForm.InnerNotebook;
+ UninstallPage.Parent := UninstallProgressForm.InnerNotebook;
+ UninstallPage.Align := alClient;
+
+ PageCaption := TNewStaticText.Create(UninstallProgressForm);
+ PageCaption.Parent := UninstallPage;
+ PageCaption.Top := UninstallProgressForm.StatusLabel.Top;
+ PageCaption.Left := UninstallProgressForm.StatusLabel.Left;
+ PageCaption.Width := UninstallProgressForm.StatusLabel.Width;
+ PageCaption.Height := UninstallProgressForm.StatusLabel.Height;
+ PageCaption.AutoSize := False;
+ PageCaption.ShowAccelChar := False;
+ PageCaption.Caption := 'Press Uninstall to proceeed with uninstallation.';
+
+ UninstallDriverCheckBox := TNewCheckBox.Create(UninstallProgressForm);
+ UninstallDriverCheckBox.Parent := UninstallPage;
+ UninstallDriverCheckBox.Top := PageCaption.Top;
+ UninstallDriverCheckBox.Left := PageCaption.Left;
+ UninstallDriverCheckBox.Width := PageCaption.Width;
+ UninstallDriverCheckBox.Height := PageCaption.Height;
+ UninstallDriverCheckBox.Caption := 'Uninstall ADALM2000/ADALM-PLUTO drivers.';
+ UninstallProgressForm.InnerNotebook.ActivePage := UninstallPage;
+
+ PageNameLabel := UninstallProgressForm.PageNameLabel.Caption;
+ PageDescriptionLabel := UninstallProgressForm.PageDescriptionLabel.Caption;
+
+
+ UninstallButton := TNewButton.Create(UninstallProgressForm);
+ UninstallButton.Parent := UninstallProgressForm;
+ UninstallButton.Left :=
+ UninstallProgressForm.CancelButton.Left -
+ UninstallProgressForm.CancelButton.Width -
+ ScaleX(10);
+ UninstallButton.Top := UninstallProgressForm.CancelButton.Top;
+ UninstallButton.Width := UninstallProgressForm.CancelButton.Width;
+ UninstallButton.Height := UninstallProgressForm.CancelButton.Height;
+ UninstallButton.OnClick := @UninstallButtonClick;
+ UninstallProgressForm.CancelButton.TabOrder := UninstallButton.TabOrder + 1;
+
+ { Run the wizard }
+ UpdateUninstallWizard;
+ CancelButtonEnabled := UninstallProgressForm.CancelButton.Enabled
+ UninstallProgressForm.CancelButton.Enabled := True;
+ CancelButtonModalResult := UninstallProgressForm.CancelButton.ModalResult;
+ UninstallProgressForm.CancelButton.ModalResult := mrCancel;
+
+ { Display the First uninstaller page }
+ if UninstallProgressForm.ShowModal = mrCancel then Abort;
+
+ if UninstallDriverCheckBox.Checked = True then
+ begin
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-cdc-acm.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-rndis.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-usbd.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-dfu.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not RegDeleteKeyIncludingSubkeys(HKEY_LOCAL_MACHINE, 'Software\Analog Devices\Scopy') then
+ begin
+ MsgBox('Failed to remove registry key: Scopy.', mbInformation, MB_OK);
+ end;
+ end;
+ UninstallProgressForm.CancelButton.Enabled := CancelButtonEnabled;
+ UninstallProgressForm.CancelButton.ModalResult := CancelButtonModalResult;
+ UninstallProgressForm.PageNameLabel.Caption := PageNameLabel;
+ UninstallProgressForm.PageDescriptionLabel.Caption := PageDescriptionLabel;
+ UninstallProgressForm.InnerNotebook.ActivePage := UninstallProgressForm.InstallingPage;
+ end;
+end;
+
+
+function GetInstallLocation(): String;
+var
+ regPath: String;
+ installLocationString: String;
+begin
+ regPath := ExpandConstant('Software\Microsoft\Windows\CurrentVersion\Uninstall\{#SetupSetting("AppId")}_is1');
+ installLocationString := '';
+ if not RegQueryStringValue(HKLM, regPath, 'InstallLocation', installLocationString) then
+ RegQueryStringValue(HKCU, regPath, 'InstallLocation', installLocationString);
+ Result := installLocationString;
+end;
+
+function GetUninstallerString(): String;
+var
+ regPath: String;
+ uninstallerString: String;
+begin
+ regPath := ExpandConstant('Software\Microsoft\Windows\CurrentVersion\Uninstall\{#SetupSetting("AppId")}_is1');
+ uninstallerString := '';
+ if not RegQueryStringValue(HKLM, regPath, 'UninstallString', uninstallerString) then
+ RegQueryStringValue(HKCU, regPath, 'UninstallString', uninstallerString);
+ Result := uninstallerString;
+end;
+
+
+function IsUpgrade(): Boolean;
+begin
+ Result := (GetInstallLocation() = ExpandConstant('{app}\'));
+end;
+
+
+procedure RemoveOldVersion();
+var
+ installLocationString: String;
+ uninstallerString: String;
+ resultCode: Integer;
+begin
+ installLocationString := GetInstallLocation();
+ uninstallerString := GetUninstallerString();
+ if installLocationString <> '' then begin
+ uninstallerString := RemoveQuotes(uninstallerString);
+ if not Exec(uninstallerString, '/SILENT /NORESTART /SUPPRESSMSGBOXES','', SW_HIDE, ewWaitUntilTerminated, resultCode) then
+ begin
+ MsgBox('Failed to uninstall previous version!', mbInformation, MB_OK);
+ end;
+ end;
+end;
+
+procedure CurStepChanged(CurStep: TSetupStep);
+begin
+ if (CurStep=ssInstall) then
+ begin
+ if (isUpgrade()) then
+ begin
+ if MsgBox('A different Scopy version was found at this location. Remove before installing?', mbConfirmation, MB_YESNO or MB_DEFBUTTON2) = IDYES then
+ begin
+ RemoveOldVersion();
+ end;
+ end;
+ end;
+end;
+
+
[Tasks]
Name: "desktopicon"; Description: "{cm:CreateDesktopIcon}"; GroupDescription: "{cm:AdditionalIcons}"
Name: "deleteini"; Description: Delete previous settings (Scopy.ini)
+Name: "deletepreferences"; Description: Delete previous application preferences (Preferences.ini)
Name: "drivers"; Description: Install drivers for ADALM2000; Check: not isDriverInstalled;
+Name: "drivers_overwrite"; Description: Install drivers for ADALM2000; Check: isDriverInstalled; Flags: unchecked
[Files]
Source: "c:\scopy_64\*"; DestDir: "{app}"; Check: Is64BitInstallMode; Flags: ignoreversion recursesubdirs createallsubdirs
@@ -74,18 +258,13 @@ Name: "{commondesktop}\{#AppName}"; Filename: "{app}\{#AppExeName}"; Tasks: desk
[InstallDelete]
Type: files; Name: "{userappdata}\ADI\Scopy.ini"; Tasks: deleteini
+Type: files; Name: "{userappdata}\ADI\Preferences.ini"; Tasks: deletepreferences
[Run]
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/PATH ""{app}\drivers"" {param:dpinstflags|/F}" ; Flags: waituntilterminated; Tasks: drivers
-
-[UninstallRun]
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-cdc-acm.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-rndis.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-usbd.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-dfu.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
+Filename: "{app}\drivers\dpinst.exe"; Parameters: "/PATH ""{app}\drivers"" {param:dpinstflags|/F}" ; Flags: waituntilterminated; Tasks: drivers drivers_overwrite
[Registry]
-Root: HKLM; Subkey: "Software\Analog Devices"; Flags: uninsdeletekeyifempty
-Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}"; Flags: uninsdeletekey
+Root: HKLM; Subkey: "Software\Analog Devices"
+Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}"
Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}\Settings"; ValueType: string; ValueName: "InstallPath"; ValueData: "{app}"
Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}\Settings"; ValueType: string; ValueName: "InstallVersion"; ValueData: {#DriverVersion}
diff --git a/scopy.iss.cmakein b/scopy.iss.cmakein
index eaa38ba170..c37ae5a061 100644
--- a/scopy.iss.cmakein
+++ b/scopy.iss.cmakein
@@ -21,7 +21,7 @@ AllowNoIcons=yes
Compression=lzma
SolidCompression=yes
ArchitecturesInstallIn64BitMode=x64
-DefaultDirName={#AppDev}\{#AppName}
+DefaultDirName={pf}\{#AppDev}\{#AppName}
DefaultGroupName={#AppName}
AlwaysRestart=yes
DisableDirPage=no
@@ -59,10 +59,192 @@ begin
end;
end;
+var
+ UninstallPage: TNewNotebookPage;
+ UninstallButton: TNewButton;
+ UninstallDriverCheckBox: TNewCheckBox;
+
+procedure UpdateUninstallWizard;
+begin
+ if UninstallProgressForm.InnerNotebook.ActivePage = UninstallPage then
+ begin
+ UninstallProgressForm.PageNameLabel.Caption := 'Uninstall Scopy';
+ UninstallProgressForm.PageDescriptionLabel.Caption := '';
+ end;
+ UninstallButton.Caption := 'Uninstall';
+ UninstallButton.ModalResult := mrOK;
+end;
+
+procedure UninstallButtonClick(Sender: TObject);
+begin
+ UninstallButton.Visible := False;
+end;
+
+procedure InitializeUninstallProgressForm();
+var
+ PageNameLabel: string;
+ PageDescriptionLabel: string;
+ CancelButtonEnabled: Boolean;
+ CancelButtonModalResult: Integer;
+ ResultCode : Integer;
+ PageCaption: TNewStaticText;
+begin
+ if not UninstallSilent then
+ begin
+ { Create the first page and make it active }
+ UninstallPage := TNewNotebookPage.Create(UninstallProgressForm);
+ UninstallPage.Notebook := UninstallProgressForm.InnerNotebook;
+ UninstallPage.Parent := UninstallProgressForm.InnerNotebook;
+ UninstallPage.Align := alClient;
+
+ PageCaption := TNewStaticText.Create(UninstallProgressForm);
+ PageCaption.Parent := UninstallPage;
+ PageCaption.Top := UninstallProgressForm.StatusLabel.Top;
+ PageCaption.Left := UninstallProgressForm.StatusLabel.Left;
+ PageCaption.Width := UninstallProgressForm.StatusLabel.Width;
+ PageCaption.Height := UninstallProgressForm.StatusLabel.Height;
+ PageCaption.AutoSize := False;
+ PageCaption.ShowAccelChar := False;
+ PageCaption.Caption := 'Press Uninstall to proceeed with uninstallation.';
+
+ UninstallDriverCheckBox := TNewCheckBox.Create(UninstallProgressForm);
+ UninstallDriverCheckBox.Parent := UninstallPage;
+ UninstallDriverCheckBox.Top := PageCaption.Top;
+ UninstallDriverCheckBox.Left := PageCaption.Left;
+ UninstallDriverCheckBox.Width := PageCaption.Width;
+ UninstallDriverCheckBox.Height := PageCaption.Height;
+ UninstallDriverCheckBox.Caption := 'Uninstall ADALM2000/ADALM-PLUTO drivers.';
+ UninstallProgressForm.InnerNotebook.ActivePage := UninstallPage;
+
+ PageNameLabel := UninstallProgressForm.PageNameLabel.Caption;
+ PageDescriptionLabel := UninstallProgressForm.PageDescriptionLabel.Caption;
+
+
+ UninstallButton := TNewButton.Create(UninstallProgressForm);
+ UninstallButton.Parent := UninstallProgressForm;
+ UninstallButton.Left :=
+ UninstallProgressForm.CancelButton.Left -
+ UninstallProgressForm.CancelButton.Width -
+ ScaleX(10);
+ UninstallButton.Top := UninstallProgressForm.CancelButton.Top;
+ UninstallButton.Width := UninstallProgressForm.CancelButton.Width;
+ UninstallButton.Height := UninstallProgressForm.CancelButton.Height;
+ UninstallButton.OnClick := @UninstallButtonClick;
+ UninstallProgressForm.CancelButton.TabOrder := UninstallButton.TabOrder + 1;
+
+ { Run the wizard }
+ UpdateUninstallWizard;
+ CancelButtonEnabled := UninstallProgressForm.CancelButton.Enabled
+ UninstallProgressForm.CancelButton.Enabled := True;
+ CancelButtonModalResult := UninstallProgressForm.CancelButton.ModalResult;
+ UninstallProgressForm.CancelButton.ModalResult := mrCancel;
+
+ { Display the First uninstaller page }
+ if UninstallProgressForm.ShowModal = mrCancel then Abort;
+
+ if UninstallDriverCheckBox.Checked = True then
+ begin
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-cdc-acm.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-rndis.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-usbd.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not Exec(ExpandConstant('{app}\drivers\dpinst.exe'), '/s /U pluto-dfu.inf', ExpandConstant('{app}\drivers'), SW_SHOW, ewWaitUntilTerminated, ResultCode) then
+ begin
+ MsgBox('Failed to uninstall drivers: ' + SysErrorMessage(ResultCode) + '.', mbInformation, MB_OK);
+ end;
+
+ if not RegDeleteKeyIncludingSubkeys(HKEY_LOCAL_MACHINE, 'Software\Analog Devices\Scopy') then
+ begin
+ MsgBox('Failed to remove registry key: Scopy.', mbInformation, MB_OK);
+ end;
+ end;
+ UninstallProgressForm.CancelButton.Enabled := CancelButtonEnabled;
+ UninstallProgressForm.CancelButton.ModalResult := CancelButtonModalResult;
+ UninstallProgressForm.PageNameLabel.Caption := PageNameLabel;
+ UninstallProgressForm.PageDescriptionLabel.Caption := PageDescriptionLabel;
+ UninstallProgressForm.InnerNotebook.ActivePage := UninstallProgressForm.InstallingPage;
+ end;
+end;
+
+function GetInstallLocation(): String;
+var
+ regPath: String;
+ installLocationString: String;
+begin
+ regPath := ExpandConstant('Software\Microsoft\Windows\CurrentVersion\Uninstall\{#SetupSetting("AppId")}_is1');
+ installLocationString := '';
+ if not RegQueryStringValue(HKLM, regPath, 'InstallLocation', installLocationString) then
+ RegQueryStringValue(HKCU, regPath, 'InstallLocation', installLocationString);
+ Result := installLocationString;
+end;
+
+function GetUninstallerString(): String;
+var
+ regPath: String;
+ uninstallerString: String;
+begin
+ regPath := ExpandConstant('Software\Microsoft\Windows\CurrentVersion\Uninstall\{#SetupSetting("AppId")}_is1');
+ uninstallerString := '';
+ if not RegQueryStringValue(HKLM, regPath, 'UninstallString', uninstallerString) then
+ RegQueryStringValue(HKCU, regPath, 'UninstallString', uninstallerString);
+ Result := uninstallerString;
+end;
+
+
+function IsUpgrade(): Boolean;
+begin
+ Result := (GetInstallLocation() = ExpandConstant('{app}\'));
+end;
+
+
+procedure RemoveOldVersion();
+var
+ installLocationString: String;
+ uninstallerString: String;
+ resultCode: Integer;
+begin
+ installLocationString := GetInstallLocation();
+ uninstallerString := GetUninstallerString();
+ if installLocationString <> '' then begin
+ uninstallerString := RemoveQuotes(uninstallerString);
+ if not Exec(uninstallerString, '/SILENT /NORESTART /SUPPRESSMSGBOXES','', SW_HIDE, ewWaitUntilTerminated, resultCode) then
+ begin
+ MsgBox('Failed to uninstall previous version!', mbInformation, MB_OK);
+ end;
+ end;
+end;
+
+procedure CurStepChanged(CurStep: TSetupStep);
+begin
+ if (CurStep=ssInstall) then
+ begin
+ if (isUpgrade()) then
+ begin
+ if MsgBox('A different Scopy version was found at this location. Remove before installing?', mbConfirmation, MB_YESNO or MB_DEFBUTTON2) = IDYES then
+ begin
+ RemoveOldVersion();
+ end;
+ end;
+ end;
+end;
+
[Tasks]
Name: "desktopicon"; Description: "{cm:CreateDesktopIcon}"; GroupDescription: "{cm:AdditionalIcons}"
Name: "deleteini"; Description: Delete previous settings (Scopy.ini)
+Name: "deletepreferences"; Description: Delete previous application preferences (Preferences.ini)
Name: "drivers"; Description: Install drivers for ADALM2000; Check: not isDriverInstalled;
+Name: "drivers_overwrite"; Description: Install drivers for ADALM2000; Check: isDriverInstalled; Flags: unchecked
[Files]
Source: "c:\scopy_64\*"; DestDir: "{app}"; Check: Is64BitInstallMode; Flags: ignoreversion recursesubdirs createallsubdirs
@@ -76,18 +258,13 @@ Name: "{commondesktop}\{#AppName}"; Filename: "{app}\{#AppExeName}"; Tasks: desk
[InstallDelete]
Type: files; Name: "{userappdata}\ADI\Scopy.ini"; Tasks: deleteini
+Type: files; Name: "{userappdata}\ADI\Preferences.ini"; Tasks: deletepreferences
[Run]
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/PATH ""{app}\drivers"" {param:dpinstflags|/F}" ; Flags: waituntilterminated; Tasks: drivers
-
-[UninstallRun]
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-cdc-acm.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-rndis.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-usbd.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
-Filename: "{app}\drivers\dpinst.exe"; Parameters: "/s /U pluto-dfu.inf"; WorkingDir: "{app}\drivers"; Flags: waituntilterminated;
+Filename: "{app}\drivers\dpinst.exe"; Parameters: "/PATH ""{app}\drivers"" {param:dpinstflags|/F}" ; Flags: waituntilterminated; Tasks: drivers drivers_overwrite
[Registry]
-Root: HKLM; Subkey: "Software\Analog Devices"; Flags: uninsdeletekeyifempty
-Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}"; Flags: uninsdeletekey
+Root: HKLM; Subkey: "Software\Analog Devices"
+Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}"
Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}\Settings"; ValueType: string; ValueName: "InstallPath"; ValueData: "{app}"
Root: HKLM; Subkey: "Software\Analog Devices\{#AppName}\Settings"; ValueType: string; ValueName: "InstallVersion"; ValueData: {#DriverVersion}
diff --git a/src/DisplayPlot.cc b/src/DisplayPlot.cc
index a6da863954..7157c9d374 100644
--- a/src/DisplayPlot.cc
+++ b/src/DisplayPlot.cc
@@ -57,6 +57,7 @@
#include
#include
#include
+#include
using namespace adiscope;
@@ -207,7 +208,7 @@ void OscScaleDraw::draw(QPainter *painter, const QPalette &) const
drawLabel(painter, delta);
}
- for (const auto &tick : ticks) {
+ for (const auto &tick : qAsConst(ticks)) {
if (tick != delta) {
drawLabel(painter, tick);
}
@@ -508,77 +509,73 @@ void PlotAxisConfiguration::setMouseGesturesEnabled(bool en)
* DisplayPlot class
*/
-DisplayPlot::DisplayPlot(int nplots, QWidget* parent,
+DisplayPlot::DisplayPlot(int nplots, QWidget* parent, bool isdBgraph,
unsigned int xNumDivs, unsigned int yNumDivs)
- : PrintablePlot(parent), d_nplots(nplots), d_stop(false),
- d_coloredLabels(false), d_mouseGesturesEnabled(false),
- d_displayScale(1), d_xAxisNumDiv(1),
- d_yAxisNumDiv(1)
+ : PrintablePlot(parent), d_nplots(nplots), d_stop(false),
+ d_coloredLabels(false), d_mouseGesturesEnabled(false),
+ d_displayScale(1), d_xAxisNumDiv(1), d_trackMode(false),
+ d_cursorsEnabled(false), d_isLogaritmicPlot(false),
+ d_isLogaritmicYPlot(false),
+ d_yAxisNumDiv(1)
{
- d_CurveColors << QColor("#ff7200") << QColor("#9013fe") << QColor(Qt::green)
- << QColor(Qt::cyan) << QColor(Qt::magenta)
- << QColor(Qt::yellow) << QColor(Qt::gray) << QColor(Qt::darkRed)
- << QColor(Qt::darkGreen) << QColor(Qt::darkBlue) << QColor(Qt::darkGray)
- << QColor(Qt::black);
- d_printColors << QColor("#ff7200") << QColor("#9013fe") << QColor(Qt::darkGreen)
- << QColor(Qt::blue) << QColor(Qt::magenta)
- << QColor(Qt::darkRed);
+ d_CurveColors << QColor("#ff7200") << QColor("#9013fe") << QColor(Qt::green)
+ << QColor(Qt::cyan) << QColor(Qt::magenta)
+ << QColor(Qt::yellow) << QColor(Qt::gray) << QColor(Qt::darkRed)
+ << QColor(Qt::darkGreen) << QColor(Qt::darkBlue) << QColor(Qt::darkGray)
+ << QColor(Qt::black);
- qRegisterMetaType("QColorList");
- resize(parent->width(), parent->height());
+ d_printColors << QColor("#ff7200") << QColor("#9013fe") << QColor(Qt::darkGreen)
+ << QColor(Qt::blue) << QColor(Qt::magenta)
+ << QColor(Qt::darkRed);
- d_autoscale_state = false;
+ qRegisterMetaType("QColorList");
+ resize(parent->width(), parent->height());
- d_yAxisUnit = "";
- d_xAxisUnit = "";
+ d_autoscale_state = false;
- setXaxisNumDiv(xNumDivs);
- setYaxisNumDiv(yNumDivs);
+ d_yAxisUnit = "";
+ d_xAxisUnit = "";
- d_usingLeftAxisScales = true;
+ setXaxisNumDiv(xNumDivs);
+ setYaxisNumDiv(yNumDivs);
- // Disable polygon clipping
+ d_usingLeftAxisScales = true;
+
+ // Disable polygon clipping
#if QWT_VERSION < 0x060000
- QwtPainter::setDeviceClipping(false);
+ QwtPainter::setDeviceClipping(false);
#else
- QwtPainter::setPolylineSplitting(false);
+ QwtPainter::setPolylineSplitting(false);
#endif
#if QWT_VERSION < 0x060000
- // We don't need the cache here
- canvas()->setPaintAttribute(QwtPlotCanvas::PaintCached, false);
- canvas()->setPaintAttribute(QwtPlotCanvas::PaintPacked, false);
+ // We don't need the cache here
+ canvas()->setPaintAttribute(QwtPlotCanvas::PaintCached, false);
+ canvas()->setPaintAttribute(QwtPlotCanvas::PaintPacked, false);
#endif
- QColor default_palette_color = QColor("white");
- setPaletteColor(default_palette_color);
+ QColor default_palette_color = QColor("white");
+ setPaletteColor(default_palette_color);
- d_panner = new QwtPlotPanner(canvas());
- d_panner->setAxisEnabled(QwtPlot::yRight, false);
- d_panner->setMouseButton(Qt::MidButton, Qt::ControlModifier);
+ d_panner = new QwtPlotPanner(canvas());
+ d_panner->setAxisEnabled(QwtPlot::yRight, false);
+ d_panner->setMouseButton(Qt::MidButton, Qt::ControlModifier);
- // emit the position of clicks on widget
- d_picker = new QwtDblClickPlotPicker(canvas());
+ // emit the position of clicks on widget
+ d_picker = new QwtDblClickPlotPicker(canvas());
#if QWT_VERSION < 0x060000
- connect(d_picker, SIGNAL(selected(const QPointF &)),
- this, SLOT(onPickerPointSelected(const QPointF &)));
+ connect(d_picker, SIGNAL(selected(const QPointF &)),
+ this, SLOT(onPickerPointSelected(const QPointF &)));
#else
- d_picker->setStateMachine(new QwtPickerDblClickPointMachine());
- connect(d_picker, SIGNAL(selected(const QPointF &)),
- this, SLOT(onPickerPointSelected6(const QPointF &)));
+ d_picker->setStateMachine(new QwtPickerDblClickPointMachine());
+ connect(d_picker, SIGNAL(selected(const QPointF &)),
+ this, SLOT(onPickerPointSelected6(const QPointF &)));
#endif
- // Configure horizontal axis
- bottomHorizAxisInit();
-
- // One vertical axis by default
- setLeftVertAxesCount(1);
-
- setActiveVertAxis(0);
-
- plotLayout()->setAlignCanvasToScales(true);
+ // Configure horizontal axis
+ bottomHorizAxisInit();
QColor plotColor;
if (QIcon::themeName() == "scopy-default") {
@@ -587,82 +584,685 @@ DisplayPlot::DisplayPlot(int nplots, QWidget* parent,
plotColor = QColor("#D3D3D3");
}
- for (unsigned int i = 0; i < 4; i++) {
- QwtScaleDraw::Alignment scale =
- static_cast(i);
- auto scaleItem = new EdgelessPlotScaleItem(scale);
-
- scaleItem->scaleDraw()->setAlignment(scale);
- scaleItem->scaleDraw()->enableComponent(QwtAbstractScaleDraw::Backbone, false);
- scaleItem->scaleDraw()->enableComponent(QwtAbstractScaleDraw::Labels, false);
- scaleItem->setFont(this->axisWidget(QwtPlot::yLeft)->font());
-
- QPalette palette = scaleItem->palette();
-
- palette.setBrush(QPalette::Foreground, plotColor);
- palette.setBrush(QPalette::Text, plotColor);
- scaleItem->setPalette(palette);
- scaleItem->setBorderDistance(0);
- scaleItem->attach(this);
- scaleItems.push_back(scaleItem);
- scaleItem->setZ(200);
- }
+ // One vertical axis by default
+ setLeftVertAxesCount(1);
+
+ setActiveVertAxis(0);
+
+ plotLayout()->setAlignCanvasToScales(true);
+
- this->plotLayout()->setCanvasMargin(0, QwtPlot::yLeft);
- this->plotLayout()->setCanvasMargin(0, QwtPlot::yRight);
- this->plotLayout()->setCanvasMargin(0, QwtPlot::xTop);
- this->plotLayout()->setCanvasMargin(0, QwtPlot::xBottom);
+ this->plotLayout()->setCanvasMargin(0, QwtPlot::yLeft);
+ this->plotLayout()->setCanvasMargin(0, QwtPlot::yRight);
+ this->plotLayout()->setCanvasMargin(0, QwtPlot::xTop);
+ this->plotLayout()->setCanvasMargin(0, QwtPlot::xBottom);
- ((QFrame*) canvas())->setLineWidth(0);
+ ((QFrame*) canvas())->setLineWidth(0);
- // Avoid jumping when labels with more/less digits
- // appear/disappear when scrolling vertically
+ //Set up the grid and the legend for all displayplots, but dBgraph
+ setupDisplayPlotDiv(isdBgraph);
- QwtLegend* legendDisplay = new QwtLegend(this);
+ d_symbolCtrl = new SymbolController(this);
+
+ /* Adjacent areas */
+ d_bottomHandlesArea = new HorizHandlesArea(this->canvas());
+ d_rightHandlesArea = new VertHandlesArea(this->canvas());
+ d_topHandlesArea = new HorizHandlesArea(this->canvas());
+ d_leftHandlesArea = new VertHandlesArea(this->canvas());
+
+ d_bottomHandlesArea->setMinimumHeight(50);
+ d_rightHandlesArea->setMinimumWidth(50);
+ d_bottomHandlesArea->setLargestChildWidth(60);
+ d_rightHandlesArea->setLargestChildHeight(60);
+ d_rightHandlesArea->setMinimumHeight(this->minimumHeight());
+
+ d_formatter = static_cast(new MetricPrefixFormatter);
+
+ markerIntersection1 = new QwtPlotMarker();
+ markerIntersection2 = new QwtPlotMarker();
+ markerIntersection1->setSymbol(new QwtSymbol(
+ QwtSymbol::Ellipse, QColor(237, 28, 36),
+ QPen(QColor(255, 255 ,255, 140), 2, Qt::SolidLine),
+ QSize(5, 5)));
+ markerIntersection2->setSymbol(new QwtSymbol(
+ QwtSymbol::Ellipse, QColor(237, 28, 36),
+ QPen(QColor(255, 255 ,255, 140), 2, Qt::SolidLine),
+ QSize(5, 5)));
+
+ d_selected_channel = -1;
+
+ setupCursors();
+ setupReadouts();
+}
+
+
+void DisplayPlot::setupDisplayPlotDiv(bool isdBgraph) {
+ if(!isdBgraph)
+ {
+
+ // Avoid jumping when labels with more/less digits
+ // appear/disappear when scrolling vertically
+ QwtLegend* legendDisplay = new QwtLegend(this);
#if QWT_VERSION < 0x060100
- legendDisplay->setItemMode(QwtLegend::CheckableItem);
- insertLegend(legendDisplay);
- connect(this, SIGNAL(legendChecked(QwtPlotItem *, bool)),
- this, SLOT(legendEntryChecked(QwtPlotItem *, bool)));
+ legendDisplay->setItemMode(QwtLegend::CheckableItem);
+ insertLegend(legendDisplay);
+ connect(this, SIGNAL(legendChecked(QwtPlotItem *, bool)),
+ this, SLOT(legendEntryChecked(QwtPlotItem *, bool)));
#else /* QWT_VERSION < 0x060100 */
- legendDisplay->setDefaultItemMode(QwtLegendData::Checkable);
- insertLegend(legendDisplay);
- connect(legendDisplay, SIGNAL(checked(const QVariant&, bool, int)),
- this, SLOT(legendEntryChecked(const QVariant&, bool, int)));
+ legendDisplay->setDefaultItemMode(QwtLegendData::Checkable);
+ insertLegend(legendDisplay);
+ connect(legendDisplay, SIGNAL(checked(const QVariant&, bool, int)),
+ this, SLOT(legendEntryChecked(const QVariant&, bool, int)));
#endif /* QWT_VERSION < 0x060100 */
- // Plot needs a grid
- d_grid = new EdgelessPlotGrid();
- QColor majorPenColor(plotColor);
- d_grid->setMajorPen(majorPenColor, 1.0, Qt::DashLine);
- d_grid->attach(this);
+ for (unsigned int i = 0; i < 4; i++) {
+ QwtScaleDraw::Alignment scale =
+ static_cast(i);
+ auto scaleItem = new EdgelessPlotScaleItem(scale);
+
+ scaleItem->scaleDraw()->setAlignment(scale);
+ scaleItem->scaleDraw()->enableComponent(QwtAbstractScaleDraw::Backbone, false);
+ scaleItem->scaleDraw()->enableComponent(QwtAbstractScaleDraw::Labels, false);
+ scaleItem->setFont(this->axisWidget(QwtPlot::yLeft)->font());
+
+ QPalette palette = scaleItem->palette();
+ palette.setBrush(QPalette::Foreground, QColor("#6E6E6F"));
+ palette.setBrush(QPalette::Text, QColor("#6E6E6F"));
+ scaleItem->setPalette(palette);
+ scaleItem->setBorderDistance(0);
+ scaleItem->attach(this);
+ scaleItems.push_back(scaleItem);
+ scaleItem->setZ(200);
+ }
+
+ // Plot needs a grid
+ d_grid = new EdgelessPlotGrid();
+ QColor majorPenColor("#353537");
+ d_grid->setMajorPen(majorPenColor, 1.0, Qt::DashLine);
+ d_grid->attach(this);
+ }
}
+
DisplayPlot::~DisplayPlot()
{
- // d_zoomer and d_panner deleted when parent deleted
+ markerIntersection1->detach();
+ markerIntersection2->detach();
+ // d_zoomer and d_panner deleted when parent deleted
+ // Since some curves may not be attached to the plot they won't get deleted
+ for (auto it = d_plot_curve.begin(); it != d_plot_curve.end() ; ++it) {
+ QwtPlotCurve * qpc = (*it);
+ qpc->detach();
+ delete qpc;
+ }
+
+ // delete vertAxes
+ for (auto it = vertAxes.begin(); it != vertAxes.end(); ++it) {
+ delete *it;
+ }
+
+ for (auto it = scaleItems.begin(); it != scaleItems.end(); ++it) {
+ delete *it;
+ }
+
+ delete markerIntersection1;
+ delete markerIntersection2;
+ delete horizAxis;
+}
- // Since some curves may not be attached to the plot they won't get deleted
- for (auto it = d_plot_curve.begin(); it != d_plot_curve.end() ; ++it) {
- QwtPlotCurve * qpc = (*it);
- qpc->detach();
- delete qpc;
+QWidget* DisplayPlot::getPlotwithElements()
+{
+ QWidget* widget = new QWidget();
+ QGridLayout *gridplot = new QGridLayout();
+
+ gridplot->addWidget(topHandlesArea(), 0, 0, 1, 3);
+ gridplot->addWidget(leftHandlesArea(), 0, 0, 3, 1);
+ gridplot->addWidget(this, 1, 1, 1, 1);
+ gridplot->addWidget(rightHandlesArea(), 0, 2, 3, 1);
+ gridplot->addWidget(bottomHandlesArea(), 2, 0, 1, 3);
+
+ gridplot->setVerticalSpacing(0);
+ gridplot->setHorizontalSpacing(0);
+ gridplot->setContentsMargins(0, 0, 0, 0);
+ widget->setLayout(gridplot);
+
+ return widget;
+}
+
+
+void DisplayPlot::setupCursors() {
+
+ d_vBar1 = new VertBar(this, true);
+ d_vBar2 = new VertBar(this, true);
+ d_hBar1 = new HorizBar(this, true);
+ d_hBar2 = new HorizBar(this, true);
+
+ d_vCursorHandle1 = new PlotLineHandleV(
+ QPixmap(":/icons/v_cursor_handle.svg"),
+ d_rightHandlesArea);
+ d_vCursorHandle2 = new PlotLineHandleV(
+ QPixmap(":/icons/v_cursor_handle.svg"),
+ d_rightHandlesArea);
+ d_hCursorHandle1 = new PlotLineHandleH(
+ QPixmap(":/icons/h_cursor_handle.svg"),
+ d_bottomHandlesArea);
+ d_hCursorHandle2 = new PlotLineHandleH(
+ QPixmap(":/icons/h_cursor_handle.svg"),
+ d_bottomHandlesArea);
+
+ d_vertCursorsHandleEnabled = true;
+
+ d_symbolCtrl->attachSymbol(d_vBar1);
+ d_symbolCtrl->attachSymbol(d_vBar2);
+ d_symbolCtrl->attachSymbol(d_hBar1);
+ d_symbolCtrl->attachSymbol(d_hBar2);
+
+ QPen cursorsLinePen = QPen(QColor(155, 155, 155), 1, Qt::DashLine);
+ d_hBar1->setPen(cursorsLinePen);
+ d_hBar2->setPen(cursorsLinePen);
+ d_vBar1->setPen(cursorsLinePen);
+ d_vBar2->setPen(cursorsLinePen);
+
+ d_vCursorHandle1->setPen(cursorsLinePen);
+ d_vCursorHandle2->setPen(cursorsLinePen);
+ d_hCursorHandle1->setPen(cursorsLinePen);
+ d_hCursorHandle2->setPen(cursorsLinePen);
+
+ d_vBar1->setVisible(false);
+ d_vBar2->setVisible(false);
+ d_hBar1->setVisible(false);
+ d_hBar2->setVisible(false);
+
+ d_vCursorHandle1->hide();
+ d_vCursorHandle2->hide();
+ d_hCursorHandle1->hide();
+ d_hCursorHandle2->hide();
+
+ vertCursorsLocked = false;
+ horizCursorsLocked = false;
+
+ /* When a handle position changes the bar follows */
+ connect(d_vCursorHandle1, SIGNAL(positionChanged(int)),
+ SLOT(onVertCursorHandle1Changed(int)));
+ connect(d_vCursorHandle2, SIGNAL(positionChanged(int)),
+ SLOT(onVertCursorHandle2Changed(int)));
+ connect(d_hCursorHandle1, SIGNAL(positionChanged(int)),
+ SLOT(onHorizCursorHandle1Changed(int)));
+ connect(d_hCursorHandle2, SIGNAL(positionChanged(int)),
+ SLOT(onHorizCursorHandle2Changed(int)));
+
+ /* When bar position changes due to plot resizes update the handle */
+ connect(d_hBar1, SIGNAL(pixelPositionChanged(int)),
+ SLOT(onHbar1PixelPosChanged(int)));
+ connect(d_hBar2, SIGNAL(pixelPositionChanged(int)),
+ SLOT(onHbar2PixelPosChanged(int)));
+ connect(d_vBar1, SIGNAL(pixelPositionChanged(int)),
+ SLOT(onVbar1PixelPosChanged(int)));
+ connect(d_vBar2, SIGNAL(pixelPositionChanged(int)),
+ SLOT(onVbar2PixelPosChanged(int)));
+}
+
+void DisplayPlot::setupReadouts() {
+ d_cursorReadoutsVisible = false;
+
+ d_cursorReadouts = new CursorReadouts(this);
+ d_cursorReadouts->setAxis(QwtPlot::xTop,QwtPlot::yLeft);
+ d_cursorReadouts->setTopLeftStartingPoint(QPoint(8, 8));
+ d_cursorReadouts->setTimeReadoutVisible(false);
+ d_cursorReadouts->setVoltageReadoutVisible(false);
+
+ /* Update Cursor Readouts */
+ connect(d_hBar1, SIGNAL(positionChanged(double)),
+ SLOT(onHCursor1Moved(double)));
+ connect(d_hBar2, SIGNAL(positionChanged(double)),
+ SLOT(onHCursor2Moved(double)));
+ connect(d_vBar1, SIGNAL(positionChanged(double)),
+ SLOT(onVCursor1Moved(double)));
+ connect(d_vBar2, SIGNAL(positionChanged(double)),
+ SLOT(onVCursor2Moved(double)));
+}
+
+void DisplayPlot::onVertCursorHandle1Changed(int value)
+{
+ if (vertCursorsLocked) {
+ int position2 = value - (pixelPosHandleVert1 - pixelPosHandleVert2);
+ pixelPosHandleVert2 = position2;
+ d_hBar2->setPixelPosition(position2);
}
+ pixelPosHandleVert1 = value;
+
+ d_hBar1->setPixelPosition(value);
+}
- // delete vertAxes
- for (auto it = vertAxes.begin(); it != vertAxes.end(); ++it) {
- delete *it;
+void DisplayPlot::onVertCursorHandle2Changed(int value)
+{
+ if (vertCursorsLocked) {
+ int position1 = value + (pixelPosHandleVert1 - pixelPosHandleVert2);
+ pixelPosHandleVert1 = position1;
+ d_hBar1->setPixelPosition(position1);
}
+ pixelPosHandleVert2 = value;
+ d_hBar2->setPixelPosition(value);
+}
+
- for (auto it = scaleItems.begin(); it != scaleItems.end(); ++it) {
- delete *it;
+void DisplayPlot::onHorizCursorHandle1Changed(int value)
+{
+ if (horizCursorsLocked) {
+ int position2 = value - (pixelPosHandleHoriz1 - pixelPosHandleHoriz2);
+ pixelPosHandleHoriz2 = position2;
+ d_vBar2->setPixelPosition(position2);
}
+ pixelPosHandleHoriz1 = value;
+ d_vBar1->setPixelPosition(value);
+}
- delete d_grid;
+void DisplayPlot::onHorizCursorHandle2Changed(int value)
+{
+ if (horizCursorsLocked) {
+ int position1 = value + (pixelPosHandleHoriz1 - pixelPosHandleHoriz2);
+ pixelPosHandleHoriz1 = position1;
+ d_vBar1->setPixelPosition(position1);
+ }
+ pixelPosHandleHoriz2 = value;
+ d_vBar2->setPixelPosition(value);
+}
- //delete horizAxis
- delete horizAxis;
+VertBar* DisplayPlot::vBar1()
+{
+ return d_vBar1;
+}
+
+VertBar* DisplayPlot::vBar2()
+{
+ return d_vBar2;
+}
+
+HorizHandlesArea* DisplayPlot::bottomHandlesArea()
+{
+ return d_bottomHandlesArea;
+}
+
+QWidget * DisplayPlot::rightHandlesArea()
+{
+ return d_rightHandlesArea;
+}
+
+QWidget * DisplayPlot::leftHandlesArea()
+{
+ return d_leftHandlesArea;
+}
+
+QWidget * DisplayPlot::topHandlesArea()
+{
+ return d_topHandlesArea;
+}
+
+QString DisplayPlot::formatXValue(double value, int precision) const
+{
+ return d_formatter->format(value, d_xAxisUnit, precision);
+}
+
+QString DisplayPlot::formatYValue(double value, int precision) const
+{
+ return d_formatter->format(value, d_yAxisUnit, precision);
+}
+
+void DisplayPlot::onHbar1PixelPosChanged(int pos)
+{
+ d_vCursorHandle1->setPositionSilenty(pos);
+}
+
+void DisplayPlot::onHbar2PixelPosChanged(int pos)
+{
+ d_vCursorHandle2->setPositionSilenty(pos);
+}
+
+void DisplayPlot::onVbar1PixelPosChanged(int pos)
+{
+ d_hCursorHandle1->setPositionSilenty(pos);
+ displayIntersection();
+}
+
+void DisplayPlot::onVbar2PixelPosChanged(int pos)
+{
+ d_hCursorHandle2->setPositionSilenty(pos);
+ displayIntersection();
+}
+
+struct cursorReadoutsText DisplayPlot::allCursorReadouts() const
+{
+ return d_cursorReadoutsText;
+}
+
+void DisplayPlot::onVCursor1Moved(double value)
+{
+ QString text;
+
+ text = d_formatter->format(value, "", 3);
+ d_cursorReadouts->setTimeCursor1Text(text);
+ d_cursorReadoutsText.t1 = text;
+
+ double diff = value - d_vBar2->plotCoord().y();
+ text = d_formatter->format(diff, "", 3);
+ d_cursorReadouts->setTimeDeltaText(text);
+ d_cursorReadoutsText.tDelta = text;
+
+ Q_EMIT cursorReadoutsChanged(d_cursorReadoutsText);
+}
+
+void DisplayPlot::onVCursor2Moved(double value)
+{
+ QString text;
+
+ text = d_formatter->format(value, "", 3);
+ d_cursorReadouts->setTimeCursor2Text(text);
+ d_cursorReadoutsText.t2 = text;
+
+ double diff = d_vBar1->plotCoord().y() - value;
+ text = d_formatter->format(diff, "", 3);
+ d_cursorReadouts->setTimeDeltaText(text);
+ d_cursorReadoutsText.tDelta = text;
+
+ Q_EMIT cursorReadoutsChanged(d_cursorReadoutsText);
+}
+
+
+void DisplayPlot::onHCursor1Moved(double value)
+{
+ QString text;
+ bool error = false;
+
+ value *= d_displayScale;
+ text = d_formatter->format(value, "", 3);
+ d_cursorReadouts->setVoltageCursor1Text(error ? "-" : text);
+ d_cursorReadoutsText.v1 = error ? "-" : text;
+
+ double valueCursor2 = d_hBar2->plotCoord().x();
+
+ double diff = value - (valueCursor2 * d_displayScale) ;
+ text = d_formatter->format(diff, "", 3);
+ d_cursorReadouts->setVoltageDeltaText(error ? "-" : text);
+ d_cursorReadoutsText.vDelta = error ? "-" : text;
+
+ Q_EMIT cursorReadoutsChanged(d_cursorReadoutsText);
+}
+
+void DisplayPlot::onHCursor2Moved(double value)
+{
+ QString text;
+ bool error = false;
+
+ value *= d_displayScale;
+ text = d_formatter->format(value, "", 3);
+ d_cursorReadouts->setVoltageCursor2Text(error ? "-" : text);
+ d_cursorReadoutsText.v2 = error ? "-" : text;
+
+ double valueCursor1 = d_hBar1->plotCoord().x();
+
+ double diff = (valueCursor1 * d_displayScale) - value;
+ text = d_formatter->format(diff, "", 3);
+ d_cursorReadouts->setVoltageDeltaText(error ? "-" : text);
+ d_cursorReadoutsText.vDelta = error ? "-" : text;
+
+ Q_EMIT cursorReadoutsChanged(d_cursorReadoutsText);
+}
+
+void DisplayPlot::setVertCursorsEnabled(bool en)
+{
+ if (d_vertCursorsEnabled != en) {
+ d_vertCursorsEnabled = en;
+ d_vBar1->setVisible(en);
+ d_vBar2->setVisible(en);
+ d_hCursorHandle1->setVisible(en);
+ d_hCursorHandle2->setVisible(en);
+ d_cursorReadouts->setTimeReadoutVisible(en &&
+ d_cursorReadoutsVisible);
+ }
+}
+
+void DisplayPlot::toggleCursors(bool en)
+{
+ if (d_cursorsEnabled != en) {
+ d_cursorsEnabled = en;
+ d_vBar1->setVisible(en);
+ d_vBar2->setVisible(en);
+
+ if(d_vertCursorsHandleEnabled)
+ {
+ d_hCursorHandle1->setVisible(en);
+ d_hCursorHandle2->setVisible(en);
+ }
+
+ d_cursorReadouts->setTimeReadoutVisible(en);
+ d_cursorReadouts->setVoltageReadoutVisible(en);
+
+ if (en) {
+ onVCursor1Moved(d_vBar1->plotCoord().x());
+ onVCursor2Moved(d_vBar2->plotCoord().x());
+ } else {
+ markerIntersection1->detach();
+ markerIntersection2->detach();
+ replot();
+ }
+ }
+}
+
+bool DisplayPlot::isLogaritmicPlot() const
+{
+ return d_isLogaritmicPlot;
+}
+
+void DisplayPlot::setPlotLogaritmic(bool value)
+{
+ d_isLogaritmicPlot = value;
+}
+
+bool DisplayPlot::isLogaritmicYPlot() const
+{
+ return d_isLogaritmicYPlot;
+}
+
+void DisplayPlot::setPlotYLogaritmic(bool value)
+{
+ d_isLogaritmicYPlot = value;
+}
+
+void DisplayPlot::setVertCursorsHandleEnabled(bool en)
+{
+ d_vertCursorsHandleEnabled = en;
+}
+
+bool DisplayPlot::vertCursorsEnabled()
+{
+ return d_vertCursorsEnabled;
+}
+
+void DisplayPlot::setHorizCursorsEnabled(bool en)
+{
+ if (d_horizCursorsEnabled != en) {
+ d_horizCursorsEnabled = en;
+ d_hBar1->setVisible(en);
+ d_hBar2->setVisible(en);
+ d_vCursorHandle1->setVisible(en);
+ d_vCursorHandle2->setVisible(en);
+ d_cursorReadouts->setVoltageReadoutVisible(en &&
+ d_cursorReadoutsVisible);
+ }
+}
+
+bool DisplayPlot::horizCursorsEnabled()
+{
+ return d_horizCursorsEnabled;
+}
+
+void DisplayPlot::setCursorReadoutsVisible(bool en)
+{
+ if (d_cursorReadoutsVisible != en) {
+ d_cursorReadoutsVisible = en;
+ d_cursorReadouts->setVoltageReadoutVisible(en &&
+ d_vertCursorsEnabled );
+ d_cursorReadouts->setTimeReadoutVisible(en &&
+ d_horizCursorsEnabled );
+ }
+}
+
+void DisplayPlot::setHorizCursorsLocked(bool value)
+{
+ horizCursorsLocked = value;
+}
+
+void DisplayPlot::setVertCursorsLocked(bool value)
+{
+ vertCursorsLocked = value;
+}
+
+void DisplayPlot::setCursorReadoutsTransparency(int value)
+{
+ d_cursorReadouts->setTransparency(value);
+}
+
+void DisplayPlot::moveCursorReadouts(CustomPlotPositionButton::ReadoutsPosition position)
+{
+ d_cursorReadouts->moveToPosition(position);
+}
+
+void DisplayPlot::trackModeEnabled(bool enabled)
+{
+ d_trackMode = !enabled;
+ if (d_horizCursorsEnabled) {
+ d_hBar1->setVisible(enabled);
+ d_hBar2->setVisible(enabled);
+ d_vCursorHandle1->setVisible(enabled);
+ d_vCursorHandle2->setVisible(enabled);
+ }
+ if (d_trackMode) {
+ onVCursor1Moved(d_vBar1->plotCoord().x());
+ onVCursor2Moved(d_vBar2->plotCoord().x());
+ displayIntersection();
+ } else {
+ onHCursor1Moved(d_hBar1->plotCoord().y());
+ onHCursor2Moved(d_hBar2->plotCoord().y());
+ markerIntersection1->detach();
+ markerIntersection2->detach();
+ replot();
+ }
+}
+
+void DisplayPlot::displayIntersection()
+{
+ if (!d_trackMode) {
+ return;
+ }
+
+ double intersectionCursor1, intersectionCursor2;
+ bool attachmk1 = true;
+ bool attachmk2 = true;
+
+
+ intersectionCursor1 = getHorizontalCursorIntersection(d_vBar1->plotCoord().x());
+ intersectionCursor2 = getHorizontalCursorIntersection(d_vBar2->plotCoord().x());
+
+ if (intersectionCursor1 == -1000000){
+ attachmk1 = false;
+ }
+ if (intersectionCursor2 == -1000000) {
+ attachmk2 = false;
+ }
+
+ bool value = isAxisValid(QwtAxisId(QwtPlot::yLeft, d_selected_channel));
+
+ if(value)
+ {
+ markerIntersection1->setAxes(QwtPlot::xBottom, QwtAxisId(QwtPlot::yLeft, d_selected_channel));
+ markerIntersection2->setAxes(QwtPlot::xBottom, QwtAxisId(QwtPlot::yLeft, d_selected_channel));
+ }
+ else
+ {
+ markerIntersection1->setAxes(QwtPlot::xBottom, QwtAxisId(QwtPlot::yLeft, 0));
+ markerIntersection2->setAxes(QwtPlot::xBottom, QwtAxisId(QwtPlot::yLeft, 0));
+ }
+
+ markerIntersection1->setValue(d_vBar1->plotCoord().x(), intersectionCursor1);
+ markerIntersection2->setValue(d_vBar2->plotCoord().x(), intersectionCursor2);
+
+ if (attachmk1) {
+ markerIntersection1->attach(this);
+ } else {
+ markerIntersection1->detach();
+ }
+ if (attachmk2) {
+ markerIntersection2->attach(this);
+ } else {
+ markerIntersection2->detach();
+ }
+
+ replot();
+}
+
+double DisplayPlot::getHorizontalCursorIntersection(double time)
+{
+ int n = Curve(d_selected_channel)->data()->size();
+
+ if (n == 0) {
+ return -1;
+ } else {
+ double leftTime, rightTime, leftCustom, rightCustom;
+ int rightIndex = -1;
+ int leftIndex = -1;
+
+ int left = 0;
+ int right = n - 1;
+
+ if (Curve(d_selected_channel)->data()->sample(right).x() < time ||
+ Curve(d_selected_channel)->data()->sample(left).x() > time) {
+ return -1;
+ }
+
+ while (left <= right) {
+ int mid = (left + right) / 2;
+ double xData = Curve(d_selected_channel)->data()->sample(mid).x();
+ if (xData == time) {
+ if (mid > 0) {
+ leftIndex = mid - 1;
+ rightIndex = mid;
+ }
+ break;
+ } else if (xData < time) {
+ left = mid + 1;
+ } else {
+ right = mid - 1;
+ }
+ }
+
+ if ((leftIndex == -1 || rightIndex == -1) && left > 0) {
+ leftIndex = left - 1;
+ rightIndex = left;
+ }
+
+ if (leftIndex == -1 || rightIndex == -1) {
+ return -1;
+ }
+
+ leftTime = Curve(d_selected_channel)->data()->sample(leftIndex).x();
+ rightTime = Curve(d_selected_channel)->data()->sample(rightIndex).x();
+
+ leftCustom = Curve(d_selected_channel)->data()->sample(leftIndex).y();
+ rightCustom = Curve(d_selected_channel)->data()->sample(rightIndex).y();
+
+ double value = (rightCustom - leftCustom) / (rightTime - leftTime) *
+ (time - leftTime) + leftCustom;
+
+ return value;
+ }
+}
+
+void DisplayPlot::repositionCursors()
+{
+ onVCursor1Moved(d_vBar1->plotCoord().x());
+ onVCursor2Moved(d_vBar2->plotCoord().x());
+ displayIntersection();
}
void
@@ -1222,6 +1822,7 @@ void DisplayPlot::bringCurveToFront(unsigned int curveIdx)
{
DetachCurve(curveIdx);
AttachCurve(curveIdx);
+ displayIntersection();
replot();
}
@@ -1555,6 +2156,26 @@ static QwtScaleDiv getEdgelessScaleDiv(const QwtScaleDiv& from_scaleDiv)
return QwtScaleDiv(lowerBound, upperBound, minorTicks, mediumTicks, majorTicks);
}
+void DisplayPlot::setXaxisMajorTicksPos(QList ticks)
+{
+ d_majorTicks = ticks;
+}
+
+QList DisplayPlot::getXaxisMajorTicksPos() const
+{
+ return d_majorTicks;
+}
+
+void DisplayPlot::setYaxisMajorTicksPos(QList ticks)
+{
+ d_majorTicksY = ticks;
+}
+
+QList DisplayPlot::getYaxisMajorTicksPos() const
+{
+ return d_majorTicksY;
+}
+
unsigned int DisplayPlot::xAxisNumDiv() const
{
return d_xAxisNumDiv;
diff --git a/src/DisplayPlot.h b/src/DisplayPlot.h
index 9ad53a588a..91469c15c4 100644
--- a/src/DisplayPlot.h
+++ b/src/DisplayPlot.h
@@ -65,6 +65,12 @@
#include "plot_utils.hpp"
#include "extendingplotzoomer.h"
#include "printableplot.h"
+#include "symbol_controller.h"
+#include "plot_line_handle.h"
+#include "cursor_readouts.h"
+#include "handles_area.hpp"
+#include "plotpickerwrapper.h"
+#include
typedef QList QColorList;
Q_DECLARE_METATYPE ( QColorList )
@@ -215,6 +221,16 @@ public Q_SLOTS:
}
};
+struct cursorReadoutsText {
+ QString t1;
+ QString t2;
+ QString tDelta;
+ QString freq;
+ QString v1;
+ QString v2;
+ QString vDelta;
+};
+
/*!
* \brief QWidget base plot to build QTGUI plotting tools.
* \ingroup qtgui_blk
@@ -284,8 +300,10 @@ class DisplayPlot:public PrintablePlot
public:
- DisplayPlot(int nplots, QWidget*, unsigned int xNumDivs = 10,
- unsigned int yNumDivs = 10);
+ DisplayPlot(int nplots, QWidget*,
+ bool isdBgraph = false,
+ unsigned int xNumDivs = 10,
+ unsigned int yNumDivs = 10);
virtual ~DisplayPlot();
virtual void replot() = 0;
@@ -377,16 +395,39 @@ class DisplayPlot:public PrintablePlot
QwtPlotZoomer *getZoomer() const;
void setZoomerParams(bool bounded, int maxStackDepth);
-
-
void bringCurveToFront(unsigned int curveIdx);
void enableColoredLabels(bool colored);
void enableMouseGesturesOnScales(bool enable);
void setDisplayScale(double value);
-
void setAllYAxis(double min, double max);
+
+ HorizHandlesArea* bottomHandlesArea();
+ QWidget *rightHandlesArea();
+ QWidget *leftHandlesArea();
+ virtual QWidget *topHandlesArea();
+ VertBar* vBar1();
+ VertBar* vBar2();
+ bool isLogaritmicPlot() const;
+ void setPlotLogaritmic(bool );
+ bool isLogaritmicYPlot() const;
+ void setPlotYLogaritmic(bool value);
+ void setXaxisMajorTicksPos(QList);
+ QList getXaxisMajorTicksPos() const;
+ void setYaxisMajorTicksPos(QList);
+ QList getYaxisMajorTicksPos() const;
+ QWidget* getPlotwithElements();
+
+ bool vertCursorsEnabled();
+ bool horizCursorsEnabled();
+ struct cursorReadoutsText allCursorReadouts() const;
+ void trackModeEnabled(bool enabled);
+ void repositionCursors();
+ void toggleCursors(bool en);
+ virtual QString formatXValue(double value, int precision) const;
+ virtual QString formatYValue(double value, int precision) const;
+
public Q_SLOTS:
virtual void disableLegend();
virtual void setYaxis(double min, double max);
@@ -498,6 +539,16 @@ public Q_SLOTS:
unsigned int xAxisNumDiv() const;
unsigned int yAxisNumDiv() const;
+ void setVertCursorsEnabled(bool en);
+ void setHorizCursorsEnabled(bool en);
+ void setVertCursorsHandleEnabled(bool en);
+ void setCursorReadoutsVisible(bool en);
+ void setHorizCursorsLocked(bool value);
+ void setVertCursorsLocked(bool value);
+
+ void setCursorReadoutsTransparency(int value);
+ void moveCursorReadouts(CustomPlotPositionButton::ReadoutsPosition position);
+
Q_SIGNALS:
void horizScaleDivisionChanged(double);
void vertScaleDivisionChanged(double);
@@ -509,6 +560,19 @@ public Q_SLOTS:
// signals that the plot size changed
void plotSizeChanged();
+ void cursorReadoutsChanged(struct cursorReadoutsText);
+
+private Q_SLOTS:
+ void onHbar1PixelPosChanged(int);
+ void onHbar2PixelPosChanged(int);
+ void onVbar1PixelPosChanged(int);
+ void onVbar2PixelPosChanged(int);
+
+ void onHorizCursorHandle1Changed(int value);
+ void onVertCursorHandle1Changed(int value);
+ void onVertCursorHandle2Changed(int value);
+ void onHorizCursorHandle2Changed(int value);
+
protected Q_SLOTS:
virtual void legendEntryChecked(QwtPlotItem *plotItem, bool on);
virtual void legendEntryChecked(const QVariant &plotItem, bool on, int index);
@@ -518,6 +582,11 @@ protected Q_SLOTS:
void onVertAxisOffsetDecrease();
void onVertAxisOffsetIncrease();
+ virtual void onHCursor1Moved(double);
+ virtual void onHCursor2Moved(double);
+ virtual void onVCursor1Moved(double);
+ virtual void onVCursor2Moved(double);
+
void _onXbottomAxisWidgetScaleDivChanged();
void _onYleftAxisWidgetScaleDivChanged();
@@ -578,11 +647,62 @@ protected Q_SLOTS:
void resizeEvent(QResizeEvent *event);
+ HorizHandlesArea *d_bottomHandlesArea;
+ VertHandlesArea *d_rightHandlesArea;
+ VertHandlesArea *d_leftHandlesArea;
+ HorizHandlesArea *d_topHandlesArea;
+
+ VertBar *d_vBar1;
+ VertBar *d_vBar2;
+ HorizBar *d_hBar1;
+ HorizBar *d_hBar2;
+ SymbolController *d_symbolCtrl;
+
+ PlotLineHandleV *d_vCursorHandle1;
+ PlotLineHandleV *d_vCursorHandle2;
+ PlotLineHandleH *d_hCursorHandle1;
+ PlotLineHandleH *d_hCursorHandle2;
+
+ struct cursorReadoutsText d_cursorReadoutsText;
+ CursorReadouts *d_cursorReadouts;
+
+ bool d_trackMode;
+ int d_selected_channel;
+ bool d_cursorsEnabled;
+
+ QwtPlotMarker *markerIntersection1;
+ QwtPlotMarker *markerIntersection2;
+
+ double getHorizontalCursorIntersection(double time);
+
private:
void AddAxisOffset(int axisPos, int axisIdx, double offset);
bool d_coloredLabels;
bool d_mouseGesturesEnabled;
+ bool d_vertCursorsHandleEnabled;
+ bool d_vertCursorsEnabled;
+ bool d_horizCursorsEnabled;
+ bool horizCursorsLocked;
+ bool vertCursorsLocked;
+
+ int pixelPosHandleHoriz1;
+ int pixelPosHandleHoriz2;
+ int pixelPosHandleVert1;
+ int pixelPosHandleVert2;
+
+ bool d_isLogaritmicPlot;
+ bool d_isLogaritmicYPlot;
+ QList d_majorTicks;
+ QList d_majorTicksY;
+ bool d_cursorReadoutsVisible;
+ PrefixFormatter * d_formatter;
+
+ void setupCursors();
+ void setupReadouts();
+ void displayIntersection();
+ void setupDisplayPlotDiv(bool isdBgraph);
+
};
/*
diff --git a/src/FftDisplayPlot.cc b/src/FftDisplayPlot.cc
index 26497f9ef3..3efe221bf8 100644
--- a/src/FftDisplayPlot.cc
+++ b/src/FftDisplayPlot.cc
@@ -31,6 +31,8 @@
#include
#include
+#define ERROR_VALUE -10000000
+
using namespace adiscope;
class FftDisplayZoomer: public LimitedPlotZoomer
@@ -129,6 +131,9 @@ FftDisplayPlot::FftDisplayPlot(int nplots, QWidget *parent) :
setAxisScaleDraw(QwtPlot::xBottom, xScaleDraw);
xScaleDraw->setFloatPrecision(2);
+ d_yAxisUnit = "dB";
+ d_xAxisUnit = "Hz";
+
_resetXAxisPoints();
d_mrkCtrl = new MarkerController(this);
@@ -156,6 +161,26 @@ FftDisplayPlot::FftDisplayPlot(int nplots, QWidget *parent) :
setMaxYaxisDivision(100); // A maximum division of 100 dB
setVertUnitsPerDiv(20);
setVertOffset(-VertUnitsPerDiv() * 5);
+
+ setYaxisNumDiv(11);
+
+ d_selected_channel = 0;
+
+ d_topHandlesArea->setMinimumHeight(50);
+ d_topHandlesArea->setLargestChildWidth(50);
+
+ d_leftHandlesArea->setMinimumWidth(50);
+ d_leftHandlesArea->setTopPadding(50);
+ d_leftHandlesArea->setBottomPadding(55);
+ d_leftHandlesArea->setMinimumHeight(this->minimumHeight());
+
+ enableAxis(QwtPlot::xBottom, false);
+ enableAxis(QwtPlot::yLeft, false);
+ d_formatter = static_cast(new MetricPrefixFormatter);
+
+ setupReadouts();
+
+ installEventFilter(this);
}
FftDisplayPlot::~FftDisplayPlot()
@@ -182,15 +207,208 @@ FftDisplayPlot::~FftDisplayPlot()
}
d_refXdata.clear();
d_refYdata.clear();
+ removeEventFilter(this);
+ canvas()->removeEventFilter(d_cursorReadouts);
+ canvas()->removeEventFilter(d_symbolCtrl);
}
void FftDisplayPlot::replot()
{
+ if (!d_leftHandlesArea || !d_bottomHandlesArea) {
+ return;
+ }
+
+ d_leftHandlesArea->repaint();
+ d_bottomHandlesArea->repaint();
+
QwtPlot::replot();
}
+QString FftDisplayPlot::formatXValue(double value, int precision) const
+{
+ return d_formatter->format(value, "Hz", precision);
+}
+
+QString FftDisplayPlot::formatYValue(double value, int precision) const
+{
+ return d_formatter->format(value, "dB", precision);
+}
+
+void FftDisplayPlot::setupReadouts()
+{
+ d_cursorReadouts->setTimeReadoutVisible(false);
+ d_cursorReadouts->setVoltageReadoutVisible(false);
+
+ d_cursorReadouts->setTimeCursor1LabelText("F1 = ");
+ d_cursorReadouts->setTimeCursor2LabelText("F2 = ");
+ d_cursorReadouts->setTimeDeltaLabelText("ΔF = ");
+ d_cursorReadouts->setVoltageCursor1LabelText("Mag1 = ");
+ d_cursorReadouts->setVoltageCursor2LabelText("Mag2 = ");
+ d_cursorReadouts->setDeltaVoltageLabelText("ΔMag = ");
+
+ d_cursorReadouts->setFrequencyDeltaVisible(false);
+ d_cursorReadouts->setTransparency(0);
+}
+
+void FftDisplayPlot::updateHandleAreaPadding()
+{
+ d_leftHandlesArea->repaint();
+ d_bottomHandlesArea->setLeftPadding(d_leftHandlesArea->width());
+ d_bottomHandlesArea->setRightPadding(50);
+
+ d_rightHandlesArea->setTopPadding(50);
+ d_rightHandlesArea->setBottomPadding(50);
+
+ //update handle position to avoid cursors getting out of the plot bounds when changing the padding;
+ d_hCursorHandle1->updatePosition();
+ d_hCursorHandle2->updatePosition();
+ d_vCursorHandle1->updatePosition();
+ d_vCursorHandle2->updatePosition();
+}
+
+void FftDisplayPlot::onHCursor1Moved(double value)
+{
+ QString text;
+ bool error = false;
+ if (d_trackMode) {
+ if (value == ERROR_VALUE) {
+ error = true;
+ }
+ }
+
+ value *= d_displayScale;
+ text = d_formatter->format(value, "dB", 3);
+ d_cursorReadouts->setVoltageCursor1Text(error ? "-" : text);
+ d_cursorReadoutsText.t1 = error ? "-" : text;
+
+ double valueCursor2;
+ if (d_trackMode) {
+ valueCursor2 = getHorizontalCursorIntersection(d_vBar2->plotCoord().x());
+ } else {
+ valueCursor2 = d_hBar2->plotCoord().y();
+ }
+
+ double diff = value - (valueCursor2 * d_displayScale);
+ text = d_formatter->format(diff, "dB", 3);
+ d_cursorReadouts->setVoltageDeltaText(error ? "-" : text);
+ d_cursorReadoutsText.tDelta = error ? "-" : text;
+
+ Q_EMIT cursorReadoutsChanged(d_cursorReadoutsText);
+}
+
+void FftDisplayPlot::onHCursor2Moved(double value)
+{
+ QString text;
+ bool error = false;
+ if (d_trackMode) {
+ if (value == ERROR_VALUE) {
+ error = true;
+ }
+ }
+
+ value *= d_displayScale;
+ text = d_formatter->format(value, "dB", 3);
+ d_cursorReadouts->setVoltageCursor2Text(error ? "-" : text);
+ d_cursorReadoutsText.t2 = error ? "-" : text;
+
+ double valueCursor1;
+ if (d_trackMode) {
+ valueCursor1 = getHorizontalCursorIntersection(d_vBar1->plotCoord().x());
+ } else {
+ valueCursor1 = d_hBar1->plotCoord().y();
+ }
+
+ double diff = (valueCursor1 * d_displayScale) - value;
+ text = d_formatter->format(diff, "dB", 3);
+ d_cursorReadouts->setVoltageDeltaText(error ? "-" : text);
+ d_cursorReadoutsText.tDelta = error ? "-" : text;
+
+ Q_EMIT cursorReadoutsChanged(d_cursorReadoutsText);
+}
+
+void FftDisplayPlot::onVCursor1Moved(double value)
+{
+ QString text;
+ text = d_formatter->format(value, "Hz", 3);
+ d_cursorReadouts->setTimeCursor1Text(text);
+ d_cursorReadoutsText.v1 = text;
+
+ double diff = value - d_vBar2->plotCoord().x();
+ text = d_formatter->format(diff, "Hz", 3);
+ d_cursorReadouts->setTimeDeltaText(text);
+ d_cursorReadoutsText.vDelta = text;
+
+ if (d_trackMode) {
+ onHCursor1Moved(getHorizontalCursorIntersection(d_vBar1->plotCoord().x()));
+ }
+
+ Q_EMIT cursorReadoutsChanged(d_cursorReadoutsText);
+}
+
+void FftDisplayPlot::onVCursor2Moved(double value)
+{
+ QString text;
+ text = d_formatter->format(value, "Hz", 3);
+ d_cursorReadouts->setTimeCursor2Text(text);
+ d_cursorReadoutsText.v2 = text;
+
+ double diff = d_vBar1->plotCoord().x() - value;
+ text = d_formatter->format(diff, "Hz", 3);
+ d_cursorReadouts->setTimeDeltaText(text);
+ d_cursorReadoutsText.vDelta = text;
+
+ if (d_trackMode) {
+ onHCursor2Moved(getHorizontalCursorIntersection(d_vBar2->plotCoord().x()));
+ }
+
+ Q_EMIT cursorReadoutsChanged(d_cursorReadoutsText);
+}
+
+void FftDisplayPlot::enableXaxisLabels()
+{
+ d_bottomHandlesArea->installExtension(std::unique_ptr(new XBottomRuller(this)));
+}
+
+void FftDisplayPlot::enableYaxisLabels()
+{
+ d_leftHandlesArea->installExtension(std::unique_ptr(new YLeftRuller(this)));
+}
+
+bool FftDisplayPlot::eventFilter(QObject *object, QEvent *event)
+{
+ if (object == canvas() && event->type() == QEvent::Resize) {
+ updateHandleAreaPadding();
+
+ //force cursor handles to emit position changed
+ //when the plot canvas is being resized
+ d_hCursorHandle1->triggerMove();
+ d_hCursorHandle2->triggerMove();
+ d_vCursorHandle1->triggerMove();
+ d_vCursorHandle2->triggerMove();
+
+ }
+ return QObject::eventFilter(object, event);
+}
+
+void FftDisplayPlot::showEvent(QShowEvent *event)
+{
+ d_vCursorHandle1->triggerMove();
+ d_vCursorHandle2->triggerMove();
+ d_hCursorHandle1->triggerMove();
+ d_hCursorHandle2->triggerMove();
+}
+
+void FftDisplayPlot::setSelectedChannel(int id)
+{
+ if (d_selected_channel != id) {
+ d_selected_channel = id;
+ }
+}
+
void FftDisplayPlot::setZoomerEnabled()
{
+ enableAxis(QwtPlot::xBottom, true);
+ enableAxis(QwtPlot::yLeft, true);
if(!d_zoomer[0]) {
d_zoomer[0] = new FftDisplayZoomer(canvas());
@@ -323,37 +541,47 @@ void FftDisplayPlot::setWindowCoefficientSum(unsigned int ch, float sum, float s
void FftDisplayPlot::useLogScaleY(bool log_scale)
{
if (log_scale) {
+ setPlotYLogaritmic(true);
QwtLogScaleEngine *scaleEngine = new QwtLogScaleEngine();
setAxisScaleEngine(QwtPlot::yLeft, (QwtScaleEngine *)scaleEngine);
- OscScaleDraw *yScaleDraw = new OscScaleDraw(&dBFormatter, "V/√Hz");
- yScaleDraw->enableComponent(QwtAbstractScaleDraw::Ticks, true);
- yScaleDraw->setFloatPrecision(2);
- setAxisScaleDraw(QwtPlot::yLeft, yScaleDraw);
+// OscScaleDraw *yScaleDraw = new OscScaleDraw(&dBFormatter, "V/√Hz");
+// yScaleDraw->enableComponent(QwtAbstractScaleDraw::Ticks, true);
+// yScaleDraw->setFloatPrecision(2);
+// setAxisScaleDraw(QwtPlot::yLeft, yScaleDraw);
+ replot();
+ auto div = axisScaleDiv(QwtPlot::yLeft);
+ setYaxisMajorTicksPos(div.ticks(2));
} else {
+ setPlotYLogaritmic(false);
OscScaleEngine *scaleEngine = new OscScaleEngine();
this->setAxisScaleEngine(QwtPlot::yLeft, (QwtScaleEngine *)scaleEngine);
- OscScaleDraw *yScaleDraw = new OscScaleDraw(&dBFormatter, "");
- yScaleDraw->setFloatPrecision(2);
- setAxisScaleDraw(QwtPlot::yLeft, yScaleDraw);
+// OscScaleDraw *yScaleDraw = new OscScaleDraw(&dBFormatter, "");
+// yScaleDraw->setFloatPrecision(2);
+// setAxisScaleDraw(QwtPlot::yLeft, yScaleDraw);
+ replot();
+ auto div = axisScaleDiv(QwtPlot::yLeft);
+ setYaxisNumDiv((div.ticks(2)).size());
}
+
replot();
}
void FftDisplayPlot::useLogFreq(bool use_log_freq)
{
if (use_log_freq) {
+ setPlotLogaritmic(true);
setAxisScaleEngine(QwtPlot::xBottom, new QwtLogScaleEngine);
- OscScaleDraw *xScaleDraw = new OscScaleDraw(&freqFormatter, "Hz");
- setAxisScaleDraw(QwtPlot::xBottom, xScaleDraw);
- xScaleDraw->setFloatPrecision(2);
+ replot();
+ auto div = axisScaleDiv(QwtPlot::xBottom);
+ setXaxisMajorTicksPos(div.ticks(2));
} else {
+ setPlotLogaritmic(false);
OscScaleEngine *scaleEngine = new OscScaleEngine();
this->setAxisScaleEngine(QwtPlot::xBottom, (QwtScaleEngine *)scaleEngine);
- OscScaleDraw *xScaleDraw = new OscScaleDraw(&freqFormatter, "Hz");
- setAxisScaleDraw(QwtPlot::xBottom, xScaleDraw);
- xScaleDraw->setFloatPrecision(2);
+ replot();
+ auto div = axisScaleDiv(QwtPlot::xBottom);
+ setXaxisNumDiv((div.ticks(2)).size() - 1);
}
-
d_logScaleEnabled = use_log_freq;
replot();
}
@@ -1257,6 +1485,9 @@ void FftDisplayPlot::setStartStop(double start, double stop)
{
m_sweepStart = start;
m_sweepStop = stop;
+ auto div = axisScaleDiv(QwtPlot::xBottom);
+ setXaxisNumDiv((div.ticks(2)).size() - 1);
+ setXaxisMajorTicksPos(div.ticks(2));
}
void FftDisplayPlot::setVisiblePeakSearch(bool enabled)
diff --git a/src/FftDisplayPlot.h b/src/FftDisplayPlot.h
index 8a1326a906..ce22535760 100644
--- a/src/FftDisplayPlot.h
+++ b/src/FftDisplayPlot.h
@@ -23,6 +23,10 @@
#include "DisplayPlot.h"
#include "spectrum_marker.hpp"
+#include "symbol_controller.h"
+#include "plot_line_handle.h"
+#include "handles_area.hpp"
+#include "cursor_readouts.h"
#include
namespace adiscope {
@@ -50,6 +54,7 @@ namespace adiscope {
class FftDisplayPlot : public DisplayPlot
{
+ friend class SpectrumAnalyzer_API;
Q_OBJECT
public:
@@ -82,6 +87,7 @@ namespace adiscope {
};
typedef boost::shared_ptr average_sptr;
+
private:
QList> d_markers;
double* x_data;
@@ -104,6 +110,7 @@ namespace adiscope {
MetricPrefixFormatter dBFormatter;
MetricPrefixFormatter freqFormatter;
+ PrefixFormatter *d_formatter;
std::vector d_ch_average_type;
std::vector d_ch_avg_obj;
@@ -132,6 +139,8 @@ namespace adiscope {
unsigned int d_nb_overlapping_avg;
std::vector> d_ps_avg;
+ void setupReadouts();
+ void updateHandleAreaPadding();
void plotData(const std::vector &pts,
uint64_t num_points);
@@ -162,6 +171,10 @@ namespace adiscope {
void onMrkCtrlMarkerPosChanged(std::shared_ptr &);
void onMrkCtrlMarkerReleased(std::shared_ptr &);
+ void onHCursor1Moved(double);
+ void onHCursor2Moved(double);
+ void onVCursor1Moved(double);
+ void onVCursor2Moved(double);
public:
explicit FftDisplayPlot(int nplots, QWidget *parent = nullptr);
~FftDisplayPlot();
@@ -228,6 +241,13 @@ namespace adiscope {
void setWindowCoefficientSum(unsigned int ch, float sum, float sqr_sum);
void setNbOverlappingAverages(unsigned int nb_avg);
void useLogScaleY(bool log_scale);
+
+ bool eventFilter(QObject *, QEvent *);
+ void enableXaxisLabels();
+ void enableYaxisLabels();
+ QString formatXValue(double value, int precision) const;
+ QString formatYValue(double value, int precision) const;
+
Q_SIGNALS:
void newData();
void sampleRateUpdated(double);
@@ -242,7 +262,9 @@ namespace adiscope {
void presetSampleRate(double sr);
void useLogFreq(bool use_log_freq);
void customEvent(QEvent *e);
+ void showEvent(QShowEvent *event);
bool getLogScale() const;
+ void setSelectedChannel(int id);
};
}
diff --git a/src/HistogramDisplayPlot.cc b/src/HistogramDisplayPlot.cc
index eac659c061..4b5024f5aa 100644
--- a/src/HistogramDisplayPlot.cc
+++ b/src/HistogramDisplayPlot.cc
@@ -332,7 +332,7 @@ HistogramDisplayPlot::HistogramDisplayPlot(int nplots, QWidget* parent)
insertLegend(nullptr);
d_grid->detach();
- for(QwtPlotScaleItem* scale : scaleItems){
+ for(QwtPlotScaleItem* scale : qAsConst(scaleItems)){
scale->detach();
}
}
@@ -353,12 +353,12 @@ void HistogramDisplayPlot::setOrientation(Qt::Orientation orientation)
if (orientation == Qt::Vertical) {
d_grid->attach(this);
- for(QwtPlotScaleItem* scale : scaleItems){
+ for(QwtPlotScaleItem* scale : qAsConst(scaleItems)){
scale->attach(this);
}
} else {
d_grid->detach();
- for(QwtPlotScaleItem* scale : scaleItems){
+ for(QwtPlotScaleItem* scale : qAsConst(scaleItems)){
scale->detach();
}
}
diff --git a/src/TimeDomainDisplayPlot.cc b/src/TimeDomainDisplayPlot.cc
index f2212fb63d..0f030cdfe8 100644
--- a/src/TimeDomainDisplayPlot.cc
+++ b/src/TimeDomainDisplayPlot.cc
@@ -171,8 +171,8 @@ int SinkManager::sinkFirstChannelPos(const std::string& name)
/***********************************************************************
* Main Time domain plotter widget
**********************************************************************/
-TimeDomainDisplayPlot::TimeDomainDisplayPlot(QWidget* parent, unsigned int xNumDivs, unsigned int yNumDivs)
- : DisplayPlot(0, parent, xNumDivs, yNumDivs)
+TimeDomainDisplayPlot::TimeDomainDisplayPlot(QWidget* parent, bool isdBgraph, unsigned int xNumDivs, unsigned int yNumDivs)
+ : DisplayPlot(0, parent, isdBgraph, xNumDivs, yNumDivs)
{
d_tag_text_color = Qt::black;
d_tag_background_color = Qt::white;
diff --git a/src/TimeDomainDisplayPlot.h b/src/TimeDomainDisplayPlot.h
index d8549efbaf..02eb47c228 100644
--- a/src/TimeDomainDisplayPlot.h
+++ b/src/TimeDomainDisplayPlot.h
@@ -100,7 +100,7 @@ class TimeDomainDisplayPlot: public DisplayPlot
Q_PROPERTY ( Qt::BrushStyle tag_background_style READ getTagBackgroundStyle WRITE setTagBackgroundStyle )
public:
- TimeDomainDisplayPlot(QWidget*, unsigned int xNumDivs = 10, unsigned int yNumDivs = 10);
+ TimeDomainDisplayPlot(QWidget*, bool isdBgraph = false, unsigned int xNumDivs = 10, unsigned int yNumDivs = 10);
virtual ~TimeDomainDisplayPlot();
void plotNewData(const std::string &sender,
diff --git a/src/connectDialog.cpp b/src/connectDialog.cpp
index 973ba45d71..bf811760cb 100644
--- a/src/connectDialog.cpp
+++ b/src/connectDialog.cpp
@@ -71,7 +71,7 @@ QString ConnectDialog::URIstringParser(QString uri)
};
bool prependIP = true;
- for( auto pre:prefixes)
+ for( const auto &pre:prefixes)
{
if(uri.startsWith(pre) == true)
prependIP = false;
diff --git a/src/cursor_readouts.cpp b/src/cursor_readouts.cpp
index 2a18d65ba9..e9945679b7 100644
--- a/src/cursor_readouts.cpp
+++ b/src/cursor_readouts.cpp
@@ -36,6 +36,7 @@ CursorReadouts::CursorReadouts(QwtPlot *plot):
ui(new Ui::CursorReadouts),
d_voltage_rd_visible(true),
d_time_rd_visible(true),
+ freq_delta_visible(true),
d_topLeft(QPoint(0, 0)),
currentPosition(CustomPlotPositionButton::topLeft),
hAxis(QwtPlot::xBottom),
@@ -247,6 +248,7 @@ void CursorReadouts::setTimeDeltaVisible(bool visible){
void CursorReadouts::setFrequencyDeltaVisible(bool visible){
ui->frequencyDeltaLabel->setVisible(visible);
ui->frequencyDelta->setVisible(visible);
+ freq_delta_visible = visible;
}
void CursorReadouts::setTimeCursor1LabelText(const QString &text){
@@ -265,6 +267,10 @@ QString CursorReadouts::timeCursor2LabelText(){
return ui->cursorT2label->text();
}
+void CursorReadouts::setTimeDeltaLabelText(const QString &text){
+ ui->timeDeltaLabel->setText(text);
+}
+
void CursorReadouts::setVoltageCursor1LabelText(const QString &text){
ui->cursorV1label->setText(text);
}
@@ -391,11 +397,11 @@ void CursorReadouts::moveTopRight(bool resize)
QRect timeRect, voltageRect;
if (d_time_rd_visible && !d_voltage_rd_visible) {
- voltageRect = QRect(0,0,0,0);
- timeRect = QRect(d_topLeft.x() - ui->TimeCursors->width(),d_topLeft.y(),d_topLeft.x(),d_topLeft.y()+ui->TimeCursors->height());
+ voltageRect = QRect(0,0,0,0);
+ timeRect = QRect(d_topLeft.x() - ui->TimeCursors->width(),d_topLeft.y(),d_topLeft.x(),d_topLeft.y()+ui->TimeCursors->height());
} else {
- voltageRect = QRect(d_topLeft.x() - ui->VoltageCursors->width(),d_topLeft.y(),d_topLeft.x(),d_topLeft.y()+ui->VoltageCursors->height());
- timeRect = QRect(voltageRect.x()-ui->TimeCursors->width(),d_topLeft.y(),voltageRect.x(),d_topLeft.y()+ui->VoltageCursors->height());
+ voltageRect = QRect(d_topLeft.x() - ui->VoltageCursors->width(),d_topLeft.y(),d_topLeft.x(),d_topLeft.y()+ui->VoltageCursors->height());
+ timeRect = QRect(voltageRect.x()-ui->TimeCursors->width(),d_topLeft.y(),voltageRect.x(),d_topLeft.y()+ui->VoltageCursors->height());
}
@@ -426,16 +432,26 @@ void CursorReadouts::moveBottomLeft(bool resize)
QRect timeRect, voltageRect;
- d_topLeft.setY(plot()->height()-8);
- d_topLeft.setX(8);
+ int value = plot()->canvas()->height()-8;
+ d_topLeft.setY(value);
+ d_topLeft.setX(8);
+
+ if(freq_delta_visible)
+ {
+ if (!d_time_rd_visible && d_voltage_rd_visible) {
+ voltageRect = QRect(QPoint(d_topLeft.x(),d_topLeft.y()-ui->VoltageCursors->height()-20), QPoint(d_topLeft.x()+ui->VoltageCursors->width(),d_topLeft.y()));
+ timeRect = QRect(0,0,0,0);
+ } else {
+ timeRect = QRect(QPoint(d_topLeft.x(),d_topLeft.y()-ui->TimeCursors->height()-20), QPoint(ui->TimeCursors->width()+d_topLeft.x(),d_topLeft.y()));
+ voltageRect = QRect(QPoint(d_topLeft.x()+timeRect.width(),d_topLeft.y()-ui->VoltageCursors->height()-20), QPoint(d_topLeft.x()+timeRect.width()+ui->VoltageCursors->width(),d_topLeft.y()));
+ }
+ }
+ else
+ {
+ timeRect = QRect(QPoint(d_topLeft.x(),d_topLeft.y()-ui->TimeCursors->height()+5), QPoint(ui->TimeCursors->width()+d_topLeft.x(),d_topLeft.y()));
+ voltageRect = QRect(QPoint(d_topLeft.x()+timeRect.width(),d_topLeft.y()-ui->VoltageCursors->height()+5), QPoint(d_topLeft.x()+timeRect.width()+ui->VoltageCursors->width(),d_topLeft.y()));
+ }
- if (!d_time_rd_visible && d_voltage_rd_visible) {
- voltageRect = QRect(QPoint(d_topLeft.x(),d_topLeft.y()-ui->VoltageCursors->height()-20), QPoint(d_topLeft.x()+ui->VoltageCursors->width(),d_topLeft.y()));
- timeRect = QRect(0,0,0,0);
- } else {
- timeRect = QRect(QPoint(d_topLeft.x(),d_topLeft.y()-ui->TimeCursors->height()-20), QPoint(ui->TimeCursors->width()+d_topLeft.x(),d_topLeft.y()));
- voltageRect = QRect(QPoint(d_topLeft.x()+timeRect.width(),d_topLeft.y()-ui->VoltageCursors->height()-20), QPoint(d_topLeft.x()+timeRect.width()+ui->VoltageCursors->width(),d_topLeft.y()));
- }
int diff = voltageRect.x() - lastVoltageRect.x();
if (diff < 10 && diff > -10) diff = voltageRect.y() - lastVoltageRect.y();
@@ -464,17 +480,24 @@ void CursorReadouts::moveBottomRight(bool resize)
QRect timeRect, voltageRect;
- d_topLeft.setY(plot()->height()-8);
- d_topLeft.setX(plot()->canvas()->width()-8);
-
- if (d_time_rd_visible && !d_voltage_rd_visible) {
- voltageRect = QRect(0,0,0,0);
- timeRect = QRect(d_topLeft.x() - ui->TimeCursors->width(),d_topLeft.y()-ui->TimeCursors->height()-20,d_topLeft.x(),d_topLeft.y());
- } else {
- voltageRect = QRect(d_topLeft.x() - ui->VoltageCursors->width(),d_topLeft.y()-ui->VoltageCursors->height()-20,d_topLeft.x(),d_topLeft.y());
- timeRect = QRect(voltageRect.x()-ui->TimeCursors->width(),voltageRect.y(),voltageRect.x(),voltageRect.y()+ui->TimeCursors->height());
-
- }
+ d_topLeft.setY(plot()->canvas()->height()-8);
+ d_topLeft.setX(plot()->canvas()->width()-8);
+
+ if(freq_delta_visible)
+ {
+ if (d_time_rd_visible && !d_voltage_rd_visible) {
+ voltageRect = QRect(0,0,0,0);
+ timeRect = QRect(d_topLeft.x() - ui->TimeCursors->width(),d_topLeft.y()-ui->TimeCursors->height()-20,d_topLeft.x(),d_topLeft.y());
+ } else {
+ voltageRect = QRect(d_topLeft.x() - ui->VoltageCursors->width(),d_topLeft.y()-ui->VoltageCursors->height()-20,d_topLeft.x(),d_topLeft.y());
+ timeRect = QRect(voltageRect.x()-ui->TimeCursors->width(),voltageRect.y(),voltageRect.x(),voltageRect.y()+ui->TimeCursors->height());
+ }
+ }
+ else
+ {
+ voltageRect = QRect(d_topLeft.x() - ui->VoltageCursors->width(),d_topLeft.y()-ui->VoltageCursors->height()+5,d_topLeft.x(),d_topLeft.y());
+ timeRect = QRect(voltageRect.x()-ui->TimeCursors->width(),voltageRect.y(),voltageRect.x(),voltageRect.y()+ui->TimeCursors->height()+5);
+ }
int diff = timeRect.x() - lastTimeRect.x();
if (diff < 10 && diff > -10) diff = timeRect.y() - lastTimeRect.y();
diff --git a/src/cursor_readouts.h b/src/cursor_readouts.h
index 21d76b77b2..c462a2ca52 100644
--- a/src/cursor_readouts.h
+++ b/src/cursor_readouts.h
@@ -66,19 +66,20 @@ namespace adiscope {
QString voltageCursor2Text();
void setVoltageDeltaText(const QString &);
QString voltageDeltaText();
- void setTimeDeltaVisible(bool);
- void setFrequencyDeltaVisible(bool);
- void setTimeCursor1LabelText(const QString &);
- QString timeCursor1LabelText();
- void setTimeCursor2LabelText(const QString &);
- QString timeCursor2LabelText();
- void setVoltageCursor1LabelText(const QString &);
- QString voltageCursor1LabelText();
- void setVoltageCursor2LabelText(const QString &);
- QString voltageCursor2LabelText();
- void setDeltaVoltageLabelText(const QString &);
- QString deltaVoltageLabelText();
- void setAxis(QwtAxisId hAxis,QwtAxisId vAxis);
+ void setTimeDeltaVisible(bool);
+ void setFrequencyDeltaVisible(bool);
+ void setTimeCursor1LabelText(const QString &);
+ QString timeCursor1LabelText();
+ void setTimeCursor2LabelText(const QString &);
+ QString timeCursor2LabelText();
+ void setTimeDeltaLabelText(const QString &text);
+ void setVoltageCursor1LabelText(const QString &);
+ QString voltageCursor1LabelText();
+ void setVoltageCursor2LabelText(const QString &);
+ QString voltageCursor2LabelText();
+ void setDeltaVoltageLabelText(const QString &);
+ QString deltaVoltageLabelText();
+ void setAxis(QwtAxisId hAxis,QwtAxisId vAxis);
virtual bool eventFilter(QObject *, QEvent *);
void setTransparency(int value);
@@ -94,6 +95,7 @@ namespace adiscope {
Ui::CursorReadouts *ui;
bool d_voltage_rd_visible;
bool d_time_rd_visible;
+ bool freq_delta_visible;
QPoint d_topLeft;
void moveTopLeft(bool resize = false);
void moveTopRight(bool resize = false);
@@ -102,7 +104,7 @@ namespace adiscope {
CustomPlotPositionButton::ReadoutsPosition currentPosition;
CustomAnimation *anim, *anim2;
QRect lastTimeRect, lastVoltageRect;
- QwtAxisId hAxis,vAxis;
+ QwtAxisId hAxis,vAxis;
};
}
diff --git a/src/db_click_buttons.cpp b/src/db_click_buttons.cpp
index cedbfbe610..1064723ba7 100644
--- a/src/db_click_buttons.cpp
+++ b/src/db_click_buttons.cpp
@@ -47,7 +47,7 @@ DbClickButtons::DbClickButtons(QWidget *parent, int maxRowBtnCount) :
btn_list = findChildren();
int n = 0;
- for (const auto& i : btn_list) {
+ for (const auto& i : qAsConst(btn_list)) {
btn_states.push_back(false);
i->setProperty("id", QVariant(n++));
connect(i, SIGNAL(clicked()),
diff --git a/src/dbgraph.cpp b/src/dbgraph.cpp
index 0a9f6d06d6..fed6611956 100644
--- a/src/dbgraph.cpp
+++ b/src/dbgraph.cpp
@@ -29,27 +29,16 @@
using namespace adiscope;
-void dBgraph::setupCursors()
+void dBgraph::setupVerticalBars()
{
- d_symbolCtrl = new SymbolController(this);
-
- d_vBar1 = new VertBar(this,true);
- d_vBar2 = new VertBar(this,true);
d_plotBar = new VertBar(this, true);
d_frequencyBar = new VertBar(this, true);
- d_symbolCtrl->attachSymbol(d_vBar1);
- d_symbolCtrl->attachSymbol(d_vBar2);
d_symbolCtrl->attachSymbol(d_plotBar);
d_symbolCtrl->attachSymbol(d_frequencyBar);
- QPen cursorsLinePen = QPen(QColor(155,155,155),1,Qt::DashLine);
QPen plotLinePen = QPen(QColor(211, 211, 211, 50), 5, Qt::SolidLine);
QPen frequencyLinePen = QPen(QColor(74, 100, 255, 150), 2, Qt::DashLine);
- d_vBar1->setPen(cursorsLinePen);
- d_vBar2->setPen(cursorsLinePen);
- d_vBar1->setVisible(false);
- d_vBar2->setVisible(false);
d_plotBar->setVisible(false);
d_frequencyBar->setPen(frequencyLinePen);
@@ -60,55 +49,33 @@ void dBgraph::setupCursors()
d_plotBar->setPen(plotLinePen);
d_plotBar->setMobileAxis(QwtPlot::xTop);
- connect(d_vBar1, SIGNAL(pixelPositionChanged(int)),
- SLOT(onVbar1PixelPosChanged(int)));
- connect(d_vBar1, SIGNAL(pixelPositionChanged(int)),
- SLOT(onCursor1Moved(int)));
-
- connect(d_vBar2, SIGNAL(pixelPositionChanged(int)),
- SLOT(onVbar2PixelPosChanged(int)));
- connect(d_vBar2, SIGNAL(pixelPositionChanged(int)),
- SLOT(onCursor2Moved(int)));
-
connect(d_frequencyBar, &VertBar::pixelPositionChanged,
this, &dBgraph::frequencyBarPositionChanged);
-}
-void dBgraph::parametersOverrange(bool enable)
-{
- if (enable) {
- d_plotBar->setPen(QPen(QColor(250, 0, 0, 50), 5, Qt::SolidLine));
- } else {
- d_plotBar->setPen(QPen(QColor(211, 211, 211, 50), 5, Qt::SolidLine));
- }
+ d_vBar1->setMobileAxis(QwtPlot::xTop);
+ d_vBar2->setMobileAxis(QwtPlot::xTop);
}
void dBgraph::setupReadouts()
{
- d_cursorReadouts = new CursorReadouts(this);
- d_cursorReadouts->setAxis(QwtPlot::xTop,QwtPlot::yLeft);
- d_cursorReadouts->setTopLeftStartingPoint(QPoint(8, 8));
- d_cursorReadouts->moveToPosition(CustomPlotPositionButton::topLeft);
-
d_cursorReadouts->setTimeReadoutVisible(false);
d_cursorReadouts->setVoltageReadoutVisible(false);
- d_cursorReadouts->setTimeCursor1LabelText("F1= ");
- d_cursorReadouts->setTimeCursor2LabelText("F2= ");
- d_cursorReadouts->setVoltageCursor1LabelText("Mag1= ");
- d_cursorReadouts->setVoltageCursor2LabelText("Mag2= ");
- d_cursorReadouts->setDeltaVoltageLabelText("ΔMag= ");
+ d_cursorReadouts->setTimeCursor1LabelText("F1 = ");
+ d_cursorReadouts->setTimeCursor2LabelText("F2 = ");
+ d_cursorReadouts->setVoltageCursor1LabelText("Mag1 = ");
+ d_cursorReadouts->setVoltageCursor2LabelText("Mag2 = ");
+ d_cursorReadouts->setDeltaVoltageLabelText("ΔMag = ");
d_cursorReadouts->setFrequencyDeltaVisible(false);
d_cursorReadouts->setTimeDeltaVisible(false);
d_cursorReadouts->setTransparency(0);
}
-dBgraph::dBgraph(QWidget *parent) : QwtPlot(parent),
+dBgraph::dBgraph(QWidget *parent, bool isdBgraph)
+ : DisplayPlot(0, parent, isdBgraph),
curve("data"),
reference("reference"),
- d_cursorsCentered(false),
- d_cursorsEnabled(false),
xmin(10),
xmax(10),
ymin(10),
@@ -133,6 +100,7 @@ dBgraph::dBgraph(QWidget *parent) : QwtPlot(parent),
EdgelessPlotGrid *grid = new EdgelessPlotGrid;
grid->setMajorPen(plotColor, 1.0, Qt::DashLine);
+
grid->setXAxis(QwtPlot::xTop);
grid->attach(this);
@@ -150,14 +118,16 @@ dBgraph::dBgraph(QWidget *parent) : QwtPlot(parent),
thickness = 1;
+ d_formatter = static_cast(new MetricPrefixFormatter);
+
OscScaleEngine *scaleLeft = new OscScaleEngine;
+ setYaxisNumDiv(7);
scaleLeft->setMajorTicksCount(7);
this->setAxisScaleEngine(QwtPlot::yLeft,
static_cast(scaleLeft));
-
/* draw_x / draw_y: Outmost X / Y scales. Only draw the labels */
- formatter = static_cast(new MetricPrefixFormatter);
- draw_x = new OscScaleDraw(formatter, "Hz");
+
+ draw_x = new OscScaleDraw(d_formatter, "Hz");
draw_x->setFloatPrecision(2);
draw_x->enableComponent(QwtAbstractScaleDraw::Ticks, false);
draw_x->enableComponent(QwtAbstractScaleDraw::Backbone, false);
@@ -170,15 +140,27 @@ dBgraph::dBgraph(QWidget *parent) : QwtPlot(parent),
draw_y->setMinimumExtent(50);
setAxisScaleDraw(QwtPlot::yLeft, draw_y);
+ d_leftHandlesArea->setMinimumWidth(60);
+ d_leftHandlesArea->setTopPadding(10);
+ d_leftHandlesArea->setBottomPadding(0);
+ d_leftHandlesArea->setMinimumHeight(this->minimumHeight());
+
+ d_rightHandlesArea->setMinimumWidth(40);
+ d_rightHandlesArea->setMinimumHeight(this->minimumHeight());
+
+
+ d_topHandlesArea->setMinimumHeight(20);
+ d_topHandlesArea->setLargestChildWidth(60);
+
useLogFreq(false);
/* Create 4 scales within the plot itself. Only draw the ticks */
for (unsigned int i = 0; i < 4; i++) {
EdgelessPlotScaleItem *scaleItem = new EdgelessPlotScaleItem(
- static_cast(i));
+ static_cast(i));
/* Top/bottom scales must be sync'd to xTop; left/right scales
- * must be sync'd to yLeft */
+ * must be sync'd to yLeft */
if (i < 2) {
scaleItem->setXAxis(QwtPlot::xTop);
} else {
@@ -186,13 +168,13 @@ dBgraph::dBgraph(QWidget *parent) : QwtPlot(parent),
}
scaleItem->scaleDraw()->enableComponent(
- QwtAbstractScaleDraw::Backbone, false);
+ QwtAbstractScaleDraw::Backbone, false);
scaleItem->scaleDraw()->enableComponent(
- QwtAbstractScaleDraw::Labels, false);
+ QwtAbstractScaleDraw::Labels, false);
QPalette palette = scaleItem->palette();
- palette.setBrush(QPalette::Foreground, plotColor);
- palette.setBrush(QPalette::Text, plotColor);
+ palette.setBrush(QPalette::Foreground, QColor(plotColor));
+ palette.setBrush(QPalette::Text, QColor(plotColor));
scaleItem->setPalette(palette);
scaleItem->setBorderDistance(0);
scaleItem->attach(this);
@@ -204,49 +186,65 @@ dBgraph::dBgraph(QWidget *parent) : QwtPlot(parent),
zoomer->setMousePattern(QwtEventPattern::MouseSelect2,
Qt::RightButton, Qt::ControlModifier);
+ installEventFilter(this);
+
static_cast(canvas())->setLineWidth(0);
setContentsMargins(10, 10, 24, 20);
-
- picker = new PlotPickerWrapper(QwtPlot::xTop,QwtPlot::yLeft,this->canvas());
-
QMargins margins = contentsMargins();
margins.setBottom(0);
setContentsMargins(margins);
+ enableAxis(QwtPlot::yLeft, false);
+ enableAxis(QwtPlot::xTop, false);
+
QwtScaleWidget *scaleWidget = axisWidget(QwtPlot::xTop);
- const int fmw = QFontMetrics(scaleWidget->font()).width("XXXX.XX XX");
+ const int fmw = QFontMetrics(scaleWidget->font()).width("-XXXX.XX XX");
scaleWidget->setMinBorderDist(fmw / 2, fmw / 2);
- markerIntersection1 = new QwtPlotMarker();
- markerIntersection2 = new QwtPlotMarker();
- markerIntersection1->setSymbol(new QwtSymbol(
- QwtSymbol::Ellipse, QColor(237, 28, 36),
- QPen(QColor(255, 255,255, 140), 2, Qt::SolidLine),
- QSize(5, 5)));
- markerIntersection2->setSymbol(new QwtSymbol(
- QwtSymbol::Ellipse, QColor(237, 28, 36),
- QPen(QColor(255, 255,255, 140), 2, Qt::SolidLine),
- QSize(5, 5)));
+ setupVerticalBars();
+ setupReadouts();
markerIntersection1->setAxes(QwtPlot::xTop, QwtPlot::yLeft);
markerIntersection2->setAxes(QwtPlot::xTop, QwtPlot::yLeft);
-
- setupCursors();
-
- setupReadouts();
-
}
dBgraph::~dBgraph()
{
- markerIntersection1->detach();
- markerIntersection2->detach();
canvas()->removeEventFilter(d_cursorReadouts);
canvas()->removeEventFilter(d_symbolCtrl);
- delete markerIntersection1;
- delete markerIntersection2;
- delete formatter;
- delete picker;
+ delete d_formatter;
+}
+
+void dBgraph::replot()
+{
+ if (!d_leftHandlesArea || !d_topHandlesArea) {
+ return;
+ }
+
+ d_leftHandlesArea->repaint();
+ d_topHandlesArea->repaint();
+
+ QwtPlot::replot();
+}
+
+void dBgraph::enableXaxisLabels()
+{
+ d_topHandlesArea->installExtension(std::unique_ptr(new XTopRuller(this)));
+}
+
+
+void dBgraph::enableYaxisLabels()
+{
+ d_leftHandlesArea->installExtension(std::unique_ptr(new YLeftRuller(this)));
+}
+
+void dBgraph::parametersOverrange(bool enable)
+{
+ if (enable) {
+ d_plotBar->setPen(QPen(QColor(250, 0, 0, 50), 5, Qt::SolidLine));
+ } else {
+ d_plotBar->setPen(QPen(QColor(211, 211, 211, 50), 5, Qt::SolidLine));
+ }
}
void dBgraph::setAxesScales(double xmin, double xmax, double ymin, double ymax)
@@ -298,13 +296,25 @@ void dBgraph::plot(double x, double y)
curve.setRawSamples(xdata.data(), ydata.data(), xdata.size());
if (d_cursorsEnabled) {
- onCursor1Moved(d_vBar1->transform(d_vBar1->plotCoord()).x());
- onCursor2Moved(d_vBar2->transform(d_vBar2->plotCoord()).x());
+ onVCursor1Moved(d_vBar1->plotCoord().x());
+ onVCursor2Moved(d_vBar2->plotCoord().x());
}
-
replot();
}
+bool dBgraph::eventFilter(QObject *object, QEvent *event)
+{
+ if (object == canvas() && event->type() == QEvent::Resize)
+ {
+
+ d_leftHandlesArea->repaint();
+ d_bottomHandlesArea->setLeftPadding(d_leftHandlesArea->width() + 10);
+ d_bottomHandlesArea->setRightPadding(d_rightHandlesArea->width() + 24);
+
+ }
+ return QObject::eventFilter(object, event);
+}
+
int dBgraph::getNumSamples() const
{
return numSamples;
@@ -313,22 +323,22 @@ int dBgraph::getNumSamples() const
QString dBgraph::getScaleValueFormat(double value, QwtAxisId scale) const
{
auto *scaleDraw = static_cast(
- axisScaleDraw(scale));
+ axisScaleDraw(scale));
- return formatter->format(value,
- scaleDraw->getUnitType(),
- scaleDraw->getFloatPrecison());
+ return d_formatter->format(value,
+ scaleDraw->getUnitType(),
+ scaleDraw->getFloatPrecison());
}
QString dBgraph::getScaleValueFormat(double value, QwtAxisId scale,
int precision) const
{
auto *scaleDraw = static_cast(
- axisScaleDraw(scale));
+ axisScaleDraw(scale));
- return formatter->format(value,
- scaleDraw->getUnitType(),
- precision);
+ return d_formatter->format(value,
+ scaleDraw->getUnitType(),
+ precision);
}
void dBgraph::setShowZero(bool en)
@@ -365,8 +375,6 @@ void dBgraph::reset()
{
xdata.clear();
ydata.clear();
- markerIntersection1->detach();
- markerIntersection2->detach();
d_plotPosition = 0;
}
@@ -422,9 +430,9 @@ void dBgraph::setYTitle(const QString& title)
yTitle.setFont(font);
setAxisTitle(QwtPlot::yLeft, yTitle);
- d_cursorReadouts->setVoltageCursor1LabelText(title.mid(0,3)+"1= ");
- d_cursorReadouts->setVoltageCursor2LabelText(title.mid(0,3)+"2= ");
- d_cursorReadouts->setDeltaVoltageLabelText("Δ"+title.mid(0,3)+"= ");
+ d_cursorReadouts->setVoltageCursor1LabelText(title.mid(0,3)+"1 = ");
+ d_cursorReadouts->setVoltageCursor2LabelText(title.mid(0,3)+"2 = ");
+ d_cursorReadouts->setDeltaVoltageLabelText("Δ"+title.mid(0,3)+" = ");
}
void dBgraph::setXMin(double val)
@@ -436,6 +444,9 @@ void dBgraph::setXMin(double val)
zoomer->setZoomBase();
replot();
+ auto div = axisScaleDiv(QwtPlot::xTop);
+ setXaxisNumDiv((div.ticks(2)).size() - 1);
+ setXaxisMajorTicksPos(div.ticks(2));
}
void dBgraph::setXMax(double val)
@@ -447,6 +458,9 @@ void dBgraph::setXMax(double val)
zoomer->setZoomBase();
replot();
+ auto div = axisScaleDiv(QwtPlot::xTop);
+ setXaxisNumDiv((div.ticks(2)).size() - 1);
+ setXaxisMajorTicksPos(div.ticks(2));
}
void dBgraph::setYMin(double val)
@@ -454,6 +468,8 @@ void dBgraph::setYMin(double val)
setAxisScale(QwtPlot::yLeft, val, ymax);
ymin = val;
replot();
+ d_leftHandlesArea->repaint();
+ d_topHandlesArea->repaint();
double width = xmax - xmin;
double height = ymax - ymin;
@@ -473,16 +489,16 @@ void dBgraph::setYMax(double val)
QString dBgraph::xUnit() const
{
- return draw_x->getUnitType();
+ return draw_x->getUnitType();;
}
QString dBgraph::yUnit() const
{
- return draw_y->getUnitType();
+ return draw_y->getUnitType();;
}
void dBgraph::setXUnit(const QString& unit)
-{
+{
draw_x->setUnitType(unit);
}
@@ -494,18 +510,25 @@ void dBgraph::setYUnit(const QString& unit)
void dBgraph::useLogFreq(bool use_log_freq)
{
if (use_log_freq) {
+ setPlotLogaritmic(true);
this->setAxisScaleEngine(QwtPlot::xTop, new QwtLogScaleEngine);
+ replot();
+ auto div = axisScaleDiv(QwtPlot::xTop);
+ setXaxisNumDiv((div.ticks(2)).size() - 1);
+ setXaxisMajorTicksPos(div.ticks(2));
} else {
+ setPlotLogaritmic(false);
auto scaleTop = new OscScaleEngine;
scaleTop->setMajorTicksCount(9);
+ setXaxisNumDiv(8);
this->setAxisScaleEngine(QwtPlot::xTop, scaleTop);
}
this->log_freq = use_log_freq;
if (d_cursorsEnabled && isVisible()) {
- onCursor1Moved(d_vBar1->transform(d_vBar1->plotCoord()).x());
- onCursor2Moved(d_vBar2->transform(d_vBar2->plotCoord()).x());
+ onVCursor1Moved(d_vBar1->plotCoord().x());
+ onVCursor2Moved(d_vBar2->plotCoord().x());
}
// Use delta only when log scale is disabled and delta
@@ -576,73 +599,23 @@ bool dBgraph::addReferenceWaveformFromPlot()
return true;
}
-void dBgraph::onCursor1PositionChanged(int pos)
-{
- pos = std::min(pos,QwtPlot::canvas()->width()-1);
- d_vBar1->setPixelPosition(pos);
- onCursor1Moved(pos);
-}
-
-void dBgraph::onCursor2PositionChanged(int pos)
+QString dBgraph::formatXValue(double value, int precision) const
{
- pos = std::min(pos,QwtPlot::canvas()->width()-1);
- d_vBar2->setPixelPosition(pos);
- onCursor2Moved(pos);
+ return d_formatter->format(value, "Hz", precision);
}
-void dBgraph::onVbar1PixelPosChanged(int pos)
+QString dBgraph::formatYValue(double value, int precision) const
{
- Q_EMIT VBar1PixelPosChanged(pos);
+ return d_formatter->format(value, draw_y->getUnitType(), precision);
}
-void dBgraph::onVbar2PixelPosChanged(int pos)
-{
- Q_EMIT VBar2PixelPosChanged(pos);
-}
-
-void dBgraph::toggleCursors(bool en)
-{
- d_frequencyBar->setPixelPosition(0);
- if (d_cursorsEnabled != en) {
- if (!d_cursorsCentered) {
- d_cursorsCentered=true;
- d_vBar1->setPixelPosition(canvas()->width()/2-30);
- d_vBar2->setPixelPosition(canvas()->width()/2+30);
- }
-
- d_cursorsEnabled = en;
- d_vBar1->setVisible(en);
- d_vBar2->setVisible(en);
-
- d_cursorReadouts->setTimeReadoutVisible(en);
- d_cursorReadouts->setVoltageReadoutVisible(en);
-
- if (en) {
- onCursor1Moved(d_vBar1->transform(d_vBar1->plotCoord()).x());
- onCursor2Moved(d_vBar2->transform(d_vBar2->plotCoord()).x());
- } else {
- markerIntersection1->detach();
- markerIntersection2->detach();
- replot();
- }
- }
-}
-
-CustomPlotPositionButton::ReadoutsPosition
-dBgraph::getCursorReadoutCurrentPosition()
-{
- return d_cursorReadouts->getCurrentPosition();
-}
-
-void dBgraph::onCursor1Moved(int value)
+void dBgraph::onVCursor1Moved(double value)
{
QString text;
-
- auto point = picker->pointCoordinates(QPoint(value,0));
- text = formatter->format(point.x(),"Hz",2);
+ text = d_formatter->format(value, "Hz", 2);
d_cursorReadouts->setTimeCursor1Text(text);
- text = cursorIntersection(point.x());
+ text = cursorIntersection(value);
d_cursorReadouts->setVoltageCursor1Text(text);
double d1 = d_cursorReadouts->voltageCursor1Text().split(" ")[0].toDouble();
@@ -653,25 +626,22 @@ void dBgraph::onCursor1Moved(int value)
} else {
if (d_cursorsEnabled) {
markerIntersection1->attach(this);
- markerIntersection1->setValue(point.x(), d1);
+ markerIntersection1->setValue(value, d1);
}
}
-
replot();
d_cursorReadouts->setVoltageDeltaText(QString::number(d2-d1)+" "+
draw_y->getUnitType());
}
-void dBgraph::onCursor2Moved(int value)
+void dBgraph::onVCursor2Moved(double value)
{
QString text;
-
- auto point = picker->pointCoordinates(QPoint(value,0));
- text = formatter->format(point.x(),"Hz",2);
+ text = d_formatter->format(value, "Hz", 2);
d_cursorReadouts->setTimeCursor2Text(text);
- text = cursorIntersection(point.x());
+ text = cursorIntersection(value);
d_cursorReadouts->setVoltageCursor2Text(text);
double d1 = d_cursorReadouts->voltageCursor1Text().split(" ")[0].toDouble();
@@ -682,10 +652,9 @@ void dBgraph::onCursor2Moved(int value)
} else {
if (d_cursorsEnabled) {
markerIntersection2->attach(this);
- markerIntersection2->setValue(point.x(), d2);
+ markerIntersection2->setValue(value, d2);
}
}
-
replot();
d_cursorReadouts->setVoltageDeltaText(QString::number(d2-d1)+" "+
@@ -725,23 +694,12 @@ QString dBgraph::cursorIntersection(qreal freq)
rightCustom = ydata.data()[rightIndex];
double val = (rightCustom - leftCustom)/(rightFreq - leftFreq)*
- (freq-leftFreq)+leftCustom;
+ (freq-leftFreq)+leftCustom;
return QString::number(val,'f',2) +" "+ draw_y->getUnitType();
}
}
-void dBgraph::setCursorReadoutsTransparency(int value)
-{
- d_cursorReadouts->setTransparency(value);
-}
-
-void dBgraph::moveCursorReadouts(CustomPlotPositionButton::ReadoutsPosition
- position)
-{
- d_cursorReadouts->moveToPosition(position);
-}
-
QVector dBgraph::getXAxisData()
{
QVector data;
@@ -798,8 +756,8 @@ void dBgraph::scaleDivChanged()
this->setAxisScale(QwtPlot::xTop, intv.minValue(), intv.maxValue());
this->replot();
- onCursor1Moved(d_vBar1->transform(d_vBar1->plotCoord()).x());
- onCursor2Moved(d_vBar2->transform(d_vBar2->plotCoord()).x());
+ onVCursor1Moved(d_vBar1->plotCoord().x());
+ onVCursor2Moved(d_vBar2->plotCoord().x());
}
void dBgraph::mousePressEvent(QMouseEvent *event)
@@ -816,6 +774,8 @@ void dBgraph::onResetZoom()
void dBgraph::showEvent(QShowEvent *event)
{
+ d_hCursorHandle1->updatePosition();
+ d_hCursorHandle2->updatePosition();
auto sw = axisWidget(QwtPlot::xTop);
sw->scaleDraw()->invalidateCache();
sw->repaint();
diff --git a/src/dbgraph.hpp b/src/dbgraph.hpp
index fab94bd78e..42a5a8602c 100644
--- a/src/dbgraph.hpp
+++ b/src/dbgraph.hpp
@@ -29,15 +29,16 @@
#include "symbol_controller.h"
#include "plot_line_handle.h"
#include "cursor_readouts.h"
-#include "plotpickerwrapper.h"
+#include "DisplayPlot.h"
namespace adiscope {
class OscScaleDraw;
class PrefixFormatter;
class OscScaleZoomer;
-class dBgraph : public QwtPlot
+class dBgraph : public DisplayPlot
{
+ friend class NetworkAnalyzer_API;
Q_OBJECT
Q_PROPERTY(int numSamples
@@ -64,7 +65,8 @@ class dBgraph : public QwtPlot
Q_PROPERTY(bool log_freq MEMBER log_freq WRITE useLogFreq);
public:
- explicit dBgraph(QWidget *parent = nullptr);
+ explicit dBgraph(QWidget *parent = nullptr, bool isdBgraph = true);
+
~dBgraph();
void setAxesScales(double xmin, double xmax,
@@ -73,6 +75,8 @@ class dBgraph : public QwtPlot
int getNumSamples() const;
+ bool eventFilter(QObject *, QEvent *);
+
QString getScaleValueFormat(double value, QwtAxisId scale) const;
QString getScaleValueFormat(double value, QwtAxisId scale, int precision) const;
@@ -84,9 +88,6 @@ class dBgraph : public QwtPlot
QString xTitle() const;
QString yTitle() const;
- void toggleCursors(bool);
- CustomPlotPositionButton::ReadoutsPosition getCursorReadoutCurrentPosition();
-
QString cursorIntersection(qreal text);
QVector getXAxisData();
QVector getYAxisData();
@@ -96,9 +97,14 @@ class dBgraph : public QwtPlot
void setPlotBarEnabled(bool enabled);
void parametersOverrange(bool enable);
+
+ void enableXaxisLabels();
+ void enableYaxisLabels();
+ QString formatXValue(double value, int precision) const;
+ QString formatYValue(double value, int precision) const;
+
+ void replot();
Q_SIGNALS:
- void VBar1PixelPosChanged(int);
- void VBar2PixelPosChanged(int);
void resetZoom();
void frequencySelected(double);
@@ -127,18 +133,6 @@ public Q_SLOTS:
void useDeltaLabel(bool use_delta);
void sweepDone();
- void onVbar1PixelPosChanged(int pos);
- void onVbar2PixelPosChanged(int pos);
-
- void onCursor1PositionChanged(int pos);
- void onCursor2PositionChanged(int pos);
-
- void onCursor1Moved(int);
- void onCursor2Moved(int);
-
- void setCursorReadoutsTransparency(int value);
- void moveCursorReadouts(CustomPlotPositionButton::ReadoutsPosition position);
-
void scaleDivChanged();
void mousePressEvent(QMouseEvent *event);
void onResetZoom();
@@ -150,15 +144,15 @@ public Q_SLOTS:
void removeReferenceWaveform();
bool addReferenceWaveformFromPlot();
-
+private Q_SLOTS:
+ void onVCursor1Moved(double);
+ void onVCursor2Moved(double);
protected Q_SLOTS:
void showEvent(QShowEvent *event);
private:
QwtPlotCurve curve;
QwtPlotCurve reference;
- QwtPlotMarker *markerIntersection1;
- QwtPlotMarker *markerIntersection2;
unsigned int numSamples;
double xmin, xmax, ymin, ymax;
QColor color;
@@ -167,25 +161,18 @@ protected Q_SLOTS:
bool delta_label;
bool d_plotBarEnabled;
- bool d_cursorsEnabled;
- bool d_cursorsCentered;
OscScaleDraw *draw_x, *draw_y;
- PrefixFormatter *formatter;
+
OscScaleZoomer *zoomer;
QVector xdata, ydata;
unsigned int d_plotPosition;
- SymbolController *d_symbolCtrl;
- VertBar *d_vBar1;
- VertBar *d_vBar2;
VertBar *d_plotBar;
VertBar *d_frequencyBar;
+ PrefixFormatter *d_formatter;
- PlotPickerWrapper *picker;
-
- CursorReadouts *d_cursorReadouts;
- void setupCursors();
+ void setupVerticalBars();
void setupReadouts();
};
}
diff --git a/src/debugger.cpp b/src/debugger.cpp
index bbd109f529..afc6647149 100644
--- a/src/debugger.cpp
+++ b/src/debugger.cpp
@@ -156,7 +156,7 @@ void Debugger::updateValueWidget(QString attribute)
QVector availableValues = debug.getAttributeVector();
ui->valueStackedWidget->setEnabled(true);
- for (QString t : availableValues) {
+ for (const QString &t : qAsConst(availableValues)) {
if (!QString::compare(t, attribute, Qt::CaseInsensitive)) {
available = true;
diff --git a/src/detachedwindowsmanager.cpp b/src/detachedwindowsmanager.cpp
index 4f46754490..5071517ccb 100644
--- a/src/detachedwindowsmanager.cpp
+++ b/src/detachedwindowsmanager.cpp
@@ -65,7 +65,7 @@ DetachedWindowsManager::DetachedWindowsManager()
DetachedWindowsManager::~DetachedWindowsManager()
{
- for (auto iterator : pool) {
+ for (auto iterator : qAsConst(pool)) {
delete iterator;
}
diff --git a/src/digitalio.cpp b/src/digitalio.cpp
index cc40bb947a..42985394a0 100644
--- a/src/digitalio.cpp
+++ b/src/digitalio.cpp
@@ -213,7 +213,7 @@ QPair *DigitalIO::findIndividualUi(int ch)
for (auto &&group : groups) {
auto i=0;
- for (auto wid : group->chui) {
+ for (auto wid : qAsConst(group->chui)) {
if (wid->first->property("dio")==ch) {
return group->chui[i];
}
@@ -274,7 +274,7 @@ void adiscope::DigitalIoGroup::changeDirection()
auto val = 0;
auto i=0;
- for (auto ch:chui) {
+ for (auto ch:qAsConst(chui)) {
ch->second->inout->setChecked(!chk);
auto channel = ch->first->property("dio").toInt();
dio->setDirection(channel,!chk);
diff --git a/src/dmm.cpp b/src/dmm.cpp
index 570608ef1f..442fe01039 100644
--- a/src/dmm.cpp
+++ b/src/dmm.cpp
@@ -75,8 +75,7 @@ DMM::DMM(struct iio_context *ctx, Filter *filt, ToolMenuItem *toolMenuItem,
logging_refresh_rate(0),
wheelEventGuard(nullptr),
m_autoGainEnabled({true, true}),
- m_historyForGain({0, 0}),
- m_gainHistorySize(10)
+ m_gainHistorySize(25)
{
ui->setupUi(this);
@@ -212,6 +211,11 @@ DMM::DMM(struct iio_context *ctx, Filter *filt, ToolMenuItem *toolMenuItem,
readPreferences();
ui->btnHelp->setUrl("https://wiki.analog.com/university/tools/m2k/scopy/voltmeter");
+
+ for(unsigned int i=0;i < m_adc_nb_channels;i++)
+ {
+ m_gainHistory.push_back(boost::circular_buffer(m_gainHistorySize));
+ }
}
void DMM::readPreferences()
@@ -249,11 +253,11 @@ void DMM::gainModeChanged(int idx)
if (idx == 0) { // auto
m_autoGainEnabled[channelIdx] = true;
} else if (idx == 1) { // low
- gainLabel->setText("Low Gain");
+ gainLabel->setText("±25V");
m_m2k_analogin->setRange(static_cast(channelIdx),
libm2k::analog::PLUS_MINUS_25V);
} else if (idx == 2) { // high
- gainLabel->setText("High Gain");
+ gainLabel->setText("±2.5V");
m_m2k_analogin->setRange(static_cast(channelIdx),
libm2k::analog::PLUS_MINUS_2_5V);
}
@@ -314,8 +318,8 @@ void DMM::updateValuesList(std::vector values)
checkAndUpdateGainMode({m_m2k_analogin->convertRawToVolts(0, static_cast(values[2])),
m_m2k_analogin->convertRawToVolts(0, static_cast(values[3])),
- m_m2k_analogin->convertRawToVolts(0, static_cast(values[4])),
- m_m2k_analogin->convertRawToVolts(0, static_cast(values[5]))});
+ m_m2k_analogin->convertRawToVolts(1, static_cast(values[4])),
+ m_m2k_analogin->convertRawToVolts(1, static_cast(values[5]))});
if(!use_timer)
data_cond.notify_all();
@@ -342,14 +346,8 @@ bool DMM::isIioManagerStarted() const
return manager->started() && ui->run_button->isChecked();
}
-void DMM::checkAndUpdateGainMode(const std::vector &volts)
+libm2k::analog::M2K_RANGE DMM::suggestRange(double volt_max, double volt_min)
{
- if (volts.size() < m_adc_nb_channels * 2) {
- return;
- }
-
- std::vector gainLabels {ui->currentGainCh1Label, ui->currentGainCh2Label};
- std::vector errorLabels {ui->ch1ErrorLabel, ui->ch2ErrorLabel};
double hi = 0.0;
double lo = 0.0;
@@ -364,80 +362,112 @@ void DMM::checkAndUpdateGainMode(const std::vector &volts)
const double lo_hi = lo + half_hist_interval;
const double lo_lo = lo - half_hist_interval;
- for (int i = 0; i < m_adc_nb_channels; ++i) {
- libm2k::analog::M2K_RANGE gain = libm2k::analog::PLUS_MINUS_25V;
+ libm2k::analog::M2K_RANGE gain = libm2k::analog::PLUS_MINUS_25V;
- bool changed = false;
- if (volts[m_adc_nb_channels * i] > 0.0) {
- changed = true;
- if (volts[m_adc_nb_channels * i] >= hi_hi) {
- gain = libm2k::analog::PLUS_MINUS_25V;
- } else if (volts[m_adc_nb_channels * i] <= hi_lo) {
- gain = libm2k::analog::PLUS_MINUS_2_5V;
- } else {
- changed = false;
- }
+ if (volt_max > 0.0) {
+ if (volt_max >= hi_hi) {
+ gain = libm2k::analog::PLUS_MINUS_25V;
+ } else if (volt_max <= hi_lo) {
+ gain = libm2k::analog::PLUS_MINUS_2_5V;
}
- if (volts[m_adc_nb_channels * i + 1] <= 0.0) {
- changed = true;
- if (volts[m_adc_nb_channels * i + 1] <= lo_lo ) {
- gain = libm2k::analog::PLUS_MINUS_25V;
- } else if (volts[m_adc_nb_channels * i + 1] >= lo_hi) {
+ if (volt_min <= 0.0) {
+ if (volt_min >= lo_hi ) {
gain = libm2k::analog::PLUS_MINUS_2_5V;
- } else {
- changed = false;
+ } else if (volt_min <= lo_lo) {
+ gain = libm2k::analog::PLUS_MINUS_25V;
}
}
+ }
+ return gain;
+}
- if (!changed) {
- continue;
- }
+void DMM::checkAndUpdateGainMode(const std::vector &volts)
+{
+ if (volts.size() < m_adc_nb_channels * 2) {
+ return;
+ }
- if (gain == libm2k::analog::PLUS_MINUS_2_5V && m_m2k_analogin->getRange(static_cast(i)) != gain
- && m_historyForGain[i] < m_gainHistorySize) {
- m_historyForGain[i]++;
- continue; // we don't wanna change the gain now;
- }
+ std::vector gainLabels {ui->currentGainCh1Label, ui->currentGainCh2Label};
+ std::vector errorLabels {ui->ch1ErrorLabel, ui->ch2ErrorLabel};
- if (gain == libm2k::analog::PLUS_MINUS_25V) {
- m_historyForGain[i] = 0;
- }
- errorLabels[i]->setText("");
- if (m_m2k_analogin->getRange(static_cast(i)) != gain) {
- if (m_autoGainEnabled[i]) {
- const bool started = isIioManagerStarted();
- if (started) {
- manager->lock();
- }
+ libm2k::analog::M2K_RANGE gain[m_adc_nb_channels];
+ libm2k::analog::M2K_RANGE currentChannelGain[m_adc_nb_channels];
+ bool recreateFlowGraph = false;
- // rebuild the flowgraph
- // there might be data on in the gnuradio flowgraph that
- // was captured using one gain mode and plotted and converted
- // with another gain mode. This will ensure this situation doesn't
- // happen
- manager->disconnect(id_ch1);
- manager->disconnect(id_ch2);
+ for (unsigned int i = 0; i < m_adc_nb_channels; ++i) {
+ gain[i]=libm2k::analog::PLUS_MINUS_25V;
+ currentChannelGain[i] = m_m2k_analogin->getRange(static_cast(i));
+ //gain[i] = currentChannelGain[i];//libm2k::analog::PLUS_MINUS_25V;
- configureModes();
+ // add all gains to circular buffer
+ auto suggested_range = suggestRange (volts[m_adc_nb_channels * i], volts[(m_adc_nb_channels * i) + 1]);
+ m_gainHistory[i].push_back(suggested_range);
- m_m2k_analogin->setRange(static_cast(i), gain);
- gainLabels[i]->setText(gain == libm2k::analog::PLUS_MINUS_25V ? "Low Gain" : "High Gain");
+ // define m2k_range sum computation operation as lambda
+ auto range_sum = [](double a, libm2k::analog::M2K_RANGE b) {
+ return (a) + static_cast(b);
+ };
+
+
+
+ // compute average of circular buffer - moving average
+ double sum = std::accumulate(m_gainHistory[i].begin(),m_gainHistory[i].end(), 0.0, range_sum);
+ double avg = sum / m_gainHistory[i].size();
+ // only change to high gain if ALL values in circular buffer == HIGH_GAIN
+ // this means as soon as we find a value out of HIGH range we switch immediately - but wait m_gainHistorySize to change back to HIGH
+ if(avg == libm2k::analog::PLUS_MINUS_2_5V) {
+ gain[i] = libm2k::analog::PLUS_MINUS_2_5V;
+ }
+
+ if(gain[i] != currentChannelGain[i] ) {
+ if(m_autoGainEnabled[i]) {
+ errorLabels[i]->setText("");
+ m_m2k_analogin->setRange(static_cast(i), gain[i]);
+ gainLabels[i]->setText(gain[i] == libm2k::analog::PLUS_MINUS_25V ? "±25V" : "±2.5V");
+ recreateFlowGraph = true;
- if (started) {
- manager->start(id_ch1);
- manager->start(id_ch2);
- manager->unlock();
- }
} else {
- errorLabels[i]->setText("Out of range!");
+ if(currentChannelGain[i] == libm2k::analog::PLUS_MINUS_2_5V) { // only show out of range for +/- 2.5
+ errorLabels[i]->setText("Out of range");
+ } else {
+ errorLabels[i]->setText("");
+ }
}
+ } else {
+ errorLabels[i]->setText("");
+ }
+
+
+ }
+
+ if(recreateFlowGraph) {
+ const bool started = isIioManagerStarted();
+ if (started) {
+ manager->lock();
+ }
+
+ // rebuild the flowgraph
+ // there might be data on in the gnuradio flowgraph that
+ // was captured using one gain mode and plotted and converted
+ // with another gain mode. This will ensure this situation doesn't
+ // happen
+ manager->disconnect(id_ch1);
+ manager->disconnect(id_ch2);
+
+ configureModes();
+
+ if (started) {
+ manager->start(id_ch1);
+ manager->start(id_ch2);
+ manager->unlock();
}
}
}
+
void DMM::collapseDataLog(bool checked)
{
if(checked)
diff --git a/src/dmm.hpp b/src/dmm.hpp
index a2bc5748a4..4b0375dae5 100644
--- a/src/dmm.hpp
+++ b/src/dmm.hpp
@@ -35,6 +35,7 @@
#include "spinbox_a.hpp"
#include
#include
+#include
/* libm2k includes */
#include
@@ -87,13 +88,14 @@ namespace adiscope {
std::vector m_min, m_max;
std::vector m_autoGainEnabled;
- std::vector m_historyForGain;
+ std::vector> m_gainHistory;
int m_gainHistorySize;
void disconnectAll();
gr::basic_block_sptr configureGraph(gr::basic_block_sptr s2f,
bool is_ac);
void configureModes();
+ libm2k::analog::M2K_RANGE suggestRange(double volt_max, double volt_min);
int numSamplesFromIdx(int idx);
void writeAllSettingsToHardware();
void checkPeakValues(int, double);
diff --git a/src/fft_block.cpp b/src/fft_block.cpp
index 164dadc377..9351fb5737 100644
--- a/src/fft_block.cpp
+++ b/src/fft_block.cpp
@@ -37,9 +37,6 @@ fft_block::fft_block(bool use_complex, size_t fft_size, unsigned int nbthreads)
io_signature::make(1, 1, sizeof(gr_complex))),
d_complex(use_complex)
{
- auto s2v = blocks::stream_to_vector::make(
- use_complex ? sizeof(gr_complex) : sizeof(float),
- fft_size);
auto v2s = blocks::vector_to_stream::make(sizeof(gr_complex), fft_size);
d_s2v_overlap = adiscope::stream_to_vector_overlap::make(
diff --git a/src/filemanager.cpp b/src/filemanager.cpp
index 63ce39bad7..89aeae3493 100644
--- a/src/filemanager.cpp
+++ b/src/filemanager.cpp
@@ -88,7 +88,7 @@ void FileManager::open(QString fileName,
QVector line_data;
QString line = in.readLine();
QStringList list = line.split(separator, QString::SkipEmptyParts);
- for (QString list_item : list) {
+ for (const QString &list_item : qAsConst(list)) {
line_data.push_back(list_item);
}
if (line_data.size() > 0) {
@@ -289,7 +289,7 @@ void FileManager::performWrite()
//column names row
exportStream << "Sample" << separator;
bool skipFirstSeparator=true;
- for (QString columnName : columnNames) {
+ for (const QString &columnName : qAsConst(columnNames)) {
if(!skipFirstSeparator)
exportStream << separator;
exportStream << columnName;
diff --git a/src/filter.cpp b/src/filter.cpp
index b2572a022c..1a3fe03d27 100644
--- a/src/filter.cpp
+++ b/src/filter.cpp
@@ -55,7 +55,8 @@ Filter::Filter(const struct iio_context *ctx)
auto doc = QJsonDocument::fromJson(file.readAll());
auto obj = doc.object();
- for (const auto &key : obj.keys()) {
+ auto obj_keys = obj.keys();
+ for (const auto &key : qAsConst(obj_keys)) {
const auto child = obj[key].toObject();
if (!child.contains("compatible-devices"))
@@ -67,7 +68,8 @@ Filter::Filter(const struct iio_context *ctx)
bool compatible = true;
- for (const auto &value : compatible_devices.toArray()) {
+ auto comp_dev = compatible_devices.toArray();
+ for (const auto &value : qAsConst(comp_dev)) {
if (!value.isString()) {
compatible = false;
break;
diff --git a/src/handlesareaextension.cpp b/src/handlesareaextension.cpp
index f471c8c9f1..29797112cb 100644
--- a/src/handlesareaextension.cpp
+++ b/src/handlesareaextension.cpp
@@ -1,177 +1,612 @@
-#include "handlesareaextension.h"
-
-#include
-
-#include
-
-#include "handles_area.hpp"
-#include "oscilloscope_plot.hpp"
-#include "paintersaverestore.h"
-
-using namespace adiscope;
-
-HandlesAreaExtension::HandlesAreaExtension(QwtPlot* plot)
- : m_plot(plot) {}
-
-XBottomRuller::XBottomRuller(QwtPlot *plot)
- : HandlesAreaExtension(plot) {}
-
-bool XBottomRuller::draw(QPainter *painter, QWidget *owner)
-{
- HorizHandlesArea *area = qobject_cast(owner);
- if (!area) {
- return false;
- }
-
- const CapturePlot *plot = qobject_cast(m_plot);
- if (!plot) {
- return false;
- }
-
- // Some extensions might alter the state of the painter
- // such as its brush or pen. Consider saving its state
- // then restore it when done using it so other extensions
- // won't be affected
-
- // PainterSaveRestore psr(painter);
-
- const QwtInterval interval = plot->axisInterval(QwtPlot::xBottom);
-
- const double leftP = area->leftPadding();
- const double rightP = area->rightPadding();
-
- const int labels = plot->xAxisNumDiv() + 1;
-
- const double totalWidth = owner->width() - (leftP + rightP);
- const double distBetween2Labels = totalWidth / (labels - 1);
- const double timeBetween2Labels = (interval.maxValue() - interval.minValue()) / (labels - 1);
-
- // compute rectangles of labels and
- // corresponding text
- QVector labelRectangles;
- QStringList labelTexts;
- double midPoint = leftP;
- double currentTime = interval.minValue();
- for (int i = 0; i < labels; ++i) {
- const QString text = plot->timeScaleValueFormat(currentTime, 2);
-
- const QSizeF textSize = QwtText(text).textSize(painter->font());
- QRectF textRect(QPointF(0.0, 0.0), textSize);
-
- textRect.moveCenter(QPointF(midPoint, textSize.height() / 2.0));
-
- labelRectangles.push_back(textRect);
- labelTexts.push_back(text);
-
- midPoint += distBetween2Labels;
- currentTime += timeBetween2Labels;
- }
-
- bool allLabelsTheSame = true;
- for (int i = 1; i < labelTexts.size(); ++i) {
- if (labelTexts[i] != labelTexts[i - 1]) {
- allLabelsTheSame = false;
- break;
- }
- }
-
- // get nr of major ticks
- const int nrMajorTicks = plot->axisScaleDiv(QwtPlot::xBottom).ticks(QwtScaleDiv::MajorTick).size();
- const int midLabelTick = nrMajorTicks / 2;
-
- if (allLabelsTheSame) {
- // draw delta as middle label
- labelRectangles.clear();
- labelTexts.clear();
- midPoint = leftP;
- currentTime = interval.minValue();
- for (int i = 0; i < labels; ++i) {
- QString text;
- if (i == midLabelTick) {
- text = plot->timeScaleValueFormat(currentTime, 6);
- } else {
- text = plot->timeScaleValueFormat(currentTime - (interval.minValue() + midLabelTick * timeBetween2Labels), 2);
- if (i > midLabelTick) {
- text = "+" + text;
- }
- }
-
- const QSizeF textSize = QwtText(text).textSize(painter->font());
- QRectF textRect(QPointF(0.0, 0.0), textSize);
-
- textRect.moveCenter(QPointF(midPoint, textSize.height() / 2.0));
-
- labelRectangles.push_back(textRect);
- labelTexts.push_back(text);
-
- midPoint += distBetween2Labels;
- currentTime += timeBetween2Labels;
- }
-
- }
-
- // adjust labels to fit visible area of the handle area
- // mainly the first and last label
- if (labelRectangles.first().topLeft().x() < owner->mask().boundingRect().bottomLeft().x()) {
- int offset = owner->mask().boundingRect().bottomLeft().x() - labelRectangles.first().topLeft().x();
- labelRectangles.first().adjust(offset, 0, offset, 0);
- }
-
- if (labelRectangles.last().bottomRight().x() > owner->mask().boundingRect().bottomRight().x()) {
- int offset = labelRectangles.last().bottomRight().x() - owner->mask().boundingRect().bottomRight().x();
- labelRectangles.last().adjust(-offset, 0, -offset, 0);
- }
-
- // filter out overlaping labels, but always drawing
- // the first and last label
- bool overlaping = false;
- do {
- // consider none overlaping
- overlaping = false;
-
- // find overlaping
- int i = 0;
- for (; i < labelRectangles.size() - 1; ++i) {
- if (labelRectangles[i].intersects(labelRectangles[i + 1])) {
- overlaping = true;
- break;
- }
- }
-
- // done
- if (!overlaping) {
- break;
- }
- if (allLabelsTheSame) {
- int center = midLabelTick;
- for (int i = center - 1; i >= 0; i -= 2) {
- // Remove the tick and make sure to update the center
- // label position
- labelRectangles.removeAt(i);
- labelTexts.removeAt(i);
- --center;
- }
- for (int j = center + 1; j < labelRectangles.size(); j += 1) {
- labelRectangles.removeAt(j);
- labelTexts.removeAt(j);
- }
-
- } else {
- // remove overlaping
- if (i + 1 == labelRectangles.size() - 1) {
- labelRectangles.removeAt(i);
- labelTexts.removeAt(i);
- } else {
- labelRectangles.removeAt(i + 1);
- labelTexts.removeAt(i + 1);
- }
- }
- } while(overlaping);
-
- // draw the labels
- for (int i = 0; i < labelRectangles.size(); ++i) {
- painter->drawText(labelRectangles[i], labelTexts[i]);
- }
-
- return false;
-}
+#include "handlesareaextension.h"
+
+#include
+
+#include
+
+#include "handles_area.hpp"
+#include "DisplayPlot.h"
+#include "paintersaverestore.h"
+
+using namespace adiscope;
+
+HandlesAreaExtension::HandlesAreaExtension(QwtPlot* plot)
+ : m_plot(plot) {}
+
+XBottomRuller::XBottomRuller(QwtPlot *plot)
+ : HandlesAreaExtension(plot) {}
+
+bool XBottomRuller::draw(QPainter *painter, QWidget *owner)
+{
+ HorizHandlesArea *area = qobject_cast(owner);
+ if (!area) {
+ return false;
+ }
+
+ const DisplayPlot *plot = qobject_cast(m_plot);
+ if (!plot) {
+ return false;
+ }
+
+ const double leftP = area->leftPadding();
+ const double rightP = area->rightPadding();
+
+ QVector labelRectangles;
+ QStringList labelTexts;
+
+ if(plot->isLogaritmicPlot())
+ {
+ QList majorTicks = plot->getXaxisMajorTicksPos();
+ double pointVal, currentValue;
+
+ for (int i = 0; i < majorTicks.size(); ++i) {
+ currentValue = majorTicks.at(i);
+ pointVal = plot->transform(QwtPlot::xBottom, currentValue) + leftP;
+
+ const QString text = plot->formatXValue(currentValue, 2);
+
+ const QSizeF textSize = QwtText(text).textSize(painter->font());
+ QRectF textRect(QPointF(0.0, 0.0), textSize);
+
+ textRect.moveCenter(QPointF(pointVal, textSize.height() / 2.0));
+
+ labelRectangles.push_back(textRect);
+ labelTexts.push_back(text);
+ }
+
+ // adjust labels to fit visible area of the handle area
+ // mainly the first and last label
+ if (labelRectangles.first().topLeft().x() < owner->mask().boundingRect().bottomLeft().x()) {
+ int offset = owner->mask().boundingRect().bottomLeft().x() - labelRectangles.first().topLeft().x();
+ labelRectangles.first().adjust(offset, 0, offset, 0);
+ }
+
+ if (labelRectangles.last().bottomRight().x() > owner->mask().boundingRect().bottomRight().x()) {
+ int offset = labelRectangles.last().bottomRight().x() - owner->mask().boundingRect().bottomRight().x();
+ labelRectangles.last().adjust(-offset, 0, -offset, 0);
+ }
+ }
+ else
+ {
+ // Some extensions might alter the state of the painter
+ // such as its brush or pen. Consider saving its state
+ // then restore it when done using it so other extensions
+ // won't be affected
+
+ // PainterSaveRestore psr(painter);
+
+ const QwtInterval interval = plot->axisInterval(QwtPlot::xBottom);
+
+ const int labels = plot->xAxisNumDiv() + 1;
+
+ const double totalWidth = owner->width() - (leftP + rightP);
+ const double distBetween2Labels = totalWidth / (labels - 1);
+ const double valueBetween2Labels = (interval.maxValue() - interval.minValue()) / (labels - 1);
+
+ double midPoint = leftP;
+ double currentValue = interval.minValue();
+ for (int i = 0; i < labels; ++i) {
+
+ const QString text = plot->formatXValue(currentValue, 2);
+
+ const QSizeF textSize = QwtText(text).textSize(painter->font());
+ QRectF textRect(QPointF(0.0, 0.0), textSize);
+
+ textRect.moveCenter(QPointF(midPoint, textSize.height() / 2.0));
+
+ labelRectangles.push_back(textRect);
+ labelTexts.push_back(text);
+
+ midPoint += distBetween2Labels;
+ currentValue += valueBetween2Labels;
+ }
+
+ bool allLabelsTheSame = true;
+ for (int i = 1; i < labelTexts.size(); ++i) {
+ if (labelTexts[i] != labelTexts[i - 1]) {
+ allLabelsTheSame = false;
+ break;
+ }
+ }
+
+ // get nr of major ticks
+ const int nrMajorTicks = plot->axisScaleDiv(QwtPlot::xBottom).ticks(QwtScaleDiv::MajorTick).size();
+ const int midLabelTick = nrMajorTicks / 2;
+
+ if (allLabelsTheSame) {
+ // draw delta as middle label
+ labelRectangles.clear();
+ labelTexts.clear();
+ midPoint = leftP;
+ currentValue = interval.minValue();
+ for (int i = 0; i < labels; ++i) {
+ QString text;
+ if (i == midLabelTick) {
+ text = plot->formatXValue(currentValue, 6);
+ } else {
+ text = plot->formatXValue(currentValue - (interval.minValue() + midLabelTick * valueBetween2Labels), 2);
+
+ if (i > midLabelTick) {
+ text = "+" + text;
+ }
+ }
+
+ const QSizeF textSize = QwtText(text).textSize(painter->font());
+ QRectF textRect(QPointF(0.0, 0.0), textSize);
+
+ textRect.moveCenter(QPointF(midPoint, textSize.height() / 2.0));
+
+ labelRectangles.push_back(textRect);
+ labelTexts.push_back(text);
+
+ midPoint += distBetween2Labels;
+ currentValue += valueBetween2Labels;
+ }
+
+ }
+
+ // adjust labels to fit visible area of the handle area
+ // mainly the first and last label
+ if (labelRectangles.first().topLeft().x() < owner->mask().boundingRect().bottomLeft().x()) {
+ int offset = owner->mask().boundingRect().bottomLeft().x() - labelRectangles.first().topLeft().x();
+ labelRectangles.first().adjust(offset, 0, offset, 0);
+ }
+
+ if (labelRectangles.last().bottomRight().x() > owner->mask().boundingRect().bottomRight().x()) {
+ int offset = labelRectangles.last().bottomRight().x() - owner->mask().boundingRect().bottomRight().x();
+ labelRectangles.last().adjust(-offset, 0, -offset, 0);
+ }
+
+ // filter out overlaping labels, but always drawing
+ // the first and last label
+ bool overlaping = false;
+ do {
+ // consider none overlaping
+ overlaping = false;
+
+ // find overlaping
+ int i = 0;
+ for (; i < labelRectangles.size() - 1; ++i) {
+ if (labelRectangles[i].intersects(labelRectangles[i + 1])) {
+ overlaping = true;
+ break;
+ }
+ }
+
+ // done
+ if (!overlaping) {
+ break;
+ }
+ if (allLabelsTheSame) {
+ int center = midLabelTick;
+ for (int i = center - 1; i >= 0; i -= 2) {
+ // Remove the tick and make sure to update the center
+ // label position
+ labelRectangles.removeAt(i);
+ labelTexts.removeAt(i);
+ --center;
+ }
+ for (int j = center + 1; j < labelRectangles.size(); j += 1) {
+ labelRectangles.removeAt(j);
+ labelTexts.removeAt(j);
+ }
+
+ } else {
+ // remove overlaping
+ if (i + 1 == labelRectangles.size() - 1) {
+ labelRectangles.removeAt(i);
+ labelTexts.removeAt(i);
+ } else {
+ labelRectangles.removeAt(i + 1);
+ labelTexts.removeAt(i + 1);
+ }
+ }
+ } while(overlaping);
+
+ }
+ // draw the labels
+ for (int i = 0; i < labelRectangles.size(); ++i) {
+ painter->drawText(labelRectangles[i], labelTexts[i]);
+ }
+
+ return false;
+}
+
+XTopRuller::XTopRuller(QwtPlot *plot)
+ : HandlesAreaExtension(plot) {}
+
+bool XTopRuller::draw(QPainter *painter, QWidget *owner)
+{
+ HorizHandlesArea *area = qobject_cast(owner);
+ if (!area) {
+ return false;
+ }
+
+ const DisplayPlot *plot = qobject_cast(m_plot);
+ if (!plot) {
+ return false;
+ }
+
+ const double leftP = area->leftPadding();
+ const double rightP = area->rightPadding();
+
+ QVector labelRectangles;
+ QStringList labelTexts;
+
+ if(plot->isLogaritmicPlot())
+ {
+ QList majorTicks = plot->getXaxisMajorTicksPos();
+ double pointVal, currentValue;
+
+ for (int i = 0; i < majorTicks.size(); ++i) {
+ currentValue = majorTicks.at(i);
+ pointVal = plot->transform(QwtPlot::xTop, currentValue) + leftP;
+
+ const QString text = plot->formatXValue(currentValue, 2);
+
+ const QSizeF textSize = QwtText(text).textSize(painter->font());
+ QRectF textRect(QPointF(0.0, 0.0), textSize);
+
+ textRect.moveCenter(QPointF(pointVal + textSize.width() / 2.0, textSize.height() / 2.0));
+
+ labelRectangles.push_back(textRect);
+ labelTexts.push_back(text);
+ }
+
+ // adjust labels to fit visible area of the handle area
+ // mainly the first and last label
+ if (labelRectangles.first().topLeft().x() < owner->mask().boundingRect().bottomLeft().x()) {
+ int offset = owner->mask().boundingRect().bottomLeft().x() - labelRectangles.first().topLeft().x();
+ labelRectangles.first().adjust(offset, 0, offset, 0);
+ }
+
+ if (labelRectangles.last().bottomRight().x() > owner->mask().boundingRect().bottomRight().x()) {
+ int offset = labelRectangles.last().bottomRight().x() - owner->mask().boundingRect().bottomRight().x();
+ labelRectangles.last().adjust(-offset, 0, -offset, 0);
+ }
+
+
+ }
+ else
+ {
+ // Some extensions might alter the state of the painter
+ // such as its brush or pen. Consider saving its state
+ // then restore it when done using it so other extensions
+ // won't be affected
+
+ // PainterSaveRestore psr(painter);
+
+ const QwtInterval interval = plot->axisInterval(QwtPlot::xTop);
+
+ const int labels = plot->xAxisNumDiv() + 1;
+
+ const double totalWidth = owner->width() - (leftP + rightP);
+ const double distBetween2Labels = totalWidth / (labels - 1);
+ const double valueBetween2Labels = (interval.maxValue() - interval.minValue()) / (labels - 1);
+ double midPoint = leftP;
+ double currentValue = interval.minValue();
+
+ for (int i = 0; i < labels; ++i) {
+ const QString text = plot->formatXValue(currentValue, 2);
+
+ const QSizeF textSize = QwtText(text).textSize(painter->font());
+ QRectF textRect(QPointF(0.0, 0.0), textSize);
+
+ textRect.moveCenter(QPointF(midPoint, textSize.height() / 2.0));
+
+ labelRectangles.push_back(textRect);
+ labelTexts.push_back(text);
+
+ midPoint += distBetween2Labels;
+ currentValue += valueBetween2Labels;
+ }
+
+ bool allLabelsTheSame = true;
+ for (int i = 1; i < labelTexts.size(); ++i) {
+ if (labelTexts[i] != labelTexts[i - 1]) {
+ allLabelsTheSame = false;
+ break;
+ }
+ }
+
+ // get nr of major ticks
+ const int nrMajorTicks = plot->axisScaleDiv(QwtPlot::xTop).ticks(QwtScaleDiv::MajorTick).size();
+ const int midLabelTick = nrMajorTicks / 2;
+
+ if (allLabelsTheSame) {
+ // draw delta as middle label
+ labelRectangles.clear();
+ labelTexts.clear();
+ midPoint = leftP;
+ currentValue = interval.minValue();
+ for (int i = 0; i < labels; ++i) {
+ QString text;
+ if (i == midLabelTick) {
+ text = plot->formatXValue(currentValue, 2);
+ } else {
+ text= plot->formatXValue(currentValue - (interval.minValue() + midLabelTick * valueBetween2Labels), 2);
+ if (i > midLabelTick) {
+ text = "+" + text;
+ }
+ }
+
+ const QSizeF textSize = QwtText(text).textSize(painter->font());
+ QRectF textRect(QPointF(0.0, 0.0), textSize);
+
+ textRect.moveCenter(QPointF(midPoint, textSize.height() / 2.0));
+
+ labelRectangles.push_back(textRect);
+ labelTexts.push_back(text);
+
+ midPoint += distBetween2Labels;
+ currentValue += valueBetween2Labels;
+ }
+
+ }
+
+ // adjust labels to fit visible area of the handle area
+ // mainly the first and last label
+ if (labelRectangles.first().topLeft().x() < owner->mask().boundingRect().bottomLeft().x()) {
+ int offset = owner->mask().boundingRect().bottomLeft().x() - labelRectangles.first().topLeft().x();
+ labelRectangles.first().adjust(offset, 0, offset, 0);
+ }
+
+ if (labelRectangles.last().bottomRight().x() > owner->mask().boundingRect().bottomRight().x()) {
+ int offset = labelRectangles.last().bottomRight().x() - owner->mask().boundingRect().bottomRight().x();
+ labelRectangles.last().adjust(-offset, 0, -offset, 0);
+ }
+
+ // filter out overlaping labels, but always drawing
+ // the first and last label
+ bool overlaping = false;
+ do {
+ // consider none overlaping
+ overlaping = false;
+
+ // find overlaping
+ int i = 0;
+ for (; i < labelRectangles.size() - 1; ++i) {
+ if (labelRectangles[i].intersects(labelRectangles[i + 1])) {
+ overlaping = true;
+ break;
+ }
+ }
+
+ // done
+ if (!overlaping) {
+ break;
+ }
+ if (allLabelsTheSame) {
+ int center = midLabelTick;
+ for (int i = center - 1; i >= 0; i -= 2) {
+ // Remove the tick and make sure to update the center
+ // label position
+ labelRectangles.removeAt(i);
+ labelTexts.removeAt(i);
+ --center;
+ }
+ for (int j = center + 1; j < labelRectangles.size(); j += 1) {
+ labelRectangles.removeAt(j);
+ labelTexts.removeAt(j);
+ }
+
+ } else {
+ // remove overlaping
+ if (i + 1 == labelRectangles.size() - 1) {
+ labelRectangles.removeAt(i);
+ labelTexts.removeAt(i);
+ } else {
+ labelRectangles.removeAt(i + 1);
+ labelTexts.removeAt(i + 1);
+ }
+ }
+ } while(overlaping);
+ }
+
+ // draw the labels
+ for (int i = 0; i < labelRectangles.size(); ++i) {
+ painter->drawText(labelRectangles[i], labelTexts[i]);
+ }
+
+ return false;
+}
+
+YLeftRuller::YLeftRuller(QwtPlot *plot)
+ : HandlesAreaExtension(plot) {}
+
+bool YLeftRuller::draw(QPainter *painter, QWidget *owner)
+{
+ VertHandlesArea *area = qobject_cast(owner);
+ if (!area) {
+ return false;
+ }
+
+ auto width_text = QFontMetrics(painter->font()).horizontalAdvance("-XXX.XX XX");
+ if(area->width() != width_text)
+ area->setMinimumWidth(width_text);
+
+ const DisplayPlot *plot = qobject_cast(m_plot);
+ if (!plot) {
+ return false;
+ }
+
+
+ const double topP = area->topPadding();
+ const double bottomP = area->bottomPadding();
+
+ QVector labelRectangles;
+ QStringList labelTexts;
+
+ if(plot->isLogaritmicYPlot())
+ {
+ QList majorTicks = plot->getYaxisMajorTicksPos();
+ double pointVal, currentValue;
+
+ for (int i = 0; i < majorTicks.size(); ++i) {
+ currentValue = majorTicks.at(i);
+ pointVal = plot->transform(QwtPlot::yLeft, currentValue) + topP;
+
+ const QString text = plot->formatYValue(currentValue, 2);
+
+ const QSizeF textSize = QwtText(text).textSize(painter->font());
+ QRectF textRect(QPointF(0.0, 0.0), textSize);
+
+ textRect.moveCenter(QPointF(textSize.width() / 2.0, pointVal));
+
+ labelRectangles.push_back(textRect);
+ labelTexts.push_back(text);
+ }
+
+ // adjust labels to fit visible area of the handle area
+ // mainly the first and last label
+ if(!labelRectangles.empty())
+ {
+ if (labelRectangles.first().topRight().y() < owner->mask().boundingRect().topLeft().y()) {
+ int offset = owner->mask().boundingRect().topLeft().y() - labelRectangles.first().topRight().y();
+ labelRectangles.first().adjust(0, offset, 0, offset);
+ }
+
+ if (labelRectangles.last().bottomRight().y() > owner->mask().boundingRect().bottomLeft().y()) {
+ int offset = labelRectangles.last().bottomRight().y() - owner->mask().boundingRect().bottomLeft().y();
+ labelRectangles.last().adjust(0, -offset, 0, -offset);
+ }
+ }
+ }
+ else
+ {
+
+ const QwtInterval interval = plot->axisInterval(QwtPlot::yLeft);
+
+ const int labels = plot->yAxisNumDiv();
+
+ const double totalHeight = owner->height() - (topP + bottomP);
+ const double distBetween2Labels = totalHeight / (labels - 1);
+ const double valueBetween2Labels = (interval.maxValue() - interval.minValue()) / (labels - 1);
+
+ double midPoint = topP;
+ double currentValue = interval.maxValue();
+
+ for (int i = 0; i < labels; ++i) {
+ const QString text = plot->formatYValue(currentValue, 2);
+ QSizeF textSize = QwtText(text).textSize(painter->font());
+ textSize.setWidth(textSize.width() + 20);
+
+ QRectF textRect(QPointF(0.0, 0.0), textSize);
+
+ textRect.moveCenter(QPointF(textSize.width() / 2.0, midPoint));
+
+ labelRectangles.push_back(textRect);
+ labelTexts.push_back(text);
+
+ midPoint += distBetween2Labels;
+ currentValue -= valueBetween2Labels;
+ }
+
+ bool allLabelsTheSame = true;
+ for (int i = 1; i < labelTexts.size(); ++i) {
+ if (labelTexts[i] != labelTexts[i - 1]) {
+ allLabelsTheSame = false;
+ break;
+ }
+ }
+
+ // get nr of major ticks
+ const int nrMajorTicks = plot->axisScaleDiv(QwtPlot::yLeft).ticks(QwtScaleDiv::MajorTick).size();
+ const int midLabelTick = nrMajorTicks / 2;
+
+ if (allLabelsTheSame) {
+ // draw delta as middle label
+ labelRectangles.clear();
+ labelTexts.clear();
+ midPoint = topP;
+ currentValue = interval.maxValue();
+ for (int i = 0; i < labels; ++i) {
+ QString text;
+ if (i == midLabelTick) {
+ text = plot->formatYValue(currentValue, 2);
+ } else {
+ text = plot->formatYValue(currentValue - (interval.maxValue() + midLabelTick * valueBetween2Labels), 2);
+ if (i > midLabelTick) {
+ text = "+" + text;
+ }
+ }
+
+ QSizeF textSize = QwtText(text).textSize(painter->font());
+ textSize.setWidth(textSize.width() + 20);
+ QRectF textRect(QPointF(0.0, 0.0), textSize);
+ textRect.moveCenter(QPointF(textSize.width() / 2.0, midPoint));
+
+ labelRectangles.push_back(textRect);
+ labelTexts.push_back(text);
+
+ midPoint += distBetween2Labels;
+ currentValue -= valueBetween2Labels;
+ }
+ }
+
+ // adjust labels to fit visible area of the handle area
+ // mainly the first and last label
+ if (labelRectangles.first().topRight().y() < owner->mask().boundingRect().topLeft().y()) {
+ int offset = owner->mask().boundingRect().topLeft().y() - labelRectangles.first().topRight().y();
+ labelRectangles.first().adjust(0, offset, 0, offset);
+ }
+
+ if (labelRectangles.last().bottomRight().y() > owner->mask().boundingRect().bottomLeft().y()) {
+ int offset = labelRectangles.last().bottomRight().y() - owner->mask().boundingRect().bottomLeft().y();
+ labelRectangles.last().adjust(0, -offset, 0, -offset);
+ }
+
+ // filter out overlaping labels, but always drawing
+ // the first and last label
+ bool overlaping = false;
+ do {
+ // consider none overlaping
+ overlaping = false;
+
+ // find overlaping
+ int i = 0;
+ for (; i < labelRectangles.size() - 1; ++i) {
+ if (labelRectangles[i].intersects(labelRectangles[i + 1])) {
+ overlaping = true;
+ break;
+ }
+ }
+
+ // done
+ if (!overlaping) {
+ break;
+ }
+ if (allLabelsTheSame) {
+ int center = midLabelTick;
+ for (int i = center - 1; i >= 0; i -= 2) {
+ // Remove the tick and make sure to update the center
+ // label position
+ labelRectangles.removeAt(i);
+ labelTexts.removeAt(i);
+ --center;
+ }
+ for (int j = center + 1; j < labelRectangles.size(); j += 1) {
+ labelRectangles.removeAt(j);
+ labelTexts.removeAt(j);
+ }
+
+ }else {
+ // remove overlaping
+ if (i + 1 == labelRectangles.size() - 1) {
+ labelRectangles.removeAt(i);
+ labelTexts.removeAt(i);
+ } else {
+ labelRectangles.removeAt(i + 1);
+ labelTexts.removeAt(i + 1);
+ }
+ }
+ }while(overlaping);
+ }
+
+ // draw the labels
+ for (int i = 0; i < labelRectangles.size(); ++i) {
+ painter->drawText(labelRectangles[i], labelTexts[i]);
+ }
+
+ return false;
+}
diff --git a/src/handlesareaextension.h b/src/handlesareaextension.h
index 70fd6a9879..2c67f18556 100644
--- a/src/handlesareaextension.h
+++ b/src/handlesareaextension.h
@@ -28,5 +28,20 @@ class XBottomRuller: public HandlesAreaExtension {
virtual bool draw(QPainter *painter, QWidget *owner) Q_DECL_OVERRIDE;
};
+class YLeftRuller: public HandlesAreaExtension {
+public:
+ YLeftRuller(QwtPlot *plot);
+ virtual ~YLeftRuller() = default;
+
+ virtual bool draw(QPainter *painter, QWidget *owner) Q_DECL_OVERRIDE;
+};
+
+class XTopRuller: public HandlesAreaExtension {
+public:
+ XTopRuller(QwtPlot *plot);
+ virtual ~XTopRuller() = default;
+
+ virtual bool draw(QPainter *painter, QWidget *owner) Q_DECL_OVERRIDE;
+};
#endif // HANDLESAREAEXTENSION_H
diff --git a/src/info_page.cpp b/src/info_page.cpp
index 2bd36d901a..23d6e5511d 100644
--- a/src/info_page.cpp
+++ b/src/info_page.cpp
@@ -253,7 +253,8 @@ void InfoPage::refreshInfoWidget()
int pos = 0;
ui->paramLayout->setRowMinimumHeight(pos, 20);
- for (auto key : m_info_params.keys()) {
+ auto info_param_keys = m_info_params.keys();
+ for (const auto &key : qAsConst(info_param_keys)) {
QLabel *valueLbl = new QLabel(this);
QLabel *keyLbl = new QLabel(this);
valueLbl->setText(m_info_params.value(key));
@@ -272,7 +273,8 @@ void InfoPage::refreshInfoWidget()
pos++;
ui->paramLayout->addWidget(new QLabel("Advanced"), pos, 0, 1, 1);
pos++;
- for (auto key : m_info_params_advanced.keys()) {
+ auto info_params_advanced = m_info_params_advanced.keys();
+ for (const auto &key : qAsConst(info_params_advanced)) {
QLabel *valueLbl = new QLabel(this);
QLabel *keyLbl = new QLabel(this);
@@ -503,7 +505,7 @@ void M2kInfoPage::refreshTemperature()
libm2k::context::contextClose(temp_m2k, false);
}
- refreshInfoWidget();
+ QMetaObject::invokeMethod(this,"refreshInfoWidget",Qt::QueuedConnection);
}
void M2kInfoPage::setCtx(iio_context *ctx)
diff --git a/src/info_page.hpp b/src/info_page.hpp
index b79b44d05b..19deef669d 100644
--- a/src/info_page.hpp
+++ b/src/info_page.hpp
@@ -68,8 +68,6 @@ class InfoPage : public QWidget
QPushButton *calibrateButton();
virtual void getDeviceInfo();
- void refreshInfoWidget();
-
void setConnectionStatus(bool);
bool supportsIdentification();
bool supportsCalibration();
@@ -81,7 +79,7 @@ public Q_SLOTS:
void readPreferences();
void identifyDevice(bool clicked = true);
void setStatusLabel(QLabel *lbl, QString str = "", QString color="white");
-
+ void refreshInfoWidget();
void setCalibrationStatusLabel(QString str = "", QString color = "white");
void setCalibrationInfoLabel(QString str = "", QString color = "white");
diff --git a/src/logicanalyzer/annotationdecoder.cpp b/src/logicanalyzer/annotationdecoder.cpp
index 8e9e7e77c9..ffcdf47df6 100644
--- a/src/logicanalyzer/annotationdecoder.cpp
+++ b/src/logicanalyzer/annotationdecoder.cpp
@@ -29,6 +29,8 @@ using namespace adiscope;
constexpr uint64_t MAX_CHUNK_SIZE = 256 * 1024;
+std::mutex AnnotationDecoder::g_sessionMutex;
+
void AnnotationDecoder::initDecoderChannels()
{
uint16_t id = 0;
@@ -243,6 +245,8 @@ void AnnotationDecoder::stopDecode()
m_decodeThread = nullptr;
}
+ std::lock_guard srd_lock(g_sessionMutex);
+
if (m_srdSession) {
srd_session_destroy(m_srdSession);
m_srdSession = nullptr;
@@ -371,6 +375,8 @@ void AnnotationDecoder::stackChanged()
{
stopDecode();
+ std::lock_guard srd_lock(g_sessionMutex);
+
if (srd_session_new(&m_srdSession) != SRD_OK) {
qDebug() << "srd_session_new returned error!";
} else {
@@ -495,6 +501,7 @@ void AnnotationDecoder::decodeProc()
memcpy(chunk.get(), data + start, chunkSize * sizeof(uint16_t));
// qDebug() << "send data!";
+ std::lock_guard srd_lock(g_sessionMutex);
if (srd_session_send(m_srdSession, start, stop, reinterpret_cast(
chunk.get()), chunkSize, sizeof(uint16_t)) != SRD_OK) {
diff --git a/src/logicanalyzer/annotationdecoder.h b/src/logicanalyzer/annotationdecoder.h
index f016089035..e136d2fe2f 100644
--- a/src/logicanalyzer/annotationdecoder.h
+++ b/src/logicanalyzer/annotationdecoder.h
@@ -85,6 +85,7 @@ class AnnotationDecoder
std::atomic m_decodeCanceled;
std::mutex m_newDataMutex;
std::condition_variable m_newDataCv;
+ static std::mutex g_sessionMutex;
std::queue> m_newDataQueue;
void initDecoderChannels();
};
diff --git a/src/logicanalyzer/logic_analyzer.cpp b/src/logicanalyzer/logic_analyzer.cpp
index 0607bc298c..0a820e86f2 100644
--- a/src/logicanalyzer/logic_analyzer.cpp
+++ b/src/logicanalyzer/logic_analyzer.cpp
@@ -80,7 +80,7 @@ LogicAnalyzer::LogicAnalyzer(struct iio_context *ctx, adiscope::Filter *filt,
bool offline_mode_):
LogicTool(nullptr, toolMenuItem, new LogicAnalyzer_API(this), "Logic Analyzer", parent),
ui(new Ui::LogicAnalyzer),
- m_plot(this, 16, 10),
+ m_plot(this, false, 16, 10),
m_bufferPreviewer(new DigitalBufferPreviewer(40, this)),
m_m2k_context(m2kOpen(ctx, "")),
m_m2kDigital(m_m2k_context->getDigital()),
@@ -1348,7 +1348,7 @@ void LogicAnalyzer::setupUi()
setDynamicProperty(cr_ui->btnLockHorizontal, "use_icon", true);
- auto cursorsPositionButton = new CustomPlotPositionButton(cr_ui->posSelect);
+ cursorsPositionButton = new CustomPlotPositionButton(cr_ui->posSelect);
connect(cursorsPositionButton, &CustomPlotPositionButton::positionChanged,
[=](CustomPlotPositionButton::ReadoutsPosition position){
m_plot.moveCursorReadouts(position);
@@ -1357,11 +1357,9 @@ void LogicAnalyzer::setupUi()
cursorsPositionButton->setPosition(CustomPlotPositionButton::ReadoutsPosition::bottomRight);
// Disable some options we don't need for this cursor settings panel
- cr_ui->btnNormalTrack->setVisible(false);
- cr_ui->label_3->setVisible(false);
- cr_ui->line_3->setVisible(false);
- cr_ui->vCursorsEnable->setVisible(false);
- cr_ui->btnLockVertical->setVisible(false);
+ cr_ui->widgteBtnNormalTrack->setVisible(false);
+ cr_ui->widgetVertical->setVisible(false);
+ cr_ui->widgetVerticalBtns->setVisible(false);
cr_ui->horizontalSlider->setMaximum(100);
cr_ui->horizontalSlider->setMinimum(0);
@@ -2330,11 +2328,12 @@ void LogicAnalyzer::setupTriggerMenu()
connect(ui->btnEnableExternalTrigger, &CustomSwitch::toggled, [=](bool on){
if (on) {
- int source = ui->externalTriggerSourceComboBox->currentIndex();
- int condition = ui->externalTriggerConditionComboBox->currentIndex();
+ const int source = ui->externalTriggerSourceComboBox->currentIndex();
+ const int condition = ui->externalTriggerConditionComboBox->currentIndex();
m_m2kDigital->getTrigger()->setDigitalSource(static_cast(source));
m_m2kDigital->getTrigger()->setDigitalExternalCondition(
static_cast((condition + 5) % 6));
+ ui->externalTriggerConditionComboBox->setDisabled(source);
} else {
m_m2kDigital->getTrigger()->setDigitalSource(M2K_TRIGGER_SOURCE_DIGITAL::SRC_NONE);
}
@@ -2408,7 +2407,7 @@ void LogicAnalyzer::restoreTriggerState()
void LogicAnalyzer::readPreferences()
{
qDebug() << "reading preferences!!!!";
- for (GenericLogicPlotCurve *curve : m_plotCurves) {
+ for (GenericLogicPlotCurve *curve : qAsConst(m_plotCurves)) {
if (curve->getType() == LogicPlotCurveType::Data) {
LogicDataCurve *ldc = dynamic_cast(curve);
if (!ldc) {
@@ -2433,7 +2432,8 @@ void LogicAnalyzer::exportData()
bool noChannelEnabled = true;
m_exportConfig = m_exportSettings->getExportConfig();
- for (auto x : m_exportConfig.keys()) {
+ auto keys = m_exportConfig.keys();
+ for (auto x : qAsConst(keys)) {
if(m_exportConfig[x]) {
noChannelEnabled = false;
break;
@@ -2460,20 +2460,24 @@ void LogicAnalyzer::exportData()
// Check the selected file type
if (selectedFilter != "") {
if(selectedFilter.contains("comma", Qt::CaseInsensitive)) {
- fileName += ".csv";
separator = ",";
}
if(selectedFilter.contains("tab", Qt::CaseInsensitive)) {
- fileName += ".txt";
separator = "\t";
}
if(selectedFilter.contains("Change Dump", Qt::CaseInsensitive)) {
endRow = " $end\n";
startRow = "$";
- fileName += ".vcd";
}
}
+ if (fileName.split(".").size() <= 1) {
+ // file name w/o extension. Let's append it
+ QString ext = selectedFilter.split(".")[1].split(")")[0];
+ fileName += "." + ext;
+ }
+
+
if (separator != "") {
done = exportTabCsv(separator, fileName);
diff --git a/src/logicanalyzer/logic_analyzer.h b/src/logicanalyzer/logic_analyzer.h
index 2f9ac9722b..13cb0e4b41 100644
--- a/src/logicanalyzer/logic_analyzer.h
+++ b/src/logicanalyzer/logic_analyzer.h
@@ -149,6 +149,7 @@ private Q_SLOTS:
// TODO: consisten naming (m_ui, m_crUi)
Ui::LogicAnalyzer *ui;
Ui::CursorsSettings *cr_ui;
+ CustomPlotPositionButton *cursorsPositionButton;
QList m_menuOrder;
QQueue> m_menuButtonActions;
diff --git a/src/logicanalyzer/logicanalyzer_api.cpp b/src/logicanalyzer/logicanalyzer_api.cpp
index 3629448e62..b3ef6a67af 100644
--- a/src/logicanalyzer/logicanalyzer_api.cpp
+++ b/src/logicanalyzer/logicanalyzer_api.cpp
@@ -24,6 +24,7 @@
#include "annotationcurve.h"
#include "annotationdecoder.h"
+#include "ui_cursors_settings.h"
#include
#include
@@ -176,7 +177,7 @@ QList>> LogicAnalyzer_API::getAssignedDecoderChannels() co
}
auto stack = annCurve->getDecoderStack();
QList> assignedChannels;
- for (std::shared_ptr decoder : stack) {
+ for (const std::shared_ptr &decoder : stack) {
for (const auto &ch : decoder->channels()) {
if (ch->assigned_signal) {
assignedChannels.push_back({ch->id, ch->bit_id});
@@ -261,7 +262,7 @@ QList LogicAnalyzer_API::getDecoderSettings() const
QJsonObject obj;
QJsonArray propArray;
- for(auto p : bindings[i]->properties()) {
+ for(const auto &p : bindings[i]->properties()) {
QJsonObject propObj;
QString prop_name(p->name());
@@ -344,7 +345,7 @@ void LogicAnalyzer_API::setDecoderSettings(const QList &decoderSett
}
QJsonArray propArray = obj["properties"].toArray();
- for (auto propRef : propArray) {
+ for (const auto &propRef : qAsConst(propArray)) {
auto prop = propRef.toObject();
for(auto p : binding->properties())
{
@@ -403,7 +404,69 @@ QString LogicAnalyzer_API::getNotes()
{
return m_logic->ui->instrumentNotes->getNotes();
}
+
void LogicAnalyzer_API::setNotes(QString str)
{
m_logic->ui->instrumentNotes->setNotes(str);
}
+
+bool LogicAnalyzer_API::hasCursors() const
+{
+ return m_logic->ui->cursorsBox->isChecked();
+}
+
+void LogicAnalyzer_API::setCursors(bool en)
+{
+ m_logic->ui->cursorsBox->setChecked(en);
+}
+
+int LogicAnalyzer_API::getCursorsPosition() const
+{
+ if (!hasCursors()) {
+ return 0;
+ }
+ auto currentPos = m_logic->m_plot.getCursorReadouts()->getCurrentPosition();
+ switch (currentPos) {
+ case CustomPlotPositionButton::ReadoutsPosition::topLeft:
+ default:
+ return 0;
+ case CustomPlotPositionButton::ReadoutsPosition::topRight:
+ return 1;
+ case CustomPlotPositionButton::ReadoutsPosition::bottomLeft:
+ return 2;
+ case CustomPlotPositionButton::ReadoutsPosition::bottomRight:
+ return 3;
+ }
+ return 2;
+}
+
+void LogicAnalyzer_API::setCursorsPosition(int val)
+{
+ if (!hasCursors()) {
+ return;
+ }
+ enum CustomPlotPositionButton::ReadoutsPosition types[] = {
+ CustomPlotPositionButton::ReadoutsPosition::topLeft,
+ CustomPlotPositionButton::ReadoutsPosition::topRight,
+ CustomPlotPositionButton::ReadoutsPosition::bottomLeft,
+ CustomPlotPositionButton::ReadoutsPosition::bottomRight
+ };
+ m_logic->cursorsPositionButton->setPosition(types[val]);
+ m_logic->m_plot.replot();
+}
+
+int LogicAnalyzer_API::getCursorsTransparency() const
+{
+ if (!hasCursors()) {
+ return 0;
+ }
+ return m_logic->cr_ui->horizontalSlider->value();
+}
+
+void LogicAnalyzer_API::setCursorsTransparency(int val)
+{
+ if (!hasCursors()) {
+ return;
+ }
+ m_logic->cr_ui->horizontalSlider->setValue(val);
+}
diff --git a/src/logicanalyzer/logicanalyzer_api.h b/src/logicanalyzer/logicanalyzer_api.h
index fcef82e67c..25f76ba047 100644
--- a/src/logicanalyzer/logicanalyzer_api.h
+++ b/src/logicanalyzer/logicanalyzer_api.h
@@ -31,6 +31,13 @@ class LogicAnalyzer_API : public ApiObject
{
Q_OBJECT
+ /*cursor settings*/
+ Q_PROPERTY(bool cursors READ hasCursors WRITE setCursors);
+ Q_PROPERTY(int cursors_position READ getCursorsPosition
+ WRITE setCursorsPosition)
+ Q_PROPERTY(int cursors_transparency READ getCursorsTransparency
+ WRITE setCursorsTransparency)
+
/* sweep settings */
Q_PROPERTY(bool streamOneShot READ getStreamOrOneShot WRITE setStreamOrOneShot)
Q_PROPERTY(double sampleRate READ getSampleRate WRITE setSampleRate)
@@ -124,6 +131,15 @@ class LogicAnalyzer_API : public ApiObject
private:
logic::LogicAnalyzer *m_logic;
+
+ bool hasCursors() const;
+ void setCursors(bool en);
+
+ int getCursorsPosition() const;
+ void setCursorsPosition(int val);
+
+ int getCursorsTransparency() const;
+ void setCursorsTransparency(int val);
};
}
}
diff --git a/src/main.cpp b/src/main.cpp
index 977452b3f0..2518826167 100644
--- a/src/main.cpp
+++ b/src/main.cpp
@@ -147,8 +147,6 @@ int main(int argc, char **argv)
myappTranslator.load(languageFileName);
app.installTranslator(&myappTranslator);
- ToolLauncher launcher(prevCrashDump);
-
ScopyColorEditor *colorEditor = new ScopyColorEditor(&app);
colorEditor->setVisible(false);
@@ -161,6 +159,7 @@ int main(int argc, char **argv)
app.setStyleSheet(colorEditor->getStyleSheet());
}
+ ToolLauncher launcher(prevCrashDump);
launcher.getPrefPanel()->setColorEditor(colorEditor);
bool nogui = parser.isSet("nogui");
diff --git a/src/network_analyzer.cpp b/src/network_analyzer.cpp
index 933aa00390..bb223ed04c 100644
--- a/src/network_analyzer.cpp
+++ b/src/network_analyzer.cpp
@@ -181,6 +181,8 @@ NetworkAnalyzer::NetworkAnalyzer(struct iio_context *ctx, Filter *filt,
m_dac_nb_channels(0),
d_cursorsEnabled(false),
m_stop(true),
+ m_dBgraph(this, true),
+ m_phaseGraph(this, true),
wheelEventGuard(nullptr), wasChecked(false),
justStarted(false),
iterationsThreadCanceled(false), iterationsThreadReady(false),
@@ -418,14 +420,52 @@ NetworkAnalyzer::NetworkAnalyzer(struct iio_context *ctx, Filter *filt,
connect(ui->cbLineThickness,SIGNAL(currentIndexChanged(int)),ui->xygraph,
SLOT(setThickness(int)));
- d_bottomHandlesArea = new HorizHandlesArea(this);
- d_bottomHandlesArea->setMinimumHeight(50);
+ m_phaseGraph.setVertCursorsHandleEnabled(false);
+
+ ui->gridLayout_plots->addWidget(bufferPreviewer, 0, 1, 1, 1);
+ ui->gridLayout_plots->addWidget(ui->statusWidget, 1, 1, 1, 1);
+ ui->gridLayout_plots->addWidget(m_dBgraph.rightHandlesArea(), 0, 2, 6, 1);
+ ui->gridLayout_plots->addWidget(m_dBgraph.topHandlesArea(), 2, 0, 1, 2);
+ ui->gridLayout_plots->addWidget(m_dBgraph.leftHandlesArea(), 3, 0, 1, 1);
+ ui->gridLayout_plots->addWidget(&m_dBgraph, 3, 1, 1, 1);
+
+ ui->gridLayout_plots->addWidget(m_phaseGraph.topHandlesArea(), 4, 0, 1, 2);
+ ui->gridLayout_plots->addWidget(m_phaseGraph.leftHandlesArea(), 5, 0, 1, 1);
+ ui->gridLayout_plots->addWidget(&m_phaseGraph, 5, 1, 1, 1);
+
+ ui->gridLayout_plots->addWidget(m_dBgraph.bottomHandlesArea(), 6, 0, 1, 3);
+
+ m_phaseGraph.enableXaxisLabels();
+ m_dBgraph.enableXaxisLabels();
+
+ m_phaseGraph.enableYaxisLabels();
+ m_dBgraph.enableYaxisLabels();
+
+ connect(m_dBgraph.vBar1(), static_cast(&HorizDebugSymbol::positionChanged),
+ [=](double x)
+ {
+ m_phaseGraph.vBar1()->setPosition(x);
+ });
+
+ connect(m_dBgraph.vBar2(), static_cast(&HorizDebugSymbol::positionChanged),
+ [=](double x)
+ {
+ m_phaseGraph.vBar2()->setPosition(x);
+ });
+
+ //The inverse connection is neccesary for the change of the boundaries for sweep
+ connect(m_phaseGraph.vBar1(), static_cast(&HorizDebugSymbol::positionChanged),
+ [=](double x)
+ {
+ m_dBgraph.vBar1()->setPosition(x);
+ });
+
+ connect(m_phaseGraph.vBar2(), static_cast(&HorizDebugSymbol::positionChanged),
+ [=](double x)
+ {
+ m_dBgraph.vBar2()->setPosition(x);
+ });
- ui->gridLayout_plots->addWidget(bufferPreviewer, 0, 0, 1, 1);
- ui->gridLayout_plots->addWidget(ui->statusWidget, 1, 0, 1, 1);
- ui->gridLayout_plots->addWidget(&m_dBgraph, 2, 0, 1, 1);
- ui->gridLayout_plots->addWidget(&m_phaseGraph, 3, 0, 1, 1);
- ui->gridLayout_plots->addWidget(d_bottomHandlesArea, 4, 0, 1, 1);
ui->currentFrequencyLabel->setVisible(false);
ui->currentSampleLabel->setVisible(false);
@@ -435,16 +475,10 @@ NetworkAnalyzer::NetworkAnalyzer(struct iio_context *ctx, Filter *filt,
QPixmap(":/icons/time_trigger_handle.svg"),
QPixmap(":/icons/time_trigger_left.svg"),
QPixmap(":/icons/time_trigger_right.svg"),
- d_bottomHandlesArea);
+ m_dBgraph.bottomHandlesArea());
d_frequencyHandle->setPen(QPen(QColor(74, 100, 255), 2, Qt::SolidLine));
d_frequencyHandle->setVisible(true);
-
- d_hCursorHandle1 = new PlotLineHandleH(
- QPixmap(":/icons/h_cursor_handle.svg"),
- d_bottomHandlesArea);
- d_hCursorHandle2 = new PlotLineHandleH(
- QPixmap(":/icons/h_cursor_handle.svg"),
- d_bottomHandlesArea);
+ d_frequencyHandle->triggerMove();
ui->nicholsgraph->enableFrequencyBar(false);
@@ -493,26 +527,6 @@ NetworkAnalyzer::NetworkAnalyzer(struct iio_context *ctx, Filter *filt,
connect(&m_dBgraph, &dBgraph::frequencySelected,
bufferPreviewer, &NetworkAnalyzerBufferViewer::selectBuffers);
- QPen cursorsLinePen = QPen(QColor(155,155,155),1,Qt::DashLine);
- d_hCursorHandle1->setPen(cursorsLinePen);
- d_hCursorHandle2->setPen(cursorsLinePen);
- d_hCursorHandle1->setVisible(false);
- d_hCursorHandle2->setVisible(false);
-
- connect(&m_dBgraph,SIGNAL(VBar1PixelPosChanged(int)),
- SLOT(onVbar1PixelPosChanged(int)));
- connect(&m_dBgraph,SIGNAL(VBar2PixelPosChanged(int)),
- SLOT(onVbar2PixelPosChanged(int)));
-
- connect(d_hCursorHandle1, SIGNAL(positionChanged(int)),&m_dBgraph,
- SLOT(onCursor1PositionChanged(int)));
- connect(d_hCursorHandle2, SIGNAL(positionChanged(int)),&m_dBgraph,
- SLOT(onCursor2PositionChanged(int)));
- connect(d_hCursorHandle1, SIGNAL(positionChanged(int)),&m_phaseGraph,
- SLOT(onCursor1PositionChanged(int)));
- connect(d_hCursorHandle2, SIGNAL(positionChanged(int)),&m_phaseGraph,
- SLOT(onCursor2PositionChanged(int)));
-
startStopRange->setStopValue((double) max_samplerate / 3.0 - 1.0);
connect(samplesCount, SIGNAL(valueChanged(double)),
@@ -573,6 +587,20 @@ NetworkAnalyzer::NetworkAnalyzer(struct iio_context *ctx, Filter *filt,
m_phaseGraph.setCursorReadoutsTransparency(value);
});
+ setDynamicProperty(ui->btnLockHorizontal, "use_icon", true);
+
+ connect(ui->btnLockHorizontal, &QPushButton::toggled,
+ &m_dBgraph, &dBgraph::setHorizCursorsLocked);
+
+ connect(ui->btnLockHorizontal, &QPushButton::toggled,
+ &m_phaseGraph, &dBgraph::setHorizCursorsLocked);
+
+ connect(ui->hCursorsEnable, &QPushButton::toggled,
+ &m_dBgraph, &dBgraph::toggleCursors);
+
+ connect(ui->hCursorsEnable, &QPushButton::toggled,
+ &m_phaseGraph, &dBgraph::toggleCursors);
+
connect(ui->posSelect, &CustomPlotPositionButton::positionChanged,
[=](CustomPlotPositionButton::ReadoutsPosition position) {
m_dBgraph.moveCursorReadouts(position);
@@ -787,7 +815,7 @@ void NetworkAnalyzer::computeIterations()
// it is safe to modify without using a lock
iterationsThreadCanceled = false;
iterationsThreadReady = false;
- iterationsThread = new boost::thread(boost::bind(&NetworkAnalyzer::computeFrequencyArray, this));
+ iterationsThread = new std::thread(boost::bind(&NetworkAnalyzer::computeFrequencyArray, this));
}
void NetworkAnalyzer::setMinimumDistanceBetween(SpinBoxA *min, SpinBoxA *max,
@@ -838,17 +866,6 @@ void NetworkAnalyzer::rightMenuFinished(bool opened)
void NetworkAnalyzer::showEvent(QShowEvent *event)
{
- d_bottomHandlesArea->setLeftPadding(m_dBgraph.axisWidget(QwtAxisId(
- QwtPlot::yLeft, 0))->width()
- + ui->gridLayout_plots->margin()
- + ui->widgetPlotContainer->layout()->margin() + 1);
- int rightPadding = 0;
- rightPadding = rightPadding + m_dBgraph.width()
- - m_dBgraph.axisWidget(QwtPlot::yLeft)->width() - m_dBgraph.canvas()->width()
- - ui->widgetPlotContainer->layout()->margin() ;
- d_bottomHandlesArea->setRightPadding(rightPadding);
- d_hCursorHandle1->setPosition(d_hCursorHandle1->pos().x());
- d_hCursorHandle2->setPosition(d_hCursorHandle2->pos().x());
Tool::showEvent(event);
}
@@ -1744,16 +1761,6 @@ void NetworkAnalyzer::configHwForNetworkAnalyzing()
}
}
-void NetworkAnalyzer::onVbar1PixelPosChanged(int pos)
-{
- d_hCursorHandle1->setPositionSilenty(pos);
-}
-
-void NetworkAnalyzer::onVbar2PixelPosChanged(int pos)
-{
- d_hCursorHandle2->setPositionSilenty(pos);
-}
-
void NetworkAnalyzer::toggleCursors(bool en)
{
if (!en) {
@@ -1764,11 +1771,8 @@ void NetworkAnalyzer::toggleCursors(bool en)
d_cursorsEnabled = en;
m_dBgraph.toggleCursors(en);
m_phaseGraph.toggleCursors(en);
- d_hCursorHandle1->setVisible(en);
- d_hCursorHandle2->setVisible(en);
ui->btnCursors->setEnabled(en);
}
-
}
void NetworkAnalyzer::readPreferences()
diff --git a/src/network_analyzer.hpp b/src/network_analyzer.hpp
index 854ee1d7f2..26a699645d 100644
--- a/src/network_analyzer.hpp
+++ b/src/network_analyzer.hpp
@@ -148,7 +148,7 @@ class NetworkAnalyzer : public Tool
QVector iterations;
QVector iterationStats;
- boost::thread *iterationsThread;
+ std::thread *iterationsThread;
bool iterationsThreadCanceled;
bool iterationsThreadReady;
@@ -197,8 +197,6 @@ class NetworkAnalyzer : public Tool
bool justStarted;
bool autoAdjustGain;
- PlotLineHandleH *d_hCursorHandle1;
- PlotLineHandleH *d_hCursorHandle2;
FreePlotLineHandleH *d_frequencyHandle;
bool d_cursorsEnabled;
@@ -217,8 +215,6 @@ class NetworkAnalyzer : public Tool
void setMinimumDistanceBetween(SpinBoxA *min, SpinBoxA *max, double distance);
- HorizHandlesArea *d_bottomHandlesArea;
-
QQueue> menuButtonActions;
MouseWheelWidgetGuard *wheelEventGuard;
@@ -271,8 +267,6 @@ private Q_SLOTS:
void _saveChannelBuffers(double frequency, double sample_rate, std::vector data1, std::vector data2);
void toggleCursors(bool en);
- void onVbar1PixelPosChanged(int pos);
- void onVbar2PixelPosChanged(int pos);
void readPreferences();
void onGraphIndexChanged(int);
void on_btnExport_clicked();
diff --git a/src/network_analyzer_api.cpp b/src/network_analyzer_api.cpp
index 97e8bc6c13..1b953f96fb 100644
--- a/src/network_analyzer_api.cpp
+++ b/src/network_analyzer_api.cpp
@@ -163,7 +163,7 @@ bool NetworkAnalyzer_API::getCursors() const
void NetworkAnalyzer_API::setCursors(bool enabled)
{
- net->ui->boxCursors->setChecked(enabled);
+ net->ui->boxCursors->setChecked(enabled);
}
bool NetworkAnalyzer_API::running() const
@@ -178,58 +178,59 @@ void NetworkAnalyzer_API::run(bool enabled)
int NetworkAnalyzer_API::getCursorsPosition() const
{
- if (!net->ui->boxCursors->isChecked()) {
- return 0;
- }
- auto currentPos = net->m_dBgraph.getCursorReadoutCurrentPosition();
- switch (currentPos) {
- case CustomPlotPositionButton::ReadoutsPosition::topLeft:
- default:
- return 0;
- case CustomPlotPositionButton::ReadoutsPosition::topRight:
- return 1;
- case CustomPlotPositionButton::ReadoutsPosition::bottomLeft:
- return 2;
- case CustomPlotPositionButton::ReadoutsPosition::bottomRight:
- return 3;
- }
+ if (!net->ui->boxCursors->isChecked()) {
+ return 0;
+ }
+ auto currentPos = net->m_dBgraph.d_cursorReadouts->getCurrentPosition();
+ switch (currentPos) {
+ case CustomPlotPositionButton::ReadoutsPosition::topLeft:
+ default:
+ return 0;
+ case CustomPlotPositionButton::ReadoutsPosition::topRight:
+ return 1;
+ case CustomPlotPositionButton::ReadoutsPosition::bottomLeft:
+ return 2;
+ case CustomPlotPositionButton::ReadoutsPosition::bottomRight:
+ return 3;
+ }
+ return 2;
}
void NetworkAnalyzer_API::setCursorsPosition(int val)
{
- if (!net->ui->boxCursors->isChecked()) {
- return;
- }
- enum CustomPlotPositionButton::ReadoutsPosition types[] = {
- CustomPlotPositionButton::ReadoutsPosition::topLeft,
- CustomPlotPositionButton::ReadoutsPosition::topRight,
- CustomPlotPositionButton::ReadoutsPosition::bottomLeft,
- CustomPlotPositionButton::ReadoutsPosition::bottomRight
- };
- net->ui->posSelect->setPosition(types[val]);
- net->m_dBgraph.moveCursorReadouts(types[val]);
- net->m_dBgraph.replot();
- net->m_phaseGraph.moveCursorReadouts(types[val]);
- net->m_phaseGraph.replot();
+ if (!net->ui->boxCursors->isChecked()) {
+ return;
+ }
+ enum CustomPlotPositionButton::ReadoutsPosition types[] = {
+ CustomPlotPositionButton::ReadoutsPosition::topLeft,
+ CustomPlotPositionButton::ReadoutsPosition::topRight,
+ CustomPlotPositionButton::ReadoutsPosition::bottomLeft,
+ CustomPlotPositionButton::ReadoutsPosition::bottomRight
+ };
+ net->ui->posSelect->setPosition(types[val]);
+ net->m_dBgraph.moveCursorReadouts(types[val]);
+ net->m_dBgraph.replot();
+ net->m_phaseGraph.moveCursorReadouts(types[val]);
+ net->m_phaseGraph.replot();
}
int NetworkAnalyzer_API::getCursorsTransparency() const
{
- if (!net->ui->boxCursors->isChecked()) {
- return 0;
- }
- return net->ui->horizontalSlider->value();
+ if (!net->ui->boxCursors->isChecked()) {
+ return 0;
+ }
+ return net->ui->horizontalSlider->value();
}
void NetworkAnalyzer_API::setCursorsTransparency(int val)
{
- if (!net->ui->boxCursors->isChecked()) {
- return;
- }
- net->ui->horizontalSlider->setValue(val);
- net->ui->transLabel->setText(tr("Transparency ") + QString::number(val) + "%");
- net->m_dBgraph.setCursorReadoutsTransparency(val);
- net->m_phaseGraph.setCursorReadoutsTransparency(val);
+ if (!net->ui->boxCursors->isChecked()) {
+ return;
+ }
+ net->ui->horizontalSlider->setValue(val);
+ net->ui->transLabel->setText(tr("Transparency ") + QString::number(val) + "%");
+ net->m_dBgraph.setCursorReadoutsTransparency(val);
+ net->m_phaseGraph.setCursorReadoutsTransparency(val);
}
diff --git a/src/network_analyzer_api.hpp b/src/network_analyzer_api.hpp
index 5451f4fda2..5d927549ae 100644
--- a/src/network_analyzer_api.hpp
+++ b/src/network_analyzer_api.hpp
@@ -103,6 +103,7 @@ class NetworkAnalyzer_API : public ApiObject
int getLineThickness() const;
void setLineThickness(int index);
+
int getCursorsPosition() const;
void setCursorsPosition(int val);
diff --git a/src/osc_export_settings.cpp b/src/osc_export_settings.cpp
index 2d4198ac94..e56eeee2eb 100644
--- a/src/osc_export_settings.cpp
+++ b/src/osc_export_settings.cpp
@@ -134,7 +134,9 @@ void ExportSettings::setExportConfig(QMap config)
{
QStandardItemModel *model =
static_cast(exportChannels->model());
- for (int key : config.keys()) {
+
+ auto keys = config.keys();
+ for (int key : qAsConst(keys)) {
model->item(key, 1)->setData(QVariant((int) config[key]),
Qt::EditRole);
}
diff --git a/src/oscilloscope.cpp b/src/oscilloscope.cpp
index 53e7708b97..b7be9c4057 100644
--- a/src/oscilloscope.cpp
+++ b/src/oscilloscope.cpp
@@ -107,7 +107,7 @@ Oscilloscope::Oscilloscope(struct iio_context *ctx, Filter *filt,
ui(new Ui::Oscilloscope),
trigger_settings(m_m2k_analogin),
measure_settings(nullptr),
- plot(this, 16, 10),
+ plot(this, false, 16, 10),
fft_plot(nb_channels, this),
xy_plot(nb_channels / 2, this),
hist_plot(nb_channels, this),
@@ -720,7 +720,9 @@ Oscilloscope::Oscilloscope(struct iio_context *ctx, Filter *filt,
}
auto max_elem = max_element(probe_attenuation.begin(), probe_attenuation.begin() + nb_channels);
- for (auto rail : math_rails.values()) {
+
+ auto const values = math_rails.values();
+ for (auto rail : values) {
rail->set_lo(MIN_MATH_RANGE);
rail->set_hi(MAX_MATH_RANGE);
}
@@ -1936,7 +1938,9 @@ void Oscilloscope::btnExport_clicked(){
fileName += "." + ext;
}
bool atleastOneChannelEnabled = false;
- for (auto x : exportConfig.keys())
+
+ auto keys = exportConfig.keys();
+ for (auto x : qAsConst(keys))
if (exportConfig[x]){
atleastOneChannelEnabled = true;
break;
@@ -2193,7 +2197,8 @@ void Oscilloscope::create_add_channel_panel()
if (tabWidget->currentIndex() != 0) {
QMap import_map = importSettings->getExportConfig();
- for (int key : import_map.keys()) {
+ auto keys = import_map.keys();
+ for (int key : qAsConst(keys)) {
if (import_map[key]) {
add_ref_waveform(key);
}
@@ -2979,7 +2984,7 @@ void Oscilloscope::onXY_view_toggled(bool visible)
adc_samp_conv_block, i));
}
}
- for(auto p : math_sinks) {
+ for(const auto &p : qAsConst(math_sinks)) {
auto math = p.first;
xy_channels.push_back(QPair(
math, 0));
diff --git a/src/oscilloscope_api.cpp b/src/oscilloscope_api.cpp
index f59e483b27..a5323e4323 100644
--- a/src/oscilloscope_api.cpp
+++ b/src/oscilloscope_api.cpp
@@ -115,42 +115,42 @@ void Oscilloscope_API::setVerticalCursors(bool en)
double Oscilloscope_API::cursorV1() const
{
- return osc->plot.value_v1;
+ return osc->plot.value_v1;
}
double Oscilloscope_API::cursorV2() const
{
- return osc->plot.value_v2;
+ return osc->plot.value_v2;
}
double Oscilloscope_API::cursorH1() const
{
- return osc->plot.value_h1;
+ return osc->plot.value_h1;
}
double Oscilloscope_API::cursorH2() const
{
- return osc->plot.value_h2;
+ return osc->plot.value_h2;
}
void Oscilloscope_API::setCursorV1(double val)
{
- osc->plot.d_vBar1->setPosition(val);
+ osc->plot.d_vBar1->setPosition(val);
}
void Oscilloscope_API::setCursorV2(double val)
{
- osc->plot.d_vBar2->setPosition(val);
+ osc->plot.d_vBar2->setPosition(val);
}
void Oscilloscope_API::setCursorH1(double val)
{
- osc->plot.d_hBar1->setPosition(val);
+ osc->plot.d_hBar1->setPosition(val);
}
void Oscilloscope_API::setCursorH2(double val)
{
- osc->plot.d_hBar2->setPosition(val);
+ osc->plot.d_hBar2->setPosition(val);
}
bool Oscilloscope_API::autoTrigger() const
@@ -585,6 +585,7 @@ int Oscilloscope_API::getCursorsPosition() const
case CustomPlotPositionButton::ReadoutsPosition::bottomRight:
return 3;
}
+ return 3;
}
void Oscilloscope_API::setCursorsPosition(int val)
@@ -652,7 +653,7 @@ QVariantList Oscilloscope_API::getChannels()
{
QVariantList list;
- for (Channel_API *each : osc->channels_api) {
+ for (Channel_API *each : qAsConst(osc->channels_api)) {
list.append(QVariant::fromValue(each));
}
return list;
diff --git a/src/oscilloscope_plot.cpp b/src/oscilloscope_plot.cpp
index abce26dc2b..7276a6f85d 100644
--- a/src/oscilloscope_plot.cpp
+++ b/src/oscilloscope_plot.cpp
@@ -40,9 +40,9 @@ using namespace adiscope;
/*
* OscilloscopePlot class
*/
-OscilloscopePlot::OscilloscopePlot(QWidget *parent,
- unsigned int xNumDivs, unsigned int yNumDivs):
- TimeDomainDisplayPlot(parent, xNumDivs, yNumDivs)
+OscilloscopePlot::OscilloscopePlot(QWidget *parent, bool isdBgraph,
+ unsigned int xNumDivs, unsigned int yNumDivs):
+ TimeDomainDisplayPlot(parent, isdBgraph, xNumDivs, yNumDivs)
{
setYaxisUnit("V");
@@ -59,29 +59,21 @@ OscilloscopePlot::~OscilloscopePlot()
/*
* CapturePlot class
*/
-CapturePlot::CapturePlot(QWidget *parent,
+CapturePlot::CapturePlot(QWidget *parent, bool isdBgraph,
unsigned int xNumDivs, unsigned int yNumDivs):
- OscilloscopePlot(parent, xNumDivs, yNumDivs),
+ OscilloscopePlot(parent, isdBgraph, xNumDivs, yNumDivs),
d_triggerAEnabled(false),
d_triggerBEnabled(false),
- d_selected_channel(-1),
d_measurementsEnabled(false),
- d_cursorReadoutsVisible(false),
d_bufferSizeLabelVal(0),
d_sampleRateLabelVal(1.0),
d_labelsEnabled(false),
d_timeTriggerMinValue(-1),
d_timeTriggerMaxValue(1),
- d_trackMode(false),
- horizCursorsLocked(false),
- vertCursorsLocked(false),
- d_horizCursorsEnabled(false),
- d_vertCursorsEnabled(false),
d_bonusWidth(0),
d_gatingEnabled(false),
m_conversion_function(nullptr),
d_startedGrouping(false),
- d_bottomHandlesArea(nullptr),
d_xAxisInterval{0.0, 0.0},
d_currentHandleInitPx(30),
d_maxBufferError(nullptr)
@@ -98,42 +90,21 @@ CapturePlot::CapturePlot(QWidget *parent,
d_timeTriggerActiveLinePen = QPen(QColor(74, 100, 255), 2, Qt::SolidLine);
/* End of: Initial colors scheme */
- markerIntersection1 = new QwtPlotMarker();
- markerIntersection2 = new QwtPlotMarker();
- markerIntersection1->setSymbol(new QwtSymbol(
- QwtSymbol::Ellipse, QColor(237, 28, 36),
- QPen(QColor(255, 255 ,255, 140), 2, Qt::SolidLine),
- QSize(5, 5)));
- markerIntersection2->setSymbol(new QwtSymbol(
- QwtSymbol::Ellipse, QColor(237, 28, 36),
- QPen(QColor(255, 255 ,255, 140), 2, Qt::SolidLine),
- QSize(5, 5)));
-
- d_symbolCtrl = new SymbolController(this);
-
setHorizUnitsPerDiv(1E-6);
zoomBaseUpdate();
- /* Adjacent areas (top/bottom/left/right) */
+ /* Adjacent areas */
d_topWidget = new QWidget(this);
- d_topHandlesArea = new GateHandlesArea(this->canvas());
- d_bottomHandlesArea = new HorizHandlesArea(this->canvas());
- d_leftHandlesArea = new VertHandlesArea(this->canvas());
- d_rightHandlesArea = new VertHandlesArea(this->canvas());
+ d_topGateHandlesArea = new GateHandlesArea(this->canvas());
d_topWidget->setStyleSheet("QWidget {background-color: transparent}");
d_topWidget->setMinimumHeight(50);
- d_topHandlesArea->setMinimumHeight(20);
- d_topHandlesArea->setLargestChildWidth(80);
- d_bottomHandlesArea->setMinimumHeight(50);
+ d_topGateHandlesArea->setMinimumHeight(20);
+ d_topGateHandlesArea->setLargestChildWidth(80);
d_leftHandlesArea->setMinimumWidth(50);
- d_rightHandlesArea->setMinimumWidth(50);
- d_bottomHandlesArea->setLargestChildWidth(60);
- d_rightHandlesArea->setLargestChildHeight(60);
d_leftHandlesArea->setMinimumHeight(this->minimumHeight());
- d_rightHandlesArea->setMinimumHeight(this->minimumHeight());
- d_topHandlesArea->hide();
+ d_topGateHandlesArea->hide();
/* Add content to the top area of the plot */
// Time Base
d_timeBaseLabel = new QLabel(this);
@@ -207,9 +178,9 @@ CapturePlot::CapturePlot(QWidget *parent,
/* When bar position changes due to plot resizes update the handle */
connect(d_timeTriggerBar, &VertBar::pixelPositionChanged,
[=](int pos) {
- updateHandleAreaPadding(d_labelsEnabled);
- d_timeTriggerHandle->setPositionSilenty(pos);
- });
+ updateHandleAreaPadding(d_labelsEnabled);
+ d_timeTriggerHandle->setPositionSilenty(pos);
+ });
connect(d_timeTriggerHandle, &FreePlotLineHandleH::positionChanged,
d_timeTriggerBar, &VertBar::setPixelPosition);
@@ -292,35 +263,16 @@ CapturePlot::CapturePlot(QWidget *parent,
connect(d_levelTriggerBHandle, SIGNAL(grabbedChanged(bool)),
SLOT(onTriggerBHandleGrabbed(bool)));
-
- /* Measurement Cursors */
- d_vCursorHandle1 = new PlotLineHandleV(
- QPixmap(":/icons/v_cursor_handle.svg"),
- d_rightHandlesArea);
- d_vCursorHandle2 = new PlotLineHandleV(
- QPixmap(":/icons/v_cursor_handle.svg"),
- d_rightHandlesArea);
- d_hCursorHandle1 = new PlotLineHandleH(
- QPixmap(":/icons/h_cursor_handle.svg"),
- d_bottomHandlesArea);
- d_hCursorHandle2 = new PlotLineHandleH(
- QPixmap(":/icons/h_cursor_handle.svg"),
- d_bottomHandlesArea);
-
/* Measurement gate cursors */
d_hGatingHandle1 = new PlotGateHandle(
QPixmap(":/icons/gate_handle.svg"),
- d_topHandlesArea);
+ d_topGateHandlesArea);
d_hGatingHandle2 = new PlotGateHandle(
QPixmap(":/icons/gate_handle.svg"),
- d_topHandlesArea);
+ d_topGateHandlesArea);
d_hGatingHandle1->setCenterLeft(false);
- d_vBar1 = new VertBar(this, true);
- d_vBar2 = new VertBar(this, true);
- d_hBar1 = new HorizBar(this, true);
- d_hBar2 = new HorizBar(this, true);
d_gateBar1 = new VertBar(this,true);
d_gateBar2 = new VertBar(this,true);
@@ -328,26 +280,9 @@ CapturePlot::CapturePlot(QWidget *parent,
d_gateBar1->setVisible(false);
d_gateBar2->setVisible(false);
- d_symbolCtrl->attachSymbol(d_vBar1);
- d_symbolCtrl->attachSymbol(d_vBar2);
- d_symbolCtrl->attachSymbol(d_hBar1);
- d_symbolCtrl->attachSymbol(d_hBar2);
-
d_symbolCtrl->attachSymbol(d_gateBar1);
d_symbolCtrl->attachSymbol(d_gateBar2);
- QPen cursorsLinePen = QPen(QColor(155, 155, 155), 1, Qt::DashLine);
- d_hBar1->setPen(cursorsLinePen);
- d_hBar2->setPen(cursorsLinePen);
- d_vBar1->setPen(cursorsLinePen);
- d_vBar2->setPen(cursorsLinePen);
-
- d_vCursorHandle1->setPen(cursorsLinePen);
- d_vCursorHandle2->setPen(cursorsLinePen);
- d_hCursorHandle1->setPen(cursorsLinePen);
- d_hCursorHandle2->setPen(cursorsLinePen);
-
-
/* gate bars */
QPen gatePen = QPen(QColor(255,255,255),1,Qt::SolidLine);
d_gateBar1->setPen(gatePen);
@@ -359,81 +294,9 @@ CapturePlot::CapturePlot(QWidget *parent,
d_hGatingHandle1->hide();
d_hGatingHandle2->hide();
- d_vCursorHandle1->hide();
- d_vCursorHandle2->hide();
- d_hCursorHandle1->hide();
- d_hCursorHandle2->hide();
-
- d_vBar1->setVisible(false);
- d_vBar2->setVisible(false);
- d_hBar1->setVisible(false);
- d_hBar2->setVisible(false);
-
- d_cursorReadouts = new CursorReadouts(this);
- d_cursorReadouts->setTopLeftStartingPoint(QPoint(8, 8));
- d_cursorReadouts->setTimeReadoutVisible(false);
- d_cursorReadouts->setVoltageReadoutVisible(false);
-
- /* Set initial values for cursors */
- double voltsPerDiv = VertUnitsPerDiv(activeVertAxis());
- double secPerDiv = HorizUnitsPerDiv();
-
- /* Update Cursor Readouts */
- onVoltageCursor1Moved(d_hBar1->plotCoord().y());
- onVoltageCursor2Moved(d_hBar2->plotCoord().y());
- onTimeCursor1Moved(d_vBar1->plotCoord().x());
- onTimeCursor2Moved(d_vBar2->plotCoord().x());
-
d_cursorMetricFormatter.setTwoDecimalMode(false);
d_cursorTimeFormatter.setTwoDecimalMode(false);
- /* When a handle position changes the bar follows */
- connect(d_vCursorHandle1, &PlotLineHandleV::positionChanged,
- [=](int value) {
-
- if (vertCursorsLocked) {
- int position2 = value - (pixelPosHandleVert1 - pixelPosHandleVert2);
- pixelPosHandleVert2 = position2;
- d_hBar2->setPixelPosition(position2);
- }
-
- pixelPosHandleVert1 = value;
- d_hBar1->setPixelPosition(value);
- });
- connect(d_vCursorHandle2, &PlotLineHandleV::positionChanged,
- [=](int value) {
-
- if (vertCursorsLocked) {
- int position1 = value + (pixelPosHandleVert1 - pixelPosHandleVert2);
- pixelPosHandleVert1 = position1;
- d_hBar1->setPixelPosition(position1);
- }
-
- pixelPosHandleVert2 = value;
- d_hBar2->setPixelPosition(value);
- });
-
- connect(d_hCursorHandle1, &PlotLineHandleH::positionChanged,
- [=](int value) {
- if (horizCursorsLocked) {
- int position2 = value - (pixelPosHandleHoriz1 - pixelPosHandleHoriz2);
- pixelPosHandleHoriz2 = position2;
- d_vBar2->setPixelPosition(position2);
- }
- pixelPosHandleHoriz1 = value;
- d_vBar1->setPixelPosition(value);
- });
- connect(d_hCursorHandle2, &PlotLineHandleH::positionChanged,
- [=](int value) {
- if (horizCursorsLocked) {
- int position1 = value + (pixelPosHandleHoriz1 - pixelPosHandleHoriz2);
- pixelPosHandleHoriz1 = position1;
- d_vBar1->setPixelPosition(position1);
- }
- pixelPosHandleHoriz2 = value;
- d_vBar2->setPixelPosition(value);
- });
-
connect(d_hGatingHandle1, &PlotLineHandleH::positionChanged,[=](int value){
d_hGatingHandle2->setOtherCursorPosition(d_hGatingHandle1->position());
/* make sure that the gate handles don't cross each other */
@@ -460,11 +323,7 @@ CapturePlot::CapturePlot(QWidget *parent,
}
});
- d_hBar1->setPosition(0 + voltsPerDiv);
- d_hBar2->setPosition(0 - voltsPerDiv);
- d_vBar1->setPosition(0 + secPerDiv);
- d_vBar2->setPosition(0 - secPerDiv);
-
+ double secPerDiv = HorizUnitsPerDiv();
d_gateBar1->setPosition(0 - 4 * secPerDiv);
d_gateBar2->setPosition(0 + 4 * secPerDiv);
@@ -472,25 +331,6 @@ CapturePlot::CapturePlot(QWidget *parent,
d_hGatingHandle1->setOtherCursorPosition(d_hGatingHandle2->position());
d_hGatingHandle2->setOtherCursorPosition(d_hGatingHandle1->position());
- /* When bar position changes due to plot resizes update the handle */
- connect(d_hBar1, SIGNAL(pixelPositionChanged(int)),
- SLOT(onHbar1PixelPosChanged(int)));
- connect(d_hBar2, SIGNAL(pixelPositionChanged(int)),
- SLOT(onHbar2PixelPosChanged(int)));
- connect(d_vBar1, SIGNAL(pixelPositionChanged(int)),
- SLOT(onVbar1PixelPosChanged(int)));
- connect(d_vBar2, SIGNAL(pixelPositionChanged(int)),
- SLOT(onVbar2PixelPosChanged(int)));
-
- connect(d_vBar1, SIGNAL(positionChanged(double)),
- SLOT(onTimeCursor1Moved(double)));
- connect(d_vBar2, SIGNAL(positionChanged(double)),
- SLOT(onTimeCursor2Moved(double)));
- connect(d_hBar1, SIGNAL(positionChanged(double)),
- SLOT(onVoltageCursor1Moved(double)));
- connect(d_hBar2, SIGNAL(positionChanged(double)),
- SLOT(onVoltageCursor2Moved(double)));
-
connect(d_timeTriggerHandle, &FreePlotLineHandleH::reset, [=](){
Q_EMIT timeTriggerValueChanged(0);
});
@@ -509,7 +349,6 @@ CapturePlot::CapturePlot(QWidget *parent,
connect(d_gateBar2,SIGNAL(positionChanged(double)),
SLOT(onGateBar2Moved(double)));
-
/* Apply measurements for every new batch of data */
connect(this, SIGNAL(newData()),
SLOT(onNewDataReceived()));
@@ -523,8 +362,8 @@ CapturePlot::CapturePlot(QWidget *parent,
installEventFilter(this);
QwtScaleWidget *scaleWidget = axisWidget(QwtPlot::xBottom);
- const int fmw = QFontMetrics(scaleWidget->font()).width("-XXX.XXX XX");
- scaleWidget->setMinBorderDist(fmw / 2 + 30, fmw / 2 + 30);
+ const int fmw = QFontMetrics(scaleWidget->font()).width("-XXX.XXX XX");
+ scaleWidget->setMinBorderDist(fmw / 2 + 30, fmw / 2 + 30);
displayGraticule = false;
@@ -552,17 +391,14 @@ CapturePlot::CapturePlot(QWidget *parent,
rightGateRect.setRight(axisScaleDiv(xBottom).upperBound());
rightGate->setRect(rightGateRect);
rightGate->setBrush(gateBrush);
+
}
CapturePlot::~CapturePlot()
{
- markerIntersection1->detach();
- markerIntersection2->detach();
- removeEventFilter(this);
canvas()->removeEventFilter(d_cursorReadouts);
+ removeEventFilter(this);
canvas()->removeEventFilter(d_symbolCtrl);
- delete markerIntersection1;
- delete markerIntersection2;
for (auto it = d_measureObjs.begin(); it != d_measureObjs.end(); ++it) {
delete *it;
}
@@ -571,6 +407,21 @@ CapturePlot::~CapturePlot()
delete rightGate;
}
+QString CapturePlot::formatXValue(double value, int precision) const
+{
+ return d_cursorTimeFormatter.format(value, "", precision);
+}
+
+QString CapturePlot::formatYValue(double value, int precision) const
+{
+ return d_cursorMetricFormatter.format(value, "", precision);
+}
+
+CursorReadouts * CapturePlot::getCursorReadouts() const
+{
+ return d_cursorReadouts;
+}
+
void CapturePlot::replot()
{
@@ -607,32 +458,9 @@ void CapturePlot::enableTimeTrigger(bool enable)
d_timeTriggerHandle->setVisible(enable);
}
-void CapturePlot::onHbar1PixelPosChanged(int pos)
-{
- d_vCursorHandle1->setPositionSilenty(pos);
-}
-
-void CapturePlot::onHbar2PixelPosChanged(int pos)
-{
- d_vCursorHandle2->setPositionSilenty(pos);
-}
-
-void CapturePlot::onVbar1PixelPosChanged(int pos)
-{
- d_hCursorHandle1->setPositionSilenty(pos);
- displayIntersection();
-}
-
-void CapturePlot::onVbar2PixelPosChanged(int pos)
-{
- displayIntersection();
- d_hCursorHandle2->setPositionSilenty(pos);
-}
-
-void CapturePlot::onTimeCursor1Moved(double value)
+void CapturePlot::onVCursor1Moved(double value)
{
QString text;
-
text = d_cursorTimeFormatter.format(value, "", 3);
d_cursorReadouts->setTimeCursor1Text(text);
d_cursorReadoutsText.t1 = text;
@@ -648,19 +476,17 @@ void CapturePlot::onTimeCursor1Moved(double value)
text = "Infinity";
d_cursorReadouts->setFreqDeltaText(text);
d_cursorReadoutsText.freq = text;
-
if (d_trackMode) {
- onVoltageCursor1Moved(getHorizontalCursorIntersection(d_vBar1->plotCoord().x()));
+ onHCursor1Moved(getHorizontalCursorIntersection(d_vBar1->plotCoord().x()));
}
value_v1 = value;
Q_EMIT cursorReadoutsChanged(d_cursorReadoutsText);
}
-void CapturePlot::onTimeCursor2Moved(double value)
+void CapturePlot::onVCursor2Moved(double value)
{
QString text;
-
text = d_cursorTimeFormatter.format(value, "", 3);
d_cursorReadouts->setTimeCursor2Text(text);
d_cursorReadoutsText.t2 = text;
@@ -676,16 +502,15 @@ void CapturePlot::onTimeCursor2Moved(double value)
text = "Infinity";
d_cursorReadouts->setFreqDeltaText(text);
d_cursorReadoutsText.freq = text;
-
if (d_trackMode) {
- onVoltageCursor2Moved(getHorizontalCursorIntersection(d_vBar2->plotCoord().x()));
+ onHCursor2Moved(getHorizontalCursorIntersection(d_vBar2->plotCoord().x()));
}
value_v2 = value;
Q_EMIT cursorReadoutsChanged(d_cursorReadoutsText);
}
-void CapturePlot::onVoltageCursor1Moved(double value)
+void CapturePlot::onHCursor1Moved(double value)
{
QString text;
@@ -717,7 +542,7 @@ void CapturePlot::onVoltageCursor1Moved(double value)
Q_EMIT cursorReadoutsChanged(d_cursorReadoutsText);
}
-void CapturePlot::onVoltageCursor2Moved(double value)
+void CapturePlot::onHCursor2Moved(double value)
{
QString text;
@@ -855,23 +680,9 @@ QWidget * CapturePlot::topArea()
}
QWidget * CapturePlot::topHandlesArea()
-{/* handle area for gate cursors */
- return d_topHandlesArea;
-}
-
-QWidget * CapturePlot::bottomHandlesArea()
-{
- return d_bottomHandlesArea;
-}
-
-QWidget * CapturePlot::leftHandlesArea()
-{
- return d_leftHandlesArea;
-}
-
-QWidget * CapturePlot::rightHandlesArea()
{
- return d_rightHandlesArea;
+ /* handle area for gate cursors */
+ return d_topGateHandlesArea;
}
void CapturePlot::setBonusWidthForHistogram(int width)
@@ -907,64 +718,11 @@ bool CapturePlot::triggerBEnabled()
return d_triggerBEnabled;
}
-void CapturePlot::setVertCursorsEnabled(bool en)
-{
- if (d_vertCursorsEnabled != en) {
- d_vertCursorsEnabled = en;
- d_vBar1->setVisible(en);
- d_vBar2->setVisible(en);
- d_hCursorHandle1->setVisible(en);
- d_hCursorHandle2->setVisible(en);
- d_cursorReadouts->setTimeReadoutVisible(en &&
- d_cursorReadoutsVisible);
- }
-}
-
-bool CapturePlot::vertCursorsEnabled()
-{
- return d_vertCursorsEnabled;
-}
-
-void CapturePlot::setHorizCursorsEnabled(bool en)
-{
- if (d_horizCursorsEnabled != en) {
- d_horizCursorsEnabled = en;
- d_hBar1->setVisible(en);
- d_hBar2->setVisible(en);
- d_vCursorHandle1->setVisible(en);
- d_vCursorHandle2->setVisible(en);
- d_cursorReadouts->setVoltageReadoutVisible(en &&
- d_cursorReadoutsVisible);
- }
-}
-
-bool CapturePlot::horizCursorsEnabled()
-{
- return d_horizCursorsEnabled;
-}
-
-void CapturePlot::setCursorReadoutsVisible(bool en)
-{
- if (d_cursorReadoutsVisible != en) {
- d_cursorReadoutsVisible = en;
- d_cursorReadouts->setVoltageReadoutVisible(en &&
- d_vertCursorsEnabled);
- d_cursorReadouts->setTimeReadoutVisible(en &&
- d_horizCursorsEnabled);
- }
-}
-
void CapturePlot::setSelectedChannel(int id)
{
if (d_selected_channel != id) {
d_selected_channel = id;
-
- if (id > -1) {
- d_hBar1->setMobileAxis(QwtAxisId(QwtPlot::yLeft, id));
- d_hBar2->setMobileAxis(QwtAxisId(QwtPlot::yLeft, id));
- }
}
- //
}
int CapturePlot::selectedChannel()
@@ -1019,11 +777,6 @@ void CapturePlot::onTriggerBHandleGrabbed(bool grabbed)
d_symbolCtrl->updateOverlay();
}
-void CapturePlot::setVertCursorsLocked(bool value)
-{
- vertCursorsLocked = value;
-}
-
void CapturePlot::showEvent(QShowEvent *event)
{
d_vCursorHandle1->triggerMove();
@@ -1056,11 +809,6 @@ int CapturePlot::getAnalogChannels() const
return d_ydata.size() + d_ref_ydata.size();
}
-void CapturePlot::setHorizCursorsLocked(bool value)
-{
- horizCursorsLocked = value;
-}
-
Measure* CapturePlot::measureOfChannel(int chnIdx) const
{
Measure *measure = nullptr;
@@ -1109,8 +857,8 @@ void CapturePlot::enableAxisLabels(bool enabled)
void CapturePlot::setDisplayScale(double value)
{
DisplayPlot::setDisplayScale(value);
- onVoltageCursor1Moved(d_hBar1->plotCoord().y());
- onVoltageCursor2Moved(d_hBar2->plotCoord().y());
+ onHCursor1Moved(d_hBar1->plotCoord().y());
+ onHCursor2Moved(d_hBar2->plotCoord().y());
}
void CapturePlot::setTimeTriggerInterval(double min, double max)
@@ -1128,13 +876,13 @@ void CapturePlot::setGraticuleEnabled(bool enabled){
displayGraticule = enabled;
if(!displayGraticule){
- for(QwtPlotScaleItem* scale : scaleItems){
+ for(QwtPlotScaleItem* scale : qAsConst(scaleItems)){
scale->attach(this);
}
graticule->enableGraticule(displayGraticule);
}
else{
- for(QwtPlotScaleItem* scale : scaleItems){
+ for(QwtPlotScaleItem* scale : qAsConst(scaleItems)){
scale->detach();
}
graticule->enableGraticule(displayGraticule);
@@ -1155,7 +903,7 @@ void CapturePlot::setGatingEnabled(bool enabled){
if(enabled){
leftGate->attach(this);
rightGate->attach(this);
- d_topHandlesArea->show();
+ d_topGateHandlesArea->show();
//update handle
onGateBar1Moved(leftGateRect.right());
onGateBar2Moved(rightGateRect.left());
@@ -1163,7 +911,7 @@ void CapturePlot::setGatingEnabled(bool enabled){
else{
leftGate->detach();
rightGate->detach();
- d_topHandlesArea->hide();
+ d_topGateHandlesArea->hide();
}
for (int i = 0; i < d_measureObjs.size(); i++) {
Measure *measure = d_measureObjs[i];
@@ -1177,35 +925,6 @@ void CapturePlot::setGatingEnabled(bool enabled){
}
}
-void CapturePlot::trackModeEnabled(bool enabled)
-{
- d_trackMode = !enabled;
- if (d_horizCursorsEnabled) {
- d_hBar1->setVisible(enabled);
- d_hBar2->setVisible(enabled);
- d_vCursorHandle1->setVisible(enabled);
- d_vCursorHandle2->setVisible(enabled);
- }
- if (d_trackMode) {
- onTimeCursor1Moved(d_vBar1->plotCoord().x());
- onTimeCursor2Moved(d_vBar2->plotCoord().x());
- displayIntersection();
- } else {
- onVoltageCursor1Moved(d_hBar1->plotCoord().y());
- onVoltageCursor2Moved(d_hBar2->plotCoord().y());
- markerIntersection1->detach();
- markerIntersection2->detach();
- replot();
- }
-}
-
-void CapturePlot::repositionCursors()
-{
- onTimeCursor1Moved(d_vBar1->plotCoord().x());
- onTimeCursor2Moved(d_vBar2->plotCoord().x());
- displayIntersection();
-}
-
void CapturePlot::setActiveVertAxis(unsigned int axisIdx, bool selected)
{
DisplayPlot::setActiveVertAxis(axisIdx, selected);
@@ -1250,22 +969,22 @@ void CapturePlot::updateHandleAreaPadding(bool enabled)
if (enabled) {
d_bottomHandlesArea->setLeftPadding(50 + axisWidget(QwtAxisId(QwtPlot::yLeft, d_activeVertAxis))->width());
- d_topHandlesArea->setLeftPadding(90 + axisWidget(QwtAxisId(QwtPlot::yLeft, d_activeVertAxis))->width());
+ d_topGateHandlesArea->setLeftPadding(90 + axisWidget(QwtAxisId(QwtPlot::yLeft, d_activeVertAxis))->width());
QwtScaleWidget *scaleWidget = axisWidget(QwtPlot::xBottom);
const int fmw = QFontMetrics(scaleWidget->font()).width("-XX.XX XX");
const int fmh = QFontMetrics(scaleWidget->font()).height();
d_bottomHandlesArea->setRightPadding(50 + fmw/2 + d_bonusWidth);
- d_topHandlesArea->setRightPadding(50 + fmw/2 + d_bonusWidth);
+ d_topGateHandlesArea->setRightPadding(50 + fmw/2 + d_bonusWidth);
d_rightHandlesArea->setTopPadding(50 + 6);
d_rightHandlesArea->setBottomPadding(50 + fmh);
QMargins margins = d_topWidget->layout()->contentsMargins();
margins.setLeft(d_leftHandlesArea->minimumWidth()+100);
d_topWidget->layout()->setContentsMargins(margins);
} else {
- if(d_topHandlesArea->leftPadding() != 90)
- d_topHandlesArea->setLeftPadding(90);
- if(d_topHandlesArea->rightPadding() != 90)
- d_topHandlesArea->setRightPadding(90);
+ if(d_topGateHandlesArea->leftPadding() != 90)
+ d_topGateHandlesArea->setLeftPadding(90);
+ if(d_topGateHandlesArea->rightPadding() != 90)
+ d_topGateHandlesArea->setRightPadding(90);
if (d_bottomHandlesArea->leftPadding() != 50 + xAxisBonusWidth)
d_bottomHandlesArea->setLeftPadding(50 + xAxisBonusWidth);
if (d_bottomHandlesArea->rightPadding() != 50 + d_bonusWidth + xAxisBonusWidth)
@@ -1275,7 +994,7 @@ void CapturePlot::updateHandleAreaPadding(bool enabled)
if (d_rightHandlesArea->bottomPadding() != 50)
d_rightHandlesArea->setBottomPadding(50);
- int topPadding = d_gatingEnabled ? d_topHandlesArea->height() : 0;
+ int topPadding = d_gatingEnabled ? d_topGateHandlesArea->height() : 0;
d_leftHandlesArea->setTopPadding(50 + topPadding);
d_rightHandlesArea->setTopPadding(50 + topPadding);
@@ -1292,104 +1011,6 @@ void CapturePlot::updateHandleAreaPadding(bool enabled)
d_vCursorHandle2->updatePosition();
}
-double CapturePlot::getHorizontalCursorIntersection(double time)
-{
- int n = Curve(d_selected_channel)->data()->size();
-
- if (n == 0) {
- return ERROR_VALUE;
- } else {
- double leftTime, rightTime, leftCustom, rightCustom;
- int rightIndex = -1;
- int leftIndex = -1;
-
- int left = 0;
- int right = n - 1;
-
- if (Curve(d_selected_channel)->data()->sample(right).x() < time ||
- Curve(d_selected_channel)->data()->sample(left).x() > time) {
- return ERROR_VALUE;
- }
-
- while (left <= right) {
- int mid = (left + right) / 2;
- double xData = Curve(d_selected_channel)->data()->sample(mid).x();
- if (xData == time) {
- if (mid > 0) {
- leftIndex = mid - 1;
- rightIndex = mid;
- }
- break;
- } else if (xData < time) {
- left = mid + 1;
- } else {
- right = mid - 1;
- }
- }
-
- if ((leftIndex == -1 || rightIndex == -1) && left > 0) {
- leftIndex = left - 1;
- rightIndex = left;
- }
-
- if (leftIndex == -1 || rightIndex == -1) {
- return ERROR_VALUE;
- }
-
- leftTime = Curve(d_selected_channel)->data()->sample(leftIndex).x();
- rightTime = Curve(d_selected_channel)->data()->sample(rightIndex).x();
-
- leftCustom = Curve(d_selected_channel)->data()->sample(leftIndex).y();
- rightCustom = Curve(d_selected_channel)->data()->sample(rightIndex).y();
-
- double value = (rightCustom - leftCustom) / (rightTime - leftTime) *
- (time - leftTime) + leftCustom;
-
- return value;
- }
-}
-
-void CapturePlot::displayIntersection()
-{
- if (!d_trackMode) {
- return;
- }
-
- double intersectionCursor1, intersectionCursor2;
- bool attachmk1 = true;
- bool attachmk2 = true;
-
-
- intersectionCursor1 = getHorizontalCursorIntersection(d_vBar1->plotCoord().x());
- intersectionCursor2 = getHorizontalCursorIntersection(d_vBar2->plotCoord().x());
-
- if (intersectionCursor1 == -1000000){
- attachmk1 = false;
- }
- if (intersectionCursor2 == -1000000) {
- attachmk2 = false;
- }
-
- markerIntersection1->setAxes(QwtPlot::xBottom, QwtAxisId(QwtPlot::yLeft, d_selected_channel));
- markerIntersection2->setAxes(QwtPlot::xBottom, QwtAxisId(QwtPlot::yLeft, d_selected_channel));
-
- markerIntersection1->setValue(d_vBar1->plotCoord().x(), intersectionCursor1);
- markerIntersection2->setValue(d_vBar2->plotCoord().x(), intersectionCursor2);
-
- if (attachmk1) {
- markerIntersection1->attach(this);
- } else {
- markerIntersection1->detach();
- }
- if (attachmk2) {
- markerIntersection2->attach(this);
- } else {
- markerIntersection2->detach();
- }
-
- replot();
-}
-
void CapturePlot::updateGateMargins(){
/* update the size of the gates */
leftGateRect.setTop(axisScaleDiv(yRight).upperBound());
@@ -1414,6 +1035,9 @@ bool CapturePlot::eventFilter(QObject *object, QEvent *event)
d_hCursorHandle2->triggerMove();
d_vCursorHandle1->triggerMove();
d_vCursorHandle2->triggerMove();
+ d_timeTriggerHandle->triggerMove();
+ d_levelTriggerAHandle->triggerMove();
+ d_levelTriggerBHandle->triggerMove();
/* update the size of the gates when the plot canvas is resized */
updateGateMargins();
@@ -1645,7 +1269,7 @@ bool CapturePlot::endGroupSelection(bool moveAnnotationCurvesLast)
// merge new group if selected channels already have a group
QList group = d_groupHandles.takeLast();
QList updatedGroup;
- for (RoundedHandleV *hdl : group) {
+ for (RoundedHandleV *hdl : qAsConst(group)) {
auto hdlGroup = std::find_if(d_groupHandles.begin(), d_groupHandles.end(),
[&hdl](const QList &group){
return group.contains(hdl);
@@ -1658,7 +1282,9 @@ bool CapturePlot::endGroupSelection(bool moveAnnotationCurvesLast)
continue;
}
- for (const auto &grpHdl : *hdlGroup) {
+
+ auto hdlGroupContainer = *hdlGroup;
+ for (const auto &grpHdl : qAsConst(hdlGroupContainer)) {
if (!updatedGroup.contains(grpHdl)) {
updatedGroup.push_back(grpHdl);
}
@@ -1718,14 +1344,14 @@ bool CapturePlot::endGroupSelection(bool moveAnnotationCurvesLast)
group.first()->setSelected(true);
group.first()->selected(true);
- for (QwtPlotZoneItem *groupMarker : d_groupMarkers) {
+ for (QwtPlotZoneItem *groupMarker : qAsConst(d_groupMarkers)) {
groupMarker->detach();
delete groupMarker;
}
d_groupMarkers.clear();
- for (const auto &group : d_groupHandles) {
+ for (const auto &group : qAsConst(d_groupHandles)) {
// Add group marker
QwtScaleMap yMap = this->canvasMap(QwtAxisId(QwtPlot::yLeft, 0));
const QwtInterval y = axisInterval(QwtAxisId(QwtPlot::yLeft, 0));
@@ -1749,7 +1375,7 @@ bool CapturePlot::endGroupSelection(bool moveAnnotationCurvesLast)
}
if (!newGroup) {
- for (const auto &group : d_groupHandles) {
+ for (const auto &group : qAsConst(d_groupHandles)) {
group.first()->triggerMove();
}
}
@@ -1775,7 +1401,8 @@ QVector CapturePlot::getGroupOfChannel(int chnIdx)
return groupIdxList;
}
- for (const auto &hdl : *hdlGroup) {
+ auto hdlGroupContainer = *hdlGroup;
+ for (const auto &hdl : qAsConst(hdlGroupContainer)) {
groupIdxList.push_back(d_offsetHandles.indexOf(hdl));
}
@@ -2011,7 +1638,7 @@ void CapturePlot::handleInGroupChangedPosition(int position)
void adiscope::CapturePlot::pushBackNewOffsetWidgets(RoundedHandleV *chOffsetHdl, HorizBar *chOffsetBar)
{
- int indexOfNewChannel = d_ydata.size() - 1;
+ const int indexOfNewChannel = (d_ydata.size() + d_ref_ydata.size()) - 1;
d_offsetBars.insert(indexOfNewChannel, chOffsetBar);
d_offsetHandles.insert(indexOfNewChannel, chOffsetHdl);
@@ -2171,7 +1798,9 @@ void CapturePlot::setOffsetWidgetVisible(int chnIdx, bool visible)
}
int count = 0;
- for (const auto &handle : *hdlGroup) {
+
+ auto hdlGroupContainer = *hdlGroup;
+ for (const auto &handle : qAsConst(hdlGroupContainer)) {
if (handle->isVisible()) {
count++;
}
@@ -2303,11 +1932,6 @@ void CapturePlot::setPeriodDetectHyst(int chnIdx, double hyst)
measure->setHysteresisSpan(hyst);
}
-struct cursorReadoutsText CapturePlot::allCursorReadouts() const
-{
- return d_cursorReadoutsText;
-}
-
void CapturePlot::setTimeBaseLabelValue(double value)
{
QString text = d_cursorTimeFormatter.format(value, "", 3);
@@ -2376,16 +2000,6 @@ void CapturePlot::setMaxBufferSizeErrorLabel(bool reached, const QString &custom
d_maxBufferError->setText(reached ? errorMessage : "");
}
-void CapturePlot::setCursorReadoutsTransparency(int value)
-{
- d_cursorReadouts->setTransparency(value);
-}
-
-void CapturePlot::moveCursorReadouts(CustomPlotPositionButton::ReadoutsPosition position)
-{
- d_cursorReadouts->moveToPosition(position);
-}
-
void CapturePlot::updateBufferSizeSampleRateLabel(int nsamples, double sr)
{
QString txtSampleRate = d_cursorMetricFormatter.format(sr, "sps", 0);
diff --git a/src/oscilloscope_plot.hpp b/src/oscilloscope_plot.hpp
index 38ca368614..8d58e9ede4 100644
--- a/src/oscilloscope_plot.hpp
+++ b/src/oscilloscope_plot.hpp
@@ -22,10 +22,6 @@
#define M2K_OSCILLOSCOPE_PLOT_H
#include "TimeDomainDisplayPlot.h"
-#include "symbol_controller.h"
-#include "handles_area.hpp"
-#include "plot_line_handle.h"
-#include "cursor_readouts.h"
#include "measure.h"
#include "customplotpositionbutton.h"
#include "graticule.h"
@@ -45,24 +41,15 @@ namespace adiscope {
Q_OBJECT
public:
- OscilloscopePlot(QWidget *parent, unsigned int xNumDivs = 10,
+ OscilloscopePlot(QWidget *parent, bool isdBgraph = false, unsigned int xNumDivs = 10,
unsigned int yNumDiv = 10);
~OscilloscopePlot();
};
- struct cursorReadoutsText {
- QString t1;
- QString t2;
- QString tDelta;
- QString freq;
- QString v1;
- QString v2;
- QString vDelta;
- };
-
class CapturePlot: public OscilloscopePlot
{
friend class Oscilloscope_API;
+ friend class LogicAnalyzer_API;
friend class Channel_API;
Q_OBJECT
@@ -76,7 +63,7 @@ namespace adiscope {
};
public:
- CapturePlot(QWidget *parent, unsigned int xNumDivs = 10,
+ CapturePlot(QWidget *parent, bool isdBgraph = false, unsigned int xNumDivs = 10,
unsigned int yNumDivs = 10);
~CapturePlot();
@@ -87,19 +74,13 @@ namespace adiscope {
QWidget *topArea();
QWidget *topHandlesArea();
- QWidget *bottomHandlesArea();
- QWidget *leftHandlesArea();
- QWidget *rightHandlesArea();
void setBonusWidthForHistogram(int width);
bool triggerAEnabled();
bool triggerBEnabled();
- bool vertCursorsEnabled();
- bool horizCursorsEnabled();
int selectedChannel();
bool measurementsEnabled();
- struct cursorReadoutsText allCursorReadouts() const;
void setOffsetWidgetVisible(int chnIdx, bool visible);
void removeOffsetWidgets(int chnIdx);
@@ -129,8 +110,6 @@ namespace adiscope {
void setTimeTriggerInterval(double min, double max);
bool labelsEnabled();
- void trackModeEnabled(bool enabled);
- void repositionCursors();
void setGraticuleEnabled(bool enabled);
void setGatingEnabled(bool enabled);
@@ -144,11 +123,15 @@ namespace adiscope {
QString getChannelName(int chIdx) const;
void setChannelName(const QString &name, int chIdx);
+ QString formatXValue(double value, int precision) const;
+ QString formatYValue(double value, int precision) const;
+
+ CursorReadouts * getCursorReadouts() const;
+
Q_SIGNALS:
void timeTriggerValueChanged(double);
void channelOffsetChanged(unsigned int, double);
void measurementsAvailable();
- void cursorReadoutsChanged(struct cursorReadoutsText);
void canvasSizeChanged();
void leftGateChanged(double);
void rightGateChanged(double);
@@ -157,22 +140,16 @@ namespace adiscope {
public Q_SLOTS:
void setTriggerAEnabled(bool en);
void setTriggerBEnabled(bool en);
- void setVertCursorsEnabled(bool en);
- void setHorizCursorsEnabled(bool en);
void setSelectedChannel(int id);
void setMeasuremensEnabled(bool en);
void setPeriodDetectLevel(int chnIdx, double lvl);
void setPeriodDetectHyst(int chnIdx, double hyst);
- void setCursorReadoutsVisible(bool en);
void setTimeBaseLabelValue(double timebase);
void setBufferSizeLabelValue(int numSamples);
void setSampleRatelabelValue(double sampleRate);
void setTriggerState(int triggerState);
void setMaxBufferSizeErrorLabel(bool reached, const QString &customWarning = "");
- void setCursorReadoutsTransparency(int value);
- void moveCursorReadouts(CustomPlotPositionButton::ReadoutsPosition position);
- void setHorizCursorsLocked(bool value);
- void setVertCursorsLocked(bool value);
+
void showEvent(QShowEvent *event);
void printWithNoBackground(const QString& toolName = "", bool editScaleDraw = true);
@@ -201,25 +178,12 @@ namespace adiscope {
Measure* measureOfChannel(int chnIdx) const;
void updateBufferSizeSampleRateLabel(int nsamples, double sr);
void updateHandleAreaPadding(bool);
- double getHorizontalCursorIntersection(double time);
- void displayIntersection();
void updateGateMargins();
private Q_SLOTS:
void onChannelAdded(int);
void onNewDataReceived();
-
- void onHbar1PixelPosChanged(int);
- void onHbar2PixelPosChanged(int);
- void onVbar1PixelPosChanged(int);
- void onVbar2PixelPosChanged(int);
-
- void onTimeCursor1Moved(double);
- void onTimeCursor2Moved(double);
- void onVoltageCursor1Moved(double);
- void onVoltageCursor2Moved(double);
-
void onGateBar1PixelPosChanged(int);
void onGateBar2PixelPosChanged(int);
@@ -233,24 +197,22 @@ namespace adiscope {
void onTriggerBHandleGrabbed(bool);
void handleInGroupChangedPosition(int position);
+
+ void onHCursor1Moved(double);
+ void onHCursor2Moved(double);
+ void onVCursor1Moved(double);
+ void onVCursor2Moved(double);
+
private:
std::function m_conversion_function;
- SymbolController *d_symbolCtrl;
bool d_triggerAEnabled;
bool d_triggerBEnabled;
- bool d_vertCursorsEnabled;
- bool d_horizCursorsEnabled;
bool d_measurementsEnabled;
bool d_labelsEnabled;
- int d_selected_channel;
-
QWidget *d_topWidget;
- GateHandlesArea *d_topHandlesArea;
- HorizHandlesArea *d_bottomHandlesArea;
- VertHandlesArea *d_leftHandlesArea;
- VertHandlesArea *d_rightHandlesArea;
+ GateHandlesArea *d_topGateHandlesArea;
int d_bonusWidth;
QLabel *d_timeBaseLabel;
@@ -269,19 +231,9 @@ namespace adiscope {
bool d_startedGrouping;
QVector d_groupMarkers;
- PlotLineHandleV *d_vCursorHandle1;
- PlotLineHandleV *d_vCursorHandle2;
- PlotLineHandleH *d_hCursorHandle1;
- PlotLineHandleH *d_hCursorHandle2;
-
PlotGateHandle *d_hGatingHandle1;
PlotGateHandle *d_hGatingHandle2;
- VertBar *d_vBar1;
- VertBar *d_vBar2;
- HorizBar *d_hBar1;
- HorizBar *d_hBar2;
-
VertBar *d_gateBar1;
VertBar *d_gateBar2;
@@ -292,13 +244,8 @@ namespace adiscope {
FreePlotLineHandleV *d_levelTriggerAHandle;
FreePlotLineHandleV *d_levelTriggerBHandle;
-
-
- CursorReadouts *d_cursorReadouts;
MetricPrefixFormatter d_cursorMetricFormatter;
- TimePrefixFormatter d_cursorTimeFormatter;
- struct cursorReadoutsText d_cursorReadoutsText;
- bool d_cursorReadoutsVisible;
+ TimePrefixFormatter d_cursorTimeFormatter;
QPen d_trigAactiveLinePen;
QPen d_trigAinactiveLinePen;
@@ -317,16 +264,6 @@ namespace adiscope {
bool displayGraticule;
Graticule *graticule;
- bool d_trackMode;
- QwtPlotMarker *markerIntersection1;
- QwtPlotMarker *markerIntersection2;
- bool horizCursorsLocked;
- bool vertCursorsLocked;
- int pixelPosHandleHoriz1;
- int pixelPosHandleHoriz2;
- int pixelPosHandleVert1;
- int pixelPosHandleVert2;
-
QwtPlotShapeItem *leftGate, *rightGate;
QRectF leftGateRect, rightGateRect;
bool d_gatingEnabled;
diff --git a/src/patterngenerator/pattern_generator.cpp b/src/patterngenerator/pattern_generator.cpp
index 90260e32ef..8efe5252ad 100644
--- a/src/patterngenerator/pattern_generator.cpp
+++ b/src/patterngenerator/pattern_generator.cpp
@@ -69,7 +69,7 @@ PatternGenerator::PatternGenerator(struct iio_context *ctx, Filter *filt,
DIOManager *diom, ToolLauncher *parent)
: LogicTool(nullptr, toolMenuItem, new PatternGenerator_API(this), "Pattern Generator", parent)
, m_ui(new Ui::PatternGenerator)
- , m_plot(this, 16, 10)
+ , m_plot(this, false, 16, 10)
, m_plotScrollBar(new QScrollBar(Qt::Vertical, this))
, m_selectedChannel(-1)
, m_nbChannels(DIGITAL_NR_CHANNELS)
@@ -334,6 +334,13 @@ void PatternGenerator::channelSelectedChanged(int chIdx, bool selected)
m_ui->patternComboBox->setEnabled(true);
m_ui->btnOutputMode->setEnabled(true);
+ if (m_selectedChannel < m_nbChannels) {
+ const DIO_MODE outputMode = m_m2kDigital->getOutputMode(m_selectedChannel);
+ const bool btnOutputModeSelected = (outputMode == DIO_MODE::DIO_OPENDRAIN ? true
+ :false);
+ m_ui->btnOutputMode->setChecked(btnOutputModeSelected);
+ }
+
updateChannelGroupWidget(true);
updateChannelGroupPattern(true);
@@ -909,12 +916,6 @@ void PatternGenerator::connectSignalsAndSlots()
connect(m_ui->nameLineEdit, &QLineEdit::textChanged, [=](const QString &text){
m_plot.setChannelName(text, m_selectedChannel);
m_plotCurves[m_selectedChannel]->setName(text);
- if (m_selectedChannel < m_nbChannels) {
- QWidget *widgetInLayout = m_ui->channelEnumeratorLayout->itemAtPosition(m_selectedChannel % 8,
- m_selectedChannel / 8)->widget();
- auto channelBox = dynamic_cast(widgetInLayout);
- channelBox->setText(text);
- }
});
connect(m_ui->printBtn, &QPushButton::clicked, [=](){
@@ -1022,7 +1023,7 @@ void PatternGenerator::updateChannelGroupPattern(bool visible)
qDebug() << "Enabled patterns: " << m_enabledPatterns;
qDebug() << "################################################################";
- for (const auto &ep : m_enabledPatterns) {
+ for (const auto &ep : qAsConst(m_enabledPatterns)) {
if (ep.first.contains(m_selectedChannel)) {
pattern = QString::fromStdString(ep.second->get_pattern()->get_name());
ep.second->setVisible(visible);
diff --git a/src/patterngenerator/pattern_generator_api.cpp b/src/patterngenerator/pattern_generator_api.cpp
index 9ba3bd50f1..3c24fc6e37 100644
--- a/src/patterngenerator/pattern_generator_api.cpp
+++ b/src/patterngenerator/pattern_generator_api.cpp
@@ -125,7 +125,7 @@ void logic::PatternGenerator_API::setCurrentGroups(const QVector >
QVector, QString> > logic::PatternGenerator_API::getEnabledPatterns() const
{
QVector, QString> > enabledPatterns;
- for (const QPair, PatternUI *> &pattern : m_pattern->m_enabledPatterns) {
+ for (const QPair, PatternUI *> &pattern : qAsConst(m_pattern->m_enabledPatterns)) {
enabledPatterns.push_back({pattern.first,
Pattern_API::toString(pattern.second->get_pattern())});
}
diff --git a/src/patterngenerator/patterns/patterns.cpp b/src/patterngenerator/patterns/patterns.cpp
index 471d9a2578..c64c7d905f 100644
--- a/src/patterngenerator/patterns/patterns.cpp
+++ b/src/patterngenerator/patterns/patterns.cpp
@@ -350,7 +350,8 @@ Pattern *Pattern_API::fromJson(QJsonObject obj)
sp->setCSPol(params["CS"].toBool());
sp->setMsbFirst(params["MSB"].toBool());
- for (auto val : params["v"].toArray()) {
+ auto paramsContainer = params["v"].toArray();
+ for (auto val : qAsConst(paramsContainer)) {
sp->v.push_back(val.toInt());
}
} else if (ip) {
@@ -361,7 +362,8 @@ Pattern *Pattern_API::fromJson(QJsonObject obj)
ip->setMsbFirst(params["MSB"].toBool());
ip->setWrite(params["write"].toBool());
- for (auto val : params["v"].toArray()) {
+ auto paramsContainer = params["v"].toArray();
+ for (auto val : qAsConst(paramsContainer)) {
ip->v.push_back(val.toInt());
}
} else if (imp) {
@@ -2010,7 +2012,7 @@ void I2CPatternUI::parse_ui()
std::vector b;
std::reverse(strList.begin(),strList.end());
- for (QString str: strList) {
+ for (const QString &str: qAsConst(strList)) {
uint64_t val;
bool ok;
b.clear();
@@ -2412,7 +2414,7 @@ void SPIPatternUI::parse_ui()
std::vector b;
std::reverse(strList.begin(),strList.end());
- for (QString str: strList) {
+ for (const QString &str: qAsConst(strList)) {
uint64_t val;
bool ok;
b.clear();
@@ -3680,7 +3682,8 @@ void ImportPatternUI::parse_ui()
}
unsigned short mask = 0;
- for (int key : import_settings->getExportConfig().keys()) {
+ auto keys = import_settings->getExportConfig().keys();
+ for (int key : qAsConst(keys)) {
mask = mask | (import_settings->getExportConfig()[key] << key);
}
@@ -3799,7 +3802,7 @@ Pattern *PatternFactory::create(QString name)
{
int i=0;
- for (auto str : ui_list) {
+ for (const auto &str : qAsConst(ui_list)) {
if (name==str) {
return create(i);
}
@@ -3878,7 +3881,7 @@ PatternUI *PatternFactory::create_ui(Pattern *pattern, QWidget *parent)
int i=0;
QString name = QString::fromStdString(pattern->get_name());
- for (auto str : ui_list) {
+ for (const auto &str : qAsConst(ui_list)) {
if (name==str) {
return create_ui(pattern,i,parent);
}
diff --git a/src/phonehome.cpp b/src/phonehome.cpp
index d7668eee6d..0349d538db 100644
--- a/src/phonehome.cpp
+++ b/src/phonehome.cpp
@@ -30,16 +30,18 @@ bool PhoneHome::getDone() const
return done;
}
-PhoneHome::PhoneHome(QSettings *settings, Preferences *pref) :
+PhoneHome::PhoneHome(QSettings *settings, Preferences *pref, QNetworkAccessManager* manager) :
ApiObject(), m_timestamp(0), m_versionsJson(""),
preferences(pref), settings(settings), done(false)
{
setObjectName("phonehome");
+ this->manager = manager;
load(*settings);
}
PhoneHome::~PhoneHome() {
save(*settings);
+ delete manager;
}
void PhoneHome::setPreferences(Preferences* preferences)
@@ -55,9 +57,7 @@ void PhoneHome::versionsRequest(bool force)
if(m_timestamp + timeout < now || force) {
// from swdownloads
- QNetworkAccessManager* manager = new QNetworkAccessManager(this);
connect(manager, &QNetworkAccessManager::finished, this, &PhoneHome::onVersionsRequestFinished);
- connect(manager, &QNetworkAccessManager::finished, manager, &QNetworkAccessManager::deleteLater);
manager->get(QNetworkRequest(QUrl(preferences->getCheck_updates_url())));
Q_EMIT scopyVersionCheckRequested();
diff --git a/src/phonehome.h b/src/phonehome.h
index 909b9da1f5..d1c9d0a5b6 100644
--- a/src/phonehome.h
+++ b/src/phonehome.h
@@ -40,6 +40,7 @@ class PhoneHome : public ApiObject
QString m_m2kLink;
qint64 m_timestamp;
QString m_versionsJson;
+ QNetworkAccessManager* manager;
PhoneHome* instance;
Preferences* preferences;
QSettings *settings;
@@ -50,7 +51,7 @@ class PhoneHome : public ApiObject
Q_PROPERTY(QString versionsJson READ getVersionsJson WRITE setVersionsJson)
public:
- PhoneHome(QSettings *settings, Preferences *preferences);
+ PhoneHome(QSettings *settings, Preferences *preferences, QNetworkAccessManager* manager);
~PhoneHome();
void versionsRequest(bool force = false);
void extractVersionStringsFromJson(const QJsonDocument &doc);
diff --git a/src/preferences.cpp b/src/preferences.cpp
index c94e1f0f94..5c3008c6b1 100644
--- a/src/preferences.cpp
+++ b/src/preferences.cpp
@@ -74,6 +74,11 @@ Preferences::Preferences(QWidget *parent) :
{
ui->setupUi(this);
+ /** Will still be available to use for development purposes.
+ * For now, no longer exposed to the users.**/
+ ui->debugMessagesCheckbox->setVisible(false);
+ ui->debugMessagesLbl->setVisible(false);
+
connect(ui->doubleClickCheckBox, &QCheckBox::stateChanged, [=](int state){
double_click_to_detach = (!state ? false : true);
Q_EMIT notify();
diff --git a/src/scopyExceptionHandler.h b/src/scopyExceptionHandler.h
index 67a4f404d1..cd72f943ff 100644
--- a/src/scopyExceptionHandler.h
+++ b/src/scopyExceptionHandler.h
@@ -1,38 +1,34 @@
#ifndef SCOPYEXCEPTIONHANDLER_H
#define SCOPYEXCEPTIONHANDLER_H
-#include
#include
#include
#include
#include
#include
+#include
using namespace adiscope;
+// Debug messages are currently disabled for users, can be used for development.
+// The message box was removed because exceptions might occur both from the control flow
+// and for signaling problems. Until those are handled separately, we can't use
+// QMessageBox to show the exception, since those can be thrown from different threads.
+
#define HANDLE_EXCEPTION(e) \
if (GetScopyApplicationInstance()->getDebugMode()) { \
auto me = dynamic_cast(&e); \
- auto handleLambda = [me, e](){ \
- QMessageBox msg; \
- QString str; \
- if (me) { \
- str = QString("Exception %1\ne.type() - %2\ne.what() - %3\ne.iioCode() - %4\nthrown from %5:%6\ncaught in %7:%8\nScopy git tag %9\n") \
- .arg("m2k_exception").arg(me->type()).arg(me->what()).arg(me->iioCode()).arg(QString::fromStdString(me->file())).arg(QString::number(me->line())).arg(__FILE__).arg(__LINE__).arg(SCOPY_VERSION_GIT); \
- } else { \
- str = QString("Exception %1\ncaught in %2:%3\nScopy git tag %4\n").arg(e.what()).arg(__FILE__).arg(__LINE__).arg(SCOPY_VERSION_GIT); \
- } \
- if (WriteScopyMinidump()) { \
- str = str + "Created minidump."; \
- } \
- msg.setText(str); \
- msg.exec(); \
- }; \
- if (GetScopyApplicationInstance()->thread() != QThread::currentThread()) { \
- QMetaObject::invokeMethod(GetScopyApplicationInstance(), handleLambda, Qt::BlockingQueuedConnection); \
+ QString str; \
+ if (me) { \
+ str = QString("Exception %1\ne.type() - %2\ne.what() - %3\ne.iioCode() - %4\nthrown from %5:%6\ncaught in %7:%8\nScopy git tag %9\n") \
+ .arg("m2k_exception").arg(me->type()).arg(me->what()).arg(me->iioCode()).arg(QString::fromStdString(me->file())).arg(QString::number(me->line())).arg(__FILE__).arg(__LINE__).arg(SCOPY_VERSION_GIT); \
} else { \
- handleLambda(); \
+ str = QString("Exception %1\ncaught in %2:%3\nScopy git tag %4\n").arg(e.what()).arg(__FILE__).arg(__LINE__).arg(SCOPY_VERSION_GIT); \
+ } \
+ if (WriteScopyMinidump()) { \
+ str = str + "Created minidump."; \
} \
+ qDebug() << str << "\n"; \
} \
#endif // SCOPYEXCEPTIONHANDLER_H
diff --git a/src/scopy_color_editor.cpp b/src/scopy_color_editor.cpp
index c642d41e91..09636bcd65 100644
--- a/src/scopy_color_editor.cpp
+++ b/src/scopy_color_editor.cpp
@@ -37,12 +37,12 @@ void ScopyColorEditor::parseAndBuildMap(QString toParse)
QString textEditText = "";
- for (auto token : print) {
+ for (const auto &token : qAsConst(print)) {
// TODO: skip empty parts is only available in qt >= 5.14
// QStringList ttoken = token.split("\n", Qt::SkipEmptyParts);
QStringList ttoken;
if (ttoken.size()) {
- for (auto t : ttoken) {
+ for (const auto &t : ttoken) {
if (t.startsWith("/*")) continue; //ignore comments
textEditText += t;
textEditText += '\n';
@@ -86,7 +86,7 @@ ScopyColorEditor::ScopyColorEditor(QApplication *app, QWidget *parent)
QDir themes(":/stylesheets/themes/");
QStringList stylesheets = themes.entryList();
- for (const QString &entry : stylesheets) {
+ for (const QString &entry : qAsConst(stylesheets)) {
m_ui->stylesheetsCmbBox->addItem(entry);
}
@@ -198,7 +198,8 @@ void ScopyColorEditor::buildMenuForMap()
bool toAdd = false;
- for (auto line : it.value()) {
+ auto itContainer = it.value();
+ for (auto line : qAsConst(itContainer)) {
std::vector controls;
int index = 0;
while ((index = line.indexOf("rgba(", index)) != -1) {
@@ -361,7 +362,8 @@ void ScopyColorEditor::rebuildAndApplyStylesheet()
for (auto it = m_entityStylesheetMap.begin(); it != m_entityStylesheetMap.end(); ++it) {
stylesheet += it.key() + " {\n";
- for (auto line : it.value()) {
+ auto itContainer = it.value();
+ for (const auto &line : qAsConst(itContainer)) {
stylesheet += line + "\n";
}
@@ -448,7 +450,7 @@ QString ScopyColorEditor::clearAndRebuildEditor(const QString &stylesheet)
{
m_entityStylesheetMap.clear();
auto layout = m_ui->scrollArea->widget()->layout();
- for (QWidget *widget : m_colorEditors) {
+ for (QWidget *widget : qAsConst(m_colorEditors)) {
layout->removeWidget(widget);
widget->deleteLater();
}
@@ -491,7 +493,7 @@ void ScopyColorEditor::stylesheetSelected(const QString &stylesheet)
void ScopyColorEditor::search(const QString &searchText)
{
- for (QWidget *w : m_colorEditors) {
+ for (QWidget *w : qAsConst(m_colorEditors)) {
QLabel *label = qobject_cast(w->layout()->itemAt(0)->widget());
bool hasSearchedWords = label->text().contains(searchText);
w->setVisible(hasSearchedWords);
diff --git a/src/scroll_filter.cpp b/src/scroll_filter.cpp
index a3100ded50..9fa0d76d8b 100644
--- a/src/scroll_filter.cpp
+++ b/src/scroll_filter.cpp
@@ -51,28 +51,28 @@ void MouseWheelWidgetGuard::installEventRecursively(QWidget *parentWidget)
}
QList comboBoxes = parentWidget->
findChildren();
- for(auto ch : comboBoxes) {
+ for(auto ch : qAsConst(comboBoxes)) {
ch->installEventFilter(new MouseWheelWidgetGuard(ch));
ch->setFocusPolicy(Qt::StrongFocus);
}
QList doubleSpinBoxes = parentWidget->
findChildren();
- for(auto ch : doubleSpinBoxes) {
+ for(auto ch : qAsConst(doubleSpinBoxes)) {
ch->installEventFilter(new MouseWheelWidgetGuard(ch));
ch->setFocusPolicy(Qt::StrongFocus);
}
QList spinBoxes = parentWidget->
findChildren();
- for(auto ch : spinBoxes) {
+ for(auto ch : qAsConst(spinBoxes)) {
ch->installEventFilter(new MouseWheelWidgetGuard(ch));
ch->setFocusPolicy(Qt::StrongFocus);
}
QList lineEdits = parentWidget->
findChildren();
- for(auto ch : lineEdits) {
+ for(auto ch : qAsConst(lineEdits)) {
ch->installEventFilter(new MouseWheelWidgetGuard(ch));
ch->setFocusPolicy(Qt::StrongFocus);
}
diff --git a/src/signal_generator.cpp b/src/signal_generator.cpp
index 87d01cb479..9acfa5c148 100644
--- a/src/signal_generator.cpp
+++ b/src/signal_generator.cpp
@@ -143,7 +143,7 @@ SignalGenerator::SignalGenerator(struct iio_context *_ctx, Filter *filt,
ui->run_button->enableSingleButton(false);
this->setAttribute(Qt::WA_DeleteOnClose, true);
- this->plot = new OscilloscopePlot(this);
+ this->m_plot = new CapturePlot(this);
QVector iio_channels;
@@ -460,40 +460,40 @@ SignalGenerator::SignalGenerator(struct iio_context *_ctx, Filter *filt,
time_block_data->time_block = scope_sink_f::make(
nb_points, sample_rate,
"Signal Generator", nb_channels,
- static_cast(plot));
+ static_cast(m_plot));
/* Attach all curves by default */
- plot->registerSink(time_block_data->time_block->name(),
+ m_plot->registerSink(time_block_data->time_block->name(),
nb_channels, nb_points);
for(auto i = 0; i < nb_channels; i++) {
- plot->Curve(i)->setPaintAttribute(QwtPlotCurve::ClipPolygons, false);
- plot->Curve(i)->setPaintAttribute(QwtPlotCurve::FilterPointsAggressive, true);
+ m_plot->Curve(i)->setPaintAttribute(QwtPlotCurve::ClipPolygons, false);
+ m_plot->Curve(i)->setPaintAttribute(QwtPlotCurve::FilterPointsAggressive, true);
}
/* This must be done after attaching the curves; otherwise
* plot->getLineColor(i) returns black. */
for (unsigned int i = 0; i < nb_channels; i++) {
- channels[i]->setColor(plot->getLineColor(i));
+ channels[i]->setColor(m_plot->getLineColor(i));
}
- plot->disableLegend();
- plot->setPaletteColor(QColor("black"));
+ m_plot->disableLegend();
+ m_plot->setPaletteColor(QColor("black"));
- plot->setVertUnitsPerDiv(AMPLITUDE_VOLTS * 2.0 / 10.0);
+ m_plot->setVertUnitsPerDiv(AMPLITUDE_VOLTS * 2.0 / 10.0);
- plot->setHorizUnitsPerDiv((double) nb_points /
+ m_plot->setHorizUnitsPerDiv((double) nb_points /
((double) sample_rate * 10.0));
- plot->setHorizOffset((double) nb_points /
+ m_plot->setHorizOffset((double) nb_points /
((double) sample_rate * 2.0));
- plot->zoomBaseUpdate();
- ui->plot->insertWidget(0,plot, 0, 0);
+ m_plot->zoomBaseUpdate();
+ //ui->plot->insertWidget(0,m_plot, 0, 0);
connect(ui->btnAppearanceCollapse, SIGNAL(toggled(bool)),ui->wAppearance, SLOT(setVisible(bool)));
connect(ui->btnSigGenAutoscale, &QPushButton::toggled, [=](bool checked){
- plot->setAutoScale(checked);
+ m_plot->setAutoScale(checked);
});
fileManager = new FileManager("Signal Generator");
@@ -585,7 +585,7 @@ SignalGenerator::SignalGenerator(struct iio_context *_ctx, Filter *filt,
time_block_data->time_block->set_update_time(0.001);
- plot->addZoomer(0);
+ m_plot->addZoomer(0);
resetZoom();
auto ptr = getCurrentData();
@@ -593,10 +593,20 @@ SignalGenerator::SignalGenerator(struct iio_context *_ctx, Filter *filt,
readPreferences();
- // Reduce the extent of the yLeft axis because it is not needed
- plot->axisWidget(QwtPlot::yLeft)->scaleDraw()->setMinimumExtent(65);
-
ui->btnHelp->setUrl("https://wiki.analog.com/university/tools/m2k/scopy/siggen");
+
+ m_plot->setOffsetHandleVisible(0,false);
+ m_plot->setOffsetHandleVisible(1,false);
+ m_plot->enableAxis(QwtPlot::yLeft, false);
+ m_plot->setActiveVertAxis(0);
+
+ m_plot->enableTimeTrigger(false);
+
+ ui->plot->addWidget(m_plot->topArea(), 0, 0, 1, 4);
+ ui->plot->addWidget(m_plot->topHandlesArea(), 1, 0, 1, 4);
+ ui->plot->removeWidget(ui->instrumentNotes);
+ ui->plot->addWidget(ui->instrumentNotes,3,0,1,4);
+ ui->plot->addWidget(m_plot, 2, 1, 1, 1);
}
SignalGenerator::~SignalGenerator()
@@ -611,7 +621,7 @@ SignalGenerator::~SignalGenerator()
delete fileManager;
- delete plot;
+ delete m_plot;
delete ui;
delete time_block_data;
}
@@ -634,7 +644,7 @@ void SignalGenerator::readPreferences()
void SignalGenerator::resetZoom()
{
- disconnect(plot->getZoomer(),SIGNAL(zoomed(QRectF)),this,SLOT(rescale()));
+ disconnect(m_plot->getZoomer(),SIGNAL(zoomed(QRectF)),this,SLOT(rescale()));
bool disable_zoom=false;
for (auto it = channels.begin(); it != channels.end(); ++it) {
@@ -647,11 +657,11 @@ void SignalGenerator::resetZoom()
}
if (!disable_zoom) {
- connect(plot->getZoomer(),SIGNAL(zoomed(QRectF)),this,SLOT(rescale()));
+ connect(m_plot->getZoomer(),SIGNAL(zoomed(QRectF)),this,SLOT(rescale()));
}
double period = 0.0;
- unsigned int slowSignalId = 0;
+ int slowSignalId = -1;
for (auto it = channels.begin(); it != channels.end(); ++it) {
if ((*it)->enableButton()->isChecked()) {
@@ -704,21 +714,23 @@ void SignalGenerator::resetZoom()
period=0.1;
}
- plot->setVertUnitsPerDiv(1);
- plot->setVertOffset(0);
- plot->setHorizUnitsPerDiv(period/10);
- plot->setHorizOffset(period/2);
- plot->zoomBaseUpdate();
+ m_plot->setVertUnitsPerDiv(1);
+ m_plot->setVertOffset(0);
+ m_plot->setHorizUnitsPerDiv(period/10);
+ m_plot->setHorizOffset(period/2);
+ m_plot->zoomBaseUpdate();
rescale();
- plot->DetachCurve(slowSignalId);
- plot->AttachCurve(slowSignalId);
+ if(slowSignalId != -1) {
+ m_plot->DetachCurve(slowSignalId);
+ m_plot->AttachCurve(slowSignalId);
+ }
}
void SignalGenerator::rescale()
{
- auto hOffset=plot->HorizOffset();
- auto hUnitsPerDiv=plot->HorizUnitsPerDiv();
+ auto hOffset=m_plot->HorizOffset();
+ auto hUnitsPerDiv=m_plot->HorizUnitsPerDiv();
auto xDivisions=10;
@@ -741,15 +753,15 @@ void SignalGenerator::rescale()
}
long startSample=sample_rate*zoomT1;
- plot->setDataStartingPoint(startSample);
- plot->setSampleRate(sample_rate,1,"Hz");
+ m_plot->setDataStartingPoint(startSample);
+ m_plot->setSampleRate(sample_rate,1,"Hz");
if (nb_points < 16) {
nb_points = 16;
}
time_block_data->time_block->set_nsamps(nb_points);
time_block_data->time_block->set_samp_rate(sample_rate);
updatePreview();
- plot->replot();
+ m_plot->replot();
}
void SignalGenerator::constantValueChanged(double value)
@@ -900,8 +912,8 @@ void SignalGenerator::lineThicknessChanged(int index)
int lineThickness = (int)(ptr->lineThickness / 0.5) - 1;
if (lineThickness != index) {
ptr->lineThickness = 0.5 * (index + 1);
- plot->setLineWidth(ptr->id, ptr->lineThickness);
- plot->replot();
+ m_plot->setLineWidth(ptr->id, ptr->lineThickness);
+ m_plot->replot();
}
}
@@ -1458,8 +1470,10 @@ void SignalGenerator::start()
m_m2k_analogout->setOversamplingRatio(i, oversampling);
m_m2k_analogout->setSampleRate(i, final_rate);
+
}
+
qDebug(CAT_SIGNAL_GENERATOR) << "Pushed cyclic buffer";
m_m2k_analogout->setCyclic(true);
@@ -1616,7 +1630,8 @@ void SignalGenerator::loadFileChannelData(int chIdx)
return;
}
- for (auto x : fileManager->read(ptr->file_channel)) {
+ auto fileChannels = fileManager->read(ptr->file_channel);
+ for (auto x : qAsConst(fileChannels)) {
ptr->file_data.push_back(x);
}
}
@@ -1895,13 +1910,13 @@ void adiscope::SignalGenerator::channelWidgetEnabled(bool en)
m_m2k_analogout->enableChannel(id, en);
if (en) {
- plot->AttachCurve(id);
+ m_plot->AttachCurve(id);
} else {
- plot->DetachCurve(id);
+ m_plot->DetachCurve(id);
}
resetZoom();
- plot->replot();
+ m_plot->replot();
bool enable_run = en;
@@ -1937,8 +1952,6 @@ void adiscope::SignalGenerator::channelWidgetMenuToggled(bool checked)
{
ChannelWidget *cw = static_cast(QObject::sender());
- plot->setActiveVertAxis(cw->id());
-
triggerRightMenuToggle(cw->id(), checked);
}
@@ -2045,6 +2058,9 @@ void SignalGenerator::updateRightMenuForChn(int chIdx)
waveformUpdateUi(ptr->waveform);
ui->tabWidget->setCurrentIndex((int) ptr->type);
resizeTabWidget((int)ptr->type);
+
+ ui->tabWidget->setStyleSheet(QString("QTabBar::tab:selected { border-bottom: 2px solid %1; }")
+ .arg(m_plot->getLineColor(chIdx).name()));
}
void SignalGenerator::updateAndToggleMenu(int chIdx, bool open)
diff --git a/src/signal_generator.hpp b/src/signal_generator.hpp
index fff07a6ebd..16e28a2857 100644
--- a/src/signal_generator.hpp
+++ b/src/signal_generator.hpp
@@ -148,7 +148,7 @@ class SignalGenerator : public Tool
libm2k::analog::M2kAnalogOut* m_m2k_analogout;
Ui::SignalGenerator *ui;
- OscilloscopePlot *plot;
+ CapturePlot *m_plot;
gr::top_block_sptr top_block;
struct time_block_data *time_block_data;
diff --git a/src/signal_generator_api.cpp b/src/signal_generator_api.cpp
index 7a8b403681..a339ee4c0c 100644
--- a/src/signal_generator_api.cpp
+++ b/src/signal_generator_api.cpp
@@ -833,8 +833,8 @@ void SignalGenerator_API::setLineThickness(const QList& list)
if(i == gen->currentChannel){
gen->updateRightMenuForChn(i);
- gen->plot->setLineWidth(i, ptr->lineThickness);
- gen->plot->replot();
+ gen->m_plot->setLineWidth(i, ptr->lineThickness);
+ gen->m_plot->replot();
}
}
int index = (int)(gen->getCurrentData()->lineThickness / 0.5) - 1;
diff --git a/src/spectrum_analyzer.cpp b/src/spectrum_analyzer.cpp
index 0b699b110e..20b5f84bd9 100644
--- a/src/spectrum_analyzer.cpp
+++ b/src/spectrum_analyzer.cpp
@@ -50,6 +50,8 @@
/* Generated UI */
#include "ui_spectrum_analyzer.h"
+#include "ui_cursors_settings.h"
+#include "ui_cursor_readouts.h"
#include
#include
@@ -129,6 +131,8 @@ SpectrumAnalyzer::SpectrumAnalyzer(struct iio_context *ctx, Filter *filt,
crt_peak(0),
max_peak_count(10),
fft_size(32768),
+ hCursorsEnabled(true),
+ vCursorsEnabled(true),
searchVisiblePeaks(true),
m_max_sample_rate(100e6),
sample_rate_divider(1),
@@ -203,10 +207,12 @@ SpectrumAnalyzer::SpectrumAnalyzer(struct iio_context *ctx, Filter *filt,
settings_group->addButton(ui->btnSweep);
settings_group->addButton(ui->btnMarkers);
settings_group->addButton(ui->btnAddRef);
+ settings_group->addButton(ui->btnCursors);
settings_group->setExclusive(true);
fft_plot = new FftDisplayPlot(m_adc_nb_channels, this);
fft_plot->disableLegend();
+
// Disable mouse interactions with the axes until they are in a working state
fft_plot->setXaxisMouseGesturesEnabled(false);
@@ -214,9 +220,10 @@ SpectrumAnalyzer::SpectrumAnalyzer(struct iio_context *ctx, Filter *filt,
fft_plot->setYaxisMouseGesturesEnabled(i, false);
}
- QGridLayout *gLayout = static_cast
- (ui->widgetPlotContainer->layout());
- gLayout->addWidget(fft_plot, 1, 0, 1, 1);
+ ui->gridLayout_plot->addWidget(fft_plot->getPlotwithElements(), 1, 0, 1, 1);
+
+ fft_plot->enableXaxisLabels();
+ fft_plot->enableYaxisLabels();
// Initialize spectrum channels
for (int i = 0 ; i < m_adc_nb_channels; i++) {
@@ -293,6 +300,7 @@ SpectrumAnalyzer::SpectrumAnalyzer(struct iio_context *ctx, Filter *filt,
fft_plot->setStartStop(start, stop);
fft_plot->setAxisScale(QwtPlot::xBottom, start, stop);
fft_plot->replot();
+ fft_plot->bottomHandlesArea()->repaint();
setSampleRate(2 * stop);
@@ -399,6 +407,10 @@ SpectrumAnalyzer::SpectrumAnalyzer(struct iio_context *ctx, Filter *filt,
connect(fft_plot, SIGNAL(sampleCountUpdated(uint)),
this, SLOT(onPlotSampleCountUpdated(uint)));
+
+ connect(this, SIGNAL(selectedChannelChanged(int)),
+ fft_plot, SLOT(setSelectedChannel(int)));
+
if (ctx) {
build_gnuradio_block_chain();
} else {
@@ -438,6 +450,12 @@ SpectrumAnalyzer::SpectrumAnalyzer(struct iio_context *ctx, Filter *filt,
connect(bottom_scale, SIGNAL(valueChanged(double)),
SLOT(onBottomValueChanged(double)));
+ cursor_panel_init();
+
+ connect(fft_plot,
+ SIGNAL(cursorReadoutsChanged(struct cursorReadoutsText)),
+ SLOT(onCursorReadoutsChanged(struct cursorReadoutsText)));
+
// UI default
ui->comboBox_window->setCurrentText("Hamming");
ui->comboBox_line_thickness->setCurrentText("1");
@@ -458,7 +476,7 @@ SpectrumAnalyzer::SpectrumAnalyzer(struct iio_context *ctx, Filter *filt,
ui->lblMagUnit->setText(ui->cmb_units->currentText());
ui->markerTable->hide();
- for (auto ch: channels) {
+ for (auto ch: qAsConst(channels)) {
ch->setFftWindow(FftWinType::HAMMING, fft_size);
}
@@ -788,6 +806,8 @@ void SpectrumAnalyzer::toggleRightMenu(CustomPushButton *btn, bool checked)
index = 3;
} else if (btn == ui->btnAddRef) {
index = 4;
+ } else if (btn == ui->btnCursors) {
+ index = 5;
}
}
@@ -820,6 +840,25 @@ void SpectrumAnalyzer::rightMenuFinished(bool opened)
}
}
+void SpectrumAnalyzer::on_boxCursors_toggled(bool on)
+{
+ fft_plot->setHorizCursorsEnabled(
+ on ? cr_ui->vCursorsEnable->isChecked() : false);
+ fft_plot->setVertCursorsEnabled(
+ on ? cr_ui->hCursorsEnable->isChecked() : false);
+
+ fft_plot->trackModeEnabled(on ? cr_ui->btnNormalTrack->isChecked() : true);
+
+ if (on) {
+ fft_plot->setCursorReadoutsVisible(on);
+ } else {
+ if (ui->btnCursors->isChecked())
+ ui->btnCursors->setChecked(false);
+
+ menuOrder.removeOne(ui->btnCursors);
+ }
+}
+
void SpectrumAnalyzer::on_btnToolSettings_toggled(bool checked)
{
triggerRightMenuToggle(
@@ -844,6 +883,12 @@ void SpectrumAnalyzer::on_btnSettings_clicked(bool checked)
}
}
+void SpectrumAnalyzer::on_btnCursors_toggled(bool checked)
+{
+ triggerRightMenuToggle(
+ static_cast(QObject::sender()), checked);
+}
+
void SpectrumAnalyzer::on_btnSweep_toggled(bool checked)
{
triggerRightMenuToggle(
@@ -919,13 +964,93 @@ void SpectrumAnalyzer::on_btnImport_clicked()
{
QMap import_map = ui->importSettings->getExportConfig();
- for (int key : import_map.keys()) {
+ auto keys = import_map.keys();
+ for (int key : qAsConst(keys)) {
if (import_map[key]) {
add_ref_waveform(key);
}
}
}
+void SpectrumAnalyzer::cursor_panel_init()
+{
+ cr_ui = new Ui::CursorsSettings;
+ cr_ui->setupUi(ui->cursorsSettings);
+ setDynamicProperty(cr_ui->btnLockHorizontal, "use_icon", true);
+ setDynamicProperty(cr_ui->btnLockVertical, "use_icon", true);
+
+ connect(cr_ui->btnLockHorizontal, &QPushButton::toggled,
+ fft_plot, &FftDisplayPlot::setHorizCursorsLocked);
+ connect(cr_ui->btnLockVertical, &QPushButton::toggled,
+ fft_plot, &FftDisplayPlot::setVertCursorsLocked);
+
+ cursorsPositionButton = new CustomPlotPositionButton(cr_ui->posSelect);
+
+ connect(cr_ui->hCursorsEnable, SIGNAL(toggled(bool)),
+ fft_plot, SLOT(setVertCursorsEnabled(bool)));
+ connect(cr_ui->vCursorsEnable, SIGNAL(toggled(bool)),
+ fft_plot, SLOT(setHorizCursorsEnabled(bool)));
+ connect(cr_ui->btnNormalTrack, &QPushButton::toggled,
+ this, &SpectrumAnalyzer::toggleCursorsMode);
+
+ cr_ui->horizontalSlider->setMaximum(100);
+ cr_ui->horizontalSlider->setMinimum(0);
+ cr_ui->horizontalSlider->setSingleStep(1);
+
+ connect(cr_ui->horizontalSlider, &QSlider::valueChanged, [=](int value){
+ cr_ui->transLabel->setText(tr("Transparency ") + QString::number(value) + "%");
+ fft_plot->setCursorReadoutsTransparency(value);
+ });
+ cr_ui->horizontalSlider->setSliderPosition(0);
+
+ connect(cursorsPositionButton, &CustomPlotPositionButton::positionChanged,
+ [=](CustomPlotPositionButton::ReadoutsPosition position){
+ fft_plot->moveCursorReadouts(position);
+ });
+
+}
+
+
+void SpectrumAnalyzer::toggleCursorsMode(bool toggled)
+{
+ cr_ui->hCursorsEnable->setEnabled(toggled);
+ cr_ui->vCursorsEnable->setEnabled(toggled);
+
+ if (toggled) {
+ fft_plot->setVertCursorsEnabled(hCursorsEnabled);
+ fft_plot->setHorizCursorsEnabled(vCursorsEnabled);
+// cursor_readouts_ui->TimeCursors->setVisible(vCursorsEnabled);
+// cursor_readouts_ui->VoltageCursors->setVisible(hCursorsEnabled);
+ } else {
+ hCursorsEnabled = cr_ui->hCursorsEnable->isChecked();
+ vCursorsEnabled = cr_ui->vCursorsEnable->isChecked();
+ fft_plot->setVertCursorsEnabled(true);
+ fft_plot->setHorizCursorsEnabled(true);
+// cursor_readouts_ui->TimeCursors->setVisible(true);
+// cursor_readouts_ui->VoltageCursors->setVisible(true);
+ }
+
+ cr_ui->btnLockVertical->setEnabled(toggled);
+ fft_plot->trackModeEnabled(toggled);
+}
+
+void SpectrumAnalyzer::onCursorReadoutsChanged(struct cursorReadoutsText data)
+{
+ fillCursorReadouts(data);
+}
+
+void SpectrumAnalyzer::fillCursorReadouts(const struct cursorReadoutsText& data)
+{
+ //needs to be filled when measure ui is added
+ // cursor_readouts_ui->cursorT1->setText(data.t1);
+ // cursor_readouts_ui->cursorT2->setText(data.t2);
+ // cursor_readouts_ui->timeDelta->setText(data.tDelta);
+ // cursor_readouts_ui->frequencyDelta->setText(data.freq);
+ // cursor_readouts_ui->cursorV1->setText(data.v1);
+ // cursor_readouts_ui->cursorV2->setText(data.v2);
+ // cursor_readouts_ui->voltageDelta->setText(data.vDelta);
+}
+
QString SpectrumAnalyzer::getReferenceChannelName() const
{
int current = 1;
@@ -933,7 +1058,7 @@ QString SpectrumAnalyzer::getReferenceChannelName() const
bool isOk = true;
for (const auto &ref_channel : referenceChannels) {
QString shortName = ref_channel->shortName();
- int channel_counter = shortName.mid(shortName.size() - 1).toInt();
+ int channel_counter = shortName.midRef(shortName.size() - 1).toInt();
if (current == channel_counter) {
isOk = false;
break;
@@ -1038,6 +1163,7 @@ void SpectrumAnalyzer::onReferenceChannelDeleted()
if (channelWidget->id() < crt_channel_id) {
crt_channel_id--;
+ Q_EMIT selectedChannelChanged(crt_channel_id);
} else if (channelWidget->id() == crt_channel_id) {
for (int i = 0; i < m_adc_nb_channels + nb_ref_channels; ++i) {
auto cw = getChannelWidgetAt(i);
@@ -1046,6 +1172,7 @@ void SpectrumAnalyzer::onReferenceChannelDeleted()
}
if (cw->enableButton()->isChecked()) {
channelsEnabled = true;
+ Q_EMIT selectedChannelChanged(0);
cw->nameButton()->setChecked(true);
break;
}
@@ -1468,7 +1595,11 @@ void SpectrumAnalyzer::onChannelSelected(bool en)
ChannelWidget *cw = static_cast(QObject::sender());
int chIdx = cw->id();
- crt_channel_id = chIdx;
+ if(crt_channel_id != chIdx)
+ {
+ crt_channel_id = chIdx;
+ Q_EMIT selectedChannelChanged(chIdx);
+ }
if (!cw->isReferenceChannel()) {
const bool visible = (channels[crt_channel_id]->averageType() != FftDisplayPlot::AverageType::SAMPLE);
@@ -2113,6 +2244,7 @@ void SpectrumAnalyzer::on_cmb_units_currentIndexChanged(const QString& unit)
fft_plot->recalculateMagnitudes();
fft_plot->replot();
+ fft_plot->leftHandlesArea()->repaint();
ui->lblMagUnit->setText(unit);
@@ -2170,11 +2302,11 @@ void SpectrumAnalyzer::on_btnMarkerTable_toggled(bool checked)
// Set the Plot 3 times taller than the Marker Table (when visible)
QGridLayout *layout = static_cast(
- ui->widgetPlotContainer->layout());
+ ui->widgetPlotContainer->layout());
int row1 = getGridLayoutPosFromIndex(layout,
- layout->indexOf(ui->markerTable)).first;
+ layout->indexOf(ui->markerTable)).first;
int row2 = getGridLayoutPosFromIndex(layout,
- layout->indexOf(fft_plot)).first;
+ layout->indexOf(ui->gridLayout_plot)).first;
if (checked) {
layout->setRowStretch(row1, 1);
@@ -2215,6 +2347,9 @@ void SpectrumAnalyzer::onTopValueChanged(double top_value)
fft_plot->setAxisScale(QwtPlot::yLeft, bottom_scale->value(), top_value);
}
fft_plot->replot();
+ auto div = fft_plot->axisScaleDiv(QwtPlot::yLeft);
+ fft_plot->setYaxisMajorTicksPos(div.ticks(2));
+ fft_plot->leftHandlesArea()->repaint();
}
void SpectrumAnalyzer::onScalePerDivValueChanged(double perDiv)
@@ -2257,6 +2392,9 @@ void SpectrumAnalyzer::onBottomValueChanged(double bottom_value)
fft_plot->setAxisScale(QwtPlot::yLeft, bottom_value, top_scale->value());
}
fft_plot->replot();
+ auto div = fft_plot->axisScaleDiv(QwtPlot::yLeft);
+ fft_plot->setYaxisMajorTicksPos(div.ticks(2));
+ fft_plot->leftHandlesArea()->repaint();
}
void SpectrumAnalyzer::onCurrentAverageIndexChanged(uint chnIdx, uint avgIdx)
diff --git a/src/spectrum_analyzer.hpp b/src/spectrum_analyzer.hpp
index 0af38fe868..938e39bf05 100644
--- a/src/spectrum_analyzer.hpp
+++ b/src/spectrum_analyzer.hpp
@@ -54,6 +54,8 @@ extern "C" {
namespace Ui {
class SpectrumAnalyzer;
+class CursorReadouts;
+class CursorsSettings;
}
namespace adiscope {
@@ -111,6 +113,7 @@ public Q_SLOTS:
Q_SIGNALS:
void started(bool);
void showTool();
+ void selectedChannelChanged(int);
private Q_SLOTS:
void on_btnHistory_toggled(bool checked);
@@ -119,6 +122,12 @@ private Q_SLOTS:
void on_btnSettings_clicked(bool checked);
void on_btnSweep_toggled(bool checked);
void on_btnMarkers_toggled(bool checked);
+
+ void on_boxCursors_toggled(bool on);
+ void on_btnCursors_toggled(bool);
+ void onCursorReadoutsChanged(struct cursorReadoutsText);
+ void toggleCursorsMode(bool toggled);
+
void on_comboBox_type_currentIndexChanged(const QString&);
void on_comboBox_window_currentIndexChanged(const QString&);
void on_comboBox_line_thickness_currentIndexChanged(int index);
@@ -197,6 +206,15 @@ private Q_SLOTS:
libm2k::context::Generic* m_generic_context;
libm2k::analog::GenericAnalogIn* m_generic_analogin;
Ui::SpectrumAnalyzer *ui;
+
+
+ Ui::CursorReadouts *cursor_readouts_ui;
+ QWidget *cursorReadouts;
+ Ui::CursorsSettings *cr_ui;
+ CustomPlotPositionButton *cursorsPositionButton;
+ bool hCursorsEnabled;
+ bool vCursorsEnabled;
+
adiscope::DbClickButtons *marker_selector;
unsigned int m_nb_overlapping_avg;
@@ -254,6 +272,9 @@ private Q_SLOTS:
bool isIioManagerStarted() const;
void setCurrentSampleLabel(double);
+ void cursor_panel_init();
+ void fillCursorReadouts(const struct cursorReadoutsText &);
+
bool canSwitchAverageHistory(FftDisplayPlot::AverageType avg_type);
};
diff --git a/src/spectrum_analyzer_api.cpp b/src/spectrum_analyzer_api.cpp
index bdd9214e46..fc15c2612e 100644
--- a/src/spectrum_analyzer_api.cpp
+++ b/src/spectrum_analyzer_api.cpp
@@ -19,6 +19,7 @@
*/
#include "spectrum_analyzer_api.hpp"
#include "ui_spectrum_analyzer.h"
+#include "ui_cursors_settings.h"
#include "channel_widget.hpp"
#include "db_click_buttons.hpp"
@@ -218,7 +219,7 @@ QVariantList SpectrumAnalyzer_API::getMarkers()
{
QVariantList list;
- for (SpectrumMarker_API *each : sp->marker_api) {
+ for (SpectrumMarker_API *each : qAsConst(sp->marker_api)) {
list.append(QVariant::fromValue(each));
}
@@ -226,6 +227,16 @@ QVariantList SpectrumAnalyzer_API::getMarkers()
}
+bool SpectrumAnalyzer_API::hasCursors() const
+{
+ return sp->ui->boxCursors->isChecked();
+}
+
+void SpectrumAnalyzer_API::setCursors(bool en)
+{
+ sp->ui->boxCursors->setChecked(en);
+}
+
bool SpectrumAnalyzer_API::running()
{
return sp->runButton()->isChecked();
@@ -249,7 +260,7 @@ QVariantList SpectrumAnalyzer_API::getChannels()
{
QVariantList list;
- for (SpectrumChannel_API *each : sp->ch_api) {
+ for (SpectrumChannel_API *each : qAsConst(sp->ch_api)) {
list.append(QVariant::fromValue(each));
}
@@ -364,11 +375,82 @@ void SpectrumAnalyzer_API::setMarkerTableVisible(bool en)
sp->ui->btnMarkerTable->setChecked(en);
}
+bool SpectrumAnalyzer_API::horizontalCursors() const
+{
+ return sp->cr_ui->hCursorsEnable->isChecked();
+}
+
+void SpectrumAnalyzer_API::setHorizontalCursors(bool en)
+{
+ sp->cr_ui->hCursorsEnable->setChecked(en);
+}
+
+bool SpectrumAnalyzer_API::verticalCursors() const
+{
+ return sp->cr_ui->vCursorsEnable->isChecked();
+}
+
+void SpectrumAnalyzer_API::setVerticalCursors(bool en)
+{
+ sp->cr_ui->vCursorsEnable->setChecked(en);
+}
+
bool SpectrumAnalyzer_API::getLogScale() const
{
return sp->fft_plot->getLogScale();
}
+int SpectrumAnalyzer_API::getCursorsPosition() const
+{
+ if (!hasCursors()) {
+ return 0;
+ }
+ auto currentPos = sp->fft_plot->d_cursorReadouts->getCurrentPosition();
+ switch (currentPos) {
+ case CustomPlotPositionButton::ReadoutsPosition::topLeft:
+ default:
+ return 0;
+ case CustomPlotPositionButton::ReadoutsPosition::topRight:
+ return 1;
+ case CustomPlotPositionButton::ReadoutsPosition::bottomLeft:
+ return 2;
+ case CustomPlotPositionButton::ReadoutsPosition::bottomRight:
+ return 3;
+ }
+ return 3;
+}
+
+void SpectrumAnalyzer_API::setCursorsPosition(int val)
+{
+ if (!hasCursors()) {
+ return;
+ }
+ enum CustomPlotPositionButton::ReadoutsPosition types[] = {
+ CustomPlotPositionButton::ReadoutsPosition::topLeft,
+ CustomPlotPositionButton::ReadoutsPosition::topRight,
+ CustomPlotPositionButton::ReadoutsPosition::bottomLeft,
+ CustomPlotPositionButton::ReadoutsPosition::bottomRight
+ };
+ sp->cursorsPositionButton->setPosition(types[val]);
+ sp->fft_plot->replot();
+}
+
+int SpectrumAnalyzer_API::getCursorsTransparency() const
+{
+ if (!hasCursors()) {
+ return 0;
+ }
+ return sp->cr_ui->horizontalSlider->value();
+}
+
+void SpectrumAnalyzer_API::setCursorsTransparency(int val)
+{
+ if (!hasCursors()) {
+ return;
+ }
+ sp->cr_ui->horizontalSlider->setValue(val);
+}
+
void SpectrumAnalyzer_API::setLogScale(bool useLogScale)
{
sp->ui->logBtn->setChecked(useLogScale);
diff --git a/src/spectrum_analyzer_api.hpp b/src/spectrum_analyzer_api.hpp
index 8439efef25..ddc6371507 100644
--- a/src/spectrum_analyzer_api.hpp
+++ b/src/spectrum_analyzer_api.hpp
@@ -27,6 +27,7 @@ namespace adiscope {
class SpectrumAnalyzer_API : public ApiObject
{
Q_OBJECT
+ Q_PROPERTY(bool cursors READ hasCursors WRITE setCursors);
Q_PROPERTY(bool running READ running WRITE run STORED false);
Q_PROPERTY(bool single READ isSingle WRITE single STORED false);
Q_PROPERTY(double startFreq READ startFreq WRITE setStartFreq);
@@ -42,6 +43,15 @@ class SpectrumAnalyzer_API : public ApiObject
setMarkerTableVisible);
Q_PROPERTY(QVariantList markers READ getMarkers);
+ Q_PROPERTY(bool horizontal_cursors READ horizontalCursors
+ WRITE setHorizontalCursors)
+ Q_PROPERTY(bool vertical_cursors READ verticalCursors
+ WRITE setVerticalCursors)
+ Q_PROPERTY(int cursors_position READ getCursorsPosition
+ WRITE setCursorsPosition)
+ Q_PROPERTY(int cursors_transparency READ getCursorsTransparency
+ WRITE setCursorsTransparency)
+
Q_PROPERTY(bool logScale READ getLogScale WRITE setLogScale)
Q_PROPERTY(QString notes READ getNotes WRITE setNotes)
@@ -53,6 +63,10 @@ class SpectrumAnalyzer_API : public ApiObject
private:
SpectrumAnalyzer *sp;
+
+ bool hasCursors() const;
+ void setCursors(bool en);
+
bool running();
void run(bool);
@@ -89,6 +103,18 @@ class SpectrumAnalyzer_API : public ApiObject
bool markerTableVisible();
void setMarkerTableVisible(bool);
+ bool horizontalCursors() const;
+ void setHorizontalCursors(bool en);
+
+ bool verticalCursors() const;
+ void setVerticalCursors(bool en);
+
+ int getCursorsPosition() const;
+ void setCursorsPosition(int val);
+
+ int getCursorsTransparency() const;
+ void setCursorsTransparency(int val);
+
bool getLogScale() const;
void setLogScale(bool useLogScale);
diff --git a/src/spinbox_a.cpp b/src/spinbox_a.cpp
index cc3c709780..307f6324e4 100644
--- a/src/spinbox_a.cpp
+++ b/src/spinbox_a.cpp
@@ -86,7 +86,7 @@ SpinBoxA::SpinBoxA(vector >units, const QString& name,
/* Compat */
QStringList list;
- for (auto unit : units) {
+ for (const auto &unit : units) {
list.append(QString("%1=%2").arg(unit.first).arg(unit.second));
}
@@ -670,6 +670,13 @@ int ScaleSpinButton::getIntegerDivider()
void ScaleSpinButton::setValue(double newVal)
{
+ if(newVal > m_max_value) {
+ newVal = m_max_value;
+ }
+ if(newVal < m_min_value) {
+ newVal = m_min_value;
+ }
+
if(integer_divider)
{
integer_step = round(integer_divider / newVal);
diff --git a/src/stream_to_vector_overlap_impl.cc b/src/stream_to_vector_overlap_impl.cc
index 4534a8f421..65b82b956a 100644
--- a/src/stream_to_vector_overlap_impl.cc
+++ b/src/stream_to_vector_overlap_impl.cc
@@ -64,10 +64,10 @@ stream_to_vector_overlap_impl::stream_to_vector_overlap_impl(size_t itemsize,
io_signature::make(1, 1, itemsize * nitems_per_block),
nitems_per_block),
m_overlap_factor(overlap_factor),
- m_nitems_per_block(nitems_per_block),
- m_itemsize(itemsize)
+ m_itemsize(itemsize),
+ m_nitems_per_block(nitems_per_block)
{
- m_nb_overlapped_items = nitems_per_block * m_overlap_factor;
+ m_nb_overlapped_items = (size_t)(nitems_per_block * m_overlap_factor);
}
int stream_to_vector_overlap_impl::work(int noutput_items,
@@ -81,8 +81,8 @@ int stream_to_vector_overlap_impl::work(int noutput_items,
const char* in = (const char*)input_items[0];
char* out = (char*)output_items[0];
- unsigned int src_index = 0;
- while (src_index + block_size < nb_input_items) {
+ size_t src_index = 0;
+ while (src_index + block_size <= nb_input_items) {
memcpy(out + nb_total_copied_items, in + src_index, block_size);
nb_total_copied_items += block_size;
src_index = src_index + block_size - overlap_size;
diff --git a/src/stream_to_vector_overlap_impl.h b/src/stream_to_vector_overlap_impl.h
index 1e4e7e4cbc..74478a7e77 100644
--- a/src/stream_to_vector_overlap_impl.h
+++ b/src/stream_to_vector_overlap_impl.h
@@ -60,7 +60,7 @@ class stream_to_vector_overlap_impl : public stream_to_vector_overlap
private:
double m_overlap_factor;
- unsigned int m_nb_overlapped_items;
+ size_t m_nb_overlapped_items;
size_t m_itemsize;
size_t m_nitems_per_block;
};
diff --git a/src/tool_launcher.cpp b/src/tool_launcher.cpp
index b1222a8dd1..373d4f050e 100644
--- a/src/tool_launcher.cpp
+++ b/src/tool_launcher.cpp
@@ -223,8 +223,8 @@ ToolLauncher::ToolLauncher(QString prevCrashDump, QWidget *parent) :
connect(ui->stackedWidget, SIGNAL(moved(int)),
this, SLOT(pageMoved(int)));
-
- m_phoneHome = new PhoneHome(settings, prefPanel);
+ networkAccessManager = new QNetworkAccessManager(this);
+ m_phoneHome = new PhoneHome(settings, prefPanel, networkAccessManager);
if (prefPanel->getFirst_application_run()) {
QMessageBox* msgBox = new QMessageBox(this);
@@ -274,7 +274,10 @@ ToolLauncher::ToolLauncher(QString prevCrashDump, QWidget *parent) :
menu->getToolMenuItemFor(TOOL_NETWORK_ANALYZER)->setCalibrating(false);
if (!okc.second && okc.first) {
- selectedDev->infoPage()->setCalibrationStatusLabel(tr("Calibrated"));
+ QMetaObject::invokeMethod(selectedDev->infoPage(),
+ "setCalibrationStatusLabel",
+ Qt::QueuedConnection,
+ Q_ARG(QString, tr("Calibrated")));
}
});
@@ -1122,6 +1125,8 @@ void adiscope::ToolLauncher::disconnect()
infoPg->setCalibrationStatusLabel("");
}
search_timer->start(TIMER_TIMEOUT_MS);
+ selectedDev->infoPage()->setConnectionStatusLabel("Not connected");
+ selectedDev->infoPage()->setCalibrationStatusLabel("");
}
/* Update the list of devices now */
@@ -1198,7 +1203,6 @@ void adiscope::ToolLauncher::connectBtn_clicked(bool pressed)
bool success = switchContext(uri);
if (success) {
selectedDev->setConnected(true, false, ctx);
- selectedDev->connectButton()->setText(tr("Calibrating..."));
selectedDev->setName(filter->hw_name());
selectedDev->infoPage()->identifyDevice(true);
setDynamicProperty(ui->btnConnect, "connected", true);
@@ -1364,7 +1368,7 @@ void adiscope::ToolLauncher::saveRunningToolsBeforeCalibration()
void adiscope::ToolLauncher::stopToolsBeforeCalibration()
{
- for(Tool* tool : calibration_saved_tools)
+ for(Tool* tool : qAsConst(calibration_saved_tools))
tool->stop();
}
void adiscope::ToolLauncher::restartToolsAfterCalibration()
@@ -1439,10 +1443,12 @@ QPair adiscope::ToolLauncher::calibrate()
bool skipCalib = false;
+ QString statusLabel;
if (calib->isInitialized()) {
if (prefPanel->getAttemptTempLutCalib() && calib->hasContextCalibration()) {
float calibTemperature = calib->calibrateFromContext();
- selectedDev->infoPage()->setCalibrationStatusLabel(tr("Calibrated from look-up table @ ") + QString::number(calibTemperature) + " deg. Celsius" );
+
+ statusLabel = tr("Calibrated from look-up table @ ") + QString::number(calibTemperature) + " deg. Celsius";
skipCalib = true;
ok = true;
@@ -1450,14 +1456,20 @@ QPair adiscope::ToolLauncher::calibrate()
// always calibrate if initial flag is set
// if it's calibrated and skip_calibration_if_calibrated - do not calibrate
if (!(initialCalibrationFlag && skip_calibration_if_already_calibrated && calib->isCalibrated() )) {
+ statusLabel = tr("Calibrating ... ");
ok = calib->calibrateAll();
} else {
- selectedDev->infoPage()->setCalibrationStatusLabel(tr("Calibration skipped because already calibrated."));
+ statusLabel = tr("Calibration skipped because already calibrated.");
skipCalib = true;
ok = true;
}
}
+ ok = calib->calibrateAll();
}
+ QMetaObject::invokeMethod(selectedDev->infoPage(),
+ "setCalibrationStatusLabel",
+ Qt::QueuedConnection,
+ Q_ARG(QString, statusLabel));
calibrating = false;
@@ -1574,9 +1586,6 @@ void adiscope::ToolLauncher::enableDacBasedTools()
if (m_adc_tools_failed || m_dac_tools_failed) {
disconnect();
- } else {
- m_sessionInfo.setLastConnectedFirmware(selectedDev->infoPage()->getFirmwareVersion());
- m_sessionInfo.setLastConnectedSerialNumber(selectedDev->infoPage()->getSerialNumber());
}
}
@@ -1666,7 +1675,6 @@ bool adiscope::ToolLauncher::switchContext(const QString& uri)
});
}
-
if (filter->compatible((TOOL_PATTERN_GENERATOR))) {
pattern_generator = new logic::PatternGenerator(ctx, filter,
menu->getToolMenuItemFor(TOOL_PATTERN_GENERATOR), &js_engine, dioManager, this);
@@ -1676,6 +1684,7 @@ bool adiscope::ToolLauncher::switchContext(const QString& uri)
});
}
}
+
catch (libm2k::m2k_exception &e) {
return false;
}
@@ -1826,12 +1835,12 @@ void ToolLauncher::closeEvent(QCloseEvent *event)
// Close all detached windows
QApplication::closeAllWindows();
- for (auto iterator : debugInstances) {
+ for (auto iterator : qAsConst(debugInstances)) {
delete iterator;
}
debugInstances.clear();
- for (auto iterator : debugWindows) {
+ for (auto iterator : qAsConst(debugWindows)) {
iterator->close();
delete iterator;
}
diff --git a/src/tool_launcher.hpp b/src/tool_launcher.hpp
index 6e98b7f65f..865c94621c 100644
--- a/src/tool_launcher.hpp
+++ b/src/tool_launcher.hpp
@@ -31,6 +31,7 @@
#include
#include
#include
+#include
#include
#include
@@ -272,6 +273,7 @@ private Q_SLOTS:
void saveRunningToolsBeforeCalibration();
void stopToolsBeforeCalibration();
+ QNetworkAccessManager* networkAccessManager;
PhoneHome* m_phoneHome;
SessionInfo m_sessionInfo;
diff --git a/src/tool_launcher_api.cpp b/src/tool_launcher_api.cpp
index 1917f980f7..adaade2851 100644
--- a/src/tool_launcher_api.cpp
+++ b/src/tool_launcher_api.cpp
@@ -197,7 +197,7 @@ void ToolLauncher_API::load(const QString& file)
ApiObjectManager::getInstance().load(settings);
- for (auto tool : tl->toolList)
+ for (auto tool : qAsConst(tl->toolList))
tool->settingsLoaded();
}
diff --git a/src/user_notes_api.cpp b/src/user_notes_api.cpp
index 47a3808ca6..decd532802 100644
--- a/src/user_notes_api.cpp
+++ b/src/user_notes_api.cpp
@@ -68,7 +68,7 @@ QVariantList UserNotes_API::getNotes()
QVariantList list;
refreshApi();
- for (auto *each : notes_list_api) {
+ for (auto *each : qAsConst(notes_list_api)) {
list.append(QVariant::fromValue(each));
}
return list;
diff --git a/ui/cursor_readouts.ui b/ui/cursor_readouts.ui
index 3e713fbb3e..ef1a1381b3 100644
--- a/ui/cursor_readouts.ui
+++ b/ui/cursor_readouts.ui
@@ -314,23 +314,7 @@
- CurV2
-
-
- Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter
-
-
-
- -
-
-
-
- 0
- 0
-
-
-
- ΔV
+ CurV2 =
Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter
@@ -346,14 +330,14 @@
- CurV1
+ CurV1 =
Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter
- -
+
-
@@ -366,7 +350,23 @@
- -
+
-
+
+
+ Qt::Horizontal
+
+
+ QSizePolicy::Expanding
+
+
+
+ 0
+ 0
+
+
+
+
+ -
false
@@ -382,7 +382,23 @@
- -
+
-
+
+
+ Qt::Vertical
+
+
+ QSizePolicy::Fixed
+
+
+
+ 0
+ 0
+
+
+
+
+ -
@@ -395,21 +411,24 @@
- -
-
-
- Qt::Vertical
+
-
+
+
+
+ 0
+ 0
+
-
- QSizePolicy::Fixed
+
+ color: rgba(255, 255, 255, 153);
-
-
- 0
- 0
-
+
+ ΔV =
-
+
+ Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter
+
+
-
@@ -427,24 +446,8 @@
- -
-
-
- Qt::Horizontal
-
-
- QSizePolicy::Expanding
-
-
-
- 0
- 0
-
-
-
-
- -
-
+
-
+
Qt::Vertical
@@ -459,7 +462,7 @@
- -
+
-
@@ -472,27 +475,6 @@
- -
-
-
- =
-
-
-
- -
-
-
- =
-
-
-
- -
-
-
- =
-
-
-
diff --git a/ui/cursors_settings.ui b/ui/cursors_settings.ui
index d2a8d845d6..f831c36fba 100644
--- a/ui/cursors_settings.ui
+++ b/ui/cursors_settings.ui
@@ -21,7 +21,7 @@
18
- 0
+ 5
18
@@ -37,6 +37,9 @@
0
+
+ QFrame::NoFrame
+
Qt::ScrollBarAsNeeded
@@ -51,8 +54,8 @@
0
0
- 276
- 601
+ 278
+ 598
@@ -82,7 +85,7 @@
- 240
+ 280
2
@@ -119,45 +122,58 @@
QLayout::SetDefaultConstraint
-
-
-
- Qt::Vertical
-
-
- QSizePolicy::Fixed
-
-
-
- 10
- 25
-
-
-
-
- -
-
-
- 0
-
-
-
-
-
- true
-
-
-
- 0
- 0
-
-
-
-
- 238
- 30
-
-
-
- QPushButton {
+
+
+
+ 0
+
+
+ 0
+
+
+ 0
+
+
+ 0
+
+
+ 0
+
+
-
+
+
+ Qt::Vertical
+
+
+ QSizePolicy::Fixed
+
+
+
+ 10
+ 25
+
+
+
+
+ -
+
+
+ true
+
+
+
+ 0
+ 0
+
+
+
+
+ 238
+ 30
+
+
+
+ QPushButton {
min-height: 30px;
max-height: 30px;
min-width: 238px;
@@ -219,47 +235,48 @@ QLabel#off:disabled {
color: rgba(255,255,255,51);
}
-
-
-
-
-
- true
-
-
- true
-
-
- false
-
-
- Normal
-
-
- Track
-
-
- 0
-
-
-
-
-
- -
-
-
- Qt::Vertical
-
-
- QSizePolicy::Fixed
-
-
-
- 20
- 15
-
-
-
+
+
+
+
+
+ true
+
+
+ true
+
+
+ false
+
+
+ Normal
+
+
+ Track
+
+
+ 0
+
+
+
+ -
+
+
+ Qt::Vertical
+
+
+ QSizePolicy::Fixed
+
+
+
+ 20
+ 15
+
+
+
+
+
+
-
@@ -375,131 +392,156 @@ color: rgba(255,255,255,51);
-
-
-
- 0
-
-
-
-
-
- Qt::Vertical
-
-
- QSizePolicy::Fixed
-
-
-
- 0
- 25
-
-
-
-
- -
-
-
-
- 0
- 1
-
-
-
-
- 16777215
- 1
-
-
-
- Qt::Horizontal
-
-
- true
-
-
-
- -
-
-
-
- 0
- 0
-
-
-
- VERTICAL
-
-
- true
-
-
-
- -
-
-
- Qt::Vertical
-
-
- QSizePolicy::Fixed
-
-
-
- 0
- 15
-
-
-
-
-
+
+
+
+ 0
+
+
+ 0
+
+
+ 0
+
+
+ 0
+
+
+ 0
+
+ -
+
+
+ Qt::Vertical
+
+
+ QSizePolicy::Fixed
+
+
+
+ 0
+ 25
+
+
+
+
+ -
+
+
+
+ 0
+ 1
+
+
+
+
+ 16777215
+ 1
+
+
+
+ Qt::Horizontal
+
+
+ true
+
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+ VERTICAL
+
+
+ true
+
+
+
+ -
+
+
+ Qt::Vertical
+
+
+ QSizePolicy::Fixed
+
+
+
+ 0
+ 15
+
+
+
+
+
+
-
-
-
- 10
-
-
-
-
-
- 0
-
-
-
-
-
- true
-
-
- true
-
-
-
- -
-
-
- Qt::Horizontal
-
-
-
- 40
- 20
-
-
-
-
- -
-
-
- QPushButton[use_icon=true]
-
-
-
-
-
- true
-
-
-
-
-
-
+
+
+
+ 10
+
+
+ 0
+
+
+ 0
+
+
+ 0
+
+ -
+
+
+ 0
+
+
-
+
+
+ true
+
+
+ true
+
+
+
+ -
+
+
+ Qt::Horizontal
+
+
+
+ 40
+ 20
+
+
+
+
+ -
+
+
+ QPushButton[use_icon=true]
+
+
+
+
+
+ true
+
+
+
+
+
+
+
-
diff --git a/ui/digitalIoElement.ui b/ui/digitalIoElement.ui
index 12ff028793..1120a30827 100644
--- a/ui/digitalIoElement.ui
+++ b/ui/digitalIoElement.ui
@@ -145,7 +145,7 @@ width: 1310px;
}
- 1
+ 0
diff --git a/ui/dmm.ui b/ui/dmm.ui
index fba8128fc3..2b568c2960 100644
--- a/ui/dmm.ui
+++ b/ui/dmm.ui
@@ -7,7 +7,7 @@
0
0
900
- 830
+ 890
@@ -227,23 +227,41 @@ QPushButton:disabled {
0
-
-
+
+
+ Qt::Horizontal
+
+
+
+ 40
+ 20
+
+
+
+
+ -
+
- font-size: 13px;
+ font-size: 13px;
+color: red;
+text-align:right;
- Low Gain
+
+
+
+ Qt::AlignBottom|Qt::AlignLeading|Qt::AlignLeft
-
-
+
font-size: 13px;
-color: red;
+text-align:center;
-
+ ±25V
@@ -542,23 +560,44 @@ QLabel[ac=true] { qproperty-text: "VRMS"; }
0
-
-
+
+
+ Qt::Horizontal
+
+
+
+ 40
+ 20
+
+
+
+
+ -
+
- font-size: 13px;
+ font-size: 13px;
+color: red;
+text-align:right;
- Low Gain
+
+
+
+ Qt::AlignBottom|Qt::AlignLeading|Qt::AlignLeft
-
-
+
font-size: 13px;
-color: red;
+text-align:center;
-
+ ±25V
+
+
+ Qt::AlignBottom|Qt::AlignLeading|Qt::AlignLeft
@@ -987,7 +1026,7 @@ QLabel[ac=true] { qproperty-text: "VRMS"; }
-
- Gain
+ Range
@@ -1000,12 +1039,12 @@ QLabel[ac=true] { qproperty-text: "VRMS"; }
-
- Low
+ ± 25V
-
- High
+ ± 2.5V
@@ -1265,7 +1304,7 @@ QLabel[ac=true] { qproperty-text: "VRMS"; }
-
- Gain
+ Range
@@ -1278,12 +1317,12 @@ QLabel[ac=true] { qproperty-text: "VRMS"; }
-
- Low
+ ± 25V
-
- High
+ ± 2.5V
@@ -1981,6 +2020,9 @@ line-height: 14px;
+
+
+
@@ -2017,7 +2059,7 @@ line-height: 14px;
-
+
diff --git a/ui/logic_analyzer.ui b/ui/logic_analyzer.ui
index efb8871aa0..1579a8795e 100644
--- a/ui/logic_analyzer.ui
+++ b/ui/logic_analyzer.ui
@@ -2047,7 +2047,7 @@ QPushButton:checked { border-image: url(:/icons/setup_btn_checked.svg); }
cursorsBox
- clicked(bool)
+ toggled(bool)
btnCursors
setEnabled(bool)
diff --git a/ui/network_analyzer.ui b/ui/network_analyzer.ui
index 7a5249ff5a..8e04fbbf07 100644
--- a/ui/network_analyzer.ui
+++ b/ui/network_analyzer.ui
@@ -796,7 +796,7 @@ border: 5px solid white;
- 0
+ 2
@@ -839,7 +839,7 @@ border: 5px solid white;
0
- -465
+ 0
340
1036
@@ -2041,6 +2041,9 @@ padding-left: 20px;
-
+
+ QFrame::NoFrame
+
Qt::ScrollBarAlwaysOff
@@ -2052,8 +2055,8 @@ padding-left: 20px;
0
0
- 298
- 529
+ 300
+ 531
@@ -2741,8 +2744,141 @@ padding-left: 20px;
+ -
+
+
+ 0
+
+
-
+
+
+
+ 0
+ 0
+
+
+
+ QLabel {
+ font-size: 12px;
+ color: rgba(255, 255, 255, 70);
+ }
+
+
+ HORIZONTAL
+
+
+
+ -
+
+
+
+ 0
+ 1
+
+
+
+
+ 16777215
+ 1
+
+
+
+ border: 1px solid rgba(255, 255, 255, 70);
+
+
+ Qt::Horizontal
+
+
+
+
+
+ -
+
+
+ Qt::Vertical
+
+
+ QSizePolicy::Fixed
+
+
+
+ 0
+ 15
+
+
+
+
+ -
+
+
+ 0
+
+
-
+
+
+ 0
+
+
-
+
+
+
+
+
+ true
+
+
+ true
+
+
+
+ -
+
+
+ Qt::Horizontal
+
+
+
+ 40
+ 20
+
+
+
+
+ -
+
+
+
+
+
+ true
+
+
+
+
+
+
+
+ -
+
+
+ Qt::Vertical
+
+
+ QSizePolicy::Fixed
+
+
+
+ 0
+ 15
+
+
+
+
-
+
+ 0
+
0
@@ -2797,7 +2933,7 @@ padding-left: 20px;
20
- 25
+ 10
@@ -2987,6 +3123,11 @@ QLabel {
+
+ adiscope::CustomSwitch
+ QPushButton
+
+
adiscope::DetachDragZone
QWidget
@@ -3004,11 +3145,6 @@ QLabel {
QPushButton
-
- adiscope::CustomSwitch
- QPushButton
-
-
adiscope::MenuAnim
QWidget
@@ -3044,6 +3180,11 @@ QLabel {
customplotpositionbutton.h
1
+
+ adiscope::SmallOnOffSwitch
+ QPushButton
+
+
diff --git a/ui/osc_general_settings.ui b/ui/osc_general_settings.ui
index c3daf86530..ffec3aff2b 100644
--- a/ui/osc_general_settings.ui
+++ b/ui/osc_general_settings.ui
@@ -46,6 +46,9 @@
0
+
+ QFrame::NoFrame
+
Qt::ScrollBarAsNeeded
@@ -63,8 +66,8 @@
0
0
- 265
- 473
+ 267
+ 475
diff --git a/ui/pattern_generator.ui b/ui/pattern_generator.ui
index c616a8acd6..f5fd868151 100644
--- a/ui/pattern_generator.ui
+++ b/ui/pattern_generator.ui
@@ -1606,25 +1606,7 @@ QPushButton:checked { border-image: url(:/icons/setup_btn_checked.svg); }
- QCheckBox {
- spacing: 8px;
- background-color: transparent;
- font-size: 14px;
- font-weight: bold;
-
-color: rgba(255, 255, 255, 153);
-}
-
-QCheckBox::indicator {
-width: 14px;
- height: 14px;
- border: 2px solid rgb(74,100,255);
- border-radius: 4px;
-}
-QCheckBox::indicator:unchecked { background-color: transparent; }
-QCheckBox::indicator:checked { background-color: rgb(74,100,255); }
-
-QPushButton {
+ QPushButton {
width: 40px;
height: 20px;
background-color: transparent;
diff --git a/ui/powercontrol.ui b/ui/powercontrol.ui
index 372cf8395f..021506bc68 100644
--- a/ui/powercontrol.ui
+++ b/ui/powercontrol.ui
@@ -590,6 +590,9 @@ color: #9013fe;
0
+
+ QFrame::NoFrame
+
Qt::ScrollBarAlwaysOff
@@ -602,7 +605,7 @@ color: #9013fe;
0
0
218
- 471
+ 473
@@ -1088,6 +1091,11 @@ QPushButton:disabled {
+
+ adiscope::CustomSwitch
+ QPushButton
+
+
adiscope::DetachDragZone
QWidget
@@ -1105,11 +1113,6 @@ QPushButton:disabled {
QPushButton
-
- adiscope::CustomSwitch
- QPushButton
-
-
QwtThermo
QWidget
diff --git a/ui/preferences.ui b/ui/preferences.ui
index 96f1aed21f..12be93daf1 100644
--- a/ui/preferences.ui
+++ b/ui/preferences.ui
@@ -1591,40 +1591,6 @@ color: white;
- -
-
-
- 0
-
-
-
-
-
-
-
-
-
- -
-
-
- Enable Debug Messages (Only for Debugging, Bugreporting)
-
-
-
- -
-
-
- Qt::Horizontal
-
-
-
- 40
- 20
-
-
-
-
-
-
-
-
@@ -1704,6 +1670,40 @@ color: white;
+ -
+
+
+ 0
+
+
-
+
+
+
+
+
+
+ -
+
+
+ Enable Debug Messages (Only for Debugging, Bugreporting)
+
+
+
+ -
+
+
+ Qt::Horizontal
+
+
+
+ 40
+ 20
+
+
+
+
+
+
diff --git a/ui/signal_generator.ui b/ui/signal_generator.ui
index 383eed93a4..66f6bd9ef3 100644
--- a/ui/signal_generator.ui
+++ b/ui/signal_generator.ui
@@ -121,10 +121,7 @@
true
-
-
- 0
-
+
0
@@ -137,7 +134,7 @@
0
- -
+
-
diff --git a/ui/spectrum_analyzer.ui b/ui/spectrum_analyzer.ui
index 101043b0e5..fec2e2c3a7 100644
--- a/ui/spectrum_analyzer.ui
+++ b/ui/spectrum_analyzer.ui
@@ -313,6 +313,26 @@ min-width: 6em;
10
+
-
+
+
+ -
+
+
+ 0
+
+
+
+ -
+
+
+
+ 200
+ 200
+
+
+
+
-
@@ -461,7 +481,7 @@ min-width: 6em;
- 2
+ 4
@@ -992,6 +1012,9 @@ min-width: 64px;
-
+
+ QFrame::NoFrame
+
Qt::ScrollBarAlwaysOff
@@ -1004,7 +1027,7 @@ min-width: 64px;
0
0
298
- 521
+ 428
@@ -1362,7 +1385,7 @@ color: rgba(255,255,255,51);
-
-
+
0
0
@@ -1409,7 +1432,7 @@ color: rgba(255,255,255,51);
-
-
+
0
0
@@ -1496,6 +1519,9 @@ color: rgba(255,255,255,51);
-
+
+ QFrame::NoFrame
+
Qt::ScrollBarAlwaysOff
@@ -2178,6 +2204,7 @@ border-width: 0px;
+
@@ -2250,23 +2277,7 @@ border-width: 0px;
- QCheckBox {
- spacing: 8px;
- background-color: transparent;
- font-size: 14px;
- font-weight: bold;
-}
-
-QCheckBox::indicator {
- width: 14px;
- height: 14px;
- border: 2px solid rgb(74,100,255);
- border-radius: 4px;
-}
-QCheckBox::indicator:unchecked { background-color: transparent; }
-QCheckBox::indicator:checked { background-color: rgb(74,100,255); }
-
-QPushButton {
+ QPushButton {
width: 40px;
height: 20px;
background-color: transparent;
@@ -2277,6 +2288,42 @@ QPushButton:hover:!pressed:!checked { border-image: url(:/icons/setup_btn_hover.
QPushButton:checked { border-image: url(:/icons/setup_btn_checked.svg); }
+ -
+
+
+ Cursors
+
+
+
+ -
+
+
+ false
+
+
+
+
+
+ true
+
+
+
+ -
+
+
+ Qt::Horizontal
+
+
+ QSizePolicy::Fixed
+
+
+
+ 10
+ 10
+
+
+
+
-
@@ -2351,25 +2398,20 @@ QPushButton:checked { border-image: url(:/icons/setup_btn_checked.svg); }1
- adiscope::InstrumentNotes
+ adiscope::MenuAnim
QWidget
-
+
1
- adiscope::LinkedButton
- QPushButton
-
-
-
- adiscope::CustomSwitch
+ adiscope::CustomPushButton
QPushButton
-
+
- adiscope::MenuAnim
+ adiscope::InstrumentNotes
QWidget
-
+
1
@@ -2379,9 +2421,14 @@ QPushButton:checked { border-image: url(:/icons/setup_btn_checked.svg); }1
- adiscope::CustomPushButton
+ adiscope::CustomSwitch
QPushButton
-
+
+
+
+ adiscope::LinkedButton
+ QPushButton
+
adiscope::MarkerTable
@@ -2400,5 +2447,38 @@ QPushButton:checked { border-image: url(:/icons/setup_btn_checked.svg); }
-
+
+
+ boxCursors
+ toggled(bool)
+ btnCursors
+ setEnabled(bool)
+
+
+ 654
+ 635
+
+
+ 719
+ 635
+
+
+
+
+ btnCursors
+ toggled(bool)
+ btnSettings
+ setChecked(bool)
+
+
+ 719
+ 635
+
+
+ 922
+ 35
+
+
+
+