1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68
|
inline void VGA_Sequencer_TextMode(VGA_Type *Sequencer_VGA,word Sequencer_Scanline, word Sequencer_x, word Sequencer_tempx, word Sequencer_tempy, byte Sequencer_bytepanning, VGA_AttributeInfo *Sequencer_attributeinfo) //Used to be: VGA_Type *VGA,word Scanline, word x, word tempx, word tempy, byte bytepanning, VGA_AttributeInfo *attributeinfo
{
//Last row info!
static word last_tempy; //Last Y position!
static uint_32 last_chary; //Last character Y position!
static uint_32 last_charheight; //Last character height!
static uint_32 last_charystart; //Last start of a row!
static byte gotlast_y = 0; //Got last to process?
byte y_updated = 0; //Y updated (combine with checking charx)?
//Last column&character info!
static uint_32 last_charx; //Last character X position!
static uint_32 last_charwidth; //Last character width!
static byte last_bytepanning; //Last byte panning!
static byte last_character; //Last character on that position in the VRAM plane!
static byte last_attribute; //Last attribute on that position in the VRAM plane!
static byte gotlast_character = 0; //Got last to process?
static uint_32 Sequencer_textmode_charindex; //Charindex within VRAM plane 0&1!
//First: character info!
byte charheight = getcharacterheight(Sequencer_VGA);
Sequencer_attributeinfo->chary = Sequencer_Scanline; //Y of current character!
Sequencer_attributeinfo->charinner_y = 0; //Set the character inner Y we need!
if (!gotlast_character || !gotlast_y || !(gotlast_y && last_charheight==charheight && last_tempy==Sequencer_tempy)) //Different character row?
{
uint_32 last_charysaved = last_chary; //For checking if we're a different character line!
last_chary = Sequencer_tempy; //Last temp Y saving for next need!
last_charheight = charheight; //Last charheight!
last_charystart = getVRAMScanlineStart(Sequencer_VGA,Sequencer_attributeinfo->chary); //Calculate row start!
y_updated = (last_charysaved!=last_chary); //Row changed?
gotlast_y = 1; //We've got the last Y and have been updated!
} //This works!
//tempx is always different, we can safely assume!
byte charwidth = getcharacterwidth(Sequencer_VGA); //Character width!
byte charx = Sequencer_attributeinfo->charx = OPTDIV(Sequencer_tempx,charwidth); //X of current character!
byte charinnerx = Sequencer_attributeinfo->charinner_x = OPTMOD(Sequencer_tempx,charwidth); //Current pixel within the ScanLine!
if (y_updated || !(gotlast_character && last_charwidth==charwidth && last_charx==charx && last_bytepanning==Sequencer_bytepanning)) //Not the same character or Y updated?
{
y_updated = 0; //Return to the default: Y isn't updated anymore!
Sequencer_textmode_charindex = last_charystart; //Get the start of the row!
Sequencer_attributeinfo->charx = last_charx = charx; //Last charx!
Sequencer_textmode_charindex += charx; //Add the character column for the base character index!
last_bytepanning = Sequencer_bytepanning; //Last bytepanning!
Sequencer_textmode_charindex += Sequencer_bytepanning; //Apply byte panning to the index!
last_charwidth = charwidth; //Update last characterwidth!
word vramstart = Sequencer_VGA->precalcs.startaddress; //Start address of VRAM display!
last_character = readVRAMplane(Sequencer_VGA,vramstart,0,Sequencer_textmode_charindex,2); //The character itself! From plane 0!
last_attribute = Sequencer_attributeinfo->attribute = readVRAMplane(Sequencer_VGA,vramstart,1,Sequencer_textmode_charindex,2); //The attribute itself! From plane 1!
gotlast_character = 1; //We've got the last character data!
}
Sequencer_attributeinfo->attribute_graphics = 0; //We're a text-mode attribute, needed for the attribute controller!
byte y2=Sequencer_VGA->LinesToRender; //The ammount to render!
if (!y2) return; //Abort when nothing to render!
for (;;) //Process all lines to render!
{
--y2; //Next pixel!
byte pixel = getcharxy(Sequencer_VGA,last_attribute,last_character,charinnerx,y2); //Check for the character, the simple way!
if (!pixel) //Not already on?
{
pixel = is_cursorscanline(Sequencer_VGA,Sequencer_x,y2,Sequencer_textmode_charindex,Sequencer_attributeinfo); //Get if we're to plot font, include cursor? (Else back) Used to be: VGA,attributeinfo->charinner_y,charindex
}
Sequencer_VGA->CurrentScanLine[y2][Sequencer_x] = pixel; //Set the pixel to use!
if (!y2) return; //Stop searching when done!
}
}
| |