Follow along with the video below to see how to install our site as a web app on your home screen.
Note: This feature may not be available in some browsers.
Sub SendByte(ByVal DataByte As Byte)
Dim i As Byte
For i = 0 To 7 ' Loop 8 times for 8 bits
If DataByte.bits(7 - i) = 1 Then ' Send a '1' bit
' Send 1-bit (T1H: ~0.8us HIGH, T1L: ~0.45us LOW)
' T1H: 12 instruction cycles (0.75us)
' T1L: 7 instruction cycles (0.4375us)
WS2812BDataPin = 1
nop ' 62.5ns
nop ' 125ns
nop ' 187.5ns
nop ' 250ns
nop ' 312.5ns
nop ' 375ns
nop ' 437.5ns
nop ' 500ns
nop ' 562.5ns
nop ' 625ns
nop ' 687.5ns
nop ' 750ns (approx T1H)
WS2812BDataPin = 0
nop ' 62.5ns
nop ' 125ns
nop ' 187.5ns
nop ' 250ns
nop ' 312.5ns
nop ' 375ns
nop ' 437.5ns (approx T1L)
Else ' Send a '0' bit
' Send 0-bit (T0H: ~0.4us HIGH, T0L: ~0.85us LOW)
' T0H: 6 instruction cycles (0.375us)
' T0L: 13 instruction cycles (0.8125us)
WS2812BDataPin = 1
nop ' 62.5ns
nop ' 125ns
nop ' 187.5ns
nop ' 250ns
nop ' 312.5ns
nop ' 375ns (approx T0H)
WS2812BDataPin = 0
nop ' 62.5ns
nop ' 125ns
nop ' 187.5ns
nop ' 250ns
nop ' 312.5ns
nop ' 375ns
nop ' 437.5ns
nop ' 500ns
nop ' 562.5ns
nop ' 625ns
nop ' 687.5ns
nop ' 750ns
nop ' 812.5ns (approx T0L)
End If
Next
End Sub
' Subroutine to send a single color (Green, Red, Blue) to the WS2812B.
'-------------------------------------------------------------------------------
' WS2812B Basic Control Example for Swordfish
' Microcontroller: PIC18F252
' Clock: 20MHz
'
' This code controls a WS2812B LED strip using software bit-banging.
' Timing is CRITICAL for WS2812B. The NOPs in SendByte are adjusted
' for a 20MHz clock (5 MIPS, 200ns per instruction cycle).
'
' You may need to fine-tune the NOP counts slightly for optimal performance
' with your specific LEDs and setup.
'-------------------------------------------------------------------------------
Device = 18f25q10
Clock = 64 ' MHz
' --- Configuration for PIC18F252 @ 20MHz ---
' Using INTRC as an option, but external crystal is more accurate for timing.
' Ensure your crystal and oscillator settings match your hardware.
'Config OSC = HSPLL ' High-Speed Crystal/Resonator with PLL (for higher speeds like 40MHz)
' If you are actually using a 20MHz crystal without PLL, use HS
' Config OSC = HS
'Config RSTOSC = HFINTOSC_64MHZ
'Config WDT = Off ' Watchdog Timer Off
'Config MCLRE = On ' Master Clear Enable
'Config PWRT = On ' Power-up Timer Enable
'Config BOR = On ' Brown-out Reset Enable
'Config LVP = Off ' Low-Voltage Programming Off (good practice for programming stability)
'Config CP0 = Off ' Code Protection Off
Include "system.bas" ' for NOP macro
Include "myosc" ' has these setting OSCCON1 = $60 OSCFRQ = 8
' --- Pin Definitions ---
Dim WS2812BDataPin As PORTC.2 ' **CHANGE THIS if you use a different pin**
' (e.g., PortB.0, PortA.5, etc.)
' --- WS2812B Parameters ---
Const NUM_LEDS As Byte = 20 ' **CHANGE THIS to the number of LEDs you have**
' Define the LED color data array (GRB format)
Dim LED_Data(NUM_LEDS * 3) As Byte ' 3 bytes per LED (Green, Red, Blue)
' --- Subroutines ---
' Subroutine to send a single byte (8 bits) to the WS2812B.
' This routine is highly time-sensitive and uses NOPs for precise delays.
' Assumes 20MHz clock (200ns per instruction cycle).
Sub SendByte(ByVal DataByte As Byte)
Dim i As Byte
For i = 0 To 7 ' Loop 8 times for 8 bits
If DataByte.bits(7 - i) = 1 Then ' Send a '1' bit
' Send 1-bit (T1H: ~0.8us HIGH, T1L: ~0.45us LOW)
' T1H: 12 instruction cycles (0.75us)
' T1L: 7 instruction cycles (0.4375us)
WS2812BDataPin = 1
nop ' 62.5ns
nop ' 125ns
nop ' 187.5ns
nop ' 250ns
nop ' 312.5ns
nop ' 375ns
nop ' 437.5ns
nop ' 500ns
nop ' 562.5ns
nop ' 625ns
nop ' 687.5ns
nop ' 750ns (approx T1H)
WS2812BDataPin = 0
nop ' 62.5ns
nop ' 125ns
nop ' 187.5ns
nop ' 250ns
nop ' 312.5ns
nop ' 375ns
nop ' 437.5ns (approx T1L)
Else ' Send a '0' bit
' Send 0-bit (T0H: ~0.4us HIGH, T0L: ~0.85us LOW)
' T0H: 6 instruction cycles (0.375us)
' T0L: 13 instruction cycles (0.8125us)
WS2812BDataPin = 1
nop ' 62.5ns
nop ' 125ns
nop ' 187.5ns
nop ' 250ns
nop ' 312.5ns
nop ' 375ns (approx T0H)
WS2812BDataPin = 0
nop ' 62.5ns
nop ' 125ns
nop ' 187.5ns
nop ' 250ns
nop ' 312.5ns
nop ' 375ns
nop ' 437.5ns
nop ' 500ns
nop ' 562.5ns
nop ' 625ns
nop ' 687.5ns
nop ' 750ns
nop ' 812.5ns (approx T0L)
End If
Next
End Sub
' Subroutine to send a single color (Green, Red, Blue) to the WS2812B.
' WS2812B expects GRB order.
Sub SendColor(ByVal Green As Byte, ByVal Red As Byte, ByVal Blue As Byte)
SendByte(Green)
SendByte(Red)
SendByte(Blue)
End Sub
' Subroutine to send all LED data from the buffer to the strip.
' This causes the LEDs to update their colors.
Sub ShowLEDs()
Dim i As Word
For i = 0 To (NUM_LEDS * 3 - 1) Step 3
SendColor(LED_Data(i), LED_Data(i + 1), LED_Data(i + 2))
Next
' Send the reset pulse (data line low for > 50us)
WS2812BDataPin = 0
DelayUS(60) ' Ensure at least 50us reset pulse (use Delay_us built-in)
End Sub
' Subroutine to set the color of a specific LED in the internal buffer.
' Colors are stored as Green, Red, Blue.
Sub SetLEDColor(ByVal LED_Index As Byte, ByVal Red As Byte, ByVal Green As Byte, ByVal Blue As Byte)
If LED_Index < NUM_LEDS Then
LED_Data(LED_Index * 3) = Green ' Store Green component
LED_Data(LED_Index * 3 + 1) = Red ' Store Red component
LED_Data(LED_Index * 3 + 2) = Blue ' Store Blue component
End If
End Sub
' --- Main Program ---
' temp variables
Dim i As Byte
Dim hue As Byte = 0
' Initialize the data pin as output low
Low(WS2812BDataPin)
' Clear all LEDs initially (set to off)
For i = 0 To NUM_LEDS - 1
SetLEDColor(i, 0, 0, 0) ' All Off
Next
ShowLEDs() ' Send all 'off' data to LEDs
DelayMS(100) ' Small delay for LEDs to update
' --- Set some colors for demonstration ---
SetLEDColor(0, 255, 0, 0) ' First LED Red
'SetLEDColor(1, 0, 255, 0) ' Second LED Green
'SetLEDColor(2, 0, 0, 255) ' Third LED Blue
'SetLEDColor(3, 255, 255, 0) ' Fourth LED Yellow (Red + Green)
'SetLEDColor(4, 0, 255, 255) ' Fifth LED Cyan (Green + Blue)
'SetLEDColor(5, 255, 0, 255) ' Sixth LED Magenta (Red + Blue)
'SetLEDColor(6, 255, 255, 255) ' Seventh LED White (Full Brightness)
'SetLEDColor(7, 10, 10, 10) ' Eighth LED Dim White
ShowLEDs() ' Send the updated data to the LEDs
'OSCCON1 = $60
' OSCFRQ = $08
' --- Simple Animation Loop ---
While (true)
SetLEDColor(0, 255, 255, 255) ' First LED white
' SetLEDColor(1, 0, 255, 0) ' First LED Red
' SetLEDColor(2, 0, 0, 255) ' First LED Red
' SetLEDColor(3, 0, 255, 0) ' First LED Red
' SetLEDColor(4, 0, 0, 255) ' First LED Red
' SetLEDColor(5, 255, 0, 0) ' First LED Red
' SetLEDColor(6, 0, 255, 0) ' First LED Red
' SetLEDColor(7, 0, 0, 255) ' First LED Red
' SetLEDColor(8, 255, 0, 0) ' First LED Red
'SetLEDColor(9, 255, 0, 0) ' First LED Red
' SetLEDColor(10, 255, 0, 0) ' First LED Red
' SetLEDColor(11, 255, 0, 0) ' First LED Red
' SetLEDColor(12, 255, 0, 0) ' First LED Red
' SetLEDColor(13, 255, 0, 0) ' First LED Red
' SetLEDColor(14, 255, 0, 0) ' First LED Red
' SetLEDColor(15, 255, 0, 0) ' First LED Red
' SetLEDColor(16, 255, 0, 0) ' First LED Red
' SetLEDColor(17, 255, 0, 0) ' First LED Red
' SetLEDColor(18, 255, 0, 0) ' First LED Red
' SetLEDColor(19, 255, 0, 0) ' First LED Red
ShowLEDs() ' Send the updated data to the LEDs.8..
End While
'End Program
Then do this-Trying to get the 18f25q10 to run at 64 mhz
Device=18F25Q10
Clock=64
Include "intosc.bas"
MAIN
?I000000_F002_001935_M000002 ; L#MK OSCTUNE = INTOSC_OSCTUNE
MOVLB 14
CLRF OSCTUNE,1
?I000001_F002_001938_M000002 ; L#MK SET_INTOSC(_clock)
?I000002_F002_001938_M000002 ; L#MK SET_INTOSC(_clock)
MOVLW 0X60
MOVWF OSCCON1,1
?I000003_F002_001938_M000002 ; L#MK SET_INTOSC(_clock)
MOVLW 0X08
MOVWF OSCFRQ,1
?I000004_END; L#MK
SBGLB2
SLEEP
BRA SBGLB2
CONFIG FEXTOSC = OFF
CONFIG RSTOSC = HFINTOSC_64MHZ
For an 18FxxQ10 what I posted should get you 64Mhz using the int osc.Jerry it worked for me just not 64 MHz clock
It’s starting up at 16 MHz and it never switched to 64 MHz