wip: Sicherungs-Commit aller Änderungen seit April + Arbeitsstruktur (CLAUDE.md, ROADMAP.md, PROGRESS.md, Autopilot)

6 Wochen uncommittete Arbeit (Voice-Channels, LiveKit-Manager, Settings-Modal u.v.m.)
als ein WIP-Commit gesichert, damit nichts verloren geht und der Pi den aktuellen
Stand klonen kann. Thematische Aufarbeitung: siehe ROADMAP M0.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CPrAGBxBT6GfPXzeWQ4AXb
This commit is contained in:
Bernd Steckmeister
2026-07-03 05:47:18 +02:00
parent d706ace35f
commit 25ed765a03
195 changed files with 47784 additions and 1236 deletions
+53
View File
@@ -0,0 +1,53 @@
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 200 200" width="200" height="200">
<g id="pyr-g"></g>
<script>
<![CDATA[
var PYR = {"duration":2000,"hold":0.2,"curveExp":3,"tilt":20,"opacity":1,"stroke":1.4,"accent":"#f5a524","accent2":"#f9c571"};
var BASE=0.7;
var APEX=[0,-1,0],B1=[BASE,1,BASE],B2=[-BASE,1,BASE],B3=[-BASE,1,-BASE],B4=[BASE,1,-BASE];
var FACES=[[APEX,B1,B4],[APEX,B4,B3],[APEX,B3,B2],[APEX,B2,B1]];
function rotY(v,a){var c=Math.cos(a),s=Math.sin(a);return [v[0]*c+v[2]*s,v[1],-v[0]*s+v[2]*c];}
function clipZ(p){var o=[];for(var i=0;i<p.length;i++){var a=p[i],b=p[(i+1)%p.length],ai=a[2]>=0,bi=b[2]>=0;if(ai)o.push(a);if(ai!==bi){var t=a[2]/(a[2]-b[2]);o.push([a[0]+t*(b[0]-a[0]),a[1]+t*(b[1]-a[1]),0]);}}return o;}
function proj(v,sc,cx,cy,tr){return [cx+v[0]*sc, cy+(v[1]*Math.cos(tr)+v[2]*Math.sin(tr))*sc];}
function frontness(v){var a=v[0],b=v[1],c=v[2];var ux=b[0]-a[0],uy=b[1]-a[1],uz=b[2]-a[2];var vx=c[0]-a[0],vy=c[1]-a[1],vz=c[2]-a[2];var nz=ux*vy-uy*vx;var len=Math.hypot(uy*vz-uz*vy,uz*vx-ux*vz,nz)||1;return Math.max(0,-nz/len);}
function hex2(h){h=h.replace('#','');if(h.length===3)h=h.split('').map(function(c){return c+c;}).join('');return [parseInt(h.slice(0,2),16),parseInt(h.slice(2,4),16),parseInt(h.slice(4,6),16)];}
function darken(h,a){var c=hex2(h);var r=Math.max(0,Math.round(c[0]*(1-a))),g=Math.max(0,Math.round(c[1]*(1-a))),b=Math.max(0,Math.round(c[2]*(1-a)));return 'rgb('+r+','+g+','+b+')';}
function mixShade(h1,h2,t,s){var c1=hex2(h1),c2=hex2(h2);return 'rgb('+Math.round((c1[0]+(c2[0]-c1[0])*t)*s)+','+Math.round((c1[1]+(c2[1]-c1[1])*t)*s)+','+Math.round((c1[2]+(c2[2]-c1[2])*t)*s)+')';}
function ease(t,e){return t<0.5?0.5*Math.pow(2*t,e):1-0.5*Math.pow(2*(1-t),e);}
function yawAt(t){var a=1-PYR.hold;if(t>a)return Math.PI/4;return ease(t/a,PYR.curveExp)*Math.PI*2+Math.PI/4;}
var svg=document.documentElement;
var S=200,cx=S/2,cy=S/2,sc=S*0.38,tr=-PYR.tilt*Math.PI/180;
var t0=performance.now();
function frame(now){
var t=((now-t0)%PYR.duration)/PYR.duration, yaw=yawAt(t);
var children=[];
for(var i=0;i<FACES.length;i++){
var rot=FACES[i].map(function(v){return rotY(v,yaw);});
var cl=clipZ(rot);if(cl.length<3)continue;
var f=Math.abs(frontness(rot))||Math.abs(frontness([rot[0],rot[2],rot[1]]));
var d=0;for(var j=0;j<cl.length;j++)d+=cl[j][2];d/=cl.length;
var pts=cl.map(function(v){return proj(v,sc,cx,cy,tr);});
children.push({pts:pts,depth:d,f:f});
}
children.sort(function(a,b){return a.depth-b.depth;});
var ns='http://www.w3.org/2000/svg';
var g=svg.getElementById('pyr-g');g.textContent='';
for(var k=0;k<children.length;k++){
var r=children[k];
var pt=r.pts.map(function(p){return p[0].toFixed(2)+','+p[1].toFixed(2);}).join(' ');
var p=document.createElementNS(ns,'polygon');
p.setAttribute('points',pt);
var sh=0.35+0.65*r.f;
p.setAttribute('fill',darken(PYR.accent,0.45));
p.setAttribute('stroke',PYR.accent);
p.setAttribute('stroke-width',(PYR.stroke*(S/96)).toFixed(2));
p.setAttribute('stroke-linejoin','round');
p.setAttribute('stroke-linecap','round');
g.appendChild(p);
}
requestAnimationFrame(frame);
}
requestAnimationFrame(frame);
]]></script>
</svg>

After

Width:  |  Height:  |  Size: 3.3 KiB