Donnerstag, 11 Dezember 2025

Diese Woche am beliebtesten

Vertiefendes Material

Mini Timer

Einfacher Timer mit Start/Stopp-Funktion für mehrere Timer gleichzeitig. Letzte Laufzeiten werden automatisch in Textdateien gespeichert. Sofort einsatzbereit, keine Datenbank nötig.

<?php
define('TIMER_DIR', __DIR__ . '/timers/');
if(!is_dir(TIMER_DIR)) mkdir(TIMER_DIR);

function jsonResponse($data,$code=200){
    http_response_code($code);
    header('Content-Type: application/json; charset=utf-8');
    echo json_encode($data);
    exit;
}

function getTimers(){
    $timers=[];
    foreach(glob(TIMER_DIR.'*.txt') as $file){
        $data = json_decode(file_get_contents($file), true);
        $timers[] = $data;
    }
    return $timers;
}

function saveTimer($id,$name,$duration,$last_runtime){
    $data=['id'=>$id,'name'=>$name,'duration'=>$duration,'last_runtime'=>$last_runtime];
    file_put_contents(TIMER_DIR.$id.'.txt', json_encode($data));
}

if(isset($_GET['action'])){
    if($_GET['action']==='add'){
        $name = trim($_POST['name'] ?? 'Timer');
        $duration = intval($_POST['duration'] ?? 60);
        $id = time().rand(100,999);
        saveTimer($id,$name,$duration,0);
        jsonResponse(['success'=>true]);
    }
    if($_GET['action']==='list'){
        jsonResponse(getTimers());
    }
    if($_GET['action']==='update'){
        $id = intval($_POST['id'] ?? 0);
        $runtime = intval($_POST['runtime'] ?? 0);
        $timers = getTimers();
        foreach($timers as $t){
            if($t['id']==$id){
                saveTimer($id,$t['name'],$t['duration'],$runtime);
                break;
            }
        }
        jsonResponse(['success'=>true]);
    }
}
?>

<!DOCTYPE html>
<html lang="de">
<head>
<meta charset="UTF-8">
<title>Dreamcodes Mini-Timer</title>
<style>
body{font-family:Arial,sans-serif;background:#f0f0f0;padding:20px;}
.timer{background:#fff;padding:15px;margin-bottom:10px;border-radius:8px;}
button{margin-left:5px;padding:5px 10px;}
</style>
</head>
<body>
<h2>Mini-Timer / Countdown</h2>
<form id="addTimerForm">
<input type="text" name="name" placeholder="Name">
<input type="number" name="duration" placeholder="Sekunden" value="60">
<button type="submit">Hinzufügen</button>
</form>
<div id="timers"></div>
<script>
let timersData = {};

async function fetchTimers(){
    const resp = await fetch('?action=list');
    const data = await resp.json();
    const container = document.getElementById('timers');
    container.innerHTML='';
    data.forEach(t=>{
        const div = document.createElement('div');
        div.className='timer';
        div.id='timer-'+t.id;
        div.innerHTML=`<strong>${t.name}</strong> - <span id='time-${t.id}'>${t.duration}</span> Sekunden
<button onclick='startTimer(${t.id}, ${t.duration})'>Start</button>
<button onclick='stopTimer(${t.id})'>Stopp</button>
`;
        container.appendChild(div);
        timersData[t.id]={duration:t.duration, interval:null, remaining:t.duration};
    });
}

async function startTimer(id,duration){
    stopTimer(id);
    timersData[id].remaining=duration;
    timersData[id].interval=setInterval(()=>{
        timersData[id].remaining--;
        document.getElementById('time-'+id).textContent=timersData[id].remaining;
        if(timersData[id].remaining<=0){
            stopTimer(id);
            saveRuntime(id,duration);
        }
    },1000);
}

function stopTimer(id){
    if(timersData[id].interval){
        clearInterval(timersData[id].interval);
        timersData[id].interval=null;
        saveRuntime(id,timersData[id].duration - timersData[id].remaining);
    }
}

async function saveRuntime(id,runtime){
    const fd=new FormData(); fd.append('id',id); fd.append('runtime',runtime);
    await fetch('?action=update',{method:'POST',body:fd});
}

document.getElementById('addTimerForm').addEventListener('submit',async(e)=>{
    e.preventDefault();
    const formData=new FormData(e.target);
    await fetch('?action=add',{method:'POST',body:formData});
    e.target.reset();
    fetchTimers();
});

fetchTimers();
</script>
</body>
</html>
Vorheriges Tutorial
Nächstes Tutorial
Dreamcodes Redaktion
Dreamcodes Redaktion
Seit 1999 bewegt sich Dreamcodes in der Welt der digitalen Entwicklung, zwischen Codezeilen, Designentscheidungen und technischen Herausforderungen, die manchmal kleiner aussehen, als sie wirklich sind. Die Herausforderung besteht darin, komplexe Themen wie Webentwicklung, SEO, SEA, GEO, IT-Strukturen, Softwareentwicklung und moderne Technologien so aufzubereiten, dass sie verständlich, nachvollziehbar und vor allem praktisch nutzbar werden. Der Fokus liegt dabei darauf, Wissen nicht nur zu erklären, sondern es für reale Projekte anwendbar zu machen. Egal ob ein einfaches Script, ein umfangreicher Leitfaden oder ein tiefes technisches Tutorial: Das oberste Ziel dabei ist, dass Leser am Ende wirklich weiterkommen und ein Thema greifbarer wird als vorher. Über die Jahre gab es viele verschiedene Ansätze, Tools und Trends die kammen und auch wieder gingen. Genau das hilft neben Jahrelanger IT Erfahrung und mehrjähriger Tätigkeit im IT Bereich heute dabei, Inhalte mit Tiefe zu schreiben, die nicht nur Grundlagen vermitteln, sondern auch Hintergründe, Zusammenhänge und Best Practices erklären. Dreamcodes teilt diese Erfahrungen, mit dem Ziel, digitale Bildung für alle zugänglich zu machen, die neugierig sind, nach Lösungen suchen oder eigene digitale Projekte erfolgreich voranbringen möchten. Wenn dieses Wissen jemandem Zeit spart, ein Problem löst oder eine neue Idee auslöst, hat sich der Aufwand dahinter gelohnt. ;)

Vielleicht einen Blick wert