HD44780 नियंत्रक और जापानी चरित्र जनरेटर के साथ प्रदर्शन पर रूसी पाठ

HD44780 कंट्रोलर पर डिस्प्ले को नियंत्रित करने के लिए एक गैर-मानक तरीका है जो किसी भी डिस्प्ले कोड टेबल के साथ रूसी फोंट को रेंडर करने के लिए है।


इस तरह के नियंत्रण का बहुत विचार HD44780 नियंत्रक के आधार पर एक कस्टम डिस्प्ले के साथ डिवाइस के रसिफिकेशन के कार्य से पैदा हुआ था। समान लैटिन वर्णों के साथ रूसी पात्रों को बदलने के विकल्प पर विचार करने के बाद, मैंने फैसला किया कि मैं इसके साथ खिलवाड़ नहीं करूंगा, क्योंकि यह अप्रमाणिक दिखता है, और उपकरण वाणिज्यिक है।

Winstar WS0010 ड्राइवर पर आधारित OLED डिस्प्ले के विपरीत, HD44780 ड्राइवरों पर प्रदर्शित होता है या उनके समकक्षों में ग्राफिकल ऑपरेटिंग मोड नहीं होता है। लेकिन उनके पास तथाकथित सीजीआरएएम मेमोरी है, जिसमें आप एक ग्राफिकल प्रतिनिधित्व में 8 अक्षर तक लिख सकते हैं।

एल्गोरिथ्म अपने आप में काफी सरल है:
  1. हम प्रोसेसर लोड के लिए स्वीकार्य बाधा आवृत्ति पर रेंडरिंग टाइमर शुरू करते हैं।
  2. टाइमर में रुकावट:
    • मिटा (रिक्त स्थान के साथ भरें) वह सब कुछ जो प्रदर्शन पर था;
    • नियंत्रक की CGRAM मेमोरी के पहले 8 परिचितों में आवश्यक ग्राफिक जानकारी लोड करें;
    • हम इन वर्णों को किसी दिए गए ऑफ़सेट में डिस्प्ले पर प्रदर्शित करते हैं और रुकावट से बाहर निकलते हैं।



कोड कुछ इस तरह दिखता है:
// Cham map 0x80 - 0xFF, with filler uint8_t cmap[] = { 0x04, 0x0a, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x00, // russian A 0x1f, 0x10, 0x10, 0x1e, 0x11, 0x11, 0x1e, 0x00, // russian Be 0x1e, 0x11, 0x11, 0x1e, 0x11, 0x11, 0x1e, 0x0, // russian Ve 0x1f, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x00, // russian Ge 0x0e, 0x0a, 0x0a, 0x0a, 0x0a, 0x1f, 0x11, 0x00, // russian De 0x1f, 0x10, 0x10, 0x1e, 0x10, 0x10, 0x1f, 0x00, // russian E 0x15, 0x15, 0x15, 0x0e, 0x15, 0x15, 0x15, 0x00, // russian Zhe 0x0e, 0x11, 0x01, 0x06, 0x01, 0x11, 0x0e, 0x00, // russian Ze 0x11, 0x11, 0x11, 0x13, 0x15, 0x19, 0x11, 0x00, // russian I 0x0e, 0x00, 0x11, 0x13, 0x15, 0x19, 0x11, 0x00, // russian Ij 0x11, 0x12, 0x14, 0x18, 0x14, 0x12, 0x11, 0x00, // russian Ka 0x07, 0x09, 0x09, 0x09, 0x09, 0x09, 0x11, 0x00, // russian L 0x11, 0x11, 0x1b, 0x15, 0x15, 0x11, 0x11, 0x00, // russian M 0x11, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x11, 0x00, // russian N 0x0e, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e, 0x00, // russian O 0x1f, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x00, // russian Pe 0x1e, 0x11, 0x11, 0x11, 0x1e, 0x10, 0x10, 0x00, // russian Re 0x0e, 0x11, 0x10, 0x10, 0x10, 0x11, 0x0e, 0x00, // russian Se 0x1f, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x00, // russian Te 0x11, 0x11, 0x11, 0x0f, 0x01, 0x11, 0x0e, 0x00, // russian U 0x0e, 0x15, 0x15, 0x15, 0x0e, 0x04, 0x04, 0x00, // russian Fe 0x11, 0x0a, 0x04, 0x04, 0x0a, 0x0a, 0x11, 0x00, // russian He 0x12, 0x12, 0x12, 0x12, 0x12, 0x1f, 0x01, 0x00, // russian Ce 0x11, 0x11, 0x11, 0x0f, 0x01, 0x01, 0x01, 0x00, // russian Che 0x11, 0x15, 0x15, 0x15, 0x15, 0x15, 0x1f, 0x00, // russian She 0x11, 0x15, 0x15, 0x15, 0x15, 0x1f, 0x01, 0x00, // russian Sche 0x18, 0x08, 0x08, 0x0e, 0x09, 0x09, 0x0e, 0x00, // russian Tverduy znak 0x11, 0x11, 0x19, 0x15, 0x15, 0x15, 0x19, 0x00, // russian bI 0x10, 0x10, 0x1e, 0x11, 0x11, 0x11, 0x1e, 0x00, // russian Myagkiy znak 0x1e, 0x01, 0x01, 0x0f, 0x01, 0x01, 0x1e, 0x00, // russian Ee 0x17, 0x15, 0x15, 0x1d, 0x15, 0x15, 0x17, 0x00, // russian You 0x0f, 0x11, 0x11, 0x0f, 0x05, 0x09, 0x11, 0x00, // russian Ya // 0x00, 0x00, 0x0e, 0x01, 0x0f, 0x11, 0x0f, 0x00, // russian small A 0x01, 0x0e, 0x10, 0x1e, 0x11, 0x11, 0x0e, 0x00, 0x00, 0x00, 0x1e, 0x11, 0x1e, 0x11, 0x1e, 0x00, 0x00, 0x00, 0x1e, 0x10, 0x10, 0x10, 0x10, 0x00, 0x00, 0x00, 0x0e, 0x0a, 0x0a, 0x1f, 0x11, 0x00, 0x00, 0x00, 0x0e, 0x11, 0x1e, 0x10, 0x0e, 0x00, 0x00, 0x00, 0x15, 0x15, 0x0e, 0x15, 0x15, 0x00, 0x00, 0x00, 0x1e, 0x01, 0x0e, 0x01, 0x1e, 0x00, 0x00, 0x00, 0x11, 0x13, 0x15, 0x19, 0x11, 0x00, 0x0e, 0x00, 0x11, 0x13, 0x15, 0x19, 0x11, 0x00, 0x00, 0x00, 0x09, 0x0a, 0x0c, 0x0a, 0x09, 0x00, 0x00, 0x00, 0x07, 0x09, 0x09, 0x09, 0x11, 0x00, 0x00, 0x00, 0x11, 0x1b, 0x15, 0x11, 0x11, 0x00, 0x00, 0x00, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x00, 0x00, 0x00, 0x0e, 0x11, 0x11, 0x11, 0x0e, 0x00, 0x00, 0x00, 0x1f, 0x11, 0x11, 0x11, 0x11, 0x00, // russian small Pe // 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler // 0x00, 0x00, 0x1e, 0x11, 0x11, 0x1e, 0x10, 0x00, // russian small Re 0x00, 0x00, 0x0e, 0x11, 0x10, 0x11, 0x0e, 0x00, 0x00, 0x00, 0x1f, 0x04, 0x04, 0x04, 0x04, 0x00, 0x00, 0x00, 0x11, 0x11, 0x0f, 0x01, 0x0e, 0x00, 0x00, 0x00, 0x1f, 0x15, 0x15, 0x1f, 0x04, 0x00, 0x00, 0x00, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x00, 0x00, 0x00, 0x12, 0x12, 0x12, 0x1f, 0x01, 0x00, 0x00, 0x00, 0x11, 0x11, 0x0f, 0x01, 0x01, 0x00, 0x00, 0x00, 0x15, 0x15, 0x15, 0x15, 0x1f, 0x00, 0x00, 0x00, 0x15, 0x15, 0x15, 0x1f, 0x01, 0x00, 0x00, 0x00, 0x18, 0x0e, 0x09, 0x09, 0x0e, 0x00, 0x00, 0x00, 0x11, 0x11, 0x1d, 0x15, 0x1d, 0x00, 0x00, 0x00, 0x10, 0x1e, 0x11, 0x11, 0x1e, 0x00, 0x00, 0x00, 0x1e, 0x01, 0x0f, 0x01, 0x1e, 0x00, 0x00, 0x00, 0x17, 0x15, 0x1d, 0x15, 0x17, 0x00, 0x00, 0x00, 0x0d, 0x13, 0x0f, 0x05, 0x09, 0x00, // russian small Ya 0x0a, 0x00, 0x1f, 0x10, 0x1e, 0x10, 0x1f, 0x00, // russian Yo 0x0a, 0x00, 0x0e, 0x11, 0x1e, 0x10, 0x0f, 0x00, // russian small Yo // 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00, // filler 0x00, 0x04, 0x0a, 0x15, 0x0a, 0x04, 0x00, 0x00 // filler }; static uint8_t lcd_draw_part = 0; static uint8_t lcd_ch; static uint8_t lcd_draw_string[16] = { 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87 }; void TIM4_IRQHandler() { if (TIM_GetITStatus(TIM4, TIM_IT_Update) != RESET) { TIM_ClearITPendingBit(TIM4, TIM_IT_Update); //     , part = 0 - 0..7, part = 1 - 8..15 LCD_gotoxy(0, (lcd_draw_part ? 0 : 8)); LCD_write_data(0x20); LCD_write_data(0x20); LCD_write_data(0x20); LCD_write_data(0x20); LCD_write_data(0x20); LCD_write_data(0x20); LCD_write_data(0x20); LCD_write_data(0x20); //   CGRAM  8  for(uint8_t i = 0; i < 8; i++) { lcd_ch = lcd_draw_string[i + (lcd_draw_part ? 8 : 0)]; if(lcd_ch > 127) LCD_load_symbol(i, cmap + 8 * (lcd_ch & 0x7f) ); } //  LCD_gotoxy(0, (lcd_draw_part ? 8 : 0)); for(uint8_t i = 0; i < 8; i++) { lcd_ch = lcd_draw_string[i + (lcd_draw_part ? 8 : 0)]; if(lcd_ch < 128) LCD_write_data(lcd_ch); else LCD_write_data(i); } lcd_draw_part ^= 0x01; } } void LCD_start_fps() { RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE); TIM_TimeBaseInitTypeDef timerInitStructure; timerInitStructure.TIM_Prescaler = 48-1; timerInitStructure.TIM_CounterMode = TIM_CounterMode_Up; timerInitStructure.TIM_Period = 20000; // 20ms/isr timerInitStructure.TIM_ClockDivision = TIM_CKD_DIV1; timerInitStructure.TIM_RepetitionCounter = 0; TIM_TimeBaseInit(TIM4, &timerInitStructure); TIM_Cmd(TIM4, ENABLE); TIM_ITConfig(TIM4, TIM_IT_Update, ENABLE); NVIC_InitTypeDef nvicStructure; nvicStructure.NVIC_IRQChannel = TIM4_IRQn; nvicStructure.NVIC_IRQChannelPreemptionPriority = 0; nvicStructure.NVIC_IRQChannelSubPriority = 2; nvicStructure.NVIC_IRQChannelCmd = ENABLE; NVIC_Init(&nvicStructure); } 



इस मामले में, डिस्प्ले कंट्रोल को ठीक से कॉन्फ़िगर करना और न्यूनतम एक्सचेंज टाइमिंग के साथ-साथ, यदि संभव हो तो, डिस्प्ले के लिए 8-बिट इंटरफ़ेस (हालांकि परीक्षणों के अनुसार, 4-बिट नियंत्रक को बहुत अधिक लोड नहीं करता है) का उपयोग करना बहुत महत्वपूर्ण है। इसकी प्रतिक्रिया के लिए प्रतीक्षा समय को कम करने के लिए प्रदर्शन से डी 7 लाइन पर बसवाई सिग्नल पढ़ने का उपयोग करना भी आवश्यक है।

वास्तविक प्रदर्शन पर यह कैसा दिखता है, यह नीचे दिए गए वीडियो में देखा जा सकता है:



शीर्ष पंक्ति को त्वरित रीड्रा विधि द्वारा नियंत्रित किया जाता है और यह CGRAM से जानकारी प्रदर्शित करता है। लाइन में कोड 0x80-0xFF के साथ CP866 कोड तालिका से चित्रमय रूप से तैयार किए गए अक्षर हैं, छद्मोग्राफी को शतरंज के छंदों द्वारा बदल दिया जाता है। नीचे पंक्ति में प्रदर्शन के अंतर्निहित चरित्र जनरेटर और उनके कोड के बगल में प्रतीक हैं।

विधि के नुकसान:
25 हर्ट्ज से कम ताज़ा दर पर, फ़्लिकरिंग स्क्रीन पर ध्यान देने योग्य होता है जब एक कोण पर देखा जाता है, और जब सीधे देखते हैं, तो यह लंबवत रूप से दिखाई नहीं देता है।
इसके अलावा, डिस्प्ले से तस्वीर का कंट्रास्ट थोड़ा कम हो जाता है, लेकिन यह लगभग ध्यान देने योग्य है।

Source: https://habr.com/ru/post/hi403831/


All Articles