Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Refactor pixel-mapping code for four-scan screens #742

Draft
wants to merge 1 commit into
base: master
Choose a base branch
from
Draft
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
85 changes: 40 additions & 45 deletions src/ESP32-VirtualMatrixPanel-I2S-DMA.h
Original file line number Diff line number Diff line change
Expand Up @@ -374,52 +374,47 @@ inline VirtualCoords VirtualMatrixPanel::getCoords(int16_t virt_x, int16_t virt_
/* START: Pixel remapping AGAIN to convert TWO parallel scanline output that the
* the underlying hardware library is designed for (because
* there's only 2 x RGB pins... and convert this to 1/4 or something
*/

if ((panel_scan_rate == FOUR_SCAN_32PX_HIGH) || (panel_scan_rate == FOUR_SCAN_64PX_HIGH))
{

if (panel_scan_rate == FOUR_SCAN_64PX_HIGH)
{
// https://github.com/mrfaptastic/ESP32-HUB75-MatrixPanel-DMA/issues/345#issuecomment-1510401192
if ((virt_y & 8) != ((virt_y & 16) >> 1)) { virt_y = (virt_y & 0b11000) ^ 0b11000 + (virt_y & 0b11100111); }
}


/* Convert Real World 'VirtualMatrixPanel' co-ordinates (i.e. Real World pixel you're looking at
on the panel or chain of panels, per the chaining configuration) to a 1/8 panels
double 'stretched' and 'squished' coordinates which is what needs to be sent from the
DMA buffer.

Note: Look at the FourScanPanel example code and you'll see that the DMA buffer is setup
as if the panel is 2 * W and 0.5 * H !
*/

if ((coords.y & 8) == 0)
{
coords.x += ((coords.x / panelResX) + 1) * panelResX; // 1st, 3rd 'block' of 8 rows of pixels, offset by panel width in DMA buffer
}
else
{
coords.x += (coords.x / panelResX) * panelResX; // 2nd, 4th 'block' of 8 rows of pixels, offset by panel width in DMA buffer
}
*/

switch (panel_scan_rate) {
case FOUR_SCAN_64PX_HIGH:
// https://github.com/mrfaptastic/ESP32-HUB75-MatrixPanel-DMA/issues/345#issuecomment-1510401192
if ((virt_y & 8) != ((virt_y & 16) >> 1))
virt_y = (virt_y & 0b11000) ^ 0b11000 + (virt_y & 0b11100111);
// no break, rest of code is the same for 64 and 32px high screens
case FOUR_SCAN_32PX_HIGH:
/* Convert Real World 'VirtualMatrixPanel' co-ordinates (i.e. Real World pixel you're looking at
on the panel or chain of panels, per the chaining configuration) to a 1/8 panels
double 'stretched' and 'squished' coordinates which is what needs to be sent from the
DMA buffer.

Note: Look at the FourScanPanel example code and you'll see that the DMA buffer is setup
as if the panel is 2 * W and 0.5 * H !
*/

if ((coords.y & 8) == 0)
// 1st, 3rd 'block' of 8 rows of pixels, offset by panel width in DMA buffer
coords.x += ((coords.x / panelResX) + 1) * panelResX;
else
// 2nd, 4th 'block' of 8 rows of pixels, offset by panel width in DMA buffer
coords.x += (coords.x / panelResX) * panelResX;

// http://cpp.sh/4ak5u
// Real number of DMA y rows is half reality
// coords.y = (y / 16)*8 + (y & 0b00000111);
coords.y = (virt_y >> 4) * 8 + (virt_y & 0b00000111);
}
else if (panel_scan_rate == FOUR_SCAN_16PX_HIGH)
{
if ((coords.y & 4) == 0)
{
coords.x += ((coords.x / panelResX) + 1) * panelResX; // 1st, 3rd 'block' of 8 rows of pixels, offset by panel width in DMA buffer
}
else
{
coords.x += (coords.x / panelResX) * panelResX; // 2nd, 4th 'block' of 8 rows of pixels, offset by panel width in DMA buffer
}
coords.y = (coords.y >> 3) * 4 + (coords.y & 0b00000011);
// http://cpp.sh/4ak5u
// Real number of DMA y rows is half reality
// coords.y = (y / 16)*8 + (y & 0b00000111);
coords.y = (virt_y >> 4) * 8 + (virt_y & 0b00000111);
break;
case FOUR_SCAN_16PX_HIGH:
if ((coords.y & 4) == 0)
// 1st, 3rd 'block' of 8 rows of pixels, offset by panel width in DMA buffer
coords.x += ((coords.x / panelResX) + 1) * panelResX;
else
// 2nd, 4th 'block' of 8 rows of pixels, offset by panel width in DMA buffer
coords.x += (coords.x / panelResX) * panelResX;
coords.y = (coords.y >> 3) * 4 + (coords.y & 0b00000011);
break;
default:
break;
}

return coords;
Expand Down