TP Percobaan 1 Kondisi 1

 



1. Prosedur [Kembali]

1. Buka software proteus lalu rangkai komponen sesuai dengan gambar yang ada di modul

2. Buka software STM32CubeIDE lalu lakukan konfigurasi pin pada STM untuk menentukan ADC input dan GPIO output

3. Masukan Program ke dalam software STM32CubeIDE lalu build untuk mendapatkan file .hex

4. Masukan file .hex ke dalam file library STM32F103C8 pada proteus

5. Simulasikan rangkaian

2. Hardware [Kembali]

  • Hardware
1. STM32F103C8T6





2. Heartbeat Sensor


3. LED



4. Buzzer



6. Resistor 

  • Diagram Blog

3. Rangkaian Simulasi dan Prinsip Kerja [Kembali]


  • Sensor mendeteksi, maka logic state berlogika 1.

  • Salah satu sensor ketika berlogika 1, maka akan diteruskan ke STM32F103C8 sebagai input PA0 (PIR) dan PA1 (Touch).

  • Setelah itu keluarannya dari PB0 dan PB1 akan mengontrol status LED dan Buzzer berdasarkan mode yang sedang aktif.

  • Pada Touch sensor, mode sistem akan berganti setiap menerima berlogika 1. Ketika disentuh kembali setelah mode manual aktif, maka sistem kembali ke mode otomatis, keluaran buzzer berhenti berbunyi, dan sensor PIR kembali aktif mendeteksi gerakan.

  • Pada PIR sensor (saat mode otomatis), output LED akan ON dan OFF setiap pergantian logika 1 dengan 0, sedangkan output Buzzer hanya akan ON sesaat pada deteksi gerakan pertama.


4. Flowchart [Kembali]

  • Flowchart

  • Listing Program
#include "stm32f1xx_hal.h"

/* ================= HANDLE ================= */
ADC_HandleTypeDef hadc1;

/* ================= VARIABLE ================= */
uint32_t adcValue = 0;
uint32_t filteredValue = 0;

uint8_t beatDetected = 0;
uint32_t BPM = 0;

uint32_t lastBeatTime = 0;
uint32_t interval = 0;

uint8_t buzzerOff = 0;

/* ================= FILTER ================= */
#define FILTER_SIZE 10
uint16_t buffer[FILTER_SIZE];
uint8_t indexBuf = 0;

uint16_t moving_average(uint16_t val)
{
    buffer[indexBuf++] = val;
    if(indexBuf >= FILTER_SIZE) indexBuf = 0;

    uint32_t sum = 0;
    for(int i=0;i<FILTER_SIZE;i++) sum += buffer[i];

    return sum / FILTER_SIZE;
}

/* ================= LED ================= */
void LED_Hijau() {
    HAL_GPIO_WritePin(GPIOB, GPIO_PIN_0, GPIO_PIN_SET);
}

void LED_Kuning() {
    HAL_GPIO_WritePin(GPIOB, GPIO_PIN_1, GPIO_PIN_SET);
}

void LED_Merah() {
    HAL_GPIO_WritePin(GPIOB, GPIO_PIN_10, GPIO_PIN_SET);
}

void LED_Mati() {
    HAL_GPIO_WritePin(GPIOB, GPIO_PIN_0 | GPIO_PIN_1 | GPIO_PIN_10, GPIO_PIN_RESET);
}

/* ================= BUZZER ================= */
void Buzzer_On()  { HAL_GPIO_WritePin(GPIOB, GPIO_PIN_11, GPIO_PIN_SET); }
void Buzzer_Off() { HAL_GPIO_WritePin(GPIOB, GPIO_PIN_11, GPIO_PIN_RESET); }

/* ================= INTERRUPT ================= */
void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
{
    if(GPIO_Pin == GPIO_PIN_1) // PA1
    {
        buzzerOff = !buzzerOff;
    }
}

/* ================= PROTOTYPE ================= */
void SystemClock_Config(void);
void MX_GPIO_Init(void);
void MX_ADC1_Init(void);

/* ================= MAIN ================= */
int main(void)
{
    HAL_Init();
    SystemClock_Config();
    MX_GPIO_Init();
    MX_ADC1_Init();

    uint32_t baseline = 0;

    while (1)
    {
        /* ==== BACA ADC ==== */
        HAL_ADC_Start(&hadc1);
        HAL_ADC_PollForConversion(&hadc1, 10);
        adcValue = HAL_ADC_GetValue(&hadc1);

        /* ==== FILTER ==== */
        filteredValue = moving_average(adcValue);

        /* ==== BASELINE (ADAPTIF) ==== */
        baseline = (baseline * 9 + filteredValue) / 10;
        uint32_t threshold = baseline + 50;

        /* ==== DETEKSI DETAK + INTERVAL ==== */
        if(filteredValue > threshold && beatDetected == 0)
        {
            beatDetected = 1;

            uint32_t now = HAL_GetTick();

            if(lastBeatTime != 0)
            {
                interval = now - lastBeatTime;

                BPM = 60000 / interval;
            }

            lastBeatTime = now;
        }

        if(filteredValue < threshold)
        {
            beatDetected = 0;
        }

        /* ==== TIMEOUT (TIDAK ADA DETAK) ==== */
        if(HAL_GetTick() - lastBeatTime > 2000)
        {
            BPM = 0;
        }

        /* ==== OUTPUT ==== */
        if(BPM > 0)
        {
            if(BPM >30 && BPM < 60)
            {
                LED_Kuning();
                Buzzer_Off();
                buzzerOff = 0;
            }
            else if(BPM <= 80)
            {
                LED_Hijau();
                Buzzer_Off();
                buzzerOff = 0;
            }
            else
            {
                LED_Merah();
                if(!buzzerOff)
                    Buzzer_On();
                else
                    Buzzer_Off();
            }
        }
        else
        {
            LED_Mati();
            Buzzer_Off();
        }

        HAL_Delay(5);
    }
}

/* ================= CLOCK ================= */
void SystemClock_Config(void)
{
    RCC_OscInitTypeDef RCC_OscInitStruct = {0};
    RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};

    RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI;
    RCC_OscInitStruct.HSIState = RCC_HSI_ON;
    RCC_OscInitStruct.PLL.PLLState = RCC_PLL_NONE;

    HAL_RCC_OscConfig(&RCC_OscInitStruct);

    RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|
                                  RCC_CLOCKTYPE_SYSCLK|
                                  RCC_CLOCKTYPE_PCLK1|
                                  RCC_CLOCKTYPE_PCLK2;

    RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_HSI;
    RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
    RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV1;
    RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;

    HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_0);
}

/* ================= ADC ================= */
void MX_ADC1_Init(void)
{
    ADC_ChannelConfTypeDef sConfig = {0};

    __HAL_RCC_ADC1_CLK_ENABLE();

    hadc1.Instance = ADC1;
    hadc1.Init.ScanConvMode = ADC_SCAN_DISABLE;
    hadc1.Init.ContinuousConvMode = DISABLE;
    hadc1.Init.ExternalTrigConv = ADC_SOFTWARE_START;
    hadc1.Init.DataAlign = ADC_DATAALIGN_RIGHT;
    hadc1.Init.NbrOfConversion = 1;

    HAL_ADC_Init(&hadc1);

    sConfig.Channel = ADC_CHANNEL_0;
    sConfig.Rank = ADC_REGULAR_RANK_1;
    sConfig.SamplingTime = ADC_SAMPLETIME_71CYCLES_5;

    HAL_ADC_ConfigChannel(&hadc1, &sConfig);
}

/* ================= GPIO ================= */
void MX_GPIO_Init(void)
{
    __HAL_RCC_GPIOA_CLK_ENABLE();
    __HAL_RCC_GPIOB_CLK_ENABLE();

    GPIO_InitTypeDef GPIO_InitStruct = {0};

    /* PA0 = ADC */
    GPIO_InitStruct.Pin = GPIO_PIN_0;
    GPIO_InitStruct.Mode = GPIO_MODE_ANALOG;
    HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);

    /* PA1 = BUTTON */
    GPIO_InitStruct.Pin = GPIO_PIN_1;
    GPIO_InitStruct.Mode = GPIO_MODE_IT_FALLING;
    GPIO_InitStruct.Pull = GPIO_PULLUP;
    HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);

    HAL_NVIC_SetPriority(EXTI1_IRQn, 0, 0);
    HAL_NVIC_EnableIRQ(EXTI1_IRQn);

    /* LED + BUZZER */
    GPIO_InitStruct.Pin = GPIO_PIN_0 | GPIO_PIN_1 |
                          GPIO_PIN_10 | GPIO_PIN_11;

    GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
    GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;

    HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);

    HAL_GPIO_WritePin(GPIOB, GPIO_PIN_0 | GPIO_PIN_1 |
                      GPIO_PIN_10 | GPIO_PIN_11, GPIO_PIN_RESET);
}

5. Video Demo [Kembali]


6. Kondisi [Kembali]

M2 P1 K1: Buatlah rangkaian seperti pada gambar percobaan 1 dengan kondisi Sensor Heartbeat membaca BPM>70 dan push button tidak ditekan, maka LED menyala merah dan Buzzer berbunyi

7. Video Simulasi [Kembali]


8. Download File [Kembali]

Rangkaian Simulasi [Klik]

Video Simulasi [Klik]


Kembali ke Halaman Atas







Komentar

Postingan populer dari blog ini