Управление дисплеем с помощью SPI.

tw911
Offline
Зарегистрирован: 22.10.2013

Добрый день! Есть дисплей LPH8731-3C, для него был написан вот такой код, в котором было использованы куски из других работ, в том числе с этого форума.

//Определяем пины для подключения дисплея
#define LCD_CS 10
#define LCD_RESET 3
#define LCD_RS 4
#define LCD_CLK 13
#define LCD_DATA 11
#define CMD 	0
#define DAT 	1
byte color;
//Определяем значения  вкл/выкл пинов
#define LCD_CLK_ON       digitalWrite(LCD_CLK,HIGH); 
#define LCD_CLK_OFF      digitalWrite(LCD_CLK,LOW);
#define LCD_RS_ON       digitalWrite(LCD_RS,HIGH); 
#define LCD_RS_OFF      digitalWrite(LCD_RS,LOW);
#define LCD_CS_OFF      digitalWrite(LCD_CS,LOW);
#define LCD_CS_ON       digitalWrite(LCD_CS,HIGH);
#define LCD_RESET_ON    digitalWrite(LCD_RESET,HIGH);
#define LCD_RESET_OFF   digitalWrite(LCD_RESET,LOW);

void setup() {
  pinMode (LCD_CS, OUTPUT);
  pinMode (LCD_RESET, OUTPUT);
  pinMode (LCD_RS, OUTPUT);
  pinMode (LCD_CLK, OUTPUT);
  pinMode (LCD_DATA, OUTPUT);
  LCD_init ();
}

void loop() {
 for (int i = 0; i < 101; i++) { 
  for (int j = 0; j < 80; j++) {   
   Send_to_lcd(CMD,0x2a);
   Send_to_lcd(DAT, i);
   Send_to_lcd(DAT, 100);
   Send_to_lcd(CMD, 0x2b);
   Send_to_lcd(DAT, j+1);
   Send_to_lcd(DAT, 80);
   Send_to_lcd(CMD,0x2c);
   Send_to_lcd(DAT, 0x00);   
  }
 }
   
for (int i = 0; i < 101; i++) {  
 for (int j = 0; j < 80; j++) {
    //command
  Send_to_lcd(CMD, 0x2a);
   //data
  Send_to_lcd(DAT, i);
  Send_to_lcd(DAT, 10);
  
  Send_to_lcd(CMD, 0x2b);
  //data
  Send_to_lcd(DAT,j+1);
  Send_to_lcd(DAT, 50);
  
  Send_to_lcd(CMD, 0x2c);
  //data
  Send_to_lcd(DAT, 0x16);

 }}
}
void reset () //Функция сброса дисплея, ПОРТИРОВАНА
{
 LCD_CS_OFF;
 digitalWrite(LCD_DATA,LOW);
 LCD_RESET_OFF;
 delay(100);
 LCD_RESET_ON;
 delay(500); 
 LCD_CS_ON;
 delay(5);
 LCD_CS_OFF;
}
 void Send_to_lcd (unsigned char RS, unsigned char data)//портирована
{
 if (RS==HIGH){
  LCD_RS_ON;
  LCD_CS_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, data);
  LCD_CS_ON;
 }
 else
 {
  LCD_RS_OFF;
  LCD_CS_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, data);
  LCD_CS_ON;
 }
}
void LCD_init ()//портирована
{
 reset ();
 Send_to_lcd(CMD,0x01); //reset sw
 delay(50);
 Send_to_lcd(CMD,0xc6); //initial escape
 delay(50);
 Send_to_lcd(CMD,0xb9); //Refresh set
 Send_to_lcd(DAT,0x00);
 Send_to_lcd(CMD,0xb6); //Display control
 Send_to_lcd(DAT,0x80); //
 Send_to_lcd(DAT,0x04); //
 Send_to_lcd(DAT,0x8a); //
 Send_to_lcd(DAT,0x54); //
 Send_to_lcd(DAT,0x45); //
 Send_to_lcd(DAT,0x52); //
 Send_to_lcd(DAT,0x43); //
 Send_to_lcd(CMD,0xb3); //Gray scale position set 0
 Send_to_lcd(DAT,0x02); //
 Send_to_lcd(DAT,0x0a); //
 Send_to_lcd(DAT,0x15); //
 Send_to_lcd(DAT,0x1f); //
 Send_to_lcd(DAT,0x28); //
 Send_to_lcd(DAT,0x30); //
 Send_to_lcd(DAT,0x37); //
 Send_to_lcd(DAT,0x3f); //
 Send_to_lcd(DAT,0x47); //
 Send_to_lcd(DAT,0x4c); //
 Send_to_lcd(DAT,0x54); //
 Send_to_lcd(DAT,0x65); //
 Send_to_lcd(DAT,0x75); //
 Send_to_lcd(DAT,0x80); //
 Send_to_lcd(DAT,0x85); //
 Send_to_lcd(CMD,0xb5); //Gamma curve
 Send_to_lcd(DAT,0x01); //
 Send_to_lcd(CMD,0xb7); //Temperature gradient
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(CMD,0xbd); //Common driver output select
 Send_to_lcd(DAT,0x00); //
 /* 
 Send_to_lcd(CMD,0x33); //Vertical scrolling definition - Границы вертикальной прокрутки
 Send_to_lcd(DAT,0x00); //Число линий, используемых в качестве верхней фиксированной области дисплея (max - 0x53)
 Send_to_lcd(DAT,0x53); //Определяем область прокрутки
 Send_to_lcd(DAT,0x00); //Число линий, используемых в качестве нижней фиксированной области дисплея
 Send_to_lcd(CMD,0x37); //Vertical scrolling start adress
 Send_to_lcd(DAT,0x00);            
*/
 Send_to_lcd(CMD,0x36); //Memory access control - Метод доступа к дисплейной памяти (установка нулевого адреса страницы и столбца, направление записи в память дисплея) 
 Send_to_lcd(DAT,0x48); //6-й бит, установленный в "1" делает адресацию столбца - слева-направо, а 3-й бит в "1" - порядок RGB (а в даташите - ошибка!!!) 
 Send_to_lcd(CMD,0x2d); //Colour set
 
 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x03); //
 Send_to_lcd(DAT,0x05); //
 Send_to_lcd(DAT,0x07); //
 Send_to_lcd(DAT,0x09); //
 Send_to_lcd(DAT,0x0b); //
 Send_to_lcd(DAT,0x0d); //
 Send_to_lcd(DAT,0x0f); //

 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x03); //
 Send_to_lcd(DAT,0x05); //
 Send_to_lcd(DAT,0x07); //
 Send_to_lcd(DAT,0x09); //
 Send_to_lcd(DAT,0x0b); //
 Send_to_lcd(DAT,0x0d); //
 Send_to_lcd(DAT,0x0f); //

 Send_to_lcd(DAT,0x00); //
 Send_to_lcd(DAT,0x05); //
 Send_to_lcd(DAT,0x0b); //
 Send_to_lcd(DAT,0x0f); //
 
 Send_to_lcd(CMD,0xba); //Voltage control
//Send_to_lcd(DAT,0x2f); //
 Send_to_lcd(DAT,0x6d);//из сектча
 Send_to_lcd(DAT,0x03);//из скетча
 Send_to_lcd(CMD,0x25); //Установка контраста
 Send_to_lcd(DAT,0x29); //от этого значения зависит контрастность изображения. 
 Send_to_lcd(CMD,0xbe); //Power control
 Send_to_lcd(DAT,0x58); //

 Send_to_lcd(CMD,0x3a); //Информация о выводе пикселя
 //#ifdef _8_BIT_COLOR 
 Send_to_lcd(DAT,0x02); //8-ми битный цвет
 //#else
// Send_to_lcd(DAT,0x03); //12-ти битный цвет 
// #endif
 Send_to_lcd(CMD,0x03); //Booster voltage ON
 delay(40);
 Send_to_lcd(CMD,0x11); //Выход из спящего режима

 delay(20); 		//Перед включением ждем 20 миллисекунд 
 Send_to_lcd(CMD,0x29); //Включение дисплея           
}

Беда в том, что все это работает безумно медленно, обновление экрана за 9 секунд это не айс. Хотелось бы для этих целей использовать SPI, на сколько я понимаю дисплей именно по такому протоколу и работает, но как использовать библиотеку я пока не пойму. Пробовал, но не получилось. Может кто то поможет написать пример, на основе даннного скетча?

Прежде всего мне не понятно как работать с CS, обязательно ли называть пин как в примерах? И какой режим работы интерфеса мне нужен?

axill
Offline
Зарегистрирован: 05.09.2011

А разве shiftout это не из библиотеки SPI?

В вашем коде место вызова этой функции это самое важное место для производительности

tw911
Offline
Зарегистрирован: 22.10.2013

Нет, SPI аппаратный интерфейс. И скорость там должна быть на порядок выше.

axill
Offline
Зарегистрирован: 05.09.2011

tw911 пишет:

Нет, SPI аппаратный интерфейс. И скорость там должна быть на порядок выше.

в терминах стоит быть аккуратным. SPI это стандарт синхронного последовательного обмена данными. Реализация может быть хоть железной хоть програмной. И та и другая будет называться SPI. Нужно очень постараться в кривонаписании программной реализации, чтобы разница была на порядок. По крайней мере на avr эта разница не такая драматичная. Я не использую ардуиновских библиотек для SPI, поэтому и спрашиваю откуда в скетче функция shiftout? В начале скетча нет ни одной директивы #include, чтобы это понять. Может быть скетч не полный

Хотя не важно, вместо shiftout надо поставить методы из стандартно для ардуино SPI библиотеки, не забыв прочитать к ней описание. Настройки Spi следуют из скетча - младший бит вперед. Со скоростью можно поиграть. Начать с предлелителя на 4 и довести до 1. Минимальный делитель при котором булет работать дисплей и обеспечит наибольшую скорость

 

axill
Offline
Зарегистрирован: 05.09.2011

Ошибся, MSB это старшим битом вперед, вам нужны буду эти методы для настройки:

Цитата:
Is data shifted in Most Significant Bit (MSB) or Least Significant Bit (LSB) first? This is controlled by the SPI.setBitOrder() function.

Is the data clock idle when high or low? Are samples on the rising or falling edge of clock pulses? These modes are controlled by the SPI.setDataMode() function.
What speed is the SPI running at? This is controlled by the SPI.setClockDivider() function.
MaksMS
Offline
Зарегистрирован: 11.03.2013

Вроде shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, data); надо заменить на SPI.transfer( data);  

Не забыть перед этим проиницилизировать: SPI.begin();  

Выводы LCD_DATA и LCD_CLK заменяются на аппаратные выводы SPI..

tw911
Offline
Зарегистрирован: 22.10.2013

Взял кусочек кода, который отправляли тут на форуме, и чуть переписал с ипользованием SPI как тут писали товарищи, не работает именно кусок с SPI, что бы небыло вопросов о работе вообще.

//Определяем пины для подключения дисплея
#define LCD_CS 10
#define LCD_RESET 3
#define LCD_RS 4
#define LCD_CLK 13
#define LCD_DATA 11
#include <SPI.h>
//Определяем значения  вкл/выкл пинов
#define LCD_CLK_ON       digitalWrite(LCD_CLK,HIGH); 
#define LCD_CLK_OFF      digitalWrite(LCD_CLK,LOW);
#define LCD_RS_ON       digitalWrite(LCD_RS,HIGH); 
#define LCD_RS_OFF      digitalWrite(LCD_RS,LOW);
#define LCD_CS_OFF      digitalWrite(LCD_CS,LOW);
#define LCD_CS_ON       digitalWrite(LCD_CS,HIGH);
#define LCD_RESET_ON    digitalWrite(LCD_RESET,HIGH);
#define LCD_RESET_OFF   digitalWrite(LCD_RESET,LOW);

int i,j; //переменная для цикла

//Пины выходные
void setup ()
{
  pinMode (LCD_CS, OUTPUT);
  pinMode (LCD_RESET, OUTPUT);
  pinMode (LCD_RS, OUTPUT);
  pinMode (LCD_CLK, OUTPUT);
  pinMode (LCD_DATA, OUTPUT);
  digitalWrite(LCD_DATA,LOW);
  LCD_RESET_OFF;
  delay(100);
  LCD_RESET_ON;
  delay(250);
  delay(250);
  LCD_CS_ON;
  delay(5);
  LCD_CS_OFF;


  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x01);  //софтовый сброс дисплея
  delay(50);

  
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0xc6); //
  delay(50);
  
  
  
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0xb9);
 
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0xb6);
 
  
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x80);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x04);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x8a);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x54);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x45);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x52);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x43);
  
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0xb3); //УРОВЕНЬ СЕРОГО
 
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x02);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x0a);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x15);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x1f);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x28);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x30);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x37);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x3f);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x47);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x4c);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x54);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x65);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x75);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x80);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x85);
  
  
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0xb5); // КРИВАЯ ГАММЫ
 
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x01);
  
 //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0xb7);
  
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);

  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0xbd);
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x36);
 
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x48);
  
  
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x2d);
 
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x03);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x05);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x07);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x09);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x0b);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x0d);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x0f);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x03);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x05);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x07);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x09);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x0b);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x0b);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x0f);
  
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x05);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x0b);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x0f);

//command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0xba);
  
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x6d);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x03);
  
  
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x25); //УСТАНОВИТЬ КОНТРАСТ
 
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x29);
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
 shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0xbe);
  
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x58);
  
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x3a);
 
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x02);
  
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x03);
  delay(40);
   
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x11);
   delay(20);
  
  //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x29);
  //КОНЕЦ ИНИЦИАЛИЗАЦИИ
}

void loop ()
{


   for (i = 0; i < 101; i++) {  //закрасить дисплей в черный цвет
      for (j = 0; j < 80; j++) {
         
    //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x2a);
   //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, i);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 100);
  
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x2b);
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, j+1);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 80);
  
   LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x2c);
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x00);
 
      
      }
   }
   
   
    for (i = 0; i < 101; i++) {  //закрасить дисплей в черный цвет
      for (j = 0; j < 80; j++) {
         
    //command
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x2a);
   //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, i);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 100);
  
  LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x2b);
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, j+1);
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 80);
  
   LCD_CS_ON;
  LCD_RS_OFF;
  LCD_CS_OFF;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x2c);
  //data
  LCD_RS_ON;
  LCD_CLK_OFF;
  shiftOut(LCD_DATA, LCD_CLK, MSBFIRST, 0x03);
 
      
      }
   }
  SPI.begin();
  SPI.setClockDivider(SPI_CLOCK_DIV32);
  SPI.setBitOrder(MSBFIRST);
  SPI.setDataMode(SPI_MODE1);
    for (i = 0; i < 101; i++) {  //закрасить дисплей в черный цвет
      for (j = 0; j < 80; j++) {
         
    //command
    LCD_RS_OFF;
    LCD_CS_OFF;
    LCD_CLK_OFF;
    SPI.transfer(0x2a);
    LCD_CS_ON;
   //data
    LCD_RS_ON;
    LCD_CLK_OFF;
    SPI.transfer(i);
    LCD_CS_ON;
    LCD_CS_OFF;
    SPI.transfer(100);
    LCD_CS_ON;
  
    LCD_RS_OFF;
    LCD_CS_OFF;
    LCD_CLK_OFF;
    SPI.transfer(0x2b);
    LCD_CS_ON;
  //data
    LCD_RS_ON;
    LCD_CS_OFF;
    LCD_CLK_OFF;
    SPI.transfer( j+1);
    LCD_CS_ON;
    LCD_CS_OFF;
    SPI.transfer( 80);
    LCD_CS_ON;
    LCD_RS_OFF;
    LCD_CS_OFF;
    LCD_CLK_OFF;
    SPI.transfer(0x2c);
    LCD_CS_ON;
    //data
    LCD_RS_ON;
    LCD_CLK_OFF;
    LCD_CS_OFF;
    SPI.transfer(0x1a);
    LCD_CS_ON;
        }
     }
     delay(1000);
     SPI.end();
  }

В моем примере мне надо CS дергать вниз, на сколько я понимаю CS и SS из описния библиотеки SPI это одно и то же. В какое он состояние переходит при инициализации интерфеса?

Вот реализация begin

void SPIClass::begin() {

  // Set SS to high so a connected chip will be "deselected" by default
  digitalWrite(SS, HIGH);

  // When the SS pin is set as OUTPUT, it can be used as
  // a general purpose output port (it doesn't influence
  // SPI operations).
  pinMode(SS, OUTPUT);

  // Warning: if the SS pin ever becomes a LOW INPUT then SPI
  // automatically switches to Slave, so the data direction of
  // the SS pin MUST be kept as OUTPUT.
  SPCR |= _BV(MSTR);
  SPCR |= _BV(SPE);

  // Set direction register for SCK and MOSI pin.
  // MISO pin automatically overrides to INPUT.
  // By doing this AFTER enabling SPI, we avoid accidentally
  // clocking in a single bit since the lines go directly
  // from "input" to SPI control.  
  // http://code.google.com/p/arduino/issues/detail?id=888
  pinMode(SCK, OUTPUT);
  pinMode(MOSI, OUTPUT);
}

Тут видно, что ss переводится в high.

Получается что по этому ничего не работает?

Вот реализация transfer

byte SPIClass::transfer(byte _data) {
  SPDR = _data;
  while (!(SPSR & _BV(SPIF)))
    ;
  return SPDR;
}

У меня Duemilanova, если что вдруг. Есть какие то мысли?

axill
Offline
Зарегистрирован: 05.09.2011

вы вопросы здесь для чего задаете? вам MaksMS совершенно конкретный совет дал. Вы его проигнорировали, начитались разрозненной ерунды. Пользуетесь ардуино - читайте первоисточники http://arduino.cc/en/Reference/SPI

tw911
Offline
Зарегистрирован: 22.10.2013

Я конечно понимаю, что код длинный, вы бы хоть в конец посмтрели. Я же написал свои конкретные вопросы и именно первоисточник я и цитирую. И все равно меня не покидает мысли что вы мой пости ли не прочитали ил не поняли. Еще раз повторяю - я сделал именно как советовали - не заработало, именно та часть, которая должна испльзовать SPI. То, что код, который я привел последним отличается от того что я приводил в первом посте - всего лишь значит, что я использую этот кусок как более удобный в отладке. И он так же хорошо работает, но не через SPI.

axill
Offline
Зарегистрирован: 05.09.2011

tw911 пишет:

Я конечно понимаю, что код длинный, вы бы хоть в конец посмтрели. Я же написал свои конкретные вопросы и именно первоисточник я и цытирую. И все равно меня не покидает мысли что вы мой пости ли не прочитали ил не поняли.

я прочитал ваши посты, но извините, не вижу в них ни одного осознанного вопроса, идет повествование

вы привели пример реализации SPI transfer прямым обращением к регистрам МК. Зачем? Вы попробовали просто взять и использовать стандартную библиотеку SPI? Этот совет в этой ветке звучит уже 4-й раз. Я не знаю в каких форумах вы нахватали слухов и кусков кода, поэтому что-то на ваше повествование ответить сложно. Про пин SS написано по моей ссылке выше. обычно его не используют, оставляют не подключенным, потому что его подключение не позволяет подключать к шине SPI больше одного устройства. С одним устройством можно использовать именно его

tw911
Offline
Зарегистрирован: 22.10.2013

Вы бы в эту библиотеку заглянули, и унали бы что там написано...эх зажили бы...Я ведь вам и привел реализацию из библотеки то...для наглядности.

А спрашиваю я уже третий раз, при вызове последовательнсоти begin transfer end как меняется cs? он же ss.

MaksMS
Offline
Зарегистрирован: 11.03.2013

Ничто не мешает после begin установить нужный уровень CS по умолчанию,а потом его уже дергать в нужную сторону..

axill
Offline
Зарегистрирован: 05.09.2011

tw911 пишет:

Вы бы в эту библиотеку заглянули, и унали бы что там написано...эх зажили бы...Я ведь вам и привел реализацию из библотеки то...для наглядности.

А спрашиваю я уже третий раз, при вызове последовательнсоти begin transfer end как меняется cs? он же ss.

зачем мне заглядывать в библиотеку которой я не пользуюсь? Но вы могли бы ее взять и просто использовать вместо того, чтобы разбираться с чужими кусками кода. Если же хотите разобраться с сутью происходящего, то читайте раздел SPI (19-й параграф), если у вас МК мега 328p то тут http://www.atmel.com/Images/Atmel-8271-8-bit-AVR-Microcontroller-ATmega48A-48PA-88A-88PA-168A-168PA-328-328P_datasheet.pdf

Там все подробно расписано и про то что происходит и про SS в частности.

В частности. CS - chip select или что в данном контексте тоже самое SS - slave select используется для активации того устройства на шине SPI с которым в данный момент МК производит сессию связи. Обычно для активации используется логический ноль (надо смотреть что написано в документе на конкретное устройство/чип). Логика простая - в начале любого обмена с устройством выставляем на CS ноль, по завершении обмена ставим там единицу.

axill
Offline
Зарегистрирован: 05.09.2011

посмотрите в свой код - у вас перед каждым shiftOut стоит LCD_CS_OFF - перевод CS в ноль

все что вам нужно - в setup() сделать инициализацию библиотеки SPI, настроить на нужный режим и это нужно сделать до первого вызова shifyOut().  Сами shiftOut() заменить на transfer()

tw911
Offline
Зарегистрирован: 22.10.2013

Почему собственно так было сделано, как у меня сейчас - что бы небыло проблем с инициализацие дисплея. То есть на момент инициализации SPI дисплей готов принимать команды. В чем осбственно проблема инициализировать SPI в теле?

tw911
Offline
Зарегистрирован: 22.10.2013

Нашел я реализацию вот такую. http://playground.arduino.cc/S1D15G10NokiaLCD/S1D15G10NokiaLCD Буду ее пробовать и паралельно в протеусе попробую свой код прогнать через логический анализатор.