Lux Metre Devresi

'Elektronik Projeler' forumunda DeMSaL tarafından 15 Haziran 2010 tarihinde açılan konu

  1. DeMSaL

    DeMSaL Özel Üye

    Sponsorlu Bağlantılar
    Lux Metre Devresi konusu Lux Metre Devresi Nedir - Lux Metre Devresi Şeması - Lux Metre Devresi Hakkında - Lux Metre Devresi Işık Ölçümü - Işık Ölçümü - Attiny26-16



    [​IMG]

    Lux metre devresi atmel attiny26-16 mikrodenetleyici üzerine kurulu led display üzerinde lux değerini görüntülüyor ledler 2sk1061 mosfetler ile sürülmüş. İlginç bir uygulama tüm kaynak dosyalar (pcb, şema, kod) paylaşılmış ayrıca devrenin kalibrasyon bilgileride verilmiş

    Lux metre devre şeması;

    [​IMG]

    Dosya ve detaylar (ingilizce): Lux Meter

    The Lux Meter is usually used to measure illumination. The illumination is how level of luminous flux is falling on a surface area. The luminous flux is visible component that is defined in radiant flux (light power) divided by relative sensitivity of human eyes over the visible spectrum. This means the Lux is well fit to light level from sense of human eyes.
    lux.c yazılımı;


    Kod:
    /*--------------------------------------------------*/
    /* Lux meter control program (C)ChaN, 2005            */
     
    #include <avr/io.h>
    #include <avr/signal.h>
    #include <avr/interrupt.h>
    #include <avr/pgmspace.h>
    #include <avr/eeprom.h>
    #include <string.h>
    #include "xitoa.h"
     
    #define    SYSCLK        1000000
     
    /* Bit definition for status flags */
    #define    F_800    (_BV(0))        // 800 Hz timer event
    #define    F_LVD    (_BV(1))        // Low battery
    #define    F_POW    (_BV(2))        // Power event
    #define F_PB    (_BV(3))        // Power button
     
    /*------------------------------------------------*/
    /* Global variables                               */
     
    uint8_t Leds[5];                // LED display buffer
    volatile uint8_t flags;            // Status flags
    volatile uint16_t OffTimer;        // Auto power off timer
     
    uint32_t Gain[2];
    uint16_t Ofs20;
     
    /*------------------------------------------------*/
    /* Interval Timer (800Hz)                         */
     
    SIGNAL(SIG_OVERFLOW1)
    {
        static uint8_t bltimer;        // LED blink timer
        static uint8_t Col;            // Dynamic scan pointer
     
        if(++Col >= sizeof(Leds)) Col = 0;
        PORTA &= 0b00000100;
        PORTB = 0;
     
        bltimer++;
        if((bltimer & 7) == 0) {    // Check power button every 8 (100/sec)
            PORTA |= _BV(3);
            DDRA &= ~_BV(3);
            DDRA &= ~_BV(3);
            DDRA &= ~_BV(3);
            if(PINA & _BV(3)) {
                flags |= F_PB;
            } else {
                if(flags & F_PB)
                    flags |= F_POW;
                flags &= ~F_PB;
            }
            PORTA &= 0b00000100;
            DDRA |= _BV(3);
        }
        if((bltimer & 0xC0) || !(flags & F_LVD))    // Blink control
            PORTB = Leds[Col];
        PORTA |= (0b00001000 << Col);
     
        if(--OffTimer == 0) flags |= F_POW;            // Auto power-off timer
     
        flags |= F_800;
    }
     
    /* Character output function for LED display (called by xitoa module) */
     
    void putled(char c)
    {
        static uint8_t wp;    // Write index
        static const prog_uint8_t seg7[]    // Segment pattern
            = {0x7E, 0x30, 0x6D, 0x79, 0x33, 0x5B, 0x5F, 0x70, 0x7F, 0x7B, 0};
     
        if(c == '\r') {        // Return index to left
            wp = 0;
            return;
        }
        c -= '0';            // Put a segment pattern into display buffer
        if((uint8_t)c > 9) c = 10;
        Leds[wp++] = pgm_read_byte(&seg7[(uint8_t)c]);
    }
     
    void delay (uint16_t dly)
    {
        do {
            cli(); flags &= ~F_800; sei();
            while((flags & F_800) == 0);
        } while(--dly);
    }
     
    uint16_t adconv(uint8_t ch)
    {
        ADMUX = ch;
        ADCSR = 0b11010011;
        while(bit_is_clear(ADCSR, ADIF));
        return ADC;
    }
     
    /*------------------------------------------------*/
    /* Main Process                                   */
     
    int main(void)
    {
        uint16_t n, d;
        uint32_t v, u;
     
        /* Initialize ports */
        PORTA = 0b00000100;
        DDRA  = 0b11111110;
     
        PORTB = 0b00000101;
        DDRB  = 0b01111111;
     
        /* Start TC1 with 800Hz OC-A */
        OCR1C = SYSCLK/8/800-1;
        TCCR1B = _BV(CTC1) | 0b0100;
        TIMSK = _BV(TOIE1);
     
        eeprom_read_block(Gain, 0, sizeof(Gain));
     
        xfunc_out = putled;        // Join xitoa molule and my output function
     
        OffTimer = 48000;    // Auto power off timer (60sec)
     
        sei();
     
        /* Lamp test */
        memset(Leds, 0x7F, sizeof(Leds));
        delay(400);
     
        delay(10);
        Ofs20 = adconv(0x80 + 13);
        delay(10);
     
        cli();
        PORTA &= 0b00000100;
        PORTB = 0b00000101;
        DDRB  = 0b01111010;
        DDRB  = 0b01111010;
        DDRB  = 0b01111010;
     
        /* MOSI is tied to GND. Low range calibration (1250 lux at -100 mV) */
        if((PINB & _BV(0)) == 0) {
            adconv(0x80 + 11);
            Gain[0] = 1250 * 65536 / (uint32_t)(adconv(0x80 + 11) - Ofs20);
            eeprom_write_block(Gain, 0, sizeof(Gain));
            Leds[0] = 0;
        }
     
        /* SCK is tied to GND. High range calibration (12500 lux at -1 V) */
        if((PINB & _BV(2)) == 0) {
            adconv(0x80 + 0);
            Gain[1] = 12500 * 65536 / (uint32_t)(adconv(0x80 + 0));
            eeprom_write_block(Gain, 0, sizeof(Gain));
            Leds[1] = 0;
        }
     
        DDRB =  0b01111111;
        sei();
     
        /* Measurement loop continued until any power event occure */
     
        while(!(flags & F_POW)) {
            v = 0;
            for(n = 0; n < 256; n++)    // 256 times averaging to filter-out flicker
            {
                d = adconv(0x80 + 11);
                while(!(flags & F_800));
                cli(); flags &= ~F_800; sei();
                d = adconv(0x80 + 11);
                if(d < 1023) {
                    d -= Ofs20;
                    u = Gain[0];
                } else {
                    d = adconv(0x80 + 0);
                    u = Gain[1];
                }
                d = (u * (uint32_t)d) >> 16;
                v += d;
            }
     
            /* Refresh lux value */
            xputc('\r');
            xitoa(v / 256, 10, 5);
     
            /* Check battrey voltage */
            DDRA &= ~_BV(1);
            d = adconv(0x80 + 1);
            cli();
            if(d >= 23)
                flags &= ~F_LVD;
            else
                flags |= F_LVD;
            sei();
            DDRA |= _BV(1);
        }
     
        /* Power off */
        memset(Leds, 0, sizeof(Leds));    // Clear display
        PORTA &= ~_BV(2);                // Release power hold
        for(;;);
    
     

Bu Sayfayı Paylaş