FabGL
ESP32 Display Controller and Graphics Library
vgadirectcontroller.cpp
1 /*
2  Created by Fabrizio Di Vittorio (fdivitto2013@gmail.com) - <http://www.fabgl.com>
3  Copyright (c) 2019-2020 Fabrizio Di Vittorio.
4  All rights reserved.
5 
6  This file is part of FabGL Library.
7 
8  FabGL is free software: you can redistribute it and/or modify
9  it under the terms of the GNU General Public License as published by
10  the Free Software Foundation, either version 3 of the License, or
11  (at your option) any later version.
12 
13  FabGL is distributed in the hope that it will be useful,
14  but WITHOUT ANY WARRANTY; without even the implied warranty of
15  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  GNU General Public License for more details.
17 
18  You should have received a copy of the GNU General Public License
19  along with FabGL. If not, see <http://www.gnu.org/licenses/>.
20  */
21 
22 
23 
24 #include <alloca.h>
25 #include <stdarg.h>
26 #include <math.h>
27 #include <string.h>
28 
29 #include "freertos/FreeRTOS.h"
30 #include "freertos/task.h"
31 
32 #include "soc/i2s_struct.h"
33 #include "soc/i2s_reg.h"
34 #include "driver/periph_ctrl.h"
35 #include "rom/lldesc.h"
36 #include "soc/rtc.h"
37 #include "esp_spi_flash.h"
38 #include "esp_heap_caps.h"
39 
40 #include "fabutils.h"
41 #include "vgadirectcontroller.h"
42 #include "devdrivers/swgenerator.h"
43 
44 
45 
46 
47 
48 
49 namespace fabgl {
50 
51 
52 
53 
54 
55 /*************************************************************************************/
56 /* VGADirectController definitions */
57 
58 
59 VGADirectController * VGADirectController::s_instance = nullptr;
60 volatile int VGADirectController::s_scanLine;
61 lldesc_t volatile * VGADirectController::s_frameResetDesc;
62 
63 
64 
65 VGADirectController::VGADirectController()
66  : m_drawScanlineCallback(nullptr)
67 {
68  s_instance = this;
69 }
70 
71 
72 void VGADirectController::init()
73 {
74  VGABaseController::init();
75  m_doubleBufferOverDMA = false;
76 }
77 
78 
79 void VGADirectController::allocateViewPort()
80 {
81  for (int i = 0; i < VGAD_LinesCount; ++i)
82  m_lines[i] = (uint8_t*) heap_caps_malloc(m_viewPortWidth, MALLOC_CAP_DMA);
83 }
84 
85 
86 void VGADirectController::freeViewPort()
87 {
88  VGABaseController::freeViewPort();
89 
90  for (int i = 0; i < VGAD_LinesCount; ++i) {
91  heap_caps_free((void*)m_lines[i]);
92  m_lines[i] = nullptr;
93  }
94 }
95 
96 
97 void VGADirectController::setResolution(VGATimings const& timings, int viewPortWidth, int viewPortHeight, bool doubleBuffered)
98 {
99  // fail if setDrawScanlineCallback() has not been called
100  if (!m_drawScanlineCallback)
101  return;
102 
103  VGABaseController::setResolution(timings, viewPortWidth, viewPortHeight, doubleBuffered);
104 
105  // must be started before interrupt alloc
106  startGPIOStream();
107 
108  // ESP_INTR_FLAG_LEVEL1: should be less than PS2Controller interrupt level, necessary when running on the same core
109  if (m_isr_handle == nullptr) {
110  CoreUsage::setBusiestCore(FABGLIB_VIDEO_CPUINTENSIVE_TASKS_CORE);
111  esp_intr_alloc_pinnedToCore(ETS_I2S1_INTR_SOURCE, ESP_INTR_FLAG_LEVEL1 | ESP_INTR_FLAG_IRAM, ISRHandler, this, &m_isr_handle, FABGLIB_VIDEO_CPUINTENSIVE_TASKS_CORE);
112  I2S1.int_clr.val = 0xFFFFFFFF;
113  I2S1.int_ena.out_eof = 1;
114  }
115 }
116 
117 
118 void VGADirectController::onSetupDMABuffer(lldesc_t volatile * buffer, bool isStartOfVertFrontPorch, int scan, bool isVisible, int visibleRow)
119 {
120  if (isVisible) {
121  buffer->buf = (uint8_t *) m_lines[visibleRow % VGAD_LinesCount];
122 
123  // generate interrupt every half VGAD_LinesCount
124  if ((scan == 0 && (visibleRow % (VGAD_LinesCount / 2)) == 0)) {
125  if (visibleRow == 0)
126  s_frameResetDesc = buffer;
127  buffer->eof = 1;
128  }
129  }
130 }
131 
132 
133 void VGADirectController::setPixelAt(PixelDesc const & pixelDesc, Rect & updateRect)
134 {
135 }
136 
137 
138 void VGADirectController::absDrawLine(int X1, int Y1, int X2, int Y2, RGB888 color)
139 {
140 }
141 
142 
143 void VGADirectController::rawFillRow(int y, int x1, int x2, RGB888 color)
144 {
145 }
146 
147 
148 void VGADirectController::rawFillRow(int y, int x1, int x2, uint8_t colorIndex)
149 {
150 }
151 
152 
153 void VGADirectController::rawInvertRow(int y, int x1, int x2)
154 {
155 }
156 
157 
158 void VGADirectController::rawCopyRow(int x1, int x2, int srcY, int dstY)
159 {
160 }
161 
162 
163 void VGADirectController::swapRows(int yA, int yB, int x1, int x2)
164 {
165 }
166 
167 
168 void VGADirectController::drawEllipse(Size const & size, Rect & updateRect)
169 {
170 }
171 
172 
173 void VGADirectController::clear(Rect & updateRect)
174 {
175 }
176 
177 
178 void VGADirectController::VScroll(int scroll, Rect & updateRect)
179 {
180 }
181 
182 
183 void VGADirectController::HScroll(int scroll, Rect & updateRect)
184 {
185 }
186 
187 
188 void VGADirectController::drawGlyph(Glyph const & glyph, GlyphOptions glyphOptions, RGB888 penColor, RGB888 brushColor, Rect & updateRect)
189 {
190 }
191 
192 
193 void VGADirectController::invertRect(Rect const & rect, Rect & updateRect)
194 {
195 }
196 
197 
198 void VGADirectController::swapFGBG(Rect const & rect, Rect & updateRect)
199 {
200 }
201 
202 
203 void VGADirectController::copyRect(Rect const & source, Rect & updateRect)
204 {
205 }
206 
207 
208 void VGADirectController::readScreen(Rect const & rect, RGB888 * destBuf)
209 {
210 }
211 
212 
213 void VGADirectController::rawDrawBitmap_Native(int destX, int destY, Bitmap const * bitmap, int X1, int Y1, int XCount, int YCount)
214 {
215 }
216 
217 
218 void VGADirectController::rawDrawBitmap_Mask(int destX, int destY, Bitmap const * bitmap, void * saveBackground, int X1, int Y1, int XCount, int YCount)
219 {
220 }
221 
222 
223 void VGADirectController::rawDrawBitmap_RGBA2222(int destX, int destY, Bitmap const * bitmap, void * saveBackground, int X1, int Y1, int XCount, int YCount)
224 {
225 }
226 
227 
228 void VGADirectController::rawDrawBitmap_RGBA8888(int destX, int destY, Bitmap const * bitmap, void * saveBackground, int X1, int Y1, int XCount, int YCount)
229 {
230 }
231 
232 
233 void IRAM_ATTR VGADirectController::ISRHandler(void * arg)
234 {
235  auto ctrl = (VGADirectController *) arg;
236 
237  if (I2S1.int_st.out_eof) {
238 
239  auto desc = (volatile lldesc_t*) I2S1.out_eof_des_addr;
240 
241  if (desc == s_frameResetDesc)
242  s_scanLine = 0;
243 
244  int scanLine = (s_scanLine + VGAD_LinesCount / 2) % ctrl->m_viewPortHeight;
245 
246  auto lineIndex = scanLine % VGAD_LinesCount;
247 
248  for (int i = 0; i < VGAD_LinesCount / 2; ++i) {
249 
250  ctrl->m_drawScanlineCallback(ctrl->m_drawScanlineArg, (uint8_t*)(ctrl->m_lines[lineIndex]), scanLine);
251 
252  ++lineIndex;
253  ++scanLine;
254  }
255 
256  s_scanLine += VGAD_LinesCount / 2;
257 
258  }
259 
260  I2S1.int_clr.val = I2S1.int_st.val;
261 }
262 
263 
264 
265 } // end of namespace
266 
int16_t X2
Definition: fabutils.h:150
int16_t Y2
Definition: fabutils.h:151
int16_t Y1
Definition: fabutils.h:149
This file contains fabgl::GPIOStream definition.
int16_t X1
Definition: fabutils.h:148
This file contains some utility classes and functions.
Definition: canvas.cpp:31
This file contains fabgl::VGADirectController definition.