Contiki 2.6

key.c

Go to the documentation of this file.
00001 /*
00002  *  Copyright (c) 2008  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 are met:
00007  *
00008  *  * Redistributions of source code must retain the above copyright
00009  *    notice, this list of conditions and the following disclaimer.
00010  *  * Redistributions in binary form must reproduce the above copyright
00011  *    notice, this list of conditions and the following disclaimer in
00012  *    the documentation and/or other materials provided with the
00013  *    distribution.
00014  *  * Neither the name of the copyright holders nor the names of
00015  *    contributors may be used to endorse or promote products derived
00016  *    from this software without specific prior written permission.
00017  *
00018  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
00019  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00020  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
00021  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
00022  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
00023  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
00024  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
00025  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
00026  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
00027  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
00028  * POSSIBILITY OF SUCH DAMAGE.
00029  */
00030 /**
00031  * \file
00032  *
00033  * \brief
00034  *      This file provides joystick operations. Combined with ADC functions.
00035  *
00036  * \author
00037  *      Mike Vidales mavida404@gmail.com
00038  *
00039  */
00040 
00041 #include "key.h"
00042 #include "uart.h"
00043 #include "main.h"
00044 #include "adc.h"
00045 
00046 /**
00047  *  \addtogroup lcd
00048  *  \{
00049 */
00050 
00051 /*---------------------------------------------------------------------------*/
00052 
00053 /**
00054  *   \brief This will intialize the joystick and the ADC for button readings.
00055 */
00056 void
00057 key_init(void)
00058 {
00059     /* Disable digital input buffer for joystick signal */
00060     DIDR0 |= (1 << ADC1D);
00061 
00062     /* Enter is input w/pullup */
00063     ENTER_DDR &= ~(1<<ENTER_PIN);
00064     ENTER_PUR |= (1<<ENTER_PIN);
00065 
00066     /* Joystick is input wo/pullup (all though normal port function is overridden by ADC module when reading) */
00067     KEY_DDR &= ~(1<<KEY_PIN);
00068     KEY_PUR &= ~(1<<KEY_PIN);
00069 
00070     /* Get the ADC ready to use */
00071     adc_init(ADC_CHAN_ADC1, ADC_TRIG_FREE_RUN, ADC_REF_AVCC, ADC_PS_128);
00072 }
00073 
00074 /*---------------------------------------------------------------------------*/
00075 
00076 /**
00077  *   \brief This will disable the ADC used for button readings.
00078 */
00079 void
00080 key_deinit(void)
00081 {
00082     /* Turn off the ADC */
00083     adc_deinit();
00084 }
00085 
00086 /*---------------------------------------------------------------------------*/
00087 
00088 /**
00089  *   \brief This will poll run key_task() to determine if a button has been pressed.
00090  *
00091  *   \retval True if button is pressed
00092  *   \retval False if button is not pressed
00093 */
00094 uint8_t
00095 is_button(void)
00096 {
00097     /* Return true if button has been pressed. */
00098     if (key_task() == KEY_NO_KEY){
00099         return false;
00100     }
00101     else{
00102         return true;
00103     }
00104 }
00105 
00106 /*---------------------------------------------------------------------------*/
00107 
00108 /**
00109  *   \brief This function will wait for a user to press a button.
00110  *
00111  *   \return retval Returns the global button state.
00112 */
00113 uint8_t
00114 get_button(void)
00115 {
00116     uint8_t retval;
00117     while (!is_button())
00118         ;
00119 
00120     retval = button;
00121     button = KEY_STATE_DONE;
00122     return retval;
00123 }
00124 
00125 /*---------------------------------------------------------------------------*/
00126 
00127 /**
00128  *   \brief This will check the joystick state to return the current button status.
00129  *
00130  *   \return button Current button state.
00131 */
00132 key_state_t
00133 key_task(void)
00134 {
00135     key_state_t key_state;
00136 
00137     /* Check joystick state. Post event if any change since last */
00138     key_state =  key_state_get();
00139     if (key_state == KEY_STATE_NO_KEY){
00140         if (button == KEY_STATE_DONE){
00141             button = KEY_STATE_NO_KEY;
00142         }
00143         return KEY_NO_KEY;
00144     }
00145 
00146     /* Key_state is button press code */
00147     if (button == KEY_STATE_DONE){
00148         /*
00149          * Button has already been used, don't return any more presses
00150          * until the button is released/re-pressed
00151          */
00152         return KEY_NO_KEY;
00153     }
00154 
00155     /* Button has been pressed for the first time */
00156     button = key_state;
00157     return button;
00158 }
00159 
00160 /*---------------------------------------------------------------------------*/
00161 
00162 /**
00163  *   \brief This function will start the ADC conversion and read the current
00164  *   converstion value to determine the button position.
00165  *
00166  *   \retval KEY_ENTER Enter button has been pressed.
00167  *   \retval KEY_UP Up Button has been pressed.
00168  *   \retval KEY_RIGHT Right Button has been pressed.
00169  *   \retval KEY_LEFT Left Button has been pressed.
00170  *   \retval KEY_DOWN Down Button has been pressed.
00171  *   \retval KEY_NO_KEY No Button has been pressed.
00172 */
00173 key_state_t
00174 key_state_get(void)
00175 {
00176     int16_t reading;
00177 
00178     /* Start the A/D conversion */
00179     adc_conversion_start();
00180 
00181     /* Wait for conversion to finish */
00182     while ((reading = adc_result_get(ADC_ADJ_RIGHT)) == EOF )
00183         ;
00184 
00185     /* Determine which button (if any) is being pressed */
00186     if (!(ENTER_PORT & (1<<ENTER_PIN))){
00187         return KEY_ENTER;
00188     }
00189     if (reading < 0x00A0){
00190         return KEY_UP;
00191     }
00192     if (reading < 0x0180){
00193         return KEY_RIGHT;
00194     }
00195     if (reading < 0x0280){
00196         return KEY_LEFT;
00197     }
00198     if (reading < 0x0380){
00199         return KEY_DOWN;
00200     }
00201     return KEY_NO_KEY;
00202 }
00203 
00204 /** \}   */