Compare commits

...

11 Commits

Author SHA1 Message Date
D. Berge
b1344bebd8 Update the required schema version.
This is necessary for the comparisons code to work.
2025-08-21 17:08:23 +02:00
D. Berge
3e91ccba8d Don't show monitor lines by default 2025-08-21 15:21:01 +02:00
D. Berge
fa0be9c0b7 Make loading indicator spin when 0% 2025-08-21 15:20:31 +02:00
D. Berge
dcbf5496f6 Remove unneded dependency 2025-08-21 15:10:45 +02:00
D. Berge
8007f46e37 Fix typo 2025-08-21 15:04:48 +02:00
D. Berge
4a7683cfd0 Add group map view 2025-08-21 14:58:53 +02:00
D. Berge
565a9d7e01 Add support for type 4 decoding 2025-08-21 14:58:53 +02:00
D. Berge
b07244c823 Fix component paths 2025-08-21 14:58:53 +02:00
D. Berge
c909edc41f Move components to subdirectory 2025-08-21 14:55:27 +02:00
D. Berge
41ef511123 Return type 4 sequence data 2025-08-21 14:52:50 +02:00
D. Berge
4196e9760b Add encoding type 4 to bundle 2025-08-21 14:51:49 +02:00
8 changed files with 1327 additions and 8 deletions

File diff suppressed because it is too large Load Diff

View File

@@ -84,8 +84,12 @@ const DougalBinaryLoader = {
for (let k = 0; k < values.length; k++) { for (let k = 0; k < values.length; k++) {
values[k] = new (k === 0 ? Uint16Array : k === 1 ? Uint32Array : k === 2 ? BigUint64Array : Float32Array)(totalCount); values[k] = new (k === 0 ? Uint16Array : k === 1 ? Uint32Array : k === 2 ? BigUint64Array : Float32Array)(totalCount);
} }
} else if (udv == 4) {
for (let k = 0; k < values.length; k++) {
values[k] = new (k === 0 ? Uint16Array : k === 1 ? Uint32Array : k === 2 ? Uint16Array : Float32Array)(totalCount);
}
} else { } else {
throw new Error(`Invalid udv: Expected 0, 1, or 2; found ${udv}`); throw new Error(`Invalid udv: Expected 0, 1, 2, or 4; found ${udv}`);
} }
let offset = 0; let offset = 0;
@@ -110,7 +114,7 @@ const DougalBinaryLoader = {
offset += chunk.jCount; offset += chunk.jCount;
} }
console.log(`Parsed ${totalCount} points, ${values.length} value arrays`); console.log(`Parsed ${totalCount} points, ${values.length} value arrays, udv = ${udv}`);
const attributes = { const attributes = {
getPosition: { getPosition: {

View File

@@ -1,5 +1,11 @@
<template> <template>
<v-container fluid fill-height class="ma-0 pa-0"> <dougal-group-map v-if="mapView"
:baseline="baseline"
:monitor="monitor"
:monitors="monitors"
@input="mapView=$event"
></dougal-group-map>
<v-container fluid fill-height class="ma-0 pa-0" v-else>
<v-overlay :value="loading && !comparisons.length" absolute> <v-overlay :value="loading && !comparisons.length" absolute>
<v-progress-circular <v-progress-circular
@@ -21,7 +27,6 @@
</v-row> </v-row>
</v-overlay> </v-overlay>
<v-row no-gutters align="stretch" class="fill-height"> <v-row no-gutters align="stretch" class="fill-height">
<v-col cols="12" v-if="groupFound"> <v-col cols="12" v-if="groupFound">
@@ -79,6 +84,14 @@
</template> </template>
<template v-slot:footer.prepend> <template v-slot:footer.prepend>
<v-btn v-if="baseline && !mapView"
text
color="primary"
title="Switch to map view"
@click="mapView = true"
>View map</v-btn>
<v-btn v-if="comparison" <v-btn v-if="comparison"
text text
color="primary" color="primary"
@@ -121,8 +134,9 @@
<script> <script>
import { mapActions, mapGetters } from 'vuex' import { mapActions, mapGetters } from 'vuex'
import AccessMixin from '@/mixins/access'; import AccessMixin from '@/mixins/access';
import DougalGroupRepeatabilitySummary from '@/components/group-repeatability-summary.vue'; import DougalGroupRepeatabilitySummary from '@/components/groups/group-repeatability-summary.vue';
import DougalGroupComparisonSummary from '@/components/group-comparison-summary'; import DougalGroupComparisonSummary from '@/components/groups/group-comparison-summary';
import DougalGroupMap from '@/components/groups/group-map';
export default { export default {
name: 'Group', name: 'Group',
@@ -134,7 +148,7 @@ export default {
components: { components: {
DougalGroupRepeatabilitySummary, DougalGroupRepeatabilitySummary,
DougalGroupComparisonSummary, DougalGroupComparisonSummary,
DougalGroupMap
}, },
data () { data () {
@@ -182,6 +196,8 @@ export default {
}, },
], ],
mapView: false,
baseline: null, baseline: null,
monitor: null, monitor: null,
comparisons: [] comparisons: []
@@ -210,6 +226,16 @@ export default {
return this.projects.indexOf(this.baseline); return this.projects.indexOf(this.baseline);
}, },
monitors () {
if (this.baseline && this.comparisons) {
return this.comparisons
.filter( i => i.baseline_pid == this.baseline.pid )
.map( i => this.projects.find( p => p.pid == i.monitor_pid ));
} else {
return null;
}
},
comparison () { comparison () {
return this.comparisons.find( row => return this.comparisons.find( row =>
row.baseline_pid == this.baseline?.pid && row.monitor_pid == this.monitor?.pid row.baseline_pid == this.baseline?.pid && row.monitor_pid == this.monitor?.pid

View File

@@ -273,6 +273,31 @@ function bundle (json, opts = {}) {
}); });
return encode.sequential(json, el => el.sequence, el => el.point, deltas, values, type) return encode.sequential(json, el => el.sequence, el => el.point, deltas, values, type)
} else if (type == 4) {
/* Bare final positions
*
* Δelem 0: Sequence no. (Uint16Array, Uint8Array)
* elem 01: Float32Array, Float32Array Final positions (x, y)
*
*/
deltas.push({
key: el => el[2],
baseType: Uint16Array,
incrType: Int8Array
});
values.push({
key: el => el[3],
type: Float32Array
});
values.push({
key: el => el[4],
type: Float32Array
});
return encode.sequential(json, el => el[0], el => el[1], deltas, values, type)
} else if (type == 0xa) { } else if (type == 0xa) {
/* 4D comparison data: /* 4D comparison data:
* *

View File

@@ -15,11 +15,50 @@ async function getSummary (projectId, sequence, opts = {}) {
return res.rows[0]; return res.rows[0];
} }
async function getPoints (projectId, sequence, opts = {}) {
const offset = Math.abs(opts.offset) || Math.abs((opts.page-1)*opts.itemsPerPage) || 0;
const limit = Math.abs(opts.limit) || Math.abs(Number(opts.itemsPerPage)) || null;
const client = await setSurvey(projectId);
const restriction = sequence
? "sequence = $3"
: "TRUE OR $3";
const text = `
SELECT line, point, sequence, st_x(ST_Transform(geometry, 4326)) longitude, st_y(ST_Transform(geometry, 4326)) latitude
FROM final_shots
WHERE ${restriction}
ORDER BY sequence, point
OFFSET $1
LIMIT $2;
`;
try {
const res = await client.query({text, values: [offset, limit, sequence], rowMode: 'array'});
return res.rows;
} catch (err) {
console.error(err);
// throw { status: 500, message: "Internal error" };
} finally {
client.release();
}
}
async function get (projectId, sequence, opts = {}) { async function get (projectId, sequence, opts = {}) {
if (opts.summary) { if (opts.summary) {
return await getSummary(projectId, sequence, opts); return await getSummary(projectId, sequence, opts);
} }
if (opts.type == 4) {
// The user is request that we send just the bare details:
// sequence, sailline, line, longitude, latitude.
//
// This will probably be a binary data request (though doesn't
// need to).
return await getPoints(projectId, sequence, opts);
}
const client = await setSurvey(projectId); const client = await setSurvey(projectId);

View File

@@ -16,7 +16,7 @@
"api": "0.4.0" "api": "0.4.0"
}, },
"wanted": { "wanted": {
"db_schema": "^0.6.0" "db_schema": "^0.6.5"
} }
}, },
"engines": { "engines": {