PWM-----LEDブリージングライトの導入と応用 (2)

この章では、呼吸する光を生み出す LED の効果について紹介します。記事の最後には完全なプロジェクト ファイルへのリンクがあり、必要に応じてダウンロードできます。

PWM の概要

パルス幅変調 (PWM) は、英語で「パルス幅変調」の略称で、パルス幅変調とも呼ばれ、マイクロプロセッサのデジタル出力を使用してアナログ回路を制御する非常に効果的な技術です
簡単に言うと
パルス幅の制御です。
TIM6 と 7 を除く STM32 タイマー。他のタイマーを使用して PWM 出力を生成することもできます。アドバンスト タイマー
TIM1 および TIM8 は、最大 7 つの PWM 出力を同時に生成できます。汎用タイマは同時に最大 4 つの
PWM 出力を生成できるため、STM32 は同時に最大 30 の PWM 出力を生成できます。

STM32の汎用タイマTIMxにPWM出力を生成させるために、PWM を制御する 3 つのレジスタも使用しますこれら 3 つのレジスタは、キャプチャ/コンペア モード レジスタ TIMx_CCMR1/2)、キャプチャ/コンペア イネーブル レジスタ ( TIMx_CCER )、キャプチャ/コンペア レジスタ ( TIMx_CCR1 ~ 4 ) です。次に、これら 3 つのレジスタを簡単に紹介します。

1 つ目はキャプチャ / コンペア モード レジスタ ( TIMx_CCMR1/2 ) で、合計 2 つのレジスタTIMx _CCMR1 があります。
および TIMx_CCMR2 TIMx_CCMR1 は CH12 を制御し TIMx_CCMR2 はCH34を制御します登録簿
各人物の説明は図に示されています
このレジスタの一部のビットはモードごとに異なる機能を持つため、図では レジスタを 2 つの層に分割し、上の層が出力に対応し、下の層が入力に対応します。このレジスタの詳細な説明については、 『STM32 Reference Manual』の 288 ページのセクション 14.4.7を参照してください ここで説明しなければならないのはモード設定ビット OCxMで 、この部分は 3 ビットで構成されます。合計 7 つのモードを設定できます。PWM モード 使用している ため、これらの3ビットは110/111に設定する必要がありますこれら 2 つの PWM モードの違いは、出力レベルの極性が反転することです。
次に、キャプチャ / コンペア イネーブル レジスタ ( TIMx_CCER ) を紹介します。
道路スイッチ。レジスタの各ビットの説明を 次の図に示します。
このレジスタは比較的単純です。ここではCC2Eビット のみを使用します 。このビットは入力 / キャプチャ 2 出力イネーブル ビットです。
PWMは IOポート から出力され 、このビットは1に設定する必要があるため、このビットを1に設定する必要がありますこのレジスタについてはさらに詳しく説明します
導入については、 「 STM32 リファレンス マニュアル」の 292 ページのセクション 14.4.9を参照してください
最後に、キャプチャ / コンペア レジスタ ( TIMx_CCR1~4 ) を紹介します。これは 4 に対応し、合計 4 つあります。
出力チャンネル CH1~4 これら 4 つの レジスタは似ているため、 TIMx_CCR1のみ を例として取り上げ、各レジスタを紹介します。
ビットの説明を次の図に示します。

 

出力モードでは、このレジスタの値が CNT の値と比較され、比較結果に応じて対応するアクションが実行されます。これを利用して、
このレジスタの値を変更することで、 PWM の出力パルス幅を制御できます。この章では、 TIM3を使用します。
チャンネル 2なので、 DS0の輝度のパルス幅制御を実現するにはTIM3_CCR2 を変更する必要があります
TIM3 CH2 出力 PWMを使用して DS0の明るさ を制御したい のですが、デフォルトではTIM3_CH2 がPA7に接続されています。
上記で、 DS0 は PB5 に接続されていますが、通常の MCUであれば、フライング ワイヤでPA7をPB5に飛ばすことしかできないかもしれません。
これは実装されていますが、より高度な STM32 を使用し、再マッピング機能を使用してTIM3_CH2を配置できます。
PB5 にマッピングされます
STM32のリマッピング制御は 、多重化リマッピングおよびデバッグ IO 構成レジスタ ( AFIO_MAPR ) によって 制御されます。
各レジスタの説明を 次の図に示します。

 ここで使用するのは TIM3の再マッピングです。上の図からわかるように、TIM3_REMAPは2ビット[11:10]によって制御されます。TIM3_REMAP[1:0]再マッピング制御テーブルを次の表に示します。 

デフォルトでは、 TIM3_REMAP[1:0]は 00 であり 、再マッピングはないため、TIM3_CH1~TIM3_CH4がポイントします
PA6 PA7 PB0 PB1 に接続されていないため TIM3_CH2 を PB5 にマップしたいので 、設定する必要があります
TIM3_REMAP[1:0]=10 、つまり部分的な再マッピング ここで、 この時点では TIM3_CH1も PB4 にマッピングされることに注意してください。
これまで、この章で使用するいくつかの関連レジスタを紹介しましたが、この章では、 TIM3_CH2の再マッピングを実装します。
PB5 では TIM3_CH2 が PWM を出力して DS0の輝度を制御します以下にライブラリ関数の構成を紹介します。
機能ステップ。
まず、 PWM 関連の関数はライブラリ関数ファイル stm32f10x_tim.h および stm32f10x_tim.cに設定されているということです。
ファイル内にあります。
1 ) TIM3クロックと多重化機能クロック をオンにし PB5 を多重化出力として設定します。
TIM3 を使用するには、まずTIM3のクロック をオンにする必要があります 。これは、多くのコードを読んだ後であれば誰もが理解できるはずだと思います。
ここでは、 TIM3_CH2チャネルが PB5 に再マッピングされるため、 PB5 多重化出力として 構成する必要もあります
多重化機能の出力に属します。 ライブラリ関数で TIM3クロック を有効にする方法は次のとおりです。
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE); //タイマー3 のクロックを有効にする
ライブラリ関数による AFIOクロックの設定方法は 以下のとおりです。
RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE); //マルチプレクスクロックイネーブル
これら 2 行のコードは整理しやすいため、ここでは繰り返しません。 PB5 を多重関数出力として設定するだけです。
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; //多重プッシュプル出力
2 ) TIM3_CH2 を PB5 に再マッピングするように設定します
TIM3_CH2 はデフォルトで PA7 に接続されている ため、 TIM3_REMAP を部分的な再マッピングとして設定する必要があります(パス
AFIO_MAPR構成 を通じて )、 TIM3_CH2 を PB5 に再マッピングします ライブラリ関数にリマッピング関数を設定する
数字は次のとおりです。
void GPIO_PinRemapConfig(uint32_t GPIO_Remap, FunctionalState NewState)
STM32 再マッピングは、特定のポートにのみ再マッピングできます。最初のエントリ パラメータは、リマッピングのタイプを設定するものとして理解できます。たとえば、 TIM3 部分リマッピングのエントリ パラメータは次のようになります。
名前が示すように、GPIO_PartialRemap_TIM3 。したがって、TIM3の部分リマッピングのためのライブラリ関数の実装方法は次のようになります。
GPIO_PinRemapConfig(GPIO_PartialRemap_TIM3, ENABLE);
3 ) TIM3 を初期化し、 TIM3ARRPSC を設定します
TIM3のクロック をオンにした後、出力PWMを制御するために2 つのレジスタARRPSCの値 を設定する必要があります。
サイクル。 PWM サイクルが遅すぎる ( 50Hz未満) 、明らかにちらつきを感じます。したがって、 PWM 週は
ここでの期間はあまり小さく設定しないでください。これは、TIM_TimeBaseInit 関数を通じてライブラリ関数に 実装され、呼び出しの形式は次のとおりです。
TIM_TimeBaseStructure.TIM_Period = arr; //自動リロード値を設定します
TIM_TimeBaseStructure.TIM_Prescaler =psc; //プリスケーラー値を設定します
TIM_TimeBaseStructure.TIM_ClockDivision = 0; //クロック分周を設定: TDTS = Tck_tim
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //アップカウントモード
TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure); //指定されたパラメータに従ってTIMxを初期化します
4 ) TIM3_CH2 PWMモードを設定し TIM3 CH2出力を有効にします
次に、 DS0が低電力であるため、 TIM3_CH2 を PWMモード (デフォルトはフリーズ) 設定する必要があります。
フラットで明るいので、 CCR2の値 が小さいと DS0 が暗くなり、 CCR2の値が 大きいと DS0 が明るくなるといいので、
TIM3_CCMR1の関連ビット を設定することでTIM3_CH2のモードを 制御する必要があります ライブラリ関数ではPWMチャネルを設定します
設定は関数 TIM_OC1Init()~TIM_OC4Init()を介して設定されます が、チャネルごとに設定関数が異なります。
チャネル2 を使用している ため、使用される関数は TIM_OC2Init()です
void TIM_OC2Init(TIM_TypeDef* TIMx, TIM_OCInitTypeDef* TIM_OCInitStruct)
この初期化形式は誰にとってもよく知られているはずなので、構造体TIM_OCInitTypeDefを見てみましょう。
意味:
typedef 構造体
{
uint16_t TIM_OCMode;
uint16_t TIM_OutputState;
uint16_t TIM_OutputNState; */
uint16_t TIM_パルス;
uint16_t TIM_OCPolarity;
uint16_t TIM_OCNPolarity;
uint16_t TIM_OCIdleState;
uint16_t TIM_OCNIdleState;
TIM_OCInitTypeDef;
ここでは、要件に関連するいくつかのメンバー変数について説明します。
パラメータ TIM_OCMode設定モードはPWMまたは出力比較で、ここではPWMモードです。
パラメータ TIM_OutputState は、比較出力イネーブルを設定するために使用されます。つまり、 ポートへの PWM出力をイネーブルにします。
パラメータ TIM_OCPolarity は、極性が高か低かを設定するために使用されます。
他のパラメータ TIM_OutputNState TIM_OCNPolarity TIM_OCIdleState および TIM_OCNIdleState は次のとおりです。
アドバンスト タイマー TIM1 および TIM8 によってのみ使用されます。
上で述べたシナリオを実現するための方法は次のとおりです。
TIM_OCInitTypeDef TIM_OCInitStructure;
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM2; // PWMモード2を選択
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable; //コンペア出力イネーブル
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High; //出力極性は高です
TIM_OC2Init(TIM3, &TIM_OCInitStructure); // TIM3 OC2を初期化します
5 ) TIM3を有効にします
上記の設定が完了したら、 TIM3 を有効にする必要があります TIM3 を 有効にする方法は 以前に説明しました。
TIM_Cmd(TIM3, ENABLE); // TIM3を有効にする
6 ) TIM3_CCR2を変更して デューティ サイクルを制御します。
最後に、上記の設定後、実際に PWM が 出力され始めますが、そのデューティ サイクルと周波数は固定されています。
TIM3_CCR2を変更することで CH2の出力デューティ サイクル を制御でき ます次にDS0の明るさを制御します
ライブラリ関数で、 TIM3_CCR2のデューティ サイクルを変更する関数は 次のとおりです。
void TIM_SetCompare2(TIM_TypeDef* TIMx, uint16_t Compare2)
もちろん、他のチャネルについてもそれぞれ関数名があり、関数の形式は TIM_SetComparex(x=1,2,3,4)になります
上記の 6 つのステップにより、 TIM3CH2 を制御してPWM波を出力する ことができます

コードプログラムの一部:

PWMの初期化

void TIM3_PWM_Init(u16 arr,u16 psc)
{ 
GPIO_InitTypeDef GPIO_InitStructure;
TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
TIM_OCInitTypeDef TIM_OCInitStructure;
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE); //使能定时器 3 时钟
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB|
RCC_APB2Periph_AFIO, ENABLE); //使能 GPIO 和 AFIO 复用功能时钟
GPIO_PinRemapConfig(GPIO_PartialRemap_TIM3, ENABLE); //重映射 TIM3_CH2->PB5 
//设置该引脚为复用输出功能,输出 TIM3 CH2 的 PWM 脉冲波形 GPIOB.5
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5; //TIM_CH2
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; //复用推挽输出
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOB, &GPIO_InitStructure); //初始化 GPIO
//初始化 TIM3
TIM_TimeBaseStructure.TIM_Period = arr; //设置在自动重装载周期值
TIM_TimeBaseStructure.TIM_Prescaler =psc; //设置预分频值
TIM_TimeBaseStructure.TIM_ClockDivision = 0; //设置时钟分割:TDTS = Tck_tim
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //TIM 向上计数模式
TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure); //初始化 TIMx
//初始化 TIM3 Channel2 PWM 模式
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM2; //选择 PWM 模式 2
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable; //比较输出使能
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High; //输出极性高
TIM_OC2Init(TIM3, &TIM_OCInitStructure); //初始化外设 TIM3 OC2
TIM_OC2PreloadConfig(TIM3, TIM_OCPreload_Enable); //使能预装载寄存器
TIM_Cmd(TIM3, ENABLE); //使能 TIM3
}

完全なプロジェクト ファイル: (メッセージ 28 件) STM32 定時原子 PWM 出力実験に基づく - 呼吸光 - MCU ドキュメント リソース - CSDN ライブラリ

おすすめ

転載: blog.csdn.net/m0_63171897/article/details/127289633