beacon measurement quest UI

This commit is contained in:
Gwendolyn 2024-12-28 18:53:43 +01:00
parent 0beee53e60
commit b977746a76
3 changed files with 121 additions and 7 deletions

View file

@ -109,6 +109,7 @@ class RangingBeaconBSSIDsQuest(Quest):
class BeaconMeasurementQuestForm(ChangeSetModelForm): class BeaconMeasurementQuestForm(ChangeSetModelForm):
def __init__(self, *args, **kwargs): def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs) super().__init__(*args, **kwargs)
self.fields["beacon_measurement_quest"] = CharField(disabled=True, initial='', widget=HiddenInput(), required=False)
self.fields["data"].widget = HiddenInput() self.fields["data"].widget = HiddenInput()
def clean_data(self): def clean_data(self):

View file

@ -2000,12 +2000,18 @@ blink {
} }
} }
.beacon-quest-scanner {
margin-bottom: 1rem;
}
.ap-name-bssid-result { .ap-name-bssid-result, .beacon-quest-scanner > table {
display: block;
max-height: 30vh;
overflow: scroll;
border-radius: 4px; border-radius: 4px;
border: 1px solid gray; border: 1px solid gray;
padding: 4px 0; padding: 4px 0;
box-shadow: inset 0px 0px 1px gray; box-shadow: inset 0 0 1px gray;
thead { thead {
border-bottom: 1px solid gray; border-bottom: 1px solid gray;

View file

@ -1471,17 +1471,112 @@ c3nav = {
}, },
_set_modal_content: function (content, no_close) { _set_modal_content: function (content, no_close) {
const $modal = $('#modal'); const $modal = $('#modal');
const $content = $modal.find('#modal-content');
$modal.toggleClass('loading', !content) $modal.toggleClass('loading', !content)
.find('#modal-content') $content.html((!no_close) ? '<button class="button-clear material-symbols" id="close-modal">clear</button>' : '')
.html((!no_close) ? '<button class="button-clear material-symbols" id="close-modal">clear</button>' : '')
.append(content || '<div class="loader"></div>'); .append(content || '<div class="loader"></div>');
if ($modal.find('[name=look_for_ap]').length) { if ($content.find('[name=look_for_ap]').length) {
$content.find('button[type=submit]').hide();
if (!window.mobileclient) { if (!window.mobileclient) {
alert('need app!') $content.find('p, form').remove();
$content.append('<p>This quest is only available in the android app.</p>'); // TODO translate
} else {
c3nav._ap_name_scan_result_update();
}
} else if ($content.find('[name=beacon_measurement_quest]').length) {
$content.find('button[type=submit]').hide();
if (!window.mobileclient) {
$content.find('p, form').remove();
$content.append('<p>This quest is only available in the android app.</p>'); // TODO translate
} else {
const $scanner = $('<div class="beacon-quest-scanner"></div>');
const $button = $('<button class="button">start scanning</button>')
.click(() => {
$button.remove();
$scanner.append('<p>Scanning… Please do not close this popup and do not move.</p>');
c3nav._quest_wifi_scans = [];
c3nav._beacon_quest_scanning = true;
})
$scanner.append($button);
$content.find('form').prev().after($scanner)
} }
$modal.find('button').hide();
} }
}, },
_quest_wifi_scans: [],
_quest_ibeacon_scans: [],
_wifi_measurement_scan_update: function () {
const wifi_display_results = [];
const bluetooth_display_results = [];
for (const scan of c3nav._quest_wifi_scans) {
for (const peer of scan) {
let found = false;
for (const existing_peer of wifi_display_results) {
if (peer.bssid === existing_peer.bssid && peer.ssid === existing_peer.ssid) {
existing_peer.rssi = peer.rssi;
found = true;
break;
}
}
if (!found) {
wifi_display_results.push(peer);
}
}
}
for (const scan of c3nav._quest_ibeacon_scans) {
for (const peer of scan) {
let found = false;
for (const existing_peer of bluetooth_display_results) {
if (peer.uuid === existing_peer.uuid && peer.major === existing_peer.major && peer.minor === existing_peer.minor) {
existing_peer.distance = peer.distance;
found = true;
break;
}
}
if (!found) {
bluetooth_display_results.push(peer);
}
}
}
const $scanner = $('#modal .beacon-quest-scanner');
const $wifi_table = $(`<table><tr><td colspan="3"><i>${c3nav._quest_wifi_scans.length} wifi scans</i></td></tr><tr><th>BSSID</th><th>SSID</th><th>RSSI</th></tr></table>`);
for (const peer of wifi_display_results) {
$wifi_table.append(`<tr><td>${peer.bssid}</td><td>${peer.ssid}</td><td>${peer.rssi}</td></tr>`);
}
const $bluetooth_table = $(`<table><tr><td colspan="3"><i>${c3nav._quest_ibeacon_scans.length} wifi scans</i></td></tr><tr><th>ID</th><th>Distance</th></table>`);
for (const peer of bluetooth_display_results) {
$bluetooth_table.append(`<tr><td>${peer.major}</td><td>${peer.minor}</td><td>${peer.distance}</td></tr>`);
}
$scanner.empty();
if (c3nav._quest_wifi_scans.length < 2) {
$scanner.append('<p>Scanning… Please do not close this popup and do not move.</p>');
} else {
if (c3nav._quest_wifi_scans.length > 2) {
$('#modal input[name=data]').val(JSON.stringify({
wifi: c3nav._quest_wifi_scans,
ibeacon: c3nav._quest_ibeacon_scans,
}))
$('#modal button[type=submit]').show();
}
}
if (wifi_display_results.length > 0) {
$scanner.append($wifi_table);
}
if (bluetooth_display_results.length > 0) {
$scanner.append($bluetooth_table);
}
},
_ap_name_scan_result_update: function () { _ap_name_scan_result_update: function () {
const $modal = $('#modal'); const $modal = $('#modal');
const $match_ap = $modal.find('[name=look_for_ap]'); const $match_ap = $modal.find('[name=look_for_ap]');
@ -2178,6 +2273,7 @@ c3nav = {
_last_ibeacon_peers: [], _last_ibeacon_peers: [],
_no_scan_count: 0, _no_scan_count: 0,
_ap_name_mappings: {}, _ap_name_mappings: {},
_beacon_quest_scan_results: {},
_enable_scan_debugging: false, _enable_scan_debugging: false,
_scan_debugging_results: [], _scan_debugging_results: [],
_wifi_scan_results: function (peers) { _wifi_scan_results: function (peers) {
@ -2221,12 +2317,23 @@ c3nav = {
c3nav._ap_name_scan_result_update(); c3nav._ap_name_scan_result_update();
if (c3nav._beacon_quest_scanning) {
c3nav._quest_wifi_scans.push(peers);
c3nav._wifi_measurement_scan_update();
}
c3nav._last_wifi_peers = peers; c3nav._last_wifi_peers = peers;
c3nav._after_scan_results(); c3nav._after_scan_results();
}, },
_ibeacon_scan_results: function (peers) { _ibeacon_scan_results: function (peers) {
peers = JSON.parse(peers); peers = JSON.parse(peers);
c3nav._last_ibeacon_peers = peers; c3nav._last_ibeacon_peers = peers;
if (c3nav._beacon_quest_scanning) {
c3nav._quest_ibeacon_scans.push(peers);
c3nav._wifi_measurement_scan_update();
}
c3nav._after_scan_results(); c3nav._after_scan_results();
}, },
_after_scan_results: function () { _after_scan_results: function () {