scoopydoo 发表于 2025-1-20 15:42:35

[实验] 树莓派 Pico 点亮 SSD1322 OLED 显示屏

本帖最后由 scoopydoo 于 2025-1-20 15:44 编辑

翻出来一块尘封已久的 OLED 屏,应该是大约十年前买的。

考虑到俺的是德 U1253B 万用表的 OLED 屏八年就点不亮了,俺很好奇这块屏还能不能点亮。

搜了一下之前写的 MicroPython 亮屏代码还在,正好这两天在鼓捣树莓派 Pico,就在面包板上简单搭了一下,还能点亮!:lol

代码发出来供参考吧,估计这么老的型号也没人用了现在,主程序 main.py :
from machine import Pin, SPI
import ssd1322

# Pin EN has been tied to VDD on board
PIN_CS = Pin(7, Pin.OUT)
PIN_RES = Pin(8, Pin.OUT)
PIN_DC = Pin(9, Pin.OUT)
PIN_SCK = Pin(10)
PIN_MOSI = Pin(11)
PIN_MISO = Pin(12)

OLED_WIDTH = 256
OLED_HEIGHT = 64
BRIGHTNESS = 7

# Use SPI1 to drive OLED, the MISO pin is not used here.
spi = SPI(1, baudrate = 8_000_000, sck = PIN_SCK, mosi = PIN_MOSI, miso = PIN_MISO)
disp = ssd1322.SSD1322_SPI(OLED_WIDTH, OLED_HEIGHT, spi, PIN_DC, PIN_CS, PIN_RES)

# Clear screen
disp.fill(0)

# Draw a border
disp.line(0, 0, OLED_WIDTH - 1, 0, BRIGHTNESS)
disp.line(OLED_WIDTH - 1, 0, OLED_WIDTH - 1, OLED_HEIGHT - 1, BRIGHTNESS)
disp.line(OLED_WIDTH - 1, OLED_HEIGHT - 1, 0, OLED_HEIGHT -1, BRIGHTNESS)
disp.line(0, OLED_HEIGHT - 1, 0, 0, BRIGHTNESS)

# Some greetings
disp.text(' RASPBERRY PIPICO ', 48, 16, BRIGHTNESS)
disp.text('SSD1322 OLED DISPLAY', 48, 40, BRIGHTNESS)

disp.show()


OLED 驱动代码应该是当年从网上找的,至于改没改过真的不记得了 ssd1322.py :
import time
import framebuf

class SSD1322:
    def __init__(self, width=256, height=64):
      self.width = width
      self.height = height
      self.buffer = bytearray(self.width * self.height //2)
      self.framebuf = framebuf.FrameBuffer(self.buffer, self.width, self.height, framebuf.GS4_HMSB)

      time.sleep_ms(5)
      self.init_display()

    def init_display(self):
      self.write_cmd(0xFD)# Set Command Lock (MCU protection status)
      self.write_data(0x12)# 0x12 = Unlock Basic Commands; 0x16 = lock

      self.write_cmd(0xA4)# Set Display Mode = OFF

      self.write_cmd(0xB3)# Set Front Clock Divider / Oscillator Frequency
      self.write_data(0x91)# 0x91 = 80FPS; 0xD0 = default / 1100b

      self.write_cmd(0xCA)# Set MUX Ratio
      self.write_data(0x3F)# 0x3F = 63d = 64MUX (1/64 duty cycle)

      self.write_cmd(0xA2)# Set Display Offset
      self.write_data(0x00)# 0x00 = (default)

      self.write_cmd(0xA1)# Set Display Start Line
      self.write_data(0x00)# 0x00 = register 00h

      self.write_cmd(0xA0)# Set Re-map and Dual COM Line mode
      self.write_data(0x14)# 0x14 = Default except Enable Nibble Re-map, Scan from COM to COM0, where N is the Multiplex ratio
      self.write_data(0x11)# 0x11 = Enable Dual COM mode (MUX <= 63)

      self.write_cmd(0xB5)# Set GPIO
      self.write_data(0x00)# 0x00 = {GPIO0, GPIO1 = HiZ (Input Disabled)}

      self.write_cmd(0xAB)# Function Selection
      self.write_data(0x01)# 0x01 = Enable internal VDD regulator (default)

      self.write_cmd(0xB4)# Display Enhancement A
      self.write_data(0xA0)# 0xA0 = Enable external VSL; 0xA2 = internal VSL
      self.write_data(0xB5)# 0xB5 = Normal (default); 0xFD = 11111101b = Enhanced low GS display quality

      self.write_cmd(0xC1)# Set Contrast Current
      self.write_data(0x7F)# 0x7F = (default)

      self.write_cmd(0xC7)# Master Contrast Current Control
      self.write_data(0x0F)# 0x0F = (default)

      self.write_cmd(0xB8)# Select Custom Gray Scale table (GS0 = 0)
      self.write_data(0x00)# GS1
      self.write_data(0x02)# GS2
      self.write_data(0x08)# GS3
      self.write_data(0x0d)# GS4
      self.write_data(0x14)# GS5
      self.write_data(0x1a)# GS6
      self.write_data(0x20)# GS7
      self.write_data(0x28)# GS8
      self.write_data(0x30)# GS9
      self.write_data(0x38)# GS10
      self.write_data(0x40)# GS11
      self.write_data(0x48)# GS12
      self.write_data(0x50)# GS13
      self.write_data(0x60)# GS14
      self.write_data(0x70)# GS15
      self.write_data(0x00)# Enable Custom Gray Scale table

      self.write_cmd(0xB1)# Set Phase Length
      self.write_data(0xE2)# 0xE2 = Phase 1 period (reset phase length) = 5 DCLKs,
                               # Phase 2 period (first pre-charge phase length) = 14 DCLKs
      self.write_cmd(0xD1)# Display Enhancement B
      self.write_data(0xA2)# 0xA2 = Normal (default); 0x82 = reserved
      self.write_data(0x20)# 0x20 = as-is

      self.write_cmd(0xBB)# Set Pre-charge voltage
      self.write_data(0x1F)# 0x17 = default; 0x1F = 0.60*Vcc (spec example)

      self.write_cmd(0xB6)# Set Second Precharge Period
      self.write_data(0x08)# 0x08 = 8 dclks (default)

      self.write_cmd(0xBE)# Set VCOMH
      self.write_data(0x07)# 0x04 = 0.80*Vcc (default); 0x07 = 0.86*Vcc (spec example)

      self.write_cmd(0xA6)# Set Display Mode = Normal Display
      self.write_cmd(0xA9)# Exit Partial Display
      self.write_cmd(0xAF)# Set Sleep mode OFF (Display ON)
      
      self.fill(0)
      self.write_data(self.buffer)

    def poweroff(self):
      self.write_cmd(0xAB)
      self.write_data(0x00) # Disable internal VDD regulator, to save power
      self.write_cmd(0xAE)

    def poweron(self):
      self.write_cmd(0xAB)
      self.write_data(0x01) # Enable internal VDD regulator
      self.write_cmd(0xAF)

    def contrast(self, contrast):
      self.write_cmd(0x81)
      self.write_data(0x81) # 0-255

    def rotate(self, rotate):
      self.write_cmd(0xA0)
      self.write_data(0x06 if rotate else 0x14)
      self.write_data(0x11)

    def invert(self, invert):
      self.write_cmd(0xA4 | (invert & 1) << 1 | (invert & 1)) # 0xA4=Normal, 0xA7=Inverted

    def show(self):
      offset=(480-self.width)//2
      col_start=offset//4
      col_end=col_start+self.width//4-1
      self.write_cmd(0x15)
      self.write_data(col_start)
      self.write_data(col_end)
      self.write_cmd(0x75)
      self.write_data(0)
      self.write_data(self.height-1)
      self.write_cmd(0x5c)
      self.write_data(self.buffer)

    def fill(self, col):
      self.framebuf.fill(col)

    def pixel(self, x, y, col):
      self.framebuf.pixel(x, y, col)

    def pp(self,x,y,col):
      self.buffer=0xff if col else 0

    def line(self, x1, y1, x2, y2, col):
      self.framebuf.line(x1, y1, x2, y2, col)

    def scroll(self, dx, dy):
      self.framebuf.scroll(dx, dy)
      # software scroll

    def text(self, string, x, y, col=15):
      self.framebuf.text(string, x, y, col)

    def write_cmd(self):
      raise NotImplementedError

    def write_data(self):
      raise NotImplementedError

class SSD1322_SPI(SSD1322):
    def __init__(self, width, height, spi, dc,cs,res):
      self.spi = spi
      self.dc=dc
      self.cs=cs
      self.res=res

      self.res(1)
      time.sleep_ms(1)
      self.res(0)
      time.sleep_ms(10)
      self.res(1)

      super().__init__(width, height)
      time.sleep_ms(5)

    def write_cmd( self, aCommand ) :
      self.dc(0)
      self.cs(0)
      self.spi.write(bytearray())
      self.cs(1)

    def write_data( self, aData ) :
      self.dc(1)
      self.cs(0)
      if type(aData)==bytes or type(aData)==bytearray:
            self.spi.write(aData)
      else:
            self.spi.write(bytearray())
      self.cs(1)

luosifu 发表于 2025-1-20 17:37:11

型号不算老,1602,12864这种分辨率的点阵LCD,我现在还在用呢:lol

zhengrob 发表于 2025-1-20 17:53:51

25664 OLED屏,别说十年前就是现在也不便宜啊。

songlouliu 发表于 2025-1-20 18:17:41

20年前,我一直用汇编,认为汇编可以深入每个寄存器,一切尽在掌握之中。后来用c以后,不用汇编了。汇编太费力气了。是不是micropython比C好用呢?请介绍一下。

scoopydoo 发表于 2025-1-20 18:31:15

songlouliu 发表于 2025-1-20 18:17
20年前,我一直用汇编,认为汇编可以深入每个寄存器,一切尽在掌握之中。后来用c以后,不用汇编了。汇编太 ...

俺觉得 MicroPython 相比于用 C/C++ 做单片机开发最大的优势就是简单。

Python 语言本身入门简单、MicroPython 开发环境配置起来也简单、网上相关的资源也非常丰富,这些对爱好者尤其是初学者是非常重要的。

washu 发表于 2025-1-20 18:41:16

25664 :o 大湿你好骚喲 (^U^)ノ~YO

scoopydoo 发表于 2025-1-20 18:43:48

washu 发表于 2025-1-20 18:41
25664大湿你好骚喲 (^U^)ノ~YO

一般般骚吧,这块是 3.12 吋的,俺还有一块更大的好像是 5.5 吋的不知道丢到哪里找不到了 ... :L

scoopydoo 发表于 2025-1-20 18:46:18

luosifu 发表于 2025-1-20 17:37
型号不算老,1602,12864这种分辨率的点阵LCD,我现在还在用呢

俺也有一些 1602 和单色点阵液晶屏,有时间都找出来一个个点亮 :lol

scoopydoo 发表于 2025-1-20 18:47:40

zhengrob 发表于 2025-1-20 17:53
25664 OLED屏,别说十年前就是现在也不便宜啊。

当年的价格记不清了,现在的价格几十块到一百块的都有,算上通胀的话应该是降价了吧。

scoopydoo 发表于 2025-1-20 20:57:48

鲁迅先生曾经说过:OLED 屏,就像海绵里的水,只要愿意挤,总还是有的。

经过俺不懈的努力,终于在一个出其不意的地方,找到了这块 5.5 吋的 OLED 屏,芯片同样是 SSD1322,直接原位替换就亮了! :lol

lxa000 发表于 2025-1-20 22:17:38

初学micropython,
感觉比汇编还难啊。
页: [1]
查看完整版本: [实验] 树莓派 Pico 点亮 SSD1322 OLED 显示屏