hand recorder: final consent text (2026-10-03), residency check, installer

Consent 2026-10-03, after a non-lawyer review: who runs this and how to reach
them, the dataset is public (Hugging Face, possibly abroad), the Hugging Face
username shows next to the contributor id, purposes (no identification), safety,
the maintainer grant passes to whoever maintains Frametop next, withdrawal
before and after merge, rights such as the GDPR's, and what a new version means.
Residents of Illinois, Texas and Washington can't take part for now (biometric
privacy laws): a third checkbox, profile consent.region_ok, checked by
validate.py from this consent version on. The DRAFT banners are gone, so uploads
no longer need FT_HANDREC_ALLOW_UPLOAD.

hands/rec/install.sh installs the recorder on a Frame with Frametop: container
packages, hand tracking and panel builds, ft-camd's capabilities, menu entry.

test_qml_backend also checks each call's argument count against the slots.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
DeeJanuzandClaude Opus 5.5 committed 2026-10-03 14:35:18 -06:00
1 parent 1eb120e6b1
commit 2351cec310
9 files changed
+158 -32

No files matched your search

+7 -6
View File
@@ -323,11 +323,12 @@ class Backend(QObject):
def handednessChoices(self):
return [{"value": k, "text": v} for k, v in HANDEDNESS]
@Slot(bool, bool, str)
def acceptConsent(self, adult, agree, handedness):
"""Write profile.json. A contributor id, once made, stays (a new consent version keeps it)."""
if not (adult and agree):
self.message.emit("Both boxes need ticking to take part", True)
@Slot(bool, bool, bool, str)
def acceptConsent(self, adult, region, agree, handedness):
"""Write profile.json. A contributor id, once made, stays (a new consent version keeps it).
region: not living in Illinois, Texas or Washington (CONSENT.md "Who can take part")."""
if not (adult and region and agree):
self.message.emit("All three boxes need ticking to take part", True)
return
profile = self.store.profile()
optional = profile.get("optional") if isinstance(profile.get("optional"), dict) else {}
@@ -336,7 +337,7 @@ class Backend(QObject):
profile = {"schema": 1, "contributor": profile.get("contributor") or str(uuid.uuid4()),
"consent": {"version": consent_version(),
"accepted": datetime.datetime.now().astimezone().isoformat(timespec="seconds"),
"adult": True},
"adult": True, "region_ok": True},
"optional": optional}
takes.write_json(self.store.profile_path, profile)
self.profileChanged.emit()