/******************************Module*Header*******************************\ * Module Name: textxlg.c * * * Copyright (c) 1995-1999 Microsoft Corporation \**************************************************************************/ #if 0 The following code assumes that the gray glyphs comming from the font driver have DWORD aligned scans..... /******************************Public*Routine******************************\ * * Routine Name * * draw_gray_nf_ntb_o_to_temp_start * * Routine Description: * * The input glyphs are 4-bpp gray scale bitmaps that are DWORD aligned. * Specialized glyph dispatch routine for non-fixed pitch, top and * bottom not aligned glyphs that do overlap. This routine calculates * the glyph's position on the temp buffer, then determines the correct * highly specialized routine to be used to draw each glyph based on * the glyph width, alignment and rotation * * Arguments: * * pGlyphPos - Pointer to first in list of GLYPHPOS structs * cGlyph - Number of glyphs to draw * pjDst - Pointer to temp 4Bpp buffer to draw into * ulLeftEdge - left edge of TextRect & 0xfffffff8 * This is equal to the position of the left * edge rounded down to the nearest 32-bit * aligned boundary (8 pixels / DWORD) * dpDst - Scan line Delta for TempBuffer (always pos) * * Return Value: * * None * \**************************************************************************/ VOID draw_gray_nf_ntb_o_to_temp_start( PGLYPHPOS pGlyphPos, ULONG cGlyphs, PUCHAR pjDst, ULONG ulLeftEdge, ULONG dpDst, ULONG ulCharInc, ULONG ulTempTop ) { GLYPHBITS *pgb; // pointer to current GLYPHBITS int x; // pixel offset of the left edge of the glyph bitmap // from the left edge of the output (4-bpp) bitmap int y; // the pixel offset of the top edge of the glyph // bitmap from the top edge of the output bitmap. GLYPHPOS *pgpOut; // sentinel for loop void (*apfnGray[8])(ULONG*,ptrdiff_t,ULONG*,ULONG*,ptrdiff_t); /**/DbgPrint( /**/ "draw_gray_nf_ntb_o_to_temp_start(\n" /**/ " PGLYPHPOS pGlyphPos = %-#x\n" /**/ " ULONG cGlyphs = %u\n" /**/ " PUCHAR pjDst = %-#x\n" /**/ " ULONG ulLeftEdge = %u\n" /**/ " ULONG dpDst = %-#x\n" /**/ " ULONG ulCharInc = %u\n" /**/ " ULONG ulTempTop = %u\n" /**/ " )\n" /**/); /**/DbgBreakPoint(); for (pgpOut = pGlyphPos + cGlyphs; pGlyphPos < pgpOut; pGlyphPos++) { ULONG *pulSrcScan; ptrdiff_t dpulSrcScan; pgb = pGlyphPos->pgdf->pgb; x = pGlyphPos->ptl.x + pgb->ptlOrigin.x - ulLeftEdge; y = pGlyphPos->ptl.y + pgb->ptlOrigin.y - ulTempTop ; pulSrcScan = (ULONG*) &(pgb->aj[0]); dpulSrcScan = (ptrdiff_t) (pgb->sizlBitmap.cx + 7)/8; // // dispatch to the appropriate function // /**/ DbgPrint( /**/ "pgb = %-#x\n" /**/ "x = %d\n" /**/ "y = %d\n" /**/ "pulSrcScan = %-#x\n" /**/ "dpulSrcScan = %u = %-#x\n" /**/ , pgb /**/ , x /**/ , y /**/ , pulSrcScan /**/ , dpulSrcScan /**/ ); /**/ DbgBreakPoint(); (*apfnGray[x & 0x07]) ( pulSrcScan , dpulSrcScan , pulSrcScan + dpulSrcScan * (unsigned) pgb->sizlBitmap.cy , (ULONG*) (pjDst + y * dpDst) + ( x / 8) , (ptrdiff_t) dpDst / sizeof(ULONG) ); } } void vOrShiftGrayGlyph0( ULONG *pulSrcScan , ptrdiff_t dpulSrcScan , ULONG *pulSrcScanOut , ULONG *pulDstScan , ptrdiff_t dpulDstScan ) { for ( ; pulSrcScan < pulSrcScanOut ; pulDstScan += dpulDstScan, pulSrcScan += dpulSrcScan ) { ULONG *pulSrc, *pulDst, *pulSrcOut; for ( pulDst = pulDstScan, pulSrc = pulSrcScan, pulSrcOut = pulSrcScan + dpulSrcScan ; pulSrc < pulSrcOut ; pulDst++, pulSrc++ ) { *pulDst |= *pulSrc; } } } void vOrShiftGrayGlyph2( ULONG *pulSrcScan , ptrdiff_t dpulSrcScan , ULONG *pulSrcScanOut , ULONG *pulDstScan , ptrdiff_t dpulDstScan ) { for ( ; pulSrcScan < pulSrcScanOut ; pulDstScan += dpulDstScan, pulSrcScan += dpulSrcScan ) { ULONG *pulSrc, *pulDst, *pulSrcOut; ULONG b = 0; for ( pulDst = pulDstScan, pulSrc = pulSrcScan, pulSrcOut = pulSrcScan + dpulSrcScan ; pulSrc < pulSrcOut ; pulDst++, pulSrc++ ) { ULONG a = *pulSrc; *pulDst |= (a << 4*2) + (b >> (32-4*2)); b = a; } } } void vOrShiftGrayGlyph4( ULONG *pulSrcScan , ptrdiff_t dpulSrcScan , ULONG *pulSrcScanOut , ULONG *pulDstScan , ptrdiff_t dpulDstScan ) { for ( ; pulSrcScan < pulSrcScanOut ; pulDstScan += dpulDstScan, pulSrcScan += dpulSrcScan ) { ULONG *pulSrc, *pulDst, *pulSrcOut; ULONG b = 0; for ( pulDst = pulDstScan, pulSrc = pulSrcScan, pulSrcOut = pulSrcScan + dpulSrcScan ; pulSrc < pulSrcOut ; pulDst++, pulSrc++ ) { ULONG a = *pulSrc; *pulDst |= (a << 4*4) + (b >> (32-4*4)); b = a; } } } void vOrShiftGrayGlyph6( ULONG *pulSrcScan , ptrdiff_t dpulSrcScan , ULONG *pulSrcScanOut , ULONG *pulDstScan , ptrdiff_t dpulDstScan ) { for ( ; pulSrcScan < pulSrcScanOut ; pulDstScan += dpulDstScan, pulSrcScan += dpulSrcScan ) { ULONG *pulSrc, *pulDst, *pulSrcOut; ULONG b = 0; for ( pulDst = pulDstScan, pulSrc = pulSrcScan, pulSrcOut = pulSrcScan + dpulSrcScan ; pulSrc < pulSrcOut ; pulDst++, pulSrc++ ) { ULONG a = *pulSrc; *pulDst |= (a << 4*6) + (b >> (32-4*6)); b = a; } } } #define MASK_0 0x0f0f0f0f #define MASK_1 0xf0f0f0f0 void vOrShiftGrayGlyph1( ULONG *pulSrcScan , ptrdiff_t dpulSrcScan , ULONG *pulSrcScanOut , ULONG *pulDstScan , ptrdiff_t dpulDstScan ) { for ( ; pulSrcScan < pulSrcScanOut ; pulDstScan += dpulDstScan, pulSrcScan += dpulSrcScan ) { ULONG *pulSrc, *pulDst, *pulSrcOut; ULONG b = 0; for ( pulDst = pulDstScan, pulSrc = pulSrcScan, pulSrcOut = pulSrcScan + dpulSrcScan ; pulSrc < pulSrcOut ; pulDst++, pulSrc++ ) { ULONG u; ULONG a = *pulSrc; u = (a & MASK_0) << 12; u |= (b & MASK_0) >> 20; u |= (a & MASK_1) >> 4; u |= (b & MASK_1) << 28; *pulDst = u; b = a; } } } void vOrShiftGrayGlyph3( ULONG *pulSrcScan , ptrdiff_t dpulSrcScan , ULONG *pulSrcScanOut , ULONG *pulDstScan , ptrdiff_t dpulDstScan ) { for ( ; pulSrcScan < pulSrcScanOut ; pulDstScan += dpulDstScan, pulSrcScan += dpulSrcScan ) { ULONG *pulSrc, *pulDst, *pulSrcOut; ULONG b = 0; for ( pulDst = pulDstScan, pulSrc = pulSrcScan, pulSrcOut = pulSrcScan + dpulSrcScan ; pulSrc < pulSrcOut ; pulDst++, pulSrc++ ) { ULONG u; ULONG a = *pulSrc; u = (a & MASK_0) << 20; u |= (b & MASK_0) >> 12; u |= (a & 0x00f0f0f0) << 4; u |= (b & MASK_1) >> 28; *pulDst = u; b = a; } } } void vOrShiftGrayGlyph5( ULONG *pulSrcScan , ptrdiff_t dpulSrcScan , ULONG *pulSrcScanOut , ULONG *pulDstScan , ptrdiff_t dpulDstScan ) { for ( ; pulSrcScan < pulSrcScanOut ; pulDstScan += dpulDstScan, pulSrcScan += dpulSrcScan ) { ULONG *pulSrc, *pulDst, *pulSrcOut; ULONG b = 0; for ( pulDst = pulDstScan, pulSrc = pulSrcScan, pulSrcOut = pulSrcScan + dpulSrcScan ; pulSrc < pulSrcOut ; pulDst++, pulSrc++ ) { ULONG u; ULONG a = *pulSrc; u = (a & MASK_0) << 28; u |= (b & MASK_0) >> 4; u |= (a & MASK_1) << 4; u |= (b & MASK_1) >> 28; *pulDst = u; b = a; } } } void vOrShiftGrayGlyph7( ULONG *pulSrcScan , ptrdiff_t dpulSrcScan , ULONG *pulSrcScanOut , ULONG *pulDstScan , ptrdiff_t dpulDstScan ) { for ( ; pulSrcScan < pulSrcScanOut ; pulDstScan += dpulDstScan, pulSrcScan += dpulSrcScan ) { ULONG *pulSrc, *pulDst, *pulSrcOut; ULONG b = 0; for ( pulDst = pulDstScan, pulSrc = pulSrcScan, pulSrcOut = pulSrcScan + dpulSrcScan ; pulSrc < pulSrcOut ; pulDst++, pulSrc++ ) { ULONG u; ULONG a = *pulSrc; u = (a & MASK_0) >> 28; u |= (b & MASK_0) << 4; u |= (a & MASK_1) << 20; u |= (b & MASK_1) >> 12; *pulDst = u; b = a; } } } void (*apfnGray[8])(ULONG*,ptrdiff_t,ULONG*,ULONG*,ptrdiff_t) = { vOrShiftGrayGlyph0 ,vOrShiftGrayGlyph1 ,vOrShiftGrayGlyph2 ,vOrShiftGrayGlyph3 ,vOrShiftGrayGlyph4 ,vOrShiftGrayGlyph5 ,vOrShiftGrayGlyph6 ,vOrShiftGrayGlyph7 }; #endif