DRUID Development Docs: ginput.inc

Gadget Sourcecode: ginput.inc

; Justice Unlimited Gadget Microcode
; (C) 2004 Nathan (Acorn) Pooley 
;
; ginput.inc
;
;@DOC@ handle low level input from spinner and button
;

;############################################
;############### HANDLE INPUT ###############
;############################################


; port b:
;    bit   desc
;     7    button lo=pressed
;     6    spinner A
;     5    spinner B
;     4    button  lo=pressed (not used (?))
;
; TYPES OF BYTES IN INPUT BUFFER
;  1ssx_xxxx  - spinner bits
;  0000_0000  - button was released
;  0000_0001  - button was pressed (NOT IMPLEMENTED)
;
; v_spinmax    = max value for v_spinval (min value is 1)
; v_spinval    = current value of spinner (1...v_spinmax)
; b_spinchange = spinner changed
;
; v_bval       = current value of buttons
;
; b_got_input   = set when input buffer is not empty
;


    ;
    ; NOTE: ENTRY POINT IS BELOW (see input:)
    ;
input_loop:
    incf    v_inbuf_ptr,f
    movf    INDF0,w
    bn      input_spin      ; not a button event?

    ;
    ; button press/release
    ;
    ; TODO - if anything other than button release is supported, then
    ;          decode it here
    ;
    bsf     b_got_input     ; may have more input to process
    movf    v_func_btn0_click,w ; button clicked?

#if TEST_INPUT
    bra     ti_button_released
#endif
    bra     main_jump

input_spin:
    movff   v_spinval, v_spinval_old
    xorwf   v_bval,w        ; which ones changed?
    xorwf   v_bval,f        ; save new value
    movff   v_bval,v_tmp    ; copy of new value

    btfsc   WREG,6
    bra     input_6

    btg     WREG,5          ; toggle bit5
    btg     v_tmp,5         ; toggle bit5

input_6:        ; bit 6 toggled
    btfsc   WREG,5
    bra     input_next      ; both or neither bits toggled

    rlncf   v_tmp,w
    xorwf   v_tmp,f         ; new bits the same or different?

    btfss   v_tmp,6
    bra     input_dec

input_inc:
    movf    v_spinval,w
    subwf   v_spinmax,w     ; max value? - wrap or clamp
    bnz     input_inc_go
    decf    v_spinval,f     ; counteract increment (clamp)
    btfsc   b_spinwrap
    clrf    v_spinval       ; wrap if enabled
input_inc_go:
    incf    v_spinval,f
    incf    v_spinval,f     ; extra inc (because we fall through dec)

input_dec:
    ;bsf        b_spinchange
    decf    v_spinval,f
    bnz     input_next

    ; underflow - wrap or clamp it
    incf    v_spinval,f             ; clamp
    btfsc   b_spinwrap
    movff   v_spinmax,v_spinval     ; wrap

input_next:
    movf    v_spinval,w         ; only set bit if actual change
    subwf   v_spinval_old,w
    btfss   STATUS,Z
    bsf     b_spinchange

    ;
    ; ENTRY POINT IS HERE
    ;
input:
    ;
    ; reset auto-off timer
    ;
    rcall   reset_sleep_time

    bcf     b_got_input
    lfsr    FSR0,BUF_INPUT
    movf    v_inbuf_ptr,w
    movwf   FSR0L
    subwf   FSR1L,w             ; empty?
    bnz     input_loop          ; loop while input buffer not empty

    return

;############################################
;############### INPUT SETUP ################
;############################################

    ;
    ; turn input off
    ;
input_disable:
    bcf     b_tmr2on        ; timer2 off
    bcf     b_rbie          ; disable portb interrupt
    bcf     b_got_input
    bcf     b_spinchange
    clrf    v_bheld

    ;
    ; turn off power to spinner
    ;
    DISABLE_SPINNER

    ;
    ; empty input buffer
    ;
    clrf    v_inbuf_ptr
    lfsr    FSR1,BUF_INPUT      ; input buffer

    ;
    ; set input functions to do nothing
    ;
    clrf    v_func_btn0_click       ; button click func
    movlw   func_spin_ignore
    movwf   v_func_spinchange       ; button click func


    return


    ;
    ; init input and enable it
    ;
    ; v_spinval_init = initial value of v_spinval
    ; v_spinval_max  = max valid v_spinval value
    ;
input_enable:
    ;
    ; clear things by disabling input first
    ;
    rcall   input_disable

    ;
    ; timer2 setup
    ;
    movlw   DEBOUNCE_CNT
    movwf   PR2             ; period
    movlw   0x01            ; timer2:
                            ;   off
                            ;   postscale = 1
                            ;   prescale  = 4
    movwf   T2CON
    bsf     b_tmr2ie        ; enable timer2 interrupt

    ;
    ; auto-off timer
    ;
    rcall   reset_sleep_time

    ;
    ; initial values
    ;  NOTE: v_spinval_max MUST be set before calling input_enable
    ;  v_spinval is not affected here
    ;
    bcf     b_spinwrap      ; spiner cannot wrap

    ;
    ; turn on power to spinner
    ;
    bcf     disab_spinner

    ;
    ; internal input values
    ;
    clrf    v_oldb
    setf    v_bdebounce
    setf    v_bnopush
    setf    v_brelmask

    ;
    ; PORTB state
    ;
    movf    PORTB,w
    movwf   v_bval          ; current spinner state
    bsf     b_rbif          ; cause initial interrupt
    bsf     b_rbie          ; enable portb interrupt


#if SIMULATE_INPUT
    movff       v_bval,v_si_oldb
#endif

    return



This file Copyright (C) 2004 by Nathan (Acorn) Pooley
Go to DRUID Development page
Go to DRUID page
Go to JU Gadgets page
Go to Justice Unlimited homepage
Go to Acorn's personal webpage
Contact Acorn
See comments from others
Post your own comments
File created by do_doc at Wed Aug 4 17:53:20 2004