// SPDX-License-Identifier: MIT // Copyright (c) 2026 Incoprea // Calibrate a slider from two actual touches // Not compiled or tested in-world // Setup: Use a spare ordinary cube owned by you. Tap the intended minimum and maximum positions; subsequent touches read the calibrated range. Reset to recalibrate. Surface mapping can differ on meshes; test one face first. // Stop / restore: Disable/remove; these controllers report privately and do not alter scene properties. Reset clears gesture/session state. // Notes: References must be on the same link/face and have distinctS coordinates. // License: see LICENSE in this distribution. // Original Incoprea. MIT. Owner input only. integer stage; integer face; integer link; float low; float high; integer ownerTouch() { return llDetectedKey(0)==llGetOwner(); } integer usable(vector uv) { return llDetectedTouchFace(0)>=0&&uv!=TOUCH_INVALID_TEXCOORD; } default { touch_start(integer n) { if(!ownerTouch())return; vector uv=llDetectedTouchST(0); if(!usable(uv))return; integer f=llDetectedTouchFace(0); integer l=llDetectedLinkNumber(0); if(stage==0) { face=f; link=l; low=uv.x; stage=1; llOwnerSay("Minimum captured; tap maximum."); return; } if(f!=face||l!=link) { llOwnerSay("Use the calibrated face."); return; } if(stage==1) { high=uv.x; if(llFabs(high-low)<0.01) { llOwnerSay("Endpoints too close; try maximum again."); return; } stage=2; llOwnerSay("Calibrated; tap to read."); return; } float value=(uv.x-low)/(high-low); if(value<0.0)value=0.0; if(value>1.0)value=1.0; llOwnerSay("Calibrated value="+(string)value); } changed(integer flags) { if(flags&CHANGED_OWNER)llResetScript(); } }