Contiki 2.6

fader.c

00001 /*
00002  * Copyright (c) 2005, Swedish Institute of Computer Science.
00003  * All rights reserved.
00004  *
00005  * Redistribution and use in source and binary forms, with or without
00006  * modification, are permitted provided that the following conditions
00007  * are met:
00008  * 1. Redistributions of source code must retain the above copyright
00009  *    notice, this list of conditions and the following disclaimer.
00010  * 2. Redistributions in binary form must reproduce the above copyright
00011  *    notice, this list of conditions and the following disclaimer in the
00012  *    documentation and/or other materials provided with the distribution.
00013  * 3. Neither the name of the Institute nor the names of its contributors
00014  *    may be used to endorse or promote products derived from this software
00015  *    without specific prior written permission.
00016  *
00017  * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
00018  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00019  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
00020  * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
00021  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
00022  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
00023  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
00024  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
00025  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
00026  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
00027  * SUCH DAMAGE.
00028  *
00029  * This file is part of the Contiki operating system.
00030  *
00031  * Author: Adam Dunkels <adam@sics.se>
00032  *
00033  * $Id: fader.c,v 1.1 2007/03/21 23:17:28 adamdunkels Exp $
00034  */
00035 
00036 #include "contiki.h"
00037 #include "dev/leds.h"
00038 
00039 PROCESS(fader_process, "LED fader");
00040 AUTOSTART_PROCESSES(&fader_process);
00041 
00042 #define ON  1
00043 #define OFF 0
00044 
00045 struct fader {
00046   struct pt fade_pt, fade_in_pt, fade_out_pt;
00047   struct etimer etimer;
00048   int led;
00049   int delay;
00050 };
00051 
00052 static unsigned char onoroff;
00053 
00054 /*---------------------------------------------------------------------------*/
00055 static
00056 PT_THREAD(fade_in(struct fader *f))
00057 {
00058   PT_BEGIN(&f->fade_in_pt);
00059   
00060   for(f->delay = 3980; f->delay > 20; f->delay -= 20) {
00061     leds_on(f->led);
00062     clock_delay(4000 - f->delay);
00063     leds_off(f->led);
00064     clock_delay(f->delay);
00065     PT_YIELD(&f->fade_in_pt);
00066   }
00067   
00068   PT_END(&f->fade_in_pt);
00069 }
00070 /*---------------------------------------------------------------------------*/
00071 static
00072 PT_THREAD(fade_out(struct fader *f))
00073 {  
00074   PT_BEGIN(&f->fade_out_pt);
00075 
00076   for(f->delay = 20; f->delay < 3980; f->delay += 20) {
00077     leds_on(f->led);
00078     clock_delay(4000 - f->delay);
00079     leds_off(f->led);
00080     clock_delay(f->delay);
00081     PT_YIELD(&f->fade_out_pt);
00082   }
00083     
00084   PT_END(&f->fade_out_pt);
00085 }
00086 /*---------------------------------------------------------------------------*/
00087 static
00088 PT_THREAD(fade(struct fader *f))
00089 {
00090   PT_BEGIN(&f->fade_pt);
00091 
00092   while(1) {
00093     
00094     PT_SPAWN(&f->fade_pt, &f->fade_in_pt, fade_in(f));
00095     PT_SPAWN(&f->fade_pt, &f->fade_out_pt, fade_out(f));
00096     
00097     etimer_set(&f->etimer, CLOCK_SECOND * 4);
00098     PT_WAIT_UNTIL(&f->fade_pt, etimer_expired(&f->etimer));
00099   }
00100     
00101   PT_END(&f->fade_pt);
00102 }
00103 /*---------------------------------------------------------------------------*/
00104 static void
00105 init_fader(struct fader *f, int led)
00106 {
00107   PT_INIT(&f->fade_pt);
00108   PT_INIT(&f->fade_in_pt);
00109   PT_INIT(&f->fade_out_pt);
00110   f->led = led;
00111 }
00112 /*---------------------------------------------------------------------------*/
00113 PROCESS_THREAD(fader_process, ev, data)
00114 {
00115   static struct fader red, green, yellow;
00116   static struct timer timer;
00117   static struct etimer etimer;
00118   
00119   PROCESS_BEGIN();
00120 
00121   init_fader(&red, LEDS_RED);
00122   init_fader(&green, LEDS_GREEN);
00123   init_fader(&yellow, LEDS_YELLOW);
00124   
00125   timer_set(&timer, CLOCK_SECOND/4);
00126   while(!timer_expired(&timer)) {
00127     PT_SCHEDULE(fade(&red));
00128   }
00129   timer_set(&timer, CLOCK_SECOND/4);
00130   while(!timer_expired(&timer)) {
00131     PT_SCHEDULE(fade(&red));
00132     PT_SCHEDULE(fade(&green));
00133   }
00134   
00135   timer_set(&timer, CLOCK_SECOND/4);
00136   while(!timer_expired(&timer)) {
00137     PT_SCHEDULE(fade(&green));
00138     PT_SCHEDULE(fade(&yellow));
00139   }
00140 
00141   etimer_set(&etimer, CLOCK_SECOND * 4);
00142   fader_on();
00143   
00144   while(1) {
00145     PROCESS_WAIT_EVENT();
00146   
00147     if(ev == PROCESS_EVENT_TIMER) {
00148       etimer_set(&etimer, CLOCK_SECOND * 4);
00149       process_poll(&fader_process);
00150     }
00151     
00152     if(onoroff == ON &&
00153        PT_SCHEDULE(fade(&red)) &&
00154        PT_SCHEDULE(fade(&yellow)) &&
00155        PT_SCHEDULE(fade(&green))) {
00156       process_poll(&fader_process);
00157     }
00158   }
00159   PROCESS_END();
00160 }
00161 /*---------------------------------------------------------------------------*/
00162 void
00163 fader_on(void)
00164 {
00165   onoroff = ON;
00166   process_poll(&fader_process);
00167 }
00168 /*---------------------------------------------------------------------------*/
00169 void
00170 fader_off(void)
00171 {
00172   onoroff = OFF;
00173 }
00174 /*---------------------------------------------------------------------------*/