คลาส Timer -- ควบคุมตัวจับเวลาภายใน

ตัวจับเวลาสามารถใช้งานได้หลากหลายรูปแบบ ในขณะนี้ มีการรองรับเฉพาะกรณีพื้นฐานที่สุดเท่านั้น ได้แก่ การเรียกฟังก์ชันซ้ำๆ ตามช่วงเวลาที่กำหนด

ตัวจับเวลาแต่ละตัวประกอบด้วยตัวนับที่นับขึ้นในอัตราหนึ่ง อัตราที่นับคือความถี่สัญญาณนาฬิกาของอุปกรณ์ต่อพ่วง (เป็น Hz) หารด้วยตัวหารของตัวจับเวลา เมื่อตัวนับถึงค่าคาบของตัวจับเวลา ก็จะก่อให้เกิดเหตุการณ์และตัวนับจะรีเซตกลับเป็นศูนย์ ด้วยการใช้เมธอด callback ตัวจับเวลาสามารถเรียกฟังก์ชัน Python ได้

ตัวอย่างการใช้งานเพื่อสลับสถานะ LED ด้วยความถี่คงที่:

tim = pyb.Timer(4)              # create a timer object using timer 4
tim.init(freq=2)                # trigger at 2Hz
tim.callback(lambda t:pyb.LED(1).toggle())

ตัวอย่างการใช้ฟังก์ชันที่มีชื่อสำหรับ callback:

def tick(timer):                # we will receive the timer object when being called
    print(timer.counter())      # show current timer's counter value
tim = pyb.Timer(4, freq=1)      # create a timer object using timer 4 - trigger at 1Hz
tim.callback(tick)              # set the callback to our tick function

ตัวอย่างเพิ่มเติม:

tim = pyb.Timer(4, freq=100)    # freq in Hz
tim = pyb.Timer(4, prescaler=0, period=99)
tim.counter()                   # get counter (can also set)
tim.prescaler(2)                # set prescaler (can also get)
tim.period(199)                 # set period (can also get)
tim.callback(lambda t: ...)     # set callback for update interrupt (t=tim instance)
tim.callback(None)              # clear callback

หมายเหตุ: Timer(1) ถูกใช้สำหรับกล้อง ในทำนองเดียวกัน Timer(5) ควบคุมไดรเวอร์เซอร์โว และ Timer(6) ใช้สำหรับการอ่าน/เขียน ADC/DAC แบบตั้งเวลา แนะนำให้ใช้ตัวจับเวลาตัวอื่นในโปรแกรมของคุณ

หมายเหตุ: ไม่สามารถจัดสรรหน่วยความจำระหว่าง callback (อินเทอร์รัปต์) ได้ ดังนั้นข้อยกเว้นที่เกิดขึ้นภายใน callback จะไม่ให้ข้อมูลมากนัก ดู micropython.alloc_emergency_exception_buf() สำหรับวิธีหลีกเลี่ยงข้อจำกัดนี้

ตัวสร้าง

class pyb.Timer(id: int, *args, **kwargs)

สร้างออบเจ็กต์ตัวจับเวลาใหม่ด้วย id ที่กำหนด หากมีอาร์กิวเมนต์เพิ่มเติม ตัวจับเวลาจะถูกเริ่มต้นด้วย init(...) ชุดค่า id ที่ถูกต้องขึ้นอยู่กับ STM32 MCU บน OpenMV Cam ที่ใช้งาน โปรดดูคู่มืออ้างอิง STM32 สำหรับตัวจับเวลาเอนกประสงค์และตัวควบคุมขั้นสูงที่มีให้ใช้

เมธอด

init(*, freq: int | float | None = None, prescaler: int | None = None, period: int | None = None, mode: int = Timer.UP, div: int = 1, callback: Callable[[Timer], None] | None = None, deadtime: int = 0, brk: int = Timer.BRK_OFF, hard: bool = True) None

เริ่มต้นตัวจับเวลา การเริ่มต้นต้องระบุด้วยความถี่ (เป็น Hz) หรือตัวหารและคาบ:

tim.init(freq=100)                  # set the timer to trigger at 100Hz
tim.init(prescaler=83, period=999)  # set the prescaler and period directly

อาร์กิวเมนต์แบบคีย์เวิร์ด:

  • freq --- ระบุความถี่แบบคาบของตัวจับเวลา คุณอาจมองว่านี่คือความถี่ที่ตัวจับเวลาใช้ผ่านหนึ่งรอบสมบูรณ์

  • prescaler [0-0xffff] - ระบุค่าที่จะโหลดเข้า Prescaler Register (PSC) ของตัวจับเวลา แหล่งสัญญาณนาฬิกาของตัวจับเวลาจะถูกหารด้วย (prescaler + 1) เพื่อหาสัญญาณนาฬิกาของตัวจับเวลา แหล่งสัญญาณนาฬิกามาจาก APB bus แม่ของตัวจับเวลาและ ขึ้นอยู่กับ MCU บน STM32 ตัวจับเวลาบน APB1 โดยทั่วไปใช้สัญญาณนาฬิกาที่ 2 * pclk1 และตัวจับเวลาบน APB2 ที่ 2 * pclk2 อ่านความถี่ bus ปัจจุบันด้วย pyb.freq() และดูคู่มืออ้างอิง STM32 สำหรับ MCU ของ OpenMV Cam

  • period [0-0xffff] สำหรับตัวจับเวลา 1, 3, 4 และ 6-15 [0-0x3fffffff] สำหรับตัวจับเวลา 2 และ 5 ระบุค่าที่จะโหลดเข้า AutoReload Register (ARR) ของตัวจับเวลา ค่านี้กำหนดคาบของตัวจับเวลา (กล่าวคือ เมื่อตัวนับวนรอบ) ตัวนับจะโรลโอเวอร์หลังจาก period + 1 รอบสัญญาณนาฬิกาของตัวจับเวลา

  • mode สามารถเป็นหนึ่งใน:

    • Timer.UP - กำหนดค่าตัวจับเวลาให้นับจาก 0 ถึง ARR (ค่าเริ่มต้น)

    • Timer.DOWN - กำหนดค่าตัวจับเวลาให้นับจาก ARR ลงมาถึง 0

    • Timer.CENTER - กำหนดค่าตัวจับเวลาให้นับจาก 0 ถึง ARR แล้วกลับลงมาถึง 0

  • div สามารถเป็นหนึ่งใน 1, 2 หรือ 4 หารสัญญาณนาฬิกาของตัวจับเวลาเพื่อกำหนดสัญญาณนาฬิกาการสุ่มตัวอย่างที่ใช้โดยฟิลเตอร์ดิจิทัล

  • callback - ตามที่ระบุใน Timer.callback()

  • deadtime - ระบุปริมาณเวลา "dead" หรือเวลาหยุดระหว่างการเปลี่ยนสถานะบนช่องสัญญาณเสริม (ทั้งสองช่องสัญญาณจะหยุดทำงานในช่วงเวลานี้) deadtime อาจเป็นจำนวนเต็มระหว่าง 0 ถึง 1008 โดยมีข้อจำกัดดังนี้: 0-128 เพิ่มทีละ 1, 128-256 เพิ่มทีละ 2, 256-512 เพิ่มทีละ 8 และ 512-1008 เพิ่มทีละ 16 deadtime วัดจำนวนเทิกของ source_freq หารด้วยสัญญาณนาฬิกา div deadtime ใช้ได้เฉพาะกับตัวจับเวลา 1 และ 8 เท่านั้น

  • brk - ระบุว่าจะใช้โหมด break เพื่อหยุด output ของ PWM เมื่อ BRK_IN input ถูกกระตุ้นหรือไม่ ค่าของอาร์กิวเมนต์นี้กำหนดว่า break เปิดใช้งานและมีขั้วใด และสามารถเป็นหนึ่งใน Timer.BRK_OFF, Timer.BRK_LOW หรือ Timer.BRK_HIGH เพื่อเลือกพิน BRK_IN ให้สร้างออบเจ็กต์ Pin ด้วย mode=Pin.ALT, alt=Pin.AFn_TIMx ลักษณะ GPIO input ของพินสามารถใช้งานได้ในโหมด alt ได้แก่ pull=, value() และ irq()

  • hard สามารถเป็นหนึ่งใน:

    • True - callback จะถูกเรียกใช้ในบริบท hard interrupt ซึ่งลดความหน่วงและความสั่นไหวให้น้อยที่สุด แต่ต้องอยู่ภายใต้ข้อจำกัดที่อธิบายไว้ใน การเขียนตัวจัดการอินเทอร์รัปต์ รวมถึงไม่สามารถจัดสรรบน heap ได้

    • False - callback จะถูกกำหนดเวลาเป็น soft interrupt ซึ่งอนุญาตให้จัดสรรได้ แต่อาจทำให้เกิดความหน่วงและความสั่นไหวจากการ garbage-collection

    ค่าเริ่มต้นของตัวเลือกนี้คือ True

คุณต้องระบุ freq หรือทั้ง period และ prescaler

deinit() None

ยกเลิกการเริ่มต้นตัวจับเวลา

ปิดใช้งาน callback (และ irq ที่เกี่ยวข้อง)

ปิดใช้งาน callback ของช่องสัญญาณ (และ irq ที่เกี่ยวข้อง) หยุดตัวจับเวลา และปิดใช้งานอุปกรณ์ต่อพ่วงของตัวจับเวลา

callback(fun: Callable[[Timer], None] | None) None

ตั้งค่าฟังก์ชันที่จะถูกเรียกเมื่อตัวจับเวลาทริกเกอร์ fun จะถูกส่งอาร์กิวเมนต์ 1 ตัว คือออบเจ็กต์ตัวจับเวลา หาก fun เป็น None callback จะถูกปิดใช้งาน

channel(channel: int, mode: int | None = None, *args, **kwargs) TimerChannel | None

หากส่งเฉพาะหมายเลขช่องสัญญาณ ออบเจ็กต์ช่องสัญญาณที่เริ่มต้นไว้ก่อนหน้าจะถูกส่งคืน (หรือ None หากไม่มีช่องสัญญาณก่อนหน้า)

มิเช่นนั้น ออบเจ็กต์ TimerChannel จะถูกเริ่มต้นและส่งคืน

แต่ละช่องสัญญาณสามารถกำหนดค่าเพื่อทำ pwm, output compare หรือ input capture ทุกช่องสัญญาณใช้ตัวจับเวลาพื้นฐานร่วมกัน ซึ่งหมายความว่าพวกมันใช้สัญญาณนาฬิกาของตัวจับเวลาร่วมกัน

อาร์กิวเมนต์แบบคีย์เวิร์ด:

  • mode สามารถเป็นหนึ่งใน:

    • Timer.PWM --- กำหนดค่าตัวจับเวลาในโหมด PWM (active high)

    • Timer.PWM_INVERTED --- กำหนดค่าตัวจับเวลาในโหมด PWM (active low)

    • Timer.OC_TIMING --- ระบุว่าไม่มีพินที่ถูกขับเคลื่อน

    • Timer.OC_ACTIVE --- พินจะถูกทำให้ active เมื่อมีการจับคู่ compare (active ถูกกำหนดโดยขั้ว)

    • Timer.OC_INACTIVE --- พินจะถูกทำให้ inactive เมื่อมีการจับคู่ compare

    • Timer.OC_TOGGLE --- พินจะสลับสถานะเมื่อมีการจับคู่ compare

    • Timer.OC_FORCED_ACTIVE --- พินถูกบังคับให้ active (การจับคู่ compare จะถูกละเว้น)

    • Timer.OC_FORCED_INACTIVE --- พินถูกบังคับให้ inactive (การจับคู่ compare จะถูกละเว้น)

    • Timer.IC --- กำหนดค่าตัวจับเวลาในโหมด Input Capture

    • Timer.ENC_A --- กำหนดค่าตัวจับเวลาในโหมด Encoder ตัวนับจะเปลี่ยนแปลงเฉพาะเมื่อ CH1 เปลี่ยน

    • Timer.ENC_B --- กำหนดค่าตัวจับเวลาในโหมด Encoder ตัวนับจะเปลี่ยนแปลงเฉพาะเมื่อ CH2 เปลี่ยน

    • Timer.ENC_AB --- กำหนดค่าตัวจับเวลาในโหมด Encoder ตัวนับจะเปลี่ยนแปลงเมื่อ CH1 หรือ CH2 เปลี่ยน

  • callback - ตามที่ระบุใน TimerChannel.callback()

  • pin None (ค่าเริ่มต้น) หรือออบเจ็กต์ Pin หากระบุ (และไม่ใช่ None) จะทำให้ฟังก์ชันสำรองของพินที่ระบุถูกกำหนดค่าสำหรับช่องสัญญาณตัวจับเวลานี้ จะเกิดข้อผิดพลาดหากพินไม่รองรับฟังก์ชันสำรองใดๆ สำหรับช่องสัญญาณตัวจับเวลานี้

อาร์กิวเมนต์แบบคีย์เวิร์ดสำหรับโหมด Timer.PWM:

  • pulse_width - กำหนดค่าความกว้างพัลส์เริ่มต้นที่จะใช้

  • pulse_width_percent - กำหนดเปอร์เซ็นต์ความกว้างพัลส์เริ่มต้นที่จะใช้

อาร์กิวเมนต์แบบคีย์เวิร์ดสำหรับโหมด Timer.OC:

  • compare - กำหนดค่าเริ่มต้นของรีจิสเตอร์ compare

  • polarity สามารถเป็นหนึ่งใน:

    • Timer.HIGH - output เป็น active high

    • Timer.LOW - output เป็น active low

อาร์กิวเมนต์แบบคีย์เวิร์ดที่เป็นทางเลือกสำหรับโหมด Timer.IC:

  • polarity สามารถเป็นหนึ่งใน:

    • Timer.RISING - จับภาพที่ rising edge

    • Timer.FALLING - จับภาพที่ falling edge

    • Timer.BOTH - จับภาพที่ทั้งสอง edge

โปรดทราบว่า capture ใช้งานได้เฉพาะกับช่องสัญญาณหลักเท่านั้น ไม่ใช่ช่องสัญญาณเสริม

หมายเหตุสำหรับโหมด Timer.ENC:

  • ต้องใช้ 2 พิน ดังนั้นพินหนึ่งหรือทั้งสองพินจะต้องกำหนดค่าให้ใช้ timer AF ที่เหมาะสมโดยใช้ Pin API

  • อ่านค่า encoder ด้วยเมธอด timer.counter()

  • ใช้งานได้เฉพาะกับ CH1 และ CH2 (ไม่ใช่ CH1N หรือ CH2N)

  • หมายเลขช่องสัญญาณจะถูกละเว้นเมื่อตั้งค่าโหมด encoder

ตัวอย่าง PWM -- บน OpenMV Cam STM32 ทุกรุ่น ช่องสัญญาณ 1 และ 2 ของ TIM4 จะถูกเชื่อมต่อกับพิน header P7 และ P8 ตามลำดับ:

timer = pyb.Timer(4, freq=1000)
ch1 = timer.channel(1, pyb.Timer.PWM, pin=pyb.Pin.board.P7,
                    pulse_width=8000)
ch2 = timer.channel(2, pyb.Timer.PWM, pin=pyb.Pin.board.P8,
                    pulse_width=16000)
counter(value: int | None = None) int | None

รับหรือตั้งค่าตัวนับของตัวจับเวลา

freq(value: int | float | None = None) int | float | None

รับหรือตั้งค่าความถี่ของตัวจับเวลา (จะเปลี่ยน prescaler และ period หากตั้งค่า)

period(value: int | None = None) int | None

รับหรือตั้งค่าคาบของตัวจับเวลา

prescaler(value: int | None = None) int | None

รับหรือตั้งค่า prescaler ของตัวจับเวลา

source_freq() int

รับความถี่ของแหล่งสัญญาณของตัวจับเวลา

ค่าคงที่

ค่าคงที่โหมดตัวนับ (อาร์กิวเมนต์ mode ของ init()):

UP: int

นับจาก 0 ขึ้นไปถึง ARR (โหมดเริ่มต้น)

DOWN: int

นับจาก ARR ลงมาถึง 0

CENTER: int

นับจาก 0 ขึ้นไปถึง ARR แล้วกลับลงมาถึง 0

ค่าคงที่โหมด break (อาร์กิวเมนต์ brk ของ init()):

BRK_OFF: int

break input ถูกปิดใช้งาน

BRK_LOW: int

break input เป็น active-low

BRK_HIGH: int

break input เป็น active-high

ค่าคงที่โหมดช่องสัญญาณ (อาร์กิวเมนต์ mode ของ channel()):

PWM: int

กำหนดค่าช่องสัญญาณสำหรับ PWM output (active high)

PWM_INVERTED: int

กำหนดค่าช่องสัญญาณสำหรับ PWM output (active low)

OC_TIMING: int

โหมด output-compare timing ไม่มีพินที่ถูกขับเคลื่อน

OC_ACTIVE: int

โหมด output-compare active พินจะถูกทำให้ active เมื่อมีการจับคู่ compare

OC_INACTIVE: int

โหมด output-compare inactive พินจะถูกทำให้ inactive เมื่อมีการจับคู่ compare

OC_TOGGLE: int

โหมด output-compare toggle พินจะสลับสถานะเมื่อมีการจับคู่ compare

OC_FORCED_ACTIVE: int

โหมด output-compare forced-active พินถูกบังคับให้ active และการจับคู่ compare จะถูกละเว้น

OC_FORCED_INACTIVE: int

โหมด output-compare forced-inactive พินถูกบังคับให้ inactive และการจับคู่ compare จะถูกละเว้น

IC: int

กำหนดค่าช่องสัญญาณสำหรับโหมด input-capture

ENC_A: int

โหมด Encoder ตัวนับจะเปลี่ยนแปลงเฉพาะเมื่อ CH1 เปลี่ยน

ENC_B: int

โหมด Encoder ตัวนับจะเปลี่ยนแปลงเฉพาะเมื่อ CH2 เปลี่ยน

ENC_AB: int

โหมด Encoder ตัวนับจะเปลี่ยนแปลงเมื่อ CH1 หรือ CH2 เปลี่ยน

ขั้วของ output-compare (อาร์กิวเมนต์ polarity ของ channel() ในโหมด OC):

HIGH: int

Output เป็น active-high

LOW: int

Output เป็น active-low

ขั้วของ input-capture (อาร์กิวเมนต์ polarity ของ channel() ในโหมด IC):

RISING: int

จับภาพที่ rising edge

FALLING: int

จับภาพที่ falling edge

BOTH: int

จับภาพที่ edge ใดก็ได้