line.cpp

来自「6410BSP3」· C++ 代码 · 共 465 行 · 第 1/2 页

CPP
465
字号
        //      3  ⒆|①  0
        //       ⒆  |  ①
        //     ⒆  2 | 1  ①
        //             +y

        switch (pLineParms->iDir & 0x07)
        {
            // major axis is X-axis, dM = X-axis, dN = Y-axis
            case    0:                // +x +1/2y
                yEnd = yStart ;
                xEnd = xStart + pLineParms->cPels;
                break;
            case    1:                // +1/2x + y
                yEnd = yStart + pLineParms->cPels;
                xEnd = xStart;
                break;
            case    2:                // -1/2x + y
                yEnd = yStart + pLineParms->cPels;
                xEnd = xStart;
                break;
            case    3:                // -x + 1/2y
                yEnd = yStart;
                xEnd = xStart - pLineParms->cPels;
                break;
            case    4:                // -x - 1/2y
                yEnd = yStart;
                xEnd = xStart - pLineParms->cPels;
                break;
            case    5:                // -1/2x - y
                yEnd = yStart - pLineParms->cPels;
                xEnd = xStart;
                break;
            case    6:                // +1/2x - y
                yEnd = yStart - pLineParms->cPels;
                xEnd = xStart;
                break;
            case    7:                // +x -1/2y
                yEnd = yStart;
                xEnd = xStart + pLineParms->cPels;
                break;
        }


        bool IsLastDraw = false;

        if(xEnd < 0) xEnd = 0;        // Cut negative coordinate
        if(yEnd < 0) yEnd = 0;        // negative coordinate is not supported on H/W IP
        EnterCriticalSection(&m_cs2D);
        m_oG2D->PutLine(xStart, yStart, xEnd, yEnd, pLineParms->solidColor, IsLastDraw);
        LeaveCriticalSection(&m_cs2D);        
#else   // In Development
        if (pLineParms->dN)            // The line has a diagonal component (we'll refresh the bounding rect)
        {
            minorlength = ((pLineParms->cPels * pLineParms->dN) / pLineParms->dM);
        }

        // Line is vertical or horizontal
        // Use fill-blt to draw a line starting at
        // pLineParms->xStart, pLineParms->yStart
        // in the direction specified by pLineParms->iDir
        // for a total of pLineParms->cPels pixels
        //           -y
        //           ^
        //     ⒇  5 | 6  ⒅
        //       ⒇  |  ⒅
        //      4  ⒇|⒅  7
        // -x<-------+-------> +x
        //      3  ⒆|①  0
        //       ⒆  |  ①
        //     ⒆  2 | 1  ①
        //             +y

        switch (pLineParms->iDir & 0x07)
        {
            // major axis is X-axis, dM = X-axis, dN = Y-axis
            case    0:                // +x +1/2y
                yEnd = yStart + nMinorLength;
                xEnd = xStart + nMajorLength;
                break;
            case    1:                // +1/2x + y
                yEnd = yStart + nMajorLength;
                xEnd = xStart + nMinorLength;
                break;
            case    2:                // -1/2x + y
                yEnd = yStart + nMajorLength;
                xEnd = xStart - nMinorLength;
                break;
            case    3:                // -x + 1/2y
                yEnd = yStart + nMinorLength;
                xEnd = xStart - nMajorLength;
                break;
            case    4:                // -x - 1/2y
                yEnd = yStart - nMinorLength;
                xEnd = xStart - nMajorLength;
                break;
            case    5:                // -1/2x - y
                yEnd = yStart - nMajorLength;
                xEnd = xStart - nMinorLength;
                break;
            case    6:                // +1/2x - y
                yEnd = yStart - nMajorLength;
                xEnd = xStart + nMinorLength;
                break;
            case    7:                // +x -1/2y
                yEnd = yStart - nMinorLength;
                xEnd = xStart + nMajorLength;
                break;
        }


        bool IsLastDraw = false;
        int y_intercept = 0;
        int x_intercept = 0;
        int x1 = xStart * 16;        // interpolation
        int x2 = xEnd * 16;
        int y1 = yStart * 16;
        int y2 = yEnd * 16;

        ASSERT(xStart >=0);
        ASSERT(yStart >=0);
        // y=(y2-y1)/(x2-x1)x + b
        // b = (y1x2-x1y2)/(x2-x1)
        // 1. line is out over y-axis
        // y value when x=0 is y=b=(y1x2-x1y2)/(x2-x1)
        if(x2 < 0)
        {
            if(x2 == x1)    // do not draw. it is clipped.
            {
                return retval;
            }
            if(y2 == y1)    // Horizontal Line.
            {
                if(yEnd < 0) yEnd = 0;
            RETAILMSG(DISP_ZONE_LINE,(_T("ACCDRAW1 : LT(%d,%d)~RB(%d,%d)\n "), xStart, yStart, xEnd, yEnd));                
                m_oG2D->PutLine(xStart, yStart, 0, yEnd, pLineParms->solidColor, IsLastDraw);
                return retval;
            }

            y_intercept = ((y1*x2)-(x1*y2))/(x2-x1);

            if(y_intercept < 0 )    // Recalc for x
            {
                x_intercept = ((x1*y2)-(y1*x2))/(y2-y1);
                if(x_intercept < 0)
                {
                    RETAILMSG(DISP_ZONE_LINE,(_T("Line Draw error\n")));
                }
                else    // (xStart, yStart) ~ (x_intercept/16, 0)
                {
            RETAILMSG(DISP_ZONE_LINE,(_T("ACCDRAW2 : LT(%d,%d)~RB(%d,%d)\n "), xStart, yStart, xEnd, yEnd));                                    
                    m_oG2D->PutLine(xStart, yStart, x_intercept/16, 0, pLineParms->solidColor, IsLastDraw);
                    return retval;
                }
            }
            else    // (xStart, yStart) ~ (0, y_intercept/16)
            {
        RETAILMSG(DISP_ZONE_LINE,(_T("ACCDRAW3 : LT(%d,%d)~RB(%d,%d)\n "), xStart, yStart, xEnd, yEnd));                                
                    m_oG2D->PutLine(xStart, yStart, 0, y_intercept/16, pLineParms->solidColor, IsLastDraw);
                    return retval;
            }
        }
        else if(y2 < 0)
        {
            if(y1 == y2)        // do not draw. it is clipped
            {
                return retval;
            }
            if(x1 == x2)    // Vertical Line
            {
                if(xEnd < 0) xEnd = 0;
        RETAILMSG(DISP_ZONE_LINE,(_T("ACCDRAW4 : LT(%d,%d)~RB(%d,%d)\n "), xStart, yStart, xEnd, yEnd));                                
                m_oG2D->PutLine(xStart, yStart, xEnd, 0, pLineParms->solidColor, IsLastDraw);
                return retval;
            }
            x_intercept = ((x1*y2)-(y1*x2))/(y2-y1);
            if(x_intercept < 0)    // Recalc for y
            {
                y_intercept = ((y1*x2)-(x1*y2))/(x2-x1);
                if(y_intercept < 0)
                {
                    RETAILMSG(DISP_ZONE_LINE,(_T("Line Draw error\n")));
                }
                else    // (xStart, yStart) ~ (0, y_intercept)
                {
        RETAILMSG(DISP_ZONE_LINE,(_T("ACCDRAW5 : LT(%d,%d)~RB(%d,%d)\n "), xStart, yStart, xEnd, yEnd));                                    
                    m_oG2D->PutLine(xStart, yStart, 0, y_intercept/16, pLineParms->solidColor, IsLastDraw);
                    return retval;
                }
            }
            else    // (xStart, yStart) ~ (x_intercept, 0)
            {
        RETAILMSG(DISP_ZONE_LINE,(_T("ACCDRAW6 : LT(%d,%d)~RB(%d,%d)\n "), xStart, yStart, xEnd, yEnd));                                
                    m_oG2D->PutLine(xStart, yStart, x_intercept/16, 0, pLineParms->solidColor, IsLastDraw);
                    return retval;
            }
        }
        else
        {
        RETAILMSG(DISP_ZONE_LINE,(_T("ACCDRAW7 : LT(%d,%d)~RB(%d,%d)\n "), xStart, yStart, xEnd, yEnd));                                            
            m_oG2D->PutLine(xStart, yStart, xEnd, yEnd, pLineParms->solidColor, IsLastDraw);
            return retval;
        }
#endif
    }


    return retval;
}

SCODE
S3C6410Disp::Line(GPELineParms *pLineParms, EGPEPhase phase)
{
    DEBUGMSG (GPE_ZONE_INIT, (TEXT("++%s()\r\n"), _T(__FUNCTION__)));

    if (phase == gpeSingle || phase == gpePrepare)
    {
        DispPerfStart(ROP_LINE);
        pLineParms->pLine = (SCODE (GPE::*)(struct GPELineParms *))&S3C6410Disp::WrappedEmulatedLine;
    }
    else if (phase == gpeComplete)
    {
        DispPerfEnd(0);
        if(m_VideoPowerState != VideoPowerOff && m_G2DControlArgs.HWOnOff)
        {
            m_oG2D->WaitForIdle();    //< Wait for Engine Idle(Fully Empty Command Fifo) for all HW Line Drawing Request
        }
    }
    DEBUGMSG(GPE_ZONE_INIT, (TEXT("--%s()\r\n"), _T(__FUNCTION__)));

    return S_OK;
}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?