#include "SceneView.h"
#include "translator.h"

void UGSTDCALL Action3DChangedCallBack(UGlong pWnd, UGSceneUserAction oldAction,UGSceneUserAction newAction)
{
//    qDebug()<<"****************oldAction:"<<oldAction;
    qDebug()<<"****************newAction:"<<newAction;

//    qDebug()<<"****************newAction:"<<newAction;

//    SceneView* pSceneView = (SceneView*)pWnd;
//    pSceneView->ReviseCursor(newAction);
//    pSceneView = NULL;
//    if(newAction==UGSceneUserAction::suaCreatePolyline)
//    {
////        pSceneView->showSettingFlightPoint = true;
//        emit pSceneView->showSettingFlightPointDialg();
//    }

//    qDebug()<<"****************Edit3DCursorShape:"<<pSceneControl->GetSceneEditWnd()->Get3DCursorShape();
//    qDebug()<<"****************3DCursorShape:"<<pSceneControl->GetSceneEditWnd()->m_SceneWindow.Get3DCursorShape();
}

void UGSTDCALL Tracking3DCallBack(UGlong pWnd, UGdouble &dx, UGdouble &dy, UGdouble &dz,
    UGint nButtonClicked, UGdouble dCurrentLength, UGdouble dCurrentAngle,
    UGdouble dTotalLength, UGdouble dTotalArea, UGdouble dHeight, UGdouble dAngle,
    UGdouble dAzimuth, UGGeometry *pGeometry)
{
    qDebug()<<"****************Tracking3DCallBack:";
    SceneView* pSceneView = (SceneView*)pWnd;
    if(pSceneView->startTrackingFlag)
    {
        emit pSceneView->sendTrackingGeometry(pGeometry);
        pSceneView->startTrackingFlag = false;
    }
}

void UGSTDCALL Tracked3DCallBack(UGlong pWnd, UGGeometry *pGeometry, UGdouble dLength,
                    UGdouble dArea, UGdouble dHeight,UGdouble dAngle, UGdouble dAzimuth)
{
    SceneView* pSceneView = (SceneView*)pWnd;
    qDebug()<<"****************Tracked3DCallBack:";
//    qDebug()<<"****************UserAction:"<<pSceneView->GetSceneControl()->GetSceneEditWnd()->GetUserAction();
//    qDebug()<<"***************GeometryType:"<<pGeometry->GetType();
//    if(pGeometry==NULL) return;
    qDebug()<<"****************Length:"<<dLength;
    if(pGeometry!=NULL)
    {
        if(pGeometry->GetType()==UGGeometry::GeoLine3D)
            emit pSceneView->sendTrackedGeometry(pGeometry);
    }

    pSceneView->GetSceneControl()->GetSceneEditWnd()->SetUserAction(UGSceneUserAction::suaPanSelect);
    qDebug()<<"****************UserAction1:"<<pSceneView->GetSceneControl()->GetSceneEditWnd()->GetUserAction();
//    pSceneView->GetSceneControl()->Refresh();
    /*
    qDebug()<<"****************SubPntCount:"<<pGeometry->GetSubPntCount(0);
    UGGeoLine3D* l = (UGGeoLine3D*)pGeometry;
    const UGPoint3D* p = NULL;
    p = l->GetPoints();
    for(int i =0;i<pGeometry->GetSubPntCount(0);i++)
    {
        qDebug()<<"****************x:"<<p->x;
        qDebug()<<"****************y:"<<p->y;
        qDebug()<<"****************z:"<<p->z;
        qDebug()<<"*********************";
        p++;
    }
    */
}


void UGSTDCALL VertexModifiedCallBack(UGlong pWnd,UGPoint3D pntPosition,UGbool bMoveZ,
    UGint nPointID,UGint nGeometryID,UGLayer3D *pLayer)
{
//    qDebug()<<"*************************VertexModifiedCallBack";
//    qDebug()<<"*************************nPointID:"<<nPointID;
}

void UGSTDCALL DynamicSelected3DCallBack(UGlong pWnd, UGString strLayerName, UGint nGeometryID)
{
    qDebug()<<"*************************strLayerNameCallBack:"<<Translator::UGStr2QStr(strLayerName);
}

void UGSTDCALL GeometrySelected3DCallBack(UGlong pWnd,UGint nSelectedGeometryCount)
{
    qDebug()<<"*************************GeometrySelected3DCallBack:"<<nSelectedGeometryCount;
    SceneView* pSceneView = (SceneView*)pWnd;
    SceneControl* pSceneControl = pSceneView->GetSceneControl();
    if(pSceneControl->GetEditStatus())
    {//编辑模式下,设置选中对象所在图层为可编辑。
        pSceneControl->SetSelectionLayerEditable(true);
    };

    pSceneView = NULL;
    pSceneControl = NULL;
};

void UGSTDCALL GeometrySelectChanged3DCallBack(UGlong pWnd,UGint nSelectedGeometryCount)
{
    qDebug()<<"*************************GeometrySelectChanged3DCallBack:";
};

void UGSTDCALL AfterGeometry3DModifiedCallBack(
    UGlong pWnd,
    UGint nGeometryID,
    UGLayer3D *pLayer)
{
    qDebug()<<"*************************AfterGeometry3DModifiedCallBack-nGeometryID:"<<nGeometryID;
};

SceneView::SceneView(QWidget *parent) : QWidget(parent)
{
    m_pSceneControl = NULL;

    QDesktopWidget* desktop = QApplication::desktop();
    int logicalDpiX = desktop->logicalDpiX();
    int logicalDpiY = desktop->logicalDpiY();
    m_pSceneControl = new SceneControl((HWND)winId(), logicalDpiX, logicalDpiX);

    renderTimer = new QTimer();
    connect(renderTimer, SIGNAL(timeout()), this, SLOT(RenderInTimer()));
//    renderTimer->start(30);

    isRenderTimerStarted = false;

    this->setMouseTracking(true);

    m_pSceneControl->GetSceneEditWnd()->m_SceneWindow.SetTracking3DFunc(Tracking3DCallBack,(UGlong)this);
    m_pSceneControl->GetSceneEditWnd()->m_SceneWindow.SetTracked3DFunc(Tracked3DCallBack,(UGlong)this);
    m_pSceneControl->GetSceneEditWnd()->m_SceneWindow.SetAction3DChangedFunc(Action3DChangedCallBack,(UGlong)this);
//    m_pSceneControl->GetSceneEditWnd()->SetVertexModifiedFunc(VertexModifiedCallBack,(UGlong)this);
    m_pSceneControl->GetSceneEditWnd()->SetVertexSelectedFunc(VertexModifiedCallBack,(UGlong)this);
    m_pSceneControl->GetScene3D()->SetDynamicSelected3DFunc(DynamicSelected3DCallBack,(UGlong)this);
    m_pSceneControl->GetScene3D()->SetGeometrySelected3DFunc(GeometrySelected3DCallBack,(UGlong)this);
//    m_pSceneControl->GetScene3D()->SetGeometrySelectChanged3DFunc(GeometrySelectChanged3DCallBack,(UGlong)this);
    m_pSceneControl->GetSceneEditWnd()->SetAfterGeometry3DModifiedFunc(AfterGeometry3DModifiedCallBack,(UGlong)this);
    //    pSceneLayersView = new SceneLayersView();

    isEditStateFlag = false;
}

SceneView::~SceneView()
{
    renderTimer->stop();
    delete renderTimer;

    /*pSceneLayersView->setParent(NULL);
    delete pSceneLayersView;*/

    delete m_pSceneControl;
}

unsigned int SceneView::getMouseOrKeyFlag(QMouseEvent* event)
{
    unsigned int flag = 0;

    if (event->modifiers() & Qt::ShiftModifier)
    {
        flag = flag | UG_VK_SHIFT;
    }
    if ((event->modifiers() & Qt::ControlModifier))
    {
        flag = flag | UG_VK_CONTROL;
    }
    if (event->modifiers()&Qt::MetaModifier)
    {
        flag = flag | UG_VK_MENU;
    }
    return flag;
}

//设置鼠标光标形状
void SceneView::ReviseCursor(int CursorShape)
{
    /*
    switch (SceneUserAction) {
    case UGSceneUserAction::suaPan:
//        setCursor(QCursor(QPixmap(":/Resources/Pan2.png")));
        setCursor(QCursor(Qt::ClosedHandCursor));
        break;
    case UGSceneUserAction::suaPanSelect:
//        setCursor(QCursor(QPixmap(":/Resources/Pan.png")));
        setCursor(QCursor(Qt::OpenHandCursor));
        break;
    case UGSceneUserAction::suaCreatePoint:
    case UGSceneUserAction::suaCreatePolygon:
    case UGSceneUserAction::suaCreateLine:
    case UGSceneUserAction::suaCreatePolyline:
    case UGSceneUserAction::suaCreateRectangle:
//        setCursor(QCursor(QPixmap(":/Resources/cross.png"), 9, 9));
        setCursor(QCursor(Qt::CrossCursor));
        break;
    case UGSceneUserAction::suaMeasureDistance:
    case UGSceneUserAction::suaMeasureArea:
    case UGSceneUserAction::suaMeasureHeight:
    case UGSceneUserAction::suaMeasureTerrainDistance:
    case UGSceneUserAction::suaMeasureTerrainArea:
    case UGSceneUserAction::suaMeasureHorizontalDistance:
        setCursor(QCursor(QPixmap(":/Resources/Length.png"), 9, 9));
        break;
    default:
        break;
    }
    */


    switch(CursorShape)
    {
    case UG3DCursorShape::ecBusy:
    {
        this->setCursor(QCursor(Qt::WaitCursor));
        break;
    }
    case UG3DCursorShape::ecArrow:
    {
        setCursor(QCursor(Qt::ArrowCursor));
        break;
    }
    case UG3DCursorShape::ecZoomFree:
    {
        setCursor(QCursor(QPixmap(":/Resources/ZoomFree.png")));
        break;
    }
    case UG3DCursorShape::ecPan:
    {
        setCursor(QCursor(Qt::OpenHandCursor));
        break;
    }
    case UG3DCursorShape::ecPanMove:
    {
        setCursor(QCursor(Qt::ClosedHandCursor));
        break;
    }
    case UG3DCursorShape::ecZoomIn:
    {
        setCursor(QCursor(QPixmap(":/Resources/ZoomIn.png"), 2, 2));
        break;
    }
    case UG3DCursorShape::ecZoomOut:
    {
        setCursor(QCursor(QPixmap(":/Resources/ZoomOut.png"), 2, 2));
        break;
    }
    case UG3DCursorShape::ecPointModeSelect:
    case UG3DCursorShape::ecPointModeSelectTrue:
    case UG3DCursorShape::ecRectModeSelect:
    case UG3DCursorShape::ecLineModeSelect:
    {
        setCursor(QCursor(QPixmap(":/Resources/Select.png"), 4, 4));
        break;
    }
    case UG3DCursorShape::ecDrawPolyGon:
    case UG3DCursorShape::ecDrawPolyLine:
    {
        setCursor(QCursor(Qt::CrossCursor));
        break;
    }
    case UG3DCursorShape::ecDrawText:
    {
        setCursor(QCursor(Qt::IBeamCursor));
        break;
    }
    case UG3DCursorShape::ecAddPoint:
        setCursor(QCursor(Qt::CrossCursor));
        break;
    case UG3DCursorShape::ecMovePoint:
        setCursor(QCursor(Qt::SizeAllCursor));
        break;
    case UG3DCursorShape::ecMoveZPoint:
        setCursor(QCursor(Qt::SizeVerCursor));
        break;
    default:
        break;
    }

}

void SceneView::paintEvent(QPaintEvent* event)
{

}

void SceneView::wheelEvent(QWheelEvent* event)
{
    if (m_pSceneControl != NULL)
    {
        m_pSceneControl->OnMouseWheel(0, event->delta(), event->x(), event->y());
    }
}

void SceneView::mousePressEvent(QMouseEvent* event)
{
    if (m_pSceneControl == NULL)
    {
        return;
    }
    int flag = getMouseOrKeyFlag(event);

    if (event->button() == Qt::LeftButton)
    {// LeftButton
        m_pSceneControl->OnLMouseDown(flag, event->x(), event->y());
        if(m_pSceneControl->GetSceneEditWnd()->GetUserAction()==UGSceneUserAction::suaCreatePolyline)
            this->startTrackingFlag = true;
//        //发送显示航高设置对话框
//        if(this->showSettingFlightPoint)
//        {
//            emit showSettingFlightPointDialg();
//            this->showSettingFlightPoint = false;
//            qDebug()<<"*******************showSettingFlightPointDialg:";
//        }
    }
    else if (event->button() == Qt::RightButton)
    {// RightButton
        m_pSceneControl->OnRMouseDown(flag, event->x(), event->y());
    }
    else if (event->button() == Qt::MidButton)
    {// MidButton
        m_pSceneControl->OnMidMouseDown(flag, event->x(), event->y());
    }
}

void SceneView::mouseReleaseEvent(QMouseEvent* event)
{
    if (m_pSceneControl == NULL)
    {
        return;
    }

    int flag = getMouseOrKeyFlag(event);

    if (event->button() == Qt::LeftButton)
    {// LeftButton
        m_pSceneControl->OnLMouseUp(flag, event->x(), event->y());
    }
    else if (event->button() == Qt::RightButton)
    {// RightButton
        m_pSceneControl->OnRMouseUp(flag, event->x(), event->y());
        if(m_pSceneControl->GetGeoSelections()!=NULL)
        {//当前有选中状态,则右键弹出属性菜单
//            qDebug()<<"********************右键菜单被调用了";
            emit showAttributeMenu();
        }
    }
    else if (event->button() == Qt::MidButton)
    {// MidButton
        m_pSceneControl->OnMidMouseUp(flag, event->x(), event->y());
    }
}

void SceneView::mouseMoveEvent(QMouseEvent* event)
{
//    qDebug()<<"******************SceneView-mouseMoveEvent:";
    if (m_pSceneControl != NULL)
    {
        m_pSceneControl->OnMouseMove(getMouseOrKeyFlag(event), event->x(), event->y());  
    }
//    qDebug()<<"******************UserAction:"<<m_pSceneControl->GetSceneEditWnd()->GetUserAction();
//    if(m_pSceneControl->GetSceneEditWnd()->GetUserAction()==108)
//        qDebug()<<"*******************Cursor0:"<<m_pSceneControl->GetSceneEditWnd()->Get3DCursorShape();
    ReviseCursor(m_pSceneControl->GetSceneEditWnd()->Get3DCursorShape());
}

void SceneView::resizeEvent(QResizeEvent* event)
{
    QWidget::resizeEvent(event);
    int width = this->width();
    int height = this->height();
//    if (!isRenderTimerStarted && width > 0 & height > 0) {
//        QDesktopWidget* desktop = QApplication::desktop();
//        int logicalDpiX = desktop->logicalDpiX();
//        int logicalDpiY = desktop->logicalDpiY();

//        m_pSceneControl = new SceneControl((HWND)winId(), logicalDpiX, logicalDpiX);

//        renderTimer->start(30);
//        isRenderTimerStarted = true;
//    }

    qDebug() << "SceneView width: " << width << "  height: " << height << endl;
    if (m_pSceneControl != NULL && width > 0 & height > 0)
    {
        m_pSceneControl->OnSizeChanged(width, height);
    }
}

void SceneView::keyPressEvent(QKeyEvent* event)
{

}

void SceneView::mouseDoubleClickEvent(QMouseEvent *event)
{
    int flag = getMouseOrKeyFlag(event);
    if(event->button() == Qt::LeftButton)
    {
//        qDebug()<<"**************************LDoubleClickEvent"<<flag;
        m_pSceneControl->OnLMouseDbClick(flag,event->x(),event->y());
    }
    else if(event->button() == Qt::RightButton)
    {

    }
}

SceneControl* SceneView::GetSceneControl()
{
    return m_pSceneControl;
}

void SceneView::startRender(int ms)
{
    renderTimer->start(ms);
}

void SceneView::stopRender()
{
    renderTimer->stop();
}

void SceneView::RenderInTimer()
{
    if (NULL != m_pSceneControl)
    {
        if (isVisible()) {
            m_pSceneControl->RenderInTimer();
        }
    }
}

//SceneLayersView* SceneView::getSceneLayersView()
//{
////    return pSceneLayersView;
//}