你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

STM8 ADC扫描(C++版本)

[复制链接]
小槑槑 发布时间:2015-4-23 22:38
刚开始学单片机,STM8在IAR环境下能用C++,对我来说实在是太好了,我是那种没对象不会编程的银,我可以把功能都封装起来,以后需要优化时再脱离库函数。
这两天总结了一下STM8 ADC的用法,手头的103F6支持5路ADC,两路被UART占用了,这里列出我的三路扫描的方法,与各位初学者共同探讨:

// 头文件:

/*
   ADC
*/

#ifndef  _ADC1_H
#define  _ADC1_H

#include "stm8s_conf.h"

#define ADC1_EOC_IRQ                    0x16

class __near cADC1
{
  public:
    cADC1(int);
    uint16_t                    read_ADC_value(ADC1_Channel_TypeDef);
    void                        NextConversion();
    void                        StartConversion();
  private:
    uint16_t                    m_channel2_value,m_channel3_value,m_channel4_value;
    ADC1_Channel_TypeDef        m_current_channel;              
};

cADC1           __near Adc1(0);
#endif

// 源程序
#include "Adc1.h"

/* ADC1 通道扫描方式, 开通了三个通道 */

cADC1 __near *Adc1_instance;  

cADC1::cADC1(int id)
{
  Adc1_instance = this;      // 中断要引用这个实例
  // 对于stm8s003 103F3,有ANI2~6
  // ADC1_CHANNEL_2:
    GPIO_Init(GPIOC, GPIO_PIN_4, GPIO_MODE_IN_FL_NO_IT);
  // ADC1_CHANNEL_3:
    GPIO_Init(GPIOD, GPIO_PIN_2, GPIO_MODE_IN_PU_NO_IT);
  // ADC1_CHANNEL_4:
    GPIO_Init(GPIOD, GPIO_PIN_3, GPIO_MODE_IN_PU_NO_IT);
  // ADC1_CHANNEL_5:  // UART1_TX
  // GPIO_Init(GPIOD, GPIO_PIN_5, GPIO_MODE_IN_FL_NO_IT);
  // ADC1_CHANNEL_6:  // UART1_RX
  // GPIO_Init(GPIOD, GPIO_PIN_6, GPIO_MODE_IN_FL_NO_IT);

  m_current_channel =  ADC1_CHANNEL_2;
  ADC1_Init(ADC1_CONVERSIONMODE_SINGLE , m_current_channel, ADC1_PRESSEL_FCPU_D8,\
    ADC1_EXTTRIG_TIM, DISABLE, ADC1_ALIGN_RIGHT,ADC1_SCHMITTTRIG_ALL,ENABLE);
  ADC1_ScanModeCmd(ENABLE);             // 扫描模式
  ADC1_DataBufferCmd(ENABLE);           // 使用数据缓冲区寄存器
  ADC1_ITConfig(ADC1_IT_EOCIE, ENABLE); // 转换结束中断
  StartConversion();                    // 执行第一次转换
}

uint16_t cADC1::read_ADC_value(ADC1_Channel_TypeDef Ani)
{
  switch (Ani)
  {
   case ADC1_CHANNEL_2:  return m_channel2_value;
   case ADC1_CHANNEL_3:  return m_channel3_value;
   case ADC1_CHANNEL_4:  return m_channel4_value;
   default: return 0;
  }
}


void cADC1::StartConversion()
{
  if (ADC1_CHANNEL_2 == m_current_channel)      // 启动通道
  {
    ADC1_Cmd(ENABLE);                           // 中断使能
    ADC1_StartConversion();
  }
}

void cADC1::NextConversion()
{
  switch (m_current_channel)
  {
    case ADC1_CHANNEL_2:
      m_channel2_value = ADC1_GetBufferValue(0x02); // 读取ADC结果,保存在成员变量中
      m_current_channel = ADC1_CHANNEL_3;           // 切换到下一个通道
      ADC1_ConversionConfig(ADC1_CONVERSIONMODE_SINGLE, m_current_channel, ADC1_ALIGN_RIGHT);
      break;

    case ADC1_CHANNEL_3:
      m_channel3_value = ADC1_GetBufferValue(0x03); // 读取ADC结果,保存在成员变量中
      m_current_channel = ADC1_CHANNEL_4;           // 切换到下一个通道
      ADC1_ConversionConfig(ADC1_CONVERSIONMODE_SINGLE, m_current_channel, ADC1_ALIGN_RIGHT);
      break;

    case ADC1_CHANNEL_4:
      m_channel4_value = ADC1_GetBufferValue(0x04); // 读取ADC结果,保存在成员变量中
      m_current_channel = ADC1_CHANNEL_2;           // 切换到下一个通道
      ADC1_ConversionConfig(ADC1_CONVERSIONMODE_SINGLE, m_current_channel, ADC1_ALIGN_RIGHT);
                                                   
      ADC1_Cmd(DISABLE);                            // 停止,由StartConversion启动下一次的扫描
      break;
                                                     //  可以扩展到通道5、6
    default:
      break;
  }
}

INTERRUPT_HANDLER(ADC1_EOC_IRQHandler, ADC1_EOC_IRQ)
{
  ADC1_ClearITPendingBit(ADC1_IT_EOC);
  Adc1_instance->NextConversion();
}

只需要定时调用Adc1.StartConversion(),就可以通过 Adc1.read_ADC_value(ADC1_CHANNEL_x)读取相应通道的ADC值。
收藏 1 评论2 发布时间:2015-4-23 22:38

举报

2个回答
小槑槑 回答时间:2015-4-23 22:59:58
void cMANAGER::Run()
{
  int value;
//  Led_yellow.Flash();
  value = Adc1.read_ADC_value(ADC1_CHANNEL_2);
  double voltage = value * 3.3/ 1023;
  double radio = (double)value / 1023 * 100;
  cUART1::printf("value = %d %d %d %fV %f% \r\n",
    Adc1.read_ADC_value(ADC1_CHANNEL_3),
    Adc1.read_ADC_value(ADC1_CHANNEL_4),
    (int)value, voltage, radio);
}
三路采样输出的结果:
22:55:29.677 value = 550 658 413 1.3322V 40.3714%
22:55:30.180 value = 550 658 414 1.3354V 40.4692%
22:55:30.683 value = 550 658 414 1.3354V 40.4692%
22:55:31.186 value = 551 657 413 1.3322V 40.3714%
22:55:31.690 value = 550 657 413 1.3322V 40.3714%
22:55:32.192 value = 550 657 413 1.3322V 40.3714%
22:55:32.695 value = 550 657 414 1.3354V 40.4692%
22:55:33.198 value = 550 658 414 1.3354V 40.4692%
22:55:33.701 value = 551 658 414 1.3354V 40.4692%
22:55:34.206 value = 550 658 413 1.3322V 40.3714%
22:55:34.707 value = 550 657 414 1.3354V 40.4692%
22:55:35.210 value = 550 657 413 1.3322V 40.3714%
22:55:35.713 value = 550 657 413 1.3322V 40.3714%
22:55:36.216 value = 550 657 413 1.3322V 40.3714%
22:55:36.719 value = 550 658 413 1.3322V 40.3714%
22:55:37.220 value = 550 658 414 1.3354V 40.4692%
22:55:37.720 value = 550 657 414 1.3354V 40.4692%
22:55:38.228 value = 550 657 413 1.3322V 40.3714%
22:55:38.731 value = 550 657 413 1.3322V 40.3714%
22:55:39.234 value = 550 658 413 1.3322V 40.3714%
lianghang 回答时间:2015-4-24 14:43:53
C 语言还是很重要的;
关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
STM32N6 AI生态系统
STM32MCU,MPU高性能GUI
ST ACEPACK电源模块
意法半导体生物传感器
STM32Cube扩展软件包
关注我们
st-img 微信公众号
st-img 手机版