-
福利一海量deepseek资料包(持续更新)
-
福利二ComfyUI工作流&模型&插件
-
福利三AI工具集合包以及AI绘画解决方案

| 名称 | 参数 |
|---|---|
| 输入电压范围 | 直流 3.3V 至 5V |
| 输出信号 | 块特设二路模拟输出和一路数字输出接口,输出值分别对应(X,Y)双轴偏移量,其类型为模拟量,按键表示用户是否在Z轴上按下,其类型为数字开关量。 |
| 结构 | 十字摇杆为一个双向的10K 电阻器 |
摇杆一般在航模、电玩、遥控车、云台等设备上应用广泛,很多带有屏幕的设备也经常使用摇杆作为菜单选择的输入控制。
双轴按键摇杆主要由两个电位器和一个按键开关组成,两个电位器随着摇杆扭转角度分别输出 X、Y 轴上对应的电压值,在 Z 轴方向上按下摇杆可触发轻触按键。
在配套机械结构的作用下,无外力扭动的摇杆初始状态下,两个电位器都处在量程的中间位置。它就是两个电位器和按键的组合体。电位器是可变电阻器,与中学时学的滑动变阻器类似。
PS2 摇杆的五个端口分别为 VCC,X,Button,Y,GND。
摆动 PS2 游戏摇杆时,随着接触刷改变接触位置,可变电阻器(电位器)的引脚处的输出电压即发生变化。
X,Y 轴为模拟输入信号而 Z 轴是数字输入信号,因此,X 和 Y 端口连接到 ADC 引脚,而 Z 端口连接到数字端口。
所以我们一共需要使用 ESP32 的三个 GPIO 引脚,其中两个模拟信号输入引脚和一个数字信号输入引脚。PS2 游戏摇杆正常状态(不受力状态)检测电压常态时为 1.65V 附近,最大值 3.3V,最小值 0V,用 ESP32 自带 ADC 模数转换模块的两个通道分别检测电压值的变化就可以知道摇杆指向的位置了。
ESP32 上有几个引脚可以用来获取模拟量——这些引脚称为 ADC 引脚(模拟值转换为数字值)。
以下所有 GPIO 均可用作 ADC 引脚:0、2、4、12、13、14、15、25、26、27、32、33、34、35、36、39。
但有些开发板上0、2、4引脚不能使用,推荐使用32、 32、33、34、35、36、39。

-ADC.ATTN_0DB— 满量程电压:1.2V
-ADC.ATTN_2_5DB— 满量程电压:1.5V
-ADC.ATTN_6DB— 全量程电压:2.0V
-ADC.ATTN_11DB— 全量程电压:3.3V
from machine import Pin, ADC
import time
ps2_y = ADC(Pin(33))
ps2_y.atten(ADC.ATTN_11DB) # 这里配置测量量程为3.3V
ps2_x = ADC(Pin(32))
ps2_x.atten(ADC.ATTN_11DB) # 这里配置测量量程为3.3V
btn = Pin(15, Pin.IN)
while True:
val_y = ps2_y.read() # 0-4095
val_x = ps2_x.read() # 0-4095
print("x:{} y:{} btn:{}".format(val_x, val_y, btn.value()))
time.sleep(0.1)
PS2 模块的 +5V 引脚接 ESP32 的 3V3 引脚,一般情况下 ESP32 的 ADC 电压输入范围为 0-3.3V,高于 3.3V 可能会烧坏 ADC。
摇杆模块的 GND 接 GND;模块的 SW 接 D4,VRX 接 D15,VRY 接 D2。舵机接开发板另一侧的 5V 引脚、GND 和 D13。
| ps2引脚 | esp32引脚 |
|---|---|
| GND | GND |
| +5V | 3.3V |
| VRX | GPIO15 |
| VRY | GPIO2 |
| SW | GPIO4 |

使用 PS2 摇杆模块控制舵机了,代码如下:
import time
from machine import Pin, ADC, PWM
# 定义摇杆引脚
ps2_x = ADC(Pin(15), atten=ADC.ATTN_11DB)
ps2_y = ADC(Pin(2), atten=ADC.ATTN_11DB)
ps2_button = Pin(4, Pin.IN)
# 定义舵机控制引脚
my_servo = PWM(Pin(13), freq=50)
while True:
# 读取 X 轴模拟信号
x_value = ps2_x.read()
# 在一个周期内(20ms), 0.5ms -> 0°, 2.4ms -> 180°
# 0.5/20 * 1024
servo_angle = x_value/4095 *(2.4-0.5)/20 *1024 + 0.5/20 * 1024
# duty 方法控制舵机转动,0-1023, 0°-> 0.5/20 * 1024;
# 180° -> 2.4/20*1024;
my_servo.duty(int(servo_angle))
time.sleep(0.1)