Справочник функций

Ваш аккаунт

Войти через: 
Забыли пароль?
Регистрация
Информацию о новых материалах можно получать и без регистрации:

Почтовая рассылка

Подписчиков: -1
Последний выпуск: 19.06.2015

TCanvas w Microsoft Visual C++?

4.7K
15 ноября 2003 года
Tatiana
9 / / 15.11.2003
Mozet li mnie kto nibud podskazat kakoj grficheskij obiekt nado primieniat' w Visual C++?
Jesli z togo , chto mne izwestno to w Builder C++ primieniajatsia obiekt TCanvas.

Spasibo za pomosh!
319
16 ноября 2003 года
xelos
577 / / 27.02.2003
Цитата:
Originally posted by Tatiana
Mozet li mnie kto nibud podskazat kakoj grficheskij obiekt nado primieniat' w Visual C++?
Jesli z togo , chto mne izwestno to w Builder C++ primieniajatsia obiekt TCanvas.

Spasibo za pomosh!


Насколько мне известно, аналога TCanvas в MFC нет. Все функции параметров реализуются через класс CWnd (типа видимый/невидимый объект, положение, размеры), функции рисования через контекст твоего окна (CDC) твоего объекта (типа нарисовать линию).

4.7K
16 ноября 2003 года
Tatiana
9 / / 15.11.2003
spasibo za otvet, tolko problema w tom , chto ja ne polzujs' MFC.
319
16 ноября 2003 года
xelos
577 / / 27.02.2003
Цитата:
Originally posted by Tatiana
spasibo za otvet, tolko problema w tom , chto ja ne polzujs' MFC.


А какой же графической библиотекой пользуешься?
В принципе оба класса являются виндовыми, в смысле они не из MFC, так что можешь ими пользоваться и без MFC.

4.7K
16 ноября 2003 года
Tatiana
9 / / 15.11.2003
ja i xotela uznat' kakije nuzny biblioteki , potomu shto u mienia kompilator nie nachodit graph.h.
319
16 ноября 2003 года
xelos
577 / / 27.02.2003
Цитата:
Originally posted by Tatiana
ja i xotela uznat' kakije nuzny biblioteki , potomu shto u mienia kompilator nie nachodit graph.h.


ты включаешь windows.h?

4.7K
16 ноября 2003 года
Tatiana
9 / / 15.11.2003
Цитата:
Originally posted by xelos

ты включаешь windows.h?



net, ja ne wkluchaju.mozesch mne woobche skazat' chto nado sdelat' chtoby narisowat' chotiaby prostuju liniju?

319
16 ноября 2003 года
xelos
577 / / 27.02.2003
Цитата:
Originally posted by Tatiana


net, ja ne wkluchaju.mozesch mne woobche skazat' chto nado sdelat' chtoby narisowat' chotiaby prostuju liniju?


если пишешь под винду и делаешь графическое приложение (в смысле не консольное, а с окном), то чтобы рисовать в окне (окно - это может быть любой элемент - кнопка, статический текст на диалоговой форме или просто окно-рамка), тебе надо получить графический контекст окна и рисовать в нем, например так:

 
Код:
CDC *dc;
dc=GetDC(); //контекст окна, для которого пишешь код, или
dc=Button1.GetDC(); // это если тебе надо контекст, например, Button1
dc->MoveTo(100,100);//переместить курсор в 100,100
dc->LineTo(150,150);//нарисовать линию
dc->ReleaseDC();//освободить контескт, иначе будут утечки памяти

GetDC() определена для класса CWnd, соответственно это все будет работать для классов, наследованных от CWnd.
Второй момент, что это рисование, перерисовка осуществляется по сообщению WM_PAINT, обработчик этого сообщения реализован в OnPaint() или OnDraw(), почитай MSDN чтобы понять разницу.
Смысл, что если ты не переопределишь OnPaint(), все что ты нарисовала будет стираться при перемещении окна, например. Ищи хелп про контексты устройств, вобщем.
319
18 ноября 2003 года
xelos
577 / / 27.02.2003
Я тут для собственных нужд сваял класс для простейшего канваса - смысл в том, что ты создаешь объект класса, потом в нем рисуешь выбирая цвет, тип и толщину линии. Перерисовка выполняется автоматически, т.е. OnPaint() переопределять не нада. Тока делаешь вызов .LineTo(...) и все автоматически сохраняется. Я этот класс цепляю заместо CStatic на диалоге - и рисую прямо в нем. Функций там всего ничего, но потом можно по желанию самому набить что угодно, сообщения ловит. Если все еще актуально - могу поделиться.
4.7K
18 ноября 2003 года
Tatiana
9 / / 15.11.2003
Цитата:
Originally posted by xelos
Я тут для собственных нужд сваял класс для простейшего канваса - смысл в том, что ты создаешь объект класса, потом в нем рисуешь выбирая цвет, тип и толщину линии. Перерисовка выполняется автоматически, т.е. OnPaint() переопределять не нада. Тока делаешь вызов .LineTo(...) и все автоматически сохраняется. Я этот класс цепляю заместо CStatic на диалоге - и рисую прямо в нем. Функций там всего ничего, но потом можно по желанию самому набить что угодно, сообщения ловит. Если все еще актуально - могу поделиться.



Bolshoje spasibo za pomosh, esli koniechno eto dla Tiebia ne problema to mozesh eto wyslat, mozet prigoditsia w budushem mne ili komu nibud' drugomu...A ja reshila zaniatsia wsio taki Borland C++ Builder :) Spasibo za pomosh esho raz...

319
19 ноября 2003 года
xelos
577 / / 27.02.2003
Цитата:
Originally posted by Tatiana

Bolshoje spasibo za pomosh, esli koniechno eto dla Tiebia ne problema to mozesh eto wyslat, mozet prigoditsia w budushem mne ili komu nibud' drugomu...A ja reshila zaniatsia wsio taki Borland C++ Builder :) Spasibo za pomosh esho raz...


Не знаю куда отправлять... Вобщем, смысл в следующем. Создаем свой класс, наследуем его от CWnd, с картой обработки сообщений и всеми делами. Чтобы его мона было пользовать в элементах управления, например на диалоге, его нужно зарегистрировать. Делаем что-то типа:

Код:
BOOL CImageV2::RegisterWndClass(void)
{
static bool is_registered = false;
 if(!is_registered) {    //Single init allowed
     is_registered = true;
    WNDCLASS wc;
    wc.style=CS_OWNDC;
    wc.lpfnWndProc=MyWndProc; //Creation WndProc
    wc.hInstance=::AfxGetInstanceHandle();
    wc.lpszClassName = _T("Image");
    wc.cbClsExtra=0;
    wc.cbWndExtra=0;
    wc.hIcon=0;
    wc.hCursor=0;
    wc.hbrBackground=(HBRUSH)::GetStockObject(WHITE_BRUSH);
    wc.lpszMenuName=0;
    if(!::AfxRegisterClass(&wc)){
        return FALSE;
    };
 };
    return TRUE;
};

is_registered - статический член класса.
процедура окна в самом начале файла класса MyWndProc:
Код:
LRESULT CALLBACK MyWndProc(HWND hWnd, UINT nMessage, WPARAM wParam, LPARAM lParam)
{
    CWnd* pWnd;
    pWnd=CWnd::FromHandlePermanent(hWnd);
    if (pWnd==NULL){
        pWnd= new CImageV2();
        pWnd->Attach(hWnd);
    };
    LRESULT lResult = AfxCallWndProc(pWnd, hWnd, nMessage,wParam, lParam);
    return lResult;
}

Вызываем регистрацию класса при построении объекта:
 
Код:
CImageV2::CImageV2()
{
    CImageV2::RegisterWndClass();
}

Теперь мы можем цеплять элементы диалога к этому классу. Чтобы избежать проблем при перерисовки, используем виртуальный контекст в памяти, к переменным класса добавляем CDC memDC;
для инициализации элемента добавляем функцию:
Код:
void CImageV2::Initialize(void)
{
    //Creer le context de la fenetre
    CClientDC DC(this);
    //Prendre les dimensions de l'element
    RECT rect;
    GetClientRect(&rect);

    //Les dimensions maximales
    maxX=rect.right;
    maxY=rect.bottom;
   
    //Creer un context virtuel, compatible avec le context de la fenetre
    m_memDC.CreateCompatibleDC(&DC);
    m_bmp.CreateCompatibleBitmap(&DC,maxX,maxY);
    m_memDC.SelectObject(&m_bmp);
   
    //Selectionner la couleur de fond
    m_bkBrush.CreateStockObject(BLACK_BRUSH);
    m_memDC.SelectObject(&m_bkBrush);
   
    //Mettre le fond
    m_memDC.PatBlt(0,0,maxX,maxY,PATCOPY);
    //m_memDC.SetMapMode(MM_TEXT);
    Scale(0,0,0,0);
    ReleaseDC(&DC);
}

maxX,maxY, m_bkBrush - переменные класса. maxX, maxY - размеры окна, m_bkBrush - кисть.
при перерисовке выполняем копирование из виртуального контекста в реальный, а все рисование идет в виртуальный контекст. Функция перерисовки:
 
Код:
void CImageV2::OnPaint()
{
    //CStatic::OnPaint();
    CPaintDC pDC(this);
    pDC.BitBlt(0,0,maxX,maxY,&m_memDC,0,0,SRCCOPY);
    ReleaseDC(&pDC);
}

Вот вобщем-то и все. Только после создания элемента, например в InitInstance() вызывающего класса, надо вызвать инициализацию для нашего элемента.
Для рисования делаем функцию, например:
 
Код:
void CImageV2::LineTo(int x, int y, int style, int nWidth, COLORREF Color)
{
    CPen pen(style, nWidth,Color);
    m_memDC.SelectObject(&pen);
   
    m_memDC.LineTo(x,y);

    InvalidateRect(NULL);

Здесь при вызове этой функции задаем толщину линий, стиль (линия с точками, пунктирная, ...) и цвет как RGB(0,255,0) - чтобы рисовать зеленым.
Дальше аналогично перегружаем остальные функции рисования или изменения состояний окна, например для реализации видимое/невидимое окно можно сделать что-то типа:
 
Код:
void CImageV2::Visible(bool Vis)
{
    if(Vis==TRUE){
        SetWindowPos(NULL,0,0,0,0,SWP_SHOWWINDOW|SWP_NOMOVE|SWP_NOSIZE);
    }else{
        SetWindowPos(NULL,0,0,0,0,SWP_HIDEWINDOW|SWP_NOMOVE|SWP_NOSIZE);
    };
}

или ту же самую функцию можно реализовать через ShowWindow().

Да, я еще явно вызываю функции связанные с построением или деструкцией окна, в смысле их обработчики.
 
Код:
void CImageV2::OnNcDestroy()
{
    CWnd::OnNcDestroy();
}
int CImageV2::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
    if (CWnd::OnCreate(lpCreateStruct) == -1)
        return -1;
      return 0;
}
Реклама на сайте | Обмен ссылками | Ссылки | Экспорт (RSS) | Контакты
Добавить статью | Добавить исходник | Добавить хостинг-провайдера | Добавить сайт в каталог