Вот чб экран по SPI работает, а цветной нет. Хотя выводы одни и те же (скетчи правда разные). Логика не ясна, берём чб экран - меняем уно,есп, пи пико - всё работает на одном скетче. Берём цветной и всё - пи пико не работает.
Дык может скетч показать и косяк найти?
И да, тестовый пример с цветным дисплеем работает?
Нет, тестовый не работает, как и все другие. Просто подсветка работает и всё.
поможем, у меня на пико все дисплеи на обоих SPI работают, выкладывай код
// для RP2040 SPI0
TFT_CS 5 // GP5 - CS
TFT_RST 6 // GP6 - RESET
TFT_DC 7 // GP7 - A0
TFT_MISO 4 // GP4 - MISO (MISO, RX)
TFT_MOSI 3 // GP3 - SDA (MOSI, TX)
TFT_SCLK 2 // GP2 - SCK
Вот этот набор брал. В чб он работает.
#include <Adafruit_GFX.h> // Core graphics library
#include <Adafruit_ST7735.h> // Hardware-specific library
#include <SPI.h>
// For the breakout, you can use any 2 or 3 pins
// These pins will also work for the 1.8" TFT shield
#define TFT_CS 5
#define TFT_RST 6 // you can also connect this to the Arduino reset
// in which case, set this #define pin to 0!
#define TFT_DC 7
// Option 1 (recommended): must use the hardware SPI pins
// (for UNO thats sclk = 13 and sid = 11) and pin 10 must be
// an output. This is much faster - also required if you want
// to use the microSD card (see the image drawing example)
Adafruit_ST7735 tft = Adafruit_ST7735(TFT_CS, TFT_DC, TFT_RST);
// Option 2: use any pins but a little slower!
#define TFT_SCLK 2 // set these to be whatever pins you like!
#define TFT_MOSI 3 // set these to be whatever pins you like!
//Adafruit_ST7735 tft = Adafruit_ST7735(TFT_CS, TFT_DC, TFT_MOSI, TFT_SCLK, TFT_RST);
float p = 3.1415926;
void setup(void) {
Serial.begin(9600);
Serial.print("Hello! ST7735 TFT Test");
// Use this initializer if you're using a 1.8" TFT
tft.initR(INITR_BLACKTAB); // initialize a ST7735S chip, black tab
// Use this initializer (uncomment) if you're using a 1.44" TFT
//tft.initR(INITR_144GREENTAB); // initialize a ST7735S chip, black tab
Serial.println("Initialized");
uint16_t time = millis();
tft.fillScreen(ST7735_BLACK);
time = millis() - time;
Serial.println(time, DEC);
delay(500);
// large block of text
tft.fillScreen(ST7735_BLACK);
testdrawtext("Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur adipiscing ante sed nibh tincidunt feugiat. Maecenas enim massa, fringilla sed malesuada et, malesuada sit amet turpis. Sed porttitor neque ut ante pretium vitae malesuada nunc bibendum. Nullam aliquet ultrices massa eu hendrerit. Ut sed nisi lorem. In vestibulum purus a tortor imperdiet posuere. ", ST7735_WHITE);
delay(1000);
// tft print function!
tftPrintTest();
delay(4000);
// a single pixel
tft.drawPixel(tft.width()/2, tft.height()/2, ST7735_GREEN);
delay(500);
// line draw test
testlines(ST7735_YELLOW);
delay(500);
// optimized lines
testfastlines(ST7735_RED, ST7735_BLUE);
delay(500);
testdrawrects(ST7735_GREEN);
delay(500);
testfillrects(ST7735_YELLOW, ST7735_MAGENTA);
delay(500);
tft.fillScreen(ST7735_BLACK);
testfillcircles(10, ST7735_BLUE);
testdrawcircles(10, ST7735_WHITE);
delay(500);
testroundrects();
delay(500);
testtriangles();
delay(500);
mediabuttons();
delay(500);
Serial.println("done");
delay(1000);
}
void loop() {
tft.invertDisplay(true);
delay(500);
tft.invertDisplay(false);
delay(500);
}
void testlines(uint16_t color) {
tft.fillScreen(ST7735_BLACK);
for (int16_t x=0; x < tft.width(); x+=6) {
tft.drawLine(0, 0, x, tft.height()-1, color);
}
for (int16_t y=0; y < tft.height(); y+=6) {
tft.drawLine(0, 0, tft.width()-1, y, color);
}
tft.fillScreen(ST7735_BLACK);
for (int16_t x=0; x < tft.width(); x+=6) {
tft.drawLine(tft.width()-1, 0, x, tft.height()-1, color);
}
for (int16_t y=0; y < tft.height(); y+=6) {
tft.drawLine(tft.width()-1, 0, 0, y, color);
}
tft.fillScreen(ST7735_BLACK);
for (int16_t x=0; x < tft.width(); x+=6) {
tft.drawLine(0, tft.height()-1, x, 0, color);
}
for (int16_t y=0; y < tft.height(); y+=6) {
tft.drawLine(0, tft.height()-1, tft.width()-1, y, color);
}
tft.fillScreen(ST7735_BLACK);
for (int16_t x=0; x < tft.width(); x+=6) {
tft.drawLine(tft.width()-1, tft.height()-1, x, 0, color);
}
for (int16_t y=0; y < tft.height(); y+=6) {
tft.drawLine(tft.width()-1, tft.height()-1, 0, y, color);
}
}
void testdrawtext(char *text, uint16_t color) {
tft.setCursor(0, 0);
tft.setTextColor(color);
tft.setTextWrap(true);
tft.print(text);
}
void testfastlines(uint16_t color1, uint16_t color2) {
tft.fillScreen(ST7735_BLACK);
for (int16_t y=0; y < tft.height(); y+=5) {
tft.drawFastHLine(0, y, tft.width(), color1);
}
for (int16_t x=0; x < tft.width(); x+=5) {
tft.drawFastVLine(x, 0, tft.height(), color2);
}
}
void testdrawrects(uint16_t color) {
tft.fillScreen(ST7735_BLACK);
for (int16_t x=0; x < tft.width(); x+=6) {
tft.drawRect(tft.width()/2 -x/2, tft.height()/2 -x/2 , x, x, color);
}
}
void testfillrects(uint16_t color1, uint16_t color2) {
tft.fillScreen(ST7735_BLACK);
for (int16_t x=tft.width()-1; x > 6; x-=6) {
tft.fillRect(tft.width()/2 -x/2, tft.height()/2 -x/2 , x, x, color1);
tft.drawRect(tft.width()/2 -x/2, tft.height()/2 -x/2 , x, x, color2);
}
}
void testfillcircles(uint8_t radius, uint16_t color) {
for (int16_t x=radius; x < tft.width(); x+=radius*2) {
for (int16_t y=radius; y < tft.height(); y+=radius*2) {
tft.fillCircle(x, y, radius, color);
}
}
}
void testdrawcircles(uint8_t radius, uint16_t color) {
for (int16_t x=0; x < tft.width()+radius; x+=radius*2) {
for (int16_t y=0; y < tft.height()+radius; y+=radius*2) {
tft.drawCircle(x, y, radius, color);
}
}
}
void testtriangles() {
tft.fillScreen(ST7735_BLACK);
int color = 0xF800;
int t;
int w = tft.width()/2;
int x = tft.height()-1;
int y = 0;
int z = tft.width();
for(t = 0 ; t <= 15; t++) {
tft.drawTriangle(w, y, y, x, z, x, color);
x-=4;
y+=4;
z-=4;
color+=100;
}
}
void testroundrects() {
tft.fillScreen(ST7735_BLACK);
int color = 100;
int i;
int t;
for(t = 0 ; t <= 4; t+=1) {
int x = 0;
int y = 0;
int w = tft.width()-2;
int h = tft.height()-2;
for(i = 0 ; i <= 16; i+=1) {
tft.drawRoundRect(x, y, w, h, 5, color);
x+=2;
y+=3;
w-=4;
h-=6;
color+=1100;
}
color+=100;
}
}
void tftPrintTest() {
tft.setTextWrap(false);
tft.fillScreen(ST7735_BLACK);
tft.setCursor(0, 30);
tft.setTextColor(ST7735_RED);
tft.setTextSize(1);
tft.println("Hello World!");
tft.setTextColor(ST7735_YELLOW);
tft.setTextSize(2);
tft.println("Hello World!");
tft.setTextColor(ST7735_GREEN);
tft.setTextSize(3);
tft.println("Hello World!");
tft.setTextColor(ST7735_BLUE);
tft.setTextSize(4);
tft.print(1234.567);
delay(1500);
tft.setCursor(0, 0);
tft.fillScreen(ST7735_BLACK);
tft.setTextColor(ST7735_WHITE);
tft.setTextSize(0);
tft.println("Hello World!");
tft.setTextSize(1);
tft.setTextColor(ST7735_GREEN);
tft.print(p, 6);
tft.println(" Want pi?");
tft.println(" ");
tft.print(8675309, HEX); // print 8,675,309 out in HEX!
tft.println(" Print HEX!");
tft.println(" ");
tft.setTextColor(ST7735_WHITE);
tft.println("Sketch has been");
tft.println("running for: ");
tft.setTextColor(ST7735_MAGENTA);
tft.print(millis() / 1000);
tft.setTextColor(ST7735_WHITE);
tft.print(" seconds.");
}
void mediabuttons() {
// play
tft.fillScreen(ST7735_BLACK);
tft.fillRoundRect(25, 10, 78, 60, 8, ST7735_WHITE);
tft.fillTriangle(42, 20, 42, 60, 90, 40, ST7735_RED);
delay(500);
// pause
tft.fillRoundRect(25, 90, 78, 60, 8, ST7735_WHITE);
tft.fillRoundRect(39, 98, 20, 45, 5, ST7735_GREEN);
tft.fillRoundRect(69, 98, 20, 45, 5, ST7735_GREEN);
delay(500);
// play color
tft.fillTriangle(42, 20, 42, 60, 90, 40, ST7735_BLUE);
delay(50);
// pause color
tft.fillRoundRect(39, 98, 20, 45, 5, ST7735_RED);
tft.fillRoundRect(69, 98, 20, 45, 5, ST7735_RED);
// play color
tft.fillTriangle(42, 20, 42, 60, 90, 40, ST7735_GREEN);
} // Universal 8bit Graphics Library (https://github.com/olikraus/u8g2/)
ты опять импровизируешь, вот как прописаны оба SPI в ядре:
#define SPI01 // Дисплей на SPIO1, NRF24L01 на SPI0 (выбор между SPI0 и SPI1)
#if defined(SPI01) // для RP2040 SPI1
#define TFT_CS 13 // GP13 - CS (hard - 13)
#define TFT_RST 10 // GP14 - RESET (10)
#define TFT_DC 11 // GP15 - A0 (11)
#define TFT_MISO 12 // GP12 - MISO (MISO, RX) (hard - 12)
#define TFT_MOSI 15 // GP11 - SDA (MOSI, TX) (hard - 15)
#define TFT_SCLK 14 // GP10 - SCK (hard - 14)
#else // для RP2040 SPI0
#define TFT_CS 17 //5 // GP5 - CS (hard - 17)
#define TFT_RST 20 //6 // GP6 - RESET
#define TFT_DC 21 //7 // GP7 - A0
#define TFT_MISO 16 //4 // GP4 - MISO (MISO, RX) (hard - 16)
#define TFT_MOSI 19 //3 // GP3 - SDA (MOSI, TX) (hard - 19)
#define TFT_SCLK 18 //2 // GP2 - SCK (hard - 18)
#endif
Никак. Отложу пока:) Примусь за Nokia 5110 LCD на уно тоже был забавен. С одной библиотеки заработал.
// LCD5110_Sleep_Mode
// Copyright (C)2015 Rinky-Dink Electronics, Henning Karlsen. All right reserved
// web: http://www.RinkyDinkElectronics.com/
//
// This program is a demo of sleep mode.
//
// This program requires a Nokia 5110 LCD module.
//
// It is assumed that the LCD module is connected to
// the following pins using a levelshifter to get the
// correct voltage to the module.
// SCK - Pin 8 - CLK
// MOSI - Pin 9 - DIN
// D/C - Pin 10 - DC
// RST - Pin 11 - RST
// SCE - Pin 12 - CE
//
#include <LCD5110_Basic.h>
LCD5110 myGLCD(8,9,10,11,12);
extern uint8_t SmallFont[];
extern uint8_t MediumNumbers[];
void setup()
{
myGLCD.InitLCD();
myGLCD.disableSleep();
myGLCD. setContrast(60);//
}
void loop()
{
myGLCD.setFont(SmallFont);
myGLCD.clrScr();
myGLCD.print("Entering", CENTER, 0);
myGLCD.print("Sleep Mode", CENTER, 8);
myGLCD.print("in", CENTER, 16);
myGLCD.print("Seconds", CENTER, 40);
myGLCD.setFont(MediumNumbers);
for (int s=59; s>=0; s--)
{
myGLCD.printNumI(s, CENTER, 24, 2, '0');
delay(1000);
}
// myGLCD.enableSleep();
delay(1000);
}
//////////////////////////////////////////////////////////
//вывод картинок
#include <Arduino.h>
#include <U8g2lib.h>
#include <SPI.h>
#include <Wire.h>
#include "ris.h"
U8G2_ST7565_ERC12864_F_4W_SW_SPI u8g2(U8G2_R0, /* scl=*/ 2, /* si=*/3 , /* cs=*/9 , /* rs=*/7 , /* rse=*/ 6);// для rp2040
U8G2_SSD1306_128X64_NONAME_F_HW_I2C u8g2A(U8G2_R0);// для rp2040 SDA-4,SCL-5
int t=100;// пауза
void setup()
{
u8g2.begin();u8g2A.begin();
u8g2.sendF("c", 0xA7);//инверсия цвета
u8g2A.sendF("c", 0xA6);//инверсия цвета
u8g2.setContrast (20);
u8g2A.setContrast (20);
}
void loop()
{
//u8g2.clearBuffer();
u8g2.drawXBMP( 0, 0, 128, 64,ris_1 ); u8g2.sendBuffer();u8g2A.drawXBMP( 0, 0, 128, 64,ris_9 ); u8g2A.sendBuffer(); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_2 ); u8g2.sendBuffer();u8g2A.drawXBMP( 0, 0, 128, 64,ris_8 ); u8g2A.sendBuffer(); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_3 ); u8g2.sendBuffer(); u8g2A.drawXBMP( 0, 0, 128, 64,ris_7 ); u8g2A.sendBuffer();delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_4 ); u8g2.sendBuffer();u8g2A.drawXBMP( 0, 0, 128, 64,ris_6 ); u8g2A.sendBuffer(); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_5 ); u8g2.sendBuffer();u8g2A.drawXBMP( 0, 0, 128, 64,ris_5 ); u8g2A.sendBuffer(); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_6 ); u8g2.sendBuffer();u8g2A.drawXBMP( 0, 0, 128, 64,ris_4 ); u8g2A.sendBuffer(); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_7 ); u8g2.sendBuffer();u8g2A.drawXBMP( 0, 0, 128, 64,ris_3 ); u8g2A.sendBuffer(); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_8 ); u8g2.sendBuffer();u8g2A.drawXBMP( 0, 0, 128, 64,ris_2 ); u8g2A.sendBuffer(); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_9 ); u8g2.sendBuffer();u8g2A.drawXBMP( 0, 0, 128, 64,ris_1 ); u8g2A.sendBuffer(); delay(t);
}
а ты попробуй его на HW SPI завести, частоту SPI можно и понизить, пока не заведётся, SW SPI это всего навсего 1 мегагерц
На уно заработал в этой библиотеке.
Дурацкий вопрос, как запустить в моём примере сразу 3 разнотипных экрана?
Понял как много и разных вешать Запустил экран и игру свою. Осталось, пишет, всего 2 Мб свободными…, а где ещё 14?
//вывод картинок на два разных дисплея
#include <Arduino.h>
#include <U8g2lib.h>
#include <Adafruit_GFX.h>
#include <Adafruit_ST7735.h>
#include <SPI.h>
#include "ris.h"
#include "ris_.h"
#define TFT_CS 16
#define TFT_DC 21
U8G2_ST7565_ERC12864_F_4W_HW_SPI u8g2(U8G2_R0,/* cs=*/17 , /* rs=*/21 , /* rse=*/ 22);// для rp2040 (отдельно разводят выводы CS и reset)
Adafruit_ST7735 tft = Adafruit_ST7735(/* TFT_CS=*/16, /* TFT_DC=*/21, /* TFT_RST=*/20);//для rp2040
// TFT_SCL 18
// TFT_SDA 19
int t=100;// пауза
void setup()
{
//
u8g2.begin();
u8g2.sendF("c", 0xA7);//инверсия цвета
u8g2.setContrast (20);
//
tft.initR(INITR_BLACKTAB);
tft.setRotation(2);
tft.fillScreen(tft.Color565(0,0,0));
//
}
void loop()
{
//u8g2.clearBuffer();
u8g2.drawXBMP( 0, 0, 128, 64,ris_1 ); u8g2.sendBuffer();drawFoto(0,0,ris_01,128,160); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_2 ); u8g2.sendBuffer();drawFoto(0,0,ris_02,128,160); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_3 ); u8g2.sendBuffer();drawFoto(0,0,ris_03,128,160); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_4 ); u8g2.sendBuffer();drawFoto(0,0,ris_04,128,160); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_5 ); u8g2.sendBuffer();drawFoto(0,0,ris_02,128,160); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_6 ); u8g2.sendBuffer();drawFoto(0,0,ris_03,128,160); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_7 ); u8g2.sendBuffer();drawFoto(0,0,ris_01,128,160); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_8 ); u8g2.sendBuffer();drawFoto(0,0,ris_02,128,160); delay(t);
u8g2.drawXBMP( 0, 0, 128, 64,ris_9 ); u8g2.sendBuffer();drawFoto(0,0,ris_03,128,160); delay(t);
}
/////////////////////////////////////////////////////////////////
void drawFoto(int x,int y, const uint8_t *bitmap,int w,int h) {//функция вывода фотокартинки
if(x<0||x+w>128||y<0||y+h>160){return;}
tft.setAddrWindow(x,y,x+w-1,y+h-1);
SPI.beginTransaction(SPISettings(40000000, MSBFIRST, SPI_MODE0));
digitalWrite(TFT_DC, HIGH);
digitalWrite(TFT_CS, LOW);
for(int j=0; j<h; j++) {
for(int i=0; i<2*w; i=i+2) {
SPI.transfer(bitmap[i+1+j*2*w]);SPI.transfer(bitmap[i+j*2*w]);
// SPI.transfer(pgm_read_byte(bitmap+i+1+j*2*w));SPI.transfer(pgm_read_byte(bitmap+i+j*2*w));
}
}
digitalWrite(TFT_CS, HIGH);
SPI.endTransaction();
///
}
////////////////////////////////////////////////////////////////////
Вот вариант, который ожидаемо заработал (не думал правда, что ресет тоже надо разводить). Это аппаратный SPI 0 , дисплеи параллельны. Ресурс платы, как я понимаю, позволяет вешать гирлянду разномастных экранов и библиотек в различных вариациях соединений. Как прописывать второй SPI ?, чтобы работало с первым на своей группе экранов.
а если учесть что там 2 ядра, а работаете вы пока только с одним, то запас еще есть.
Если пакет поддержки в Ардуино от Эрла Филхофера - там можно прямо в скетче завести два сетапа и два лупа и в каждом прописать свой код
распиновку выкладывал выше, инициализация тут (ниже еще можно SW SPI использовать)
//hard SPI для RP2040
Adafruit_ST7735 tft = Adafruit_ST7735(&SPI1, TFT_CS, TFT_DC, TFT_RST); //via hard SPI1
//Soft SPI для RP2040
Adafruit_ST7735 tft = Adafruit_ST7735(TFT_CS, TFT_DC, TFT_MOSI, TFT_SCLK, TFT_RST); // Via Soft SPI
Если пинов не хватает, то можно ставить в параметрах (-1)
вот тут можно подглядывать
к примеру:
// SPI для RP2040
tft.setSPISpeed(25000000);
Да вроде это ядро переставил. То есть можно на одной половине в лоб ставить игру, а на другой матрицу ws2812 с их персональными вариантами скетчей?..
А где примеры простенькие посмотреть можно?
одну программу в один setup() loop() другую в setup1() и loop1(), какие тебе еще примеры, глобальные переменные можно общими сделать
Не уверен, что это все вот так просто, слыхал что вроде с общими областями памяти надо как-то специально работать. Впрочем, сам я только два блинка на двух ядрах запускал, когда осваивал плату, дальше не продвинулся.
я запускал два дисплея, работает
Ну, к примеру две игры, мои пойдут параллельно? Игроки будут на свои кнопки жать по разному. Это фактически два совершенно независимых исполнения, а библиотека для одинаковых экранов одна :), и как пины делятся? Но в целом если это аппаратно независимые луупы, то здорово. Рывок после УНО.