From b478ef76de41fc729b14eb683514e2f862591fd2 Mon Sep 17 00:00:00 2001 From: Jonas Schumacher Date: Wed, 20 Mar 2024 09:18:05 +0100 Subject: [PATCH 01/14] Fix `axes` for `RegularGridPositions` (#72) Add axes to Base Co-authored-by: Jonas Schumacher --- src/Positions/Positions.jl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Positions/Positions.jl b/src/Positions/Positions.jl index 0c2560de..2bccf64f 100644 --- a/src/Positions/Positions.jl +++ b/src/Positions/Positions.jl @@ -83,7 +83,7 @@ function range(grid::RegularGridPositions, dim::Int) end end ndims(grid::RegularGridPositions) = length(grid.shape) -axes(grid::RegularGridPositions) = tuple([range(grid, i) for i in 1:ndims(grid)]...) +Base.axes(grid::RegularGridPositions) = tuple([range(grid, i) for i in 1:ndims(grid)]...) RegularGridPositions(shape, fov, center) = RegularGridPositions(shape, fov, center, ones(Int,length(shape))) From 64527541c940961c0b52e9e5bf02c6ec1cdcabc8 Mon Sep 17 00:00:00 2001 From: Jonas Schumacher Date: Wed, 20 Mar 2024 09:40:11 +0100 Subject: [PATCH 02/14] Patch release bump --- Project.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Project.toml b/Project.toml index 2f052824..65590171 100644 --- a/Project.toml +++ b/Project.toml @@ -1,7 +1,7 @@ name = "MPIFiles" uuid = "371237a9-e6c1-5201-9adb-3d8cfa78fa9f" authors = ["Tobias Knopp "] -version = "0.15.0" +version = "0.15.1" [deps] AxisArrays = "39de3d68-74b9-583c-8d2d-e117c070f3a9" From 3db639123e094c14eabb0dedadb1c17ef706f052 Mon Sep 17 00:00:00 2001 From: Jonas Schumacher Date: Wed, 27 Mar 2024 09:13:30 +0100 Subject: [PATCH 03/14] Add Dependabot --- .github/dependabot.yml | 7 +++++++ 1 file changed, 7 insertions(+) create mode 100644 .github/dependabot.yml diff --git a/.github/dependabot.yml b/.github/dependabot.yml new file mode 100644 index 00000000..700707ce --- /dev/null +++ b/.github/dependabot.yml @@ -0,0 +1,7 @@ +# https://docs.github.com/github/administering-a-repository/configuration-options-for-dependency-updates +version: 2 +updates: + - package-ecosystem: "github-actions" + directory: "/" # Location of package manifests + schedule: + interval: "weekly" From 59260ddc3fecd6ae1a04eb5418b418e0c5956aae Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 27 Mar 2024 08:55:40 +0000 Subject: [PATCH 04/14] Bump codecov/codecov-action from 3 to 4 (#74) Bumps [codecov/codecov-action](https://github.com/codecov/codecov-action) from 3 to 4. - [Release notes](https://github.com/codecov/codecov-action/releases) - [Changelog](https://github.com/codecov/codecov-action/blob/main/CHANGELOG.md) - [Commits](https://github.com/codecov/codecov-action/compare/v3...v4) --- updated-dependencies: - dependency-name: codecov/codecov-action dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/ci.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 88d4a4a6..aa55a2b1 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -43,7 +43,7 @@ jobs: - uses: julia-actions/julia-buildpkg@v1 - uses: julia-actions/julia-runtest@v1 - uses: julia-actions/julia-processcoverage@v1 - - uses: codecov/codecov-action@v3 + - uses: codecov/codecov-action@v4 with: file: lcov.info docs: From 11b25d1a6be16e2231b5f300e1203e84ba473137 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 27 Mar 2024 08:56:47 +0000 Subject: [PATCH 05/14] Bump actions/cache from 3 to 4 (#73) Bumps [actions/cache](https://github.com/actions/cache) from 3 to 4. - [Release notes](https://github.com/actions/cache/releases) - [Changelog](https://github.com/actions/cache/blob/main/RELEASES.md) - [Commits](https://github.com/actions/cache/compare/v3...v4) --- updated-dependencies: - dependency-name: actions/cache dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/ci.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index aa55a2b1..a98ab3ec 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -30,7 +30,7 @@ jobs: with: version: ${{ matrix.version }} arch: ${{ matrix.arch }} - - uses: actions/cache@v3 + - uses: actions/cache@v4 env: cache-name: cache-artifacts with: From a57d11ac4a34b06af1386aac18d54e46ae74e473 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 2 Apr 2024 18:55:04 +0200 Subject: [PATCH 06/14] Bump julia-actions/setup-julia from 1 to 2 (#75) Bumps [julia-actions/setup-julia](https://github.com/julia-actions/setup-julia) from 1 to 2. - [Release notes](https://github.com/julia-actions/setup-julia/releases) - [Commits](https://github.com/julia-actions/setup-julia/compare/v1...v2) --- updated-dependencies: - dependency-name: julia-actions/setup-julia dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/ci.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index a98ab3ec..838d24a0 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -26,7 +26,7 @@ jobs: - x64 steps: - uses: actions/checkout@v4 - - uses: julia-actions/setup-julia@v1 + - uses: julia-actions/setup-julia@v2 with: version: ${{ matrix.version }} arch: ${{ matrix.arch }} @@ -51,7 +51,7 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - - uses: julia-actions/setup-julia@v1 + - uses: julia-actions/setup-julia@v2 with: version: '1' - run: | From b0f88d7e0aa0c5470241696aca88d01dce71c76c Mon Sep 17 00:00:00 2001 From: Justin <38977690+jusack@users.noreply.github.com> Date: Fri, 5 Apr 2024 11:37:33 +0200 Subject: [PATCH 07/14] fix SFDatabase for smaller calibSizes --- src/DatasetStore/SFDatabase.jl | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/DatasetStore/SFDatabase.jl b/src/DatasetStore/SFDatabase.jl index b62ca003..8a25bbd6 100644 --- a/src/DatasetStore/SFDatabase.jl +++ b/src/DatasetStore/SFDatabase.jl @@ -109,8 +109,8 @@ function _innerGenerateSFDatabase(A,i,sf,b) end N = calibSize(b) A[i,6] = N[1] - A[i,7] = N[2] - A[i,8] = N[3] + A[i,7] = try N[2]; catch; 0 end + A[i,8] = try N[3]; catch; 0 end A[i,9] = rxBandwidth(b) / 1e6 A[i,10] = tracerName(b)[1] A[i,11] = tracerBatch(b)[1] From 121a44a7037ada055cddac53e9c68a816db4fa29 Mon Sep 17 00:00:00 2001 From: Jonas Schumacher Date: Mon, 8 Apr 2024 09:13:44 +0200 Subject: [PATCH 08/14] Fix loading of frequency-selected files (#77) * WIP * Fix transfer function from file * Minor changes * Remove todo --------- Co-authored-by: Jonas Schumacher --- src/Derived.jl | 8 +++++++- src/FrequencyFilter.jl | 2 +- src/Measurements.jl | 12 +++--------- src/SystemMatrix.jl | 4 ++-- src/TransferFunction.jl | 11 ++++++++--- 5 files changed, 21 insertions(+), 16 deletions(-) diff --git a/src/Derived.jl b/src/Derived.jl index fe6b3015..051b1197 100644 --- a/src/Derived.jl +++ b/src/Derived.jl @@ -138,7 +138,13 @@ function measDataTD(f, frames=1:acqNumFrames(f), periods=1:acqNumPeriodsPerFrame end if measIsFourierTransformed(f) - dataTD = irfft(data2, rxNumSamplingPoints(f), 1) + if measIsFrequencySelection(f) + dataPadded = zeros(eltype(data2), (rxNumFrequencies(f), size(data2, 2), size(data2, 3), size(data2, 4))) + dataPadded[measFrequencySelection(f), :, :, :] .= data2 + dataTD = irfft(dataPadded, rxNumSamplingPoints(f), 1) + else + dataTD = irfft(data2, rxNumSamplingPoints(f), 1) + end else dataTD = data2 end diff --git a/src/FrequencyFilter.jl b/src/FrequencyFilter.jl index cf947b08..5b464807 100644 --- a/src/FrequencyFilter.jl +++ b/src/FrequencyFilter.jl @@ -68,7 +68,7 @@ function filterFrequencies(f::MPIFile; SNRThresh=-1, minFreq=0, idx = measIsFrequencySelection(f) ? measFrequencySelection(f) : idx = 1:nFreq SNRAll = calibSNR(f) - if SNRAll != nothing + if !isnothing(SNRAll) SNR[idx,:] = SNRAll[:,:,1] end end diff --git a/src/Measurements.jl b/src/Measurements.jl index dd134f0d..07b6efe4 100644 --- a/src/Measurements.jl +++ b/src/Measurements.jl @@ -321,7 +321,7 @@ Supported keyword arguments: """ function getMeasurementsFD(f::MPIFile, args...; loadasreal=false, transposed=false, frequencies=nothing, - tfCorrection=rxHasTransferFunction(f), kargs...) + tfCorrection=rxHasTransferFunction(f), kargs...) data = getMeasurements(f, args..., tfCorrection=false; kargs...) @@ -354,13 +354,13 @@ function getMeasurementsFD(f::MPIFile, args...; end end - if frequencies != nothing + if !isnothing(frequencies) # here we merge frequencies and channels data = data[frequencies, :, :] end if transposed - if frequencies != nothing + if !isnothing(frequencies) data = permutedims(data, [3,1,2]) else data = permutedims(data, [4,1,2,3]) @@ -374,12 +374,6 @@ function getMeasurementsFD(f::MPIFile, args...; return data end - - - - - - function spectralLeakageCorrectedData(dataIn) @debug "Apply Spectral Cleaning" diff --git a/src/SystemMatrix.jl b/src/SystemMatrix.jl index c98c71fd..8fcb489a 100644 --- a/src/SystemMatrix.jl +++ b/src/SystemMatrix.jl @@ -15,7 +15,7 @@ function getSystemMatrix(f::MPIFile, frequencies=nothing; tfCorrection=rxHasTransferFunction(f), numPeriodAverages=1, numPeriodGrouping=1, kargs...) - if frequencies == nothing + if isnothing(frequencies) frequencies = filterFrequencies(f) end @@ -32,7 +32,7 @@ function getSystemMatrix(f::MPIFile, frequencies=nothing; if tfCorrection && !measIsTFCorrected(f) tf = rxTransferFunction(f) - if tf != nothing + if !isnothing(tf) _corrTFSF(S,tf[rowsToSubsampledRows(f,frequencies)]) @info "System matrix has been corrected with a Transfer Function. Name of TF: $(rxTransferFunctionFileName(f))" else diff --git a/src/TransferFunction.jl b/src/TransferFunction.jl index 38d42af4..02bb61ea 100644 --- a/src/TransferFunction.jl +++ b/src/TransferFunction.jl @@ -81,7 +81,7 @@ function TransferFunction(file::MPIFile) tf_file = rxTransferFunction(file) inductionFactor = rxInductionFactor(file) f = collect(rfftfreq(rxNumSamplingPoints(file), rxBandwidth(file)*2)) - return TransferFunction(f, abs.(tf_file), angle.(tf_file), inductionFactor) + return TransferFunction(f, abs.(tf_file), angle.(tf_file), inductionFactor=inductionFactor) end """ @@ -261,7 +261,7 @@ function setTF(b::BrukerFile, filenameTF::AbstractString) A = readlines(joinpath(filepath(b),"acqp")) l = findfirst( s->occursin("ACQ_comment", s), A) - if l == nothing + if isnothing(l) ll = findfirst( s->occursin("ACQ_experiment_mode", s), A) insert!(A, ll, "##\$ACQ_comment=( 2048 )") insert!(A, ll+1, "<$(filenameTF)>") @@ -274,7 +274,7 @@ function setTF(b::BrukerFile, filenameTF::AbstractString) # For some reason ACQ_comment is also in the method file -> also change that B = readlines(joinpath(filepath(b),"method")) g = findfirst( s->occursin("ACQ_comment", s), B) - if g != nothing + if !isnothing(g) B[g+1] = "<$(filenameTF)>" _writeBrukerParamFile(b, B, "method") end @@ -311,3 +311,8 @@ function setTF(f::MDFFile, filenameTF::AbstractString) end return end + +function setTF(f::MDFv2InMemory, tf::TransferFunction) + rxTransferFunction(f, sampleTF(tf, f)) + rxInductionFactor(f, tf.inductionFactor) +end \ No newline at end of file From 43c4c67c5e72c02e6db9837e2b3e1126c8e7a99c Mon Sep 17 00:00:00 2001 From: Jonas Schumacher Date: Mon, 8 Apr 2024 10:00:09 +0200 Subject: [PATCH 09/14] Patch release bump --- Project.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Project.toml b/Project.toml index 65590171..7cc58606 100644 --- a/Project.toml +++ b/Project.toml @@ -1,7 +1,7 @@ name = "MPIFiles" uuid = "371237a9-e6c1-5201-9adb-3d8cfa78fa9f" authors = ["Tobias Knopp "] -version = "0.15.1" +version = "0.15.2" [deps] AxisArrays = "39de3d68-74b9-583c-8d2d-e117c070f3a9" From ab516c35825bdddca3ee8acec310103a3b6dfa30 Mon Sep 17 00:00:00 2001 From: Jonas Schumacher Date: Wed, 10 Apr 2024 12:13:01 +0200 Subject: [PATCH 10/14] Minor fixes of checking (#78) * Fixes * Fix tests --------- Co-authored-by: Jonas Schumacher --- src/MDFInMemory.jl | 90 ++++++++++++++++++++--------------------- src/TransferFunction.jl | 3 ++ test/MDFInMemory.jl | 80 ++++++++++++++++++------------------ 3 files changed, 88 insertions(+), 85 deletions(-) diff --git a/src/MDFInMemory.jl b/src/MDFInMemory.jl index 32af6a26..303cab19 100644 --- a/src/MDFInMemory.jl +++ b/src/MDFInMemory.jl @@ -660,27 +660,27 @@ function check(part::MDFv2Acquisition, variables::MDFv2Variables) # Check dimensions of `gradient` field if !isnothing(part.gradient) if isnothing(variables.J) - variables.J = size(part.gradient, 1) + variables.J = size(part.gradient, 4) else - @assert variables.J == size(part.gradient, 1) "Inconsistent dimension J in `gradient` in `acquisition`." + @assert variables.J == size(part.gradient, 4) "Inconsistent dimension J in `gradient` in `acquisition`." end if isnothing(variables.Y) - variables.Y = size(part.gradient, 2) + variables.Y = size(part.gradient, 3) else - @assert variables.Y == size(part.gradient, 1) "Inconsistent dimension Y in `gradient` in `acquisition`." + @assert variables.Y == size(part.gradient, 3) "Inconsistent dimension Y in `gradient` in `acquisition`." end - @assert size(part.gradient, 3) == 3 "Inconsistent third dimension in `gradient` in `acquisition`." - @assert size(part.gradient, 4) == 3 "Inconsistent fourth dimension in `gradient` in `acquisition`." + @assert size(part.gradient, 1) == 3 "Inconsistent first dimension in `gradient` in `acquisition`." + @assert size(part.gradient, 2) == 3 "Inconsistent second dimension in `gradient` in `acquisition`." end # Check dimensions of `offsetField` field if !isnothing(part.offsetField) if isnothing(variables.J) - variables.J = size(part.offsetField, 1) + variables.J = size(part.offsetField, 3) else - @assert variables.J == size(part.offsetField, 1) "Inconsistent dimension J in `offsetField` in `acquisition`." + @assert variables.J == size(part.offsetField, 3) "Inconsistent dimension J in `offsetField` in `acquisition`." end if isnothing(variables.Y) @@ -689,7 +689,7 @@ function check(part::MDFv2Acquisition, variables::MDFv2Variables) @assert variables.Y == size(part.offsetField, 2) "Inconsistent dimension Y in `offsetField` in `acquisition`." end - @assert size(part.offsetField, 3) == 3 "Inconsistent third dimension in `offsetField` in `acquisition`." + @assert size(part.offsetField, 1) == 3 "Inconsistent first dimension in `offsetField` in `acquisition`." end end @@ -699,26 +699,26 @@ function check(part::MDFv2Drivefield, variables::MDFv2Variables) variables.D = part.numChannels end if isnothing(variables.F) - variables.F = size(part.divider, 2) + variables.F = size(part.divider, 1) end if isnothing(variables.J) - variables.J = size(part.phase, 1) + variables.J = size(part.phase, 3) end # Then check dimensions for multidimensional fields - @assert variables.D == size(part.divider, 1) "Inconsistent dimension D in `divider` in `drivefield`." - @assert variables.F == size(part.divider, 2) "Inconsistent dimension F in `divider` in `drivefield`." + @assert variables.F == size(part.divider, 1) "Inconsistent dimension F in `divider` in `drivefield`." + @assert variables.D == size(part.divider, 2) "Inconsistent dimension D in `divider` in `drivefield`." - @assert variables.J == size(part.phase, 1) "Inconsistent dimension J in `phase` in `drivefield`." + @assert variables.F == size(part.phase, 1) "Inconsistent dimension F in `phase` in `drivefield`." @assert variables.D == size(part.phase, 2) "Inconsistent dimension D in `phase` in `drivefield`." - @assert variables.F == size(part.phase, 3) "Inconsistent dimension F in `phase` in `drivefield`." + @assert variables.J == size(part.phase, 3) "Inconsistent dimension J in `phase` in `drivefield`." - @assert variables.J == size(part.strength, 1) "Inconsistent dimension J in `strength` in `drivefield`." + @assert variables.F == size(part.strength, 1) "Inconsistent dimension F in `strength` in `drivefield`." @assert variables.D == size(part.strength, 2) "Inconsistent dimension D in `strength` in `drivefield`." - @assert variables.F == size(part.strength, 3) "Inconsistent dimension F in `strength` in `drivefield`." + @assert variables.J == size(part.strength, 3) "Inconsistent dimension J in `strength` in `drivefield`." - @assert variables.D == size(part.waveform, 1) "Inconsistent dimension D in `waveform` in `drivefield`." - @assert variables.F == size(part.waveform, 2) "Inconsistent dimension F in `waveform` in `drivefield`." + @assert variables.F == size(part.waveform, 1) "Inconsistent dimension F in `waveform` in `drivefield`." + @assert variables.D == size(part.waveform, 2) "Inconsistent dimension D in `waveform` in `drivefield`." end function check(part::MDFv2Receiver, variables::MDFv2Variables) @@ -732,21 +732,21 @@ function check(part::MDFv2Receiver, variables::MDFv2Variables) end if !isnothing(part.dataConversionFactor) - @assert variables.C == size(part.dataConversionFactor, 1) "Inconsistent dimension C in `dataConversionFactor` in `receiver`." - @assert size(part.dataConversionFactor, 2) == 2 "Inconsistent second dimension in `dataConversionFactor` in `receiver`." + @assert variables.C == size(part.dataConversionFactor, 2) "Inconsistent dimension C in `dataConversionFactor` in `receiver`." + @assert size(part.dataConversionFactor, 1) == 2 "Inconsistent first dimension in `dataConversionFactor` in `receiver`." end if !isnothing(part.inductionFactor) - @assert variables.C == size(part.inductionFactor, 1) "Inconsistent dimension C in `inductionFactor` in `receiver`." + @assert variables.C == length(part.inductionFactor) "Inconsistent dimension C in `inductionFactor` in `receiver`." end if !isnothing(part.transferFunction) - @assert variables.C == size(part.transferFunction, 1) "Inconsistent dimension C in `transferFunction` in `receiver`." + @assert variables.C == size(part.transferFunction, 2) "Inconsistent dimension C in `transferFunction` in `receiver`." if isnothing(variables.K) - variables.K = size(part.transferFunction, 2) + variables.K = size(part.transferFunction, 1) else - @assert variables.K == size(part.transferFunction, 2) "Inconsistent dimension K in `transferFunction` in `receiver`." + @assert variables.K == size(part.transferFunction, 1) "Inconsistent dimension K in `transferFunction` in `receiver`." end end end @@ -781,28 +781,28 @@ function check(part::MDFv2Measurement, variables::MDFv2Variables) if isnothing(variables.J) if !part.isSparsityTransformed - @warn "Can't determine variable J for measurement from `subsamplingIndices` since the dataset is not sparsity transformed." + @debug "Can't determine variable J for measurement from `subsamplingIndices` since the dataset is not sparsity transformed." else variables.J = size(part.subsamplingIndices, 1) end end if isnothing(variables.C) if !part.isSparsityTransformed - @warn "Can't determine variable C for measurement from `subsamplingIndices` since the dataset is not sparsity transformed. Should happen in receiver." + @debug "Can't determine variable C for measurement from `subsamplingIndices` since the dataset is not sparsity transformed. Should happen in receiver." else variables.C = size(part.subsamplingIndices, 2) end end if isnothing(variables.K) if !part.isSparsityTransformed - @warn "Can't determine variable K for measurement from `subsamplingIndices` since the dataset is not sparsity transformed. Should happen in receiver." + @debug "Can't determine variable K for measurement from `subsamplingIndices` since the dataset is not sparsity transformed. Should happen in receiver." else variables.K = size(part.subsamplingIndices, 3) end end if isnothing(variables.B) if !part.isSparsityTransformed - @warn "Can't determine variable B for measurement from `subsamplingIndices` since the dataset is not sparsity transformed. Should happen in receiver." + @debug "Can't determine variable B for measurement from `subsamplingIndices` since the dataset is not sparsity transformed. Should happen in receiver." else variables.B = size(part.subsamplingIndices, 4) end @@ -829,10 +829,10 @@ function check(part::MDFv2Measurement, variables::MDFv2Variables) if part.isSparsityTransformed # J, C, K and B should be defined by now - @assert variables.J == size(part.subsamplingIndices, 1) "Inconsistent dimension J in `subsamplingIndices` in `measurement`." - @assert variables.C == size(part.subsamplingIndices, 2) "Inconsistent dimension C in `subsamplingIndices` in `measurement`." - @assert variables.K == size(part.subsamplingIndices, 3) "Inconsistent dimension K in `subsamplingIndices` in `measurement`." - @assert variables.B == size(part.subsamplingIndices, 4) "Inconsistent dimension B in `subsamplingIndices` in `measurement`." + @assert variables.B == size(part.subsamplingIndices, 1) "Inconsistent dimension B in `subsamplingIndices` in `measurement`." + @assert variables.K == size(part.subsamplingIndices, 2) "Inconsistent dimension K in `subsamplingIndices` in `measurement`." + @assert variables.C == size(part.subsamplingIndices, 3) "Inconsistent dimension C in `subsamplingIndices` in `measurement`." + @assert variables.J == size(part.subsamplingIndices, 4) "Inconsistent dimension J in `subsamplingIndices` in `measurement`." end end @@ -851,11 +851,11 @@ function check(part::MDFv2Calibration, variables::MDFv2Variables) if !isnothing(part.offsetFields) if isnothing(variables.O) - variables.O = size(part.offsetFields, 1) + variables.O = size(part.offsetFields, 2) else - @assert variables.O == size(part.offsetFields, 1) "Inconsistent dimension O in `offsetFields` in `calibration`." + @assert variables.O == size(part.offsetFields, 2) "Inconsistent dimension O in `offsetFields` in `calibration`." end - @assert size(part.offsetFields, 2) == 3 "Inconsistent second dimension in `offsetFields` in `calibration`." + @assert size(part.offsetFields, 1) == 3 "Inconsistent first dimension in `offsetFields` in `calibration`." end if !isnothing(part.order) @@ -864,8 +864,8 @@ function check(part::MDFv2Calibration, variables::MDFv2Variables) if !isnothing(part.positions) # O must be defined by now - @assert variables.O == size(part.positions, 1) "Inconsistent dimension O in `positions` in `calibration`." - @assert size(part.positions, 2) == 3 "Inconsistent second dimension in `positions` in `calibration`." + @assert variables.O == size(part.positions, 2) "Inconsistent dimension O in `positions` in `calibration`." + @assert size(part.positions, 1) == 3 "Inconsistent first dimension in `positions` in `calibration`." end if !isnothing(part.size) @@ -876,9 +876,9 @@ function check(part::MDFv2Calibration, variables::MDFv2Variables) if !isnothing(part.snr) if isnothing(variables.J) - variables.J = size(part.snr, 1) + variables.J = size(part.snr, 3) else - @assert variables.J == size(part.snr, 1) "Inconsistent dimension J in `snr` in `calibration`." + @assert variables.J == size(part.snr, 3) "Inconsistent dimension J in `snr` in `calibration`." end if isnothing(variables.C) @@ -888,9 +888,9 @@ function check(part::MDFv2Calibration, variables::MDFv2Variables) end if isnothing(variables.K) - variables.K = size(part.snr, 3) + variables.K = size(part.snr, 1) else - @assert variables.K == size(part.snr, 3) "Inconsistent dimension K in `snr` in `calibration`." + @assert variables.K == size(part.snr, 1) "Inconsistent dimension K in `snr` in `calibration`." end end end @@ -898,7 +898,7 @@ end function check(part::MDFv2Reconstruction, variables::MDFv2Variables) # Pick variables first if isnothing(variables.Q) - variables.Q = size(part.data, 1) + variables.Q = size(part.data, 3) end if isnothing(variables.P) variables.P = size(part.data, 2) @@ -924,8 +924,8 @@ function check(part::MDFv2Reconstruction, variables::MDFv2Variables) end if !isnothing(part.positions) - @assert variables.P == size(part.positions, 1) "Inconsistent dimension P in `positions` in `reconstruction`." - @assert size(part.positions, 2) == 3 "Inconsistent second dimension in `positions` in `reconstruction`." + @assert variables.P == size(part.positions, 2) "Inconsistent dimension P in `positions` in `reconstruction`." + @assert size(part.positions, 1) == 3 "Inconsistent first dimension in `positions` in `reconstruction`." end if !isnothing(part.size) diff --git a/src/TransferFunction.jl b/src/TransferFunction.jl index 02bb61ea..1961206e 100644 --- a/src/TransferFunction.jl +++ b/src/TransferFunction.jl @@ -241,6 +241,9 @@ end function sampleTF(tf::TransferFunction, f::MPIFile) freq = rxFrequencies(f) + if measIsFrequencySelection(f) + freq = freq[measFrequencySelection(f)] + end numChan = rxNumChannels(f) return tf(freq,1:numChan) end diff --git a/test/MDFInMemory.jl b/test/MDFInMemory.jl index 23dac34f..c2b4ec47 100644 --- a/test/MDFInMemory.jl +++ b/test/MDFInMemory.jl @@ -28,7 +28,6 @@ end fnSMBruker = joinpath(datadir,"BrukerStore","20141121_130749_CalibrationScans_1_1","76") fnSM1DBruker = joinpath(datadir,"BrukerStore","20170807_142514_Service_1_1","89") - fnMeasV1 = joinpath(tmpdir,"mdfim","measurement_V1.mdf") fnMeasV2 = joinpath(tmpdir,"mdfim","measurement_V2.mdf") fnSMV1 = joinpath(tmpdir,"mdfim","systemMatrix_V1.mdf") @@ -56,7 +55,8 @@ end mdfv2InMemory = MDFv2InMemory(mdfv2) @test typeof(mdfv2InMemory) <: MDFv2InMemory - message = "There is an inconsistency in the given in-memory MDF. The message is: `Inconsistent dimension J in `gradient` in `acquisition`.`." + # The file seems to have some transposed fields! + message = "There is an inconsistency in the given in-memory MDF. The message is: `Inconsistent dimension D in `divider` in `drivefield`.`." @test_logs (:warn, message) saveasMDF(fnMeasV2_converted, mdfv2InMemory) mdf = MPIFile(fnMeasV2_converted) @@ -346,33 +346,33 @@ end drivefield = MDFv2Drivefield( baseFrequency = 40e3, cycle = 1600/40e3, - divider = fill(1600, (D, F)), + divider = fill(1600, (F, D)), numChannels = D, - phase = fill(0.0, (J, D, F)), - strength = fill(1.0, (J, D, F)), - waveform = fill("sine", (D, F)), + phase = fill(0.0, (F, D, J)), + strength = fill(1.0, (F, D, J)), + waveform = fill("sine", (F, D)), ) receiver = MDFv2Receiver( bandwidth = 20e3, - dataConversionFactor = repeat([1/2^16 0], C), + dataConversionFactor = repeat([1/2^16 0]', outer=(1, C)), inductionFactor = fill(1.0, C), numChannels = C, numSamplingPoints = V, - transferFunction = fill(1+0.5im, (C, K)), + transferFunction = fill(1+0.5im, (K, C)), unit = "V" ) mdf.acquisition = MDFv2Acquisition( - gradient = fill(0.0, (J, Y, 3, 3)), + gradient = fill(0.0, (3, 3, Y, J)), numAverages = 1, numFrames = N, numPeriodsPerFrame = J, - offsetField = fill(0.0, (J, Y, 3)), + offsetField = fill(0.0, (3, Y, J)), startTime = DateTime("2021-04-26T17:12:21.686"), drivefield = drivefield, receiver = receiver ) mdf.measurement = MDFv2Measurement(; - data = fill(0, (N, J, C, K)), + data = fill(0, (K, C, J, N)), framePermutation = fill(0, N), frequencySelection = collect(1:K), isBackgroundCorrected = true, @@ -385,26 +385,26 @@ end isSpectralLeakageCorrected = true, isTransferFunctionCorrected = true, sparsityTransformation = "DCT-I", - subsamplingIndices = fill(0, (J, C, K, B)) + subsamplingIndices = fill(0, (B, K, C, J)) ) mdf.calibration = MDFv2Calibration( deltaSampleSize = fill(0.001, 3), fieldOfView = fill(0.2, 3), fieldOfViewCenter = fill(0.0, 3), method = "robot", - offsetFields = fill(0.0, (O, 3)), + offsetFields = fill(0.0, (3, O)), order = "xyz", - positions = fill(0.0, (O, 3)), + positions = fill(0.0, (3, O)), size = [1, 1, 1], - snr = fill(0.0, (J, C, K)) + snr = fill(0.0, (K, C, J)) ) mdf.reconstruction = MDFv2Reconstruction( - data = fill(0, (Q, P, S)), + data = fill(0, (S, P, Q)), fieldOfView = fill(0.2, 3), fieldOfViewCenter = fill(0.0, 3), isOverscanRegion = fill(false, P), order = "xyz", - positions = fill(0.0, (P, 3)), + positions = fill(0.0, (3, P)), size = [1, 1, 1] ) @@ -532,23 +532,23 @@ end test_mdf_replacement(mdf, :tracerVolume, fill(1.0, A+1), "Inconsistent dimensions in `volume` in `tracer`.") # Drivefield - test_mdf_replacement(mdf, :dfDivider, fill(1600, (D+1, F)), "Inconsistent dimension D in `divider` in `drivefield`.") - test_mdf_replacement(mdf, :dfDivider, fill(1600, (D, F+1)), "Inconsistent dimension F in `divider` in `drivefield`.") # Works because F has been determined earlier - test_mdf_replacement(mdf, :dfPhase, fill(0.0, (J+1, D, F)), "Inconsistent dimension J in `phase` in `drivefield`.") # Works because J has been determined earlier - test_mdf_replacement(mdf, :dfPhase, fill(0.0, (J, D+1, F)), "Inconsistent dimension D in `phase` in `drivefield`.") - test_mdf_replacement(mdf, :dfPhase, fill(0.0, (J, D, F+1)), "Inconsistent dimension F in `phase` in `drivefield`.") - test_mdf_replacement(mdf, :dfStrength, fill(1.0, (J+1, D, F)), "Inconsistent dimension J in `strength` in `drivefield`.") - test_mdf_replacement(mdf, :dfStrength, fill(1.0, (J, D+1, F)), "Inconsistent dimension D in `strength` in `drivefield`.") - test_mdf_replacement(mdf, :dfStrength, fill(1.0, (J, D, F+1)), "Inconsistent dimension F in `strength` in `drivefield`.") - test_mdf_replacement(mdf, :dfWaveform, fill("sine", (D+1, F)), "Inconsistent dimension D in `waveform` in `drivefield`.") - test_mdf_replacement(mdf, :dfWaveform, fill("sine", (D, F+1)), "Inconsistent dimension F in `waveform` in `drivefield`.") + test_mdf_replacement(mdf, :dfDivider, fill(1600, (F, D+1)), "Inconsistent dimension D in `divider` in `drivefield`.") + test_mdf_replacement(mdf, :dfDivider, fill(1600, (F+1, D)), "Inconsistent dimension F in `divider` in `drivefield`.") # Works because F has been determined earlier + test_mdf_replacement(mdf, :dfPhase, fill(0.0, (F, D, J+1)), "Inconsistent dimension J in `phase` in `drivefield`.") # Works because J has been determined earlier + test_mdf_replacement(mdf, :dfPhase, fill(0.0, (F, D+1, J)), "Inconsistent dimension D in `phase` in `drivefield`.") + test_mdf_replacement(mdf, :dfPhase, fill(0.0, (F+1, D, J)), "Inconsistent dimension F in `phase` in `drivefield`.") + test_mdf_replacement(mdf, :dfStrength, fill(1.0, (F, D, J+1)), "Inconsistent dimension J in `strength` in `drivefield`.") + test_mdf_replacement(mdf, :dfStrength, fill(1.0, (F, D+1, J)), "Inconsistent dimension D in `strength` in `drivefield`.") + test_mdf_replacement(mdf, :dfStrength, fill(1.0, (F+1, D, J)), "Inconsistent dimension F in `strength` in `drivefield`.") + test_mdf_replacement(mdf, :dfWaveform, fill("sine", (F, D+1)), "Inconsistent dimension D in `waveform` in `drivefield`.") + test_mdf_replacement(mdf, :dfWaveform, fill("sine", (F+1, D)), "Inconsistent dimension F in `waveform` in `drivefield`.") # Receiver - test_mdf_replacement(mdf, :rxDataConversionFactor, repeat([1/2^16 0], C+1), "Inconsistent dimension C in `dataConversionFactor` in `receiver`.") - test_mdf_replacement(mdf, :rxDataConversionFactor, repeat([1/2^16 0 0], C), "Inconsistent second dimension in `dataConversionFactor` in `receiver`.") + test_mdf_replacement(mdf, :rxDataConversionFactor, repeat([1/2^16 0]', outer=(1, C+1)), "Inconsistent dimension C in `dataConversionFactor` in `receiver`.") + test_mdf_replacement(mdf, :rxDataConversionFactor, repeat([1/2^16 0 0]', outer=(1, C)), "Inconsistent first dimension in `dataConversionFactor` in `receiver`.") test_mdf_replacement(mdf, :rxInductionFactor, fill(1.0, C+1), "Inconsistent dimension C in `inductionFactor` in `receiver`.") - test_mdf_replacement(mdf, :rxTransferFunction, fill(1+0.5im, (C+1, K)), "Inconsistent dimension C in `transferFunction` in `receiver`.") - test_mdf_replacement(mdf, :rxTransferFunction, fill(1+0.5im, (C, K+1)), "Inconsistent dimension K in `transferFunction` in `receiver`.") + test_mdf_replacement(mdf, :rxTransferFunction, fill(1+0.5im, (K, C+1)), "Inconsistent dimension C in `transferFunction` in `receiver`.") + test_mdf_replacement(mdf, :rxTransferFunction, fill(1+0.5im, (K+1, C)), "Inconsistent dimension K in `transferFunction` in `receiver`.") # Measurement test_mdf_replacement(mdf, :measFramePermutation, fill(0, N+1), "Inconsistent dimension N in `framePermutation` in `measurement`.") @@ -560,24 +560,24 @@ end test_mdf_replacement(mdf, :calibDeltaSampleSize, fill(0.001, 4), "Inconsistent length in `deltaSampleSize` in `calibration`.") test_mdf_replacement(mdf, :calibFieldOfView, fill(0.2, 4), "Inconsistent length in `fieldOfView` in `calibration`.") test_mdf_replacement(mdf, :calibFieldOfViewCenter, fill(0.0, 4), "Inconsistent length in `fieldOfViewCenter` in `calibration`.") - test_mdf_replacement(mdf, :calibOffsetFields, fill(0.0, (O+1, 3)), "Inconsistent dimension O in `offsetFields` in `calibration`.") - test_mdf_replacement(mdf, :calibOffsetFields, fill(0.0, (O, 4)), "Inconsistent second dimension in `offsetFields` in `calibration`.") + test_mdf_replacement(mdf, :calibOffsetFields, fill(0.0, (3, O+1)), "Inconsistent dimension O in `offsetFields` in `calibration`.") + test_mdf_replacement(mdf, :calibOffsetFields, fill(0.0, (4, O)), "Inconsistent first dimension in `offsetFields` in `calibration`.") test_mdf_replacement(mdf, :calibOrder, "bla", "Wrong `order` of `bla` in `calibration`.") - test_mdf_replacement(mdf, :calibPositions, fill(0.0, (O+1, 3)), "Inconsistent dimension O in `positions` in `calibration`.") - test_mdf_replacement(mdf, :calibPositions, fill(0.0, (O, 4)), "Inconsistent second dimension in `positions` in `calibration`.") + test_mdf_replacement(mdf, :calibPositions, fill(0.0, (3, O+1)), "Inconsistent dimension O in `positions` in `calibration`.") + test_mdf_replacement(mdf, :calibPositions, fill(0.0, (3+1, O)), "Inconsistent first dimension in `positions` in `calibration`.") test_mdf_replacement(mdf, :calibSize, [1, 1, 1, 1], "Inconsistent length in `size` in `calibration`.") test_mdf_replacement(mdf, :calibSize, [1, 1, 2], "The product of `size` with `[1, 1, 2]` must equal O.") - test_mdf_replacement(mdf, :calibSnr, fill(0.0, (J+1, C, K)), "Inconsistent dimension J in `snr` in `calibration`.") - test_mdf_replacement(mdf, :calibSnr, fill(0.0, (J, C+1, K)), "Inconsistent dimension C in `snr` in `calibration`.") - test_mdf_replacement(mdf, :calibSnr, fill(0.0, (J, C, K+1)), "Inconsistent dimension K in `snr` in `calibration`.") + test_mdf_replacement(mdf, :calibSnr, fill(0.0, (K, C, J+1)), "Inconsistent dimension J in `snr` in `calibration`.") + test_mdf_replacement(mdf, :calibSnr, fill(0.0, (K, C+1, J)), "Inconsistent dimension C in `snr` in `calibration`.") + test_mdf_replacement(mdf, :calibSnr, fill(0.0, (K+1, C, J)), "Inconsistent dimension K in `snr` in `calibration`.") # Reconstruction test_mdf_replacement(mdf, :recoFieldOfView, fill(0.2, 4), "Inconsistent length in `fieldOfView` in `reconstruction`.") test_mdf_replacement(mdf, :recoFieldOfViewCenter, fill(0.0, 4), "Inconsistent length in `fieldOfViewCenter` in `reconstruction`.") test_mdf_replacement(mdf, :recoIsOverscanRegion, fill(false, P+1), "Inconsistent length in `isOverscanRegion` in `reconstruction`.") test_mdf_replacement(mdf, :recoOrder, "bla", "Wrong `order` of `bla` in `reconstruction`.") - test_mdf_replacement(mdf, :recoPositions, fill(0.0, (P+1, 3)), "Inconsistent dimension P in `positions` in `reconstruction`.") - test_mdf_replacement(mdf, :recoPositions, fill(0.0, (P, 4)), "Inconsistent second dimension in `positions` in `reconstruction`.") + test_mdf_replacement(mdf, :recoPositions, fill(0.0, (3, P+1)), "Inconsistent dimension P in `positions` in `reconstruction`.") + test_mdf_replacement(mdf, :recoPositions, fill(0.0, (3+1, P)), "Inconsistent first dimension in `positions` in `reconstruction`.") test_mdf_replacement(mdf, :recoSize, [1, 1, 1, 1], "Inconsistent length in `size` in `reconstruction`.") test_mdf_replacement(mdf, :recoSize, [1, 1, 2], "The product of `size` with `[1, 1, 2]` must equal P.") end From 0ea9992621775a7b917f365c3df08be330d29c83 Mon Sep 17 00:00:00 2001 From: Jonas Schumacher Date: Wed, 10 Apr 2024 13:02:19 +0200 Subject: [PATCH 11/14] Add `scannerBoreSize` to exports --- src/MPIFiles.jl | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/MPIFiles.jl b/src/MPIFiles.jl index d0d09a59..63cf7dff 100644 --- a/src/MPIFiles.jl +++ b/src/MPIFiles.jl @@ -59,8 +59,8 @@ export tracerName, tracerBatch, tracerVolume, tracerConcentration, tracerSolute, tracerInjectionTime, tracerVendor # scanner parameters -export scannerFacility, scannerOperator, scannerManufacturer, scannerName, - scannerTopology +export scannerBoreSize, scannerFacility, scannerOperator, scannerManufacturer, + scannerName, scannerTopology # acquisition parameters export acqStartTime, acqNumFrames, acqNumAverages, From c8031c250beeab5b144c9f77a5a3f598558fe770 Mon Sep 17 00:00:00 2001 From: Jonas Schumacher Date: Wed, 10 Apr 2024 13:21:48 +0200 Subject: [PATCH 12/14] Fix error with bore size --- src/MDF.jl | 2 +- src/MDFInMemory.jl | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/MDF.jl b/src/MDF.jl index ea84a2a8..20051f38 100644 --- a/src/MDF.jl +++ b/src/MDF.jl @@ -159,7 +159,7 @@ tracerVendor(f::MDFFileV1)::Union{Vector{String}, Missing} = @keyrequired [f["/t tracerVendor(f::MDFFileV2)::Union{Vector{String}, Missing} = @keyrequired _makeStringArray(f["/tracer/vendor"]) # scanner parameters -scannerBoreSize(f::MDFFile)::Union{String, Nothing} = @keyoptional f["/scanner/boreSize"] +scannerBoreSize(f::MDFFile)::Union{Float64, Nothing} = @keyoptional f["/scanner/boreSize"] scannerFacility(f::MDFFile)::Union{String, Missing} = @keyrequired f["/scanner/facility"] scannerOperator(f::MDFFile)::Union{String, Missing} = @keyrequired f["/scanner/operator"] scannerManufacturer(f::MDFFile)::Union{String, Missing} = @keyrequired f["/scanner/manufacturer"] diff --git a/src/MDFInMemory.jl b/src/MDFInMemory.jl index 303cab19..4d82c2d6 100644 --- a/src/MDFInMemory.jl +++ b/src/MDFInMemory.jl @@ -1382,7 +1382,7 @@ function inMemoryMDFFromMDFFileV2(mdfFile::MDFFileV2)::MDFv2InMemory try result = f(mdfFile) catch e - @warn "Exception while reading symbol $(functionSymbol). Please check closely." + @warn "Exception while reading symbol $(functionSymbol). Please check closely. Exception was `$e`." end if !(isnothing(result) || ismissing(result)) From 22e9718153b955151d7d02834582f93bed633557 Mon Sep 17 00:00:00 2001 From: Jonas Schumacher Date: Wed, 24 Apr 2024 09:38:23 +0200 Subject: [PATCH 13/14] Bump patch release (for `boreSize`) --- Project.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Project.toml b/Project.toml index 7cc58606..54d83a3a 100644 --- a/Project.toml +++ b/Project.toml @@ -1,7 +1,7 @@ name = "MPIFiles" uuid = "371237a9-e6c1-5201-9adb-3d8cfa78fa9f" authors = ["Tobias Knopp "] -version = "0.15.2" +version = "0.15.3" [deps] AxisArrays = "39de3d68-74b9-583c-8d2d-e117c070f3a9" From 1c4d82b2104b7e72d0f90cb3f97ba84db7f38cc4 Mon Sep 17 00:00:00 2001 From: jonschumacher Date: Wed, 24 Apr 2024 10:00:51 +0200 Subject: [PATCH 14/14] Minor fixes of checking and calculating position indices --- src/MDFInMemory.jl | 2 +- src/Positions/Positions.jl | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/MDFInMemory.jl b/src/MDFInMemory.jl index 4d82c2d6..bde3346e 100644 --- a/src/MDFInMemory.jl +++ b/src/MDFInMemory.jl @@ -767,7 +767,7 @@ function check(part::MDFv2Measurement, variables::MDFv2Variables) if isnothing(variables.E) variables.E = length([x for x in part.isBackgroundFrame if x == true]) end - # E is defined by the number of `false` values in isBackgroundFrame here; should have been retrieved earlier + # O is defined by the number of `false` values in isBackgroundFrame here; should have been retrieved earlier if isnothing(variables.O) variables.O = length([x for x in part.isBackgroundFrame if x == false]) end diff --git a/src/Positions/Positions.jl b/src/Positions/Positions.jl index 2bccf64f..36def6f6 100644 --- a/src/Positions/Positions.jl +++ b/src/Positions/Positions.jl @@ -220,7 +220,7 @@ end function posToIdxFloat(grid::RegularGridPositions, pos) idx = 0.5 .* (shape(grid) .* ((pos .- fieldOfViewCenter(grid)) ./ ( 0.5 .* fieldOfView(grid) ) .+ 1) .+ 1) - #idx = [isnan(val) ? one(eltype(idx)) : val for val in idx] + idx = [isnan(val) ? one(eltype(idx)) : val for val in idx] return idx end