Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Координаты Scroll окна и Потоки. Как задать нужные координаты 
:(
    Опции темы
OberonTSM
Дата 8.12.2007, 17:12 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 4
Регистрация: 7.12.2006

Репутация: нет
Всего: нет



Проблема такая:
Есть Приложение, вычисляющее точку оптимума функции по методу симплекса. объект вида - скроллинговый, причём размер больше размера экрана, то есть скролл нужен всегда. В главном окне в OnDraw рисуются координатные оси для трёх графиков. Также есть отдальный поток, рисующий сам процесс поиска методом симплекса (рисует наглядно, то есть шаг за шагом, по типу анимации). Собственно суть проблемы в том, что при любом скролле вниз координатная система для потока меняется и точка (0,0) совпадает с левым верхним углом ОТОБРАЖАЕМОЙ В ДАННЫЙ МОМЕНТ части объекта вида. А координатные оси остаются на своих местах. Соответственно
следующий после прокрутки вниз шаг графика рисуется ниже чем надо.  Как сделать так чтобы координаты для потока были постоянными и не зависили от скроллинга и отображаемой части объекта вида? Возможно ошибка в контексте устройства... Пожалуйста, подскажите что и где надо поменять\дописать...

Также интересно, как сделать чтобы прис выходе за границу области где должен быть рисунок (когда сильно прокручиваешь вниз), графическая информация потока не стиралась а оставалась нарисованной.
вот код потока и метода OnDraw:

Код

///////////////////////////////////////////////////////////////////////////////////////////////////

Объявление класса
class CSimplexView : public CScrollView
{
protected: // create from serialization only
    CSimplexView();
    DECLARE_DYNCREATE(CSimplexView)

// Attributes
public:
    CSimplexDoc* GetDocument();

// Operations
public:
    CClientDC *m_pDC;        // óêàçàòåëü íà êîíòåêñò êëèåíòñêîé ÷àñòè îêíà
    CRITICAL_SECTION m_ClientDCLock;    // êðèòè÷åñêàÿ ñåêöèÿ
//    int m_nThreadCounter;        // ñ÷åò÷èê ÷èñëà çàïóùåííûõ ïîòîêîâ 
    bool m_bWorking;    
    int ViewCheck;
// Overrides
    // ClassWizard generated virtual function overrides
    //{{AFX_VIRTUAL(CSimplexView)
    public:
    virtual void OnDraw(CDC* pDC);  // overridden to draw this view
    virtual BOOL PreCreateWindow(CREATESTRUCT& cs);
    protected:
    virtual void OnInitialUpdate(); // called first time after construct
    virtual BOOL OnPreparePrinting(CPrintInfo* pInfo);
    virtual void OnBeginPrinting(CDC* pDC, CPrintInfo* pInfo);
    virtual void OnEndPrinting(CDC* pDC, CPrintInfo* pInfo);
    //}}AFX_VIRTUAL

// Implementation
public:
    virtual ~CSimplexView();
#ifdef _DEBUG
    virtual void AssertValid() const;
    virtual void Dump(CDumpContext& dc) const;
#endif


// SimplexView.cpp : implementation of the CSimplexView class
//

#include "stdafx.h"
#include "Simplex.h"

#include "SimplexDoc.h"
#include "SimplexView.h"

#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif

/////////////////////////////////////////////////////////////////////////////
// CSimplexView

IMPLEMENT_DYNCREATE(CSimplexView, CScrollView)

BEGIN_MESSAGE_MAP(CSimplexView, CScrollView)
    //{{AFX_MSG_MAP(CSimplexView)
    ON_COMMAND(ID_VIEW_GRAPH, OnViewGraph)
    ON_COMMAND(ID_VIEW_TABLE, OnViewTable)
    ON_WM_CREATE()
    ON_WM_DESTROY()
    ON_UPDATE_COMMAND_UI(ID_VIEW_SEARCHPROCESS, OnUpdateViewSearchprocess)
    ON_COMMAND(ID_VIEW_SEARCHPROCESS, OnViewSearchprocess)
    //}}AFX_MSG_MAP
    // Standard printing commands
    ON_COMMAND(ID_FILE_PRINT, CScrollView::OnFilePrint)
    ON_COMMAND(ID_FILE_PRINT_DIRECT, CScrollView::OnFilePrint)
    ON_COMMAND(ID_FILE_PRINT_PREVIEW, CScrollView::OnFilePrintPreview)
END_MESSAGE_MAP()

/////////////////////////////////////////////////////////////////////////////
// CSimplexView construction/destruction

CSimplexView::CSimplexView()
{
    // TODO: add construction code here
    ViewCheck=0;
    m_pDC = 0;
    m_bWorking = false;
//  m_nThreadCounter = 0;
    InitializeCriticalSection(&m_ClientDCLock);

}

CSimplexView::~CSimplexView()
{
    DeleteCriticalSection(&m_ClientDCLock);
}

BOOL CSimplexView::PreCreateWindow(CREATESTRUCT& cs)
{
    // TODO: Modify the Window class or styles here by modifying
    //  the CREATESTRUCT cs

    return CScrollView::PreCreateWindow(cs);
}

/////////////////////////////////////////////////////////////////////////////
// CSimplexView drawing

UINT SearchThread(LPVOID pParam)
{
    CSimplexView* pView = (CSimplexView*)pParam; // ïðåîáðàçîâàíèå àðãóìåíòà ê óêàçàòåëþ íà îáúåêò âèäà
    CSimplexDoc* pDoc = pView->GetDocument();
//    ASSERT_VALID(pDoc);
    pView->m_bWorking = true;
        int xmin=30, xmax=1030, ymin=30, ymax=1030;
        int morphX=(xmax-xmin)/5;
        int morphY=-morphX;
        CPen penlight(PS_SOLID, 1, RGB(230,230,230));
        CPen pendark(PS_SOLID, 2, RGB(25,25,25));
        CPen pengreen(PS_SOLID, 5, RGB(0,255,0));
        CPen penbluefat(PS_SOLID, 5, RGB(0,0,255));
        CPen penbluethin(PS_SOLID, 1, RGB(0,0,255));
        for (int i=0;i<pDoc->Iter;i++)
            if (pView->ViewCheck==1)
            {
                EnterCriticalSection(&pView->m_ClientDCLock);
                pView->m_pDC->SelectObject(pengreen);
                pView->m_pDC->MoveTo(pDoc->X[i][0][0]*morphX+(xmax+xmin)/2, pDoc->X[i][0][1]*morphY+(ymax+ymin)/2);
                pView->m_pDC->LineTo(pDoc->X[i][0][0]*morphX+(xmax+xmin)/2, pDoc->X[i][0][1]*morphY+(ymax+ymin)/2);

                pView->m_pDC->SelectObject(penlight);
                pView->m_pDC->LineTo(pDoc->X[i][1][0]*morphX+(xmax+xmin)/2, pDoc->X[i][1][1]*morphY+(ymax+ymin)/2);
                pView->m_pDC->LineTo(pDoc->X[i][2][0]*morphX+(xmax+xmin)/2, pDoc->X[i][2][1]*morphY+(ymax+ymin)/2);
                pView->m_pDC->LineTo(pDoc->X[i][0][0]*morphX+(xmax+xmin)/2, pDoc->X[i][0][1]*morphY+(ymax+ymin)/2);

                pView->m_pDC->SelectObject(penbluefat);
                pView->m_pDC->MoveTo(pDoc->X[i][pDoc->MaxF[i]][0]*morphX+(xmax+xmin)/2, pDoc->X[i][pDoc->MaxF[i]][1]*morphY+(ymax+ymin)/2);
                pView->m_pDC->LineTo(pDoc->X[i][pDoc->MaxF[i]][0]*morphX+(xmax+xmin)/2, pDoc->X[i][pDoc->MaxF[i]][1]*morphY+(ymax+ymin)/2);
                pView->m_pDC->SelectObject(penbluethin);
                pView->m_pDC->LineTo(pDoc->X[i+1][0][0]*morphX+(xmax+xmin)/2, pDoc->X[i+1][0][1]*morphY+(ymax+ymin)/2);        
                pView->m_pDC->SelectObject(penbluefat);
                pView->m_pDC->LineTo(pDoc->X[i+1][0][0]*morphX+(xmax+xmin)/2, pDoc->X[i+1][0][1]*morphY+(ymax+ymin)/2);
                GdiFlush();
                LeaveCriticalSection(&pView->m_ClientDCLock);

                Sleep(1000);
            }
        pView->m_pDC->SelectObject(pendark);
        for (i=0;i<pDoc->Iter-1;i++)
            if (pView->ViewCheck==1)
            {
                pView->m_pDC->MoveTo(pDoc->X[i][pDoc->MinF[i]][0]*morphX+(xmax+xmin)/2, pDoc->X[i][pDoc->MinF[i]][1]*morphY+(ymax+ymin)/2);
                pView->m_pDC->LineTo(pDoc->X[i+1][pDoc->MinF[i+1]][0]*morphX+(xmax+xmin)/2, pDoc->X[i+1][pDoc->MinF[i+1]][1]*morphY+(ymax+ymin)/2);
            }
    pView->m_bWorking = false;
    return 0;
}

void CSimplexView::OnDraw(CDC* pDC)
{
    CSimplexDoc* pDoc = GetDocument();
    ASSERT_VALID(pDoc);
    // TODO: add draw code for native data here
    TEXTMETRIC Metric;
    pDC->GetTextMetrics(&Metric);
    CString str;
    CSize size;
    if (ViewCheck==1)
    {
        CPen pen(PS_SOLID, 1, RGB(0,0,0));
        pDC->SelectObject(pen);
        CSize NameSize;
        CString strName;
        CFont font;
        CFont* pOldFont = NULL;    // óêàçàòåëü íà ðàíåå èñïîëüçóåìûé øðèôò
    //    int xmin[3]={30,30,560}, xmax[3]={530,530,1060}, ymin[3]={30,560,30}, ymax[3]={530,1060,530};
        int xmin[3]={30,30,30}, xmax[3]={1030,1030,1030}, ymin[3]={2090,1060,30}, ymax[3]={3090,2060,1030};
        int morphX=(xmax[1]-xmin[1])/5;
        int morphY=-morphX;
        if(font.CreateFontIndirect(&pDoc->m_logFont)) pOldFont=pDC->SelectObject(&font);

        //Ñèñòåìà êîîðäèíàò
        //îêíà        
        for (int i=0;i<3;i++)
        {
            pDC->MoveTo(xmin[i]-5,ymin[i]-5);
            pDC->LineTo(xmax[i]+5,ymin[i]-5);
            pDC->LineTo(xmax[i]+5,ymax[i]+5);
            pDC->LineTo(xmin[i]-5,ymax[i]+5);
            pDC->LineTo(xmin[i]-5,ymin[i]-5);
            pDC->MoveTo(xmin[i]-10,ymin[i]-10);
            pDC->LineTo(xmax[i]+10,ymin[i]-10);
            pDC->LineTo(xmax[i]+10,ymax[i]+10);
            pDC->LineTo(xmin[i]-10,ymax[i]+10);
            pDC->LineTo(xmin[i]-10,ymin[i]-10);
        }

        //îñè äëÿ òðàåêòîðèè
        i=2;
        pDC->MoveTo((xmax[i]+xmin[i])/2,ymin[i]);
        pDC->LineTo((xmax[i]+xmin[i])/2+3,ymin[i]+10);
        pDC->MoveTo((xmax[i]+xmin[i])/2,ymin[i]);
        pDC->LineTo((xmax[i]+xmin[i])/2-3,ymin[i]+10);
        pDC->MoveTo((xmax[i]+xmin[i])/2,ymin[i]);
        pDC->LineTo((xmax[i]+xmin[i])/2,ymax[i]);
        pDC->MoveTo(xmin[i],(ymax[i]+ymin[i])/2);
        pDC->LineTo(xmax[i],(ymax[i]+ymin[i])/2);
        pDC->LineTo(xmax[i]-10,(ymax[i]+ymin[i])/2+3);
        pDC->MoveTo(xmax[i],(ymax[i]+ymin[i])/2);
        pDC->LineTo(xmax[i]-10,(ymax[i]+ymin[i])/2-3);                
        //ðàçìåòêà äëÿ òðàåêòîðèè
        for (int j=-4;j<5;j++)
        {
            pDC->MoveTo((xmax[i]+xmin[i])/2+(morphX/2)*j,(ymax[i]+ymin[i])/2-2);
            pDC->LineTo((xmax[i]+xmin[i])/2+(morphX/2)*j,(ymax[i]+ymin[i])/2+3);
            str.Format("%.1f",j*0.5);
            pDC->TextOut((xmax[i]+xmin[i])/2+(morphX/2)*j-5,(ymax[i]+ymin[i])/2+10,str);
        }
        for (j=-4;j<5;j++)
        {
            pDC->MoveTo((xmax[i]+xmin[i])/2-2, (ymax[i]+ymin[i])/2+(morphY/2)*j);
            pDC->LineTo((xmax[i]+xmin[i])/2+3, (ymax[i]+ymin[i])/2+(morphY/2)*j);
            str.Format("%.1f",-j*0.5);
            pDC->TextOut((xmax[i]+xmin[i])/2+10,(ymax[i]+ymin[i])/2+(morphY/2)*j-5, str);
        }
        for (i=1;i>=0;i--)
        {
            //îñè äëÿ îñòàëüíûõ ãðàôèêîâ
            pDC->MoveTo(xmin[i],ymin[i]);
            pDC->LineTo(xmin[i]+3,ymin[i]+10);
            pDC->MoveTo(xmin[i],ymin[i]);
            pDC->LineTo(xmin[i]-3,ymin[i]+10);
            pDC->MoveTo(xmin[i],ymin[i]);
            pDC->LineTo(xmin[i],ymax[i]);
            pDC->LineTo(xmax[i],ymax[i]);
            pDC->LineTo(xmax[i]-10,ymax[i]+3);
            pDC->MoveTo(xmax[i],ymax[i]);
            pDC->LineTo(xmax[i]-10,ymax[i]-3);                
            //ðàçìåòêà äëÿ îñòàëüíûõ ãðàôèêîâ
            for (int j=0;j<10;j++)
            {
                pDC->MoveTo(xmin[i]+(morphX/2)*j,ymax[i]-2);
                pDC->LineTo(xmin[i]+(morphX/2)*j,ymax[i]+3);
                str.Format("%.1f",j*0.5);
                pDC->TextOut(xmin[i]+(morphX/2)*j-5,ymax[i]-20,str);
            }
            for (j=0;j<10;j++)
            {
                pDC->MoveTo(xmin[i]-2,ymax[i]+(morphY/2)*j);
                pDC->LineTo(xmin[i]+3,ymax[i]+(morphY/2)*j);
                str.Format("%.1f",-j*0.5);
                pDC->TextOut(xmin[i]+10,ymax[i]+(morphY/2)*j-5, str);
            }
        }
        //íàçâàíèÿ
        if (pOldFont != NULL) pDC->SelectObject(pOldFont);

        i=2;
        strName="Òðàåêòîðèÿ ïîèñêà";
        NameSize=pDC->GetTextExtent(strName);
        pDC->TextOut((xmax[i]+xmin[i]-NameSize.cx)/2,ymin[i]+30,strName);
        pDC->TextOut((xmax[i]+xmin[i])/2+10,ymin[i],"X2");
        pDC->TextOut(xmax[i]-15,(ymax[i]+ymin[i])/2-25, "X1");
        
        for (i=1; i>=0; i--)
        {
            if (i==0)
                strName="Ãðàôèê çíà÷åíèÿ ôóíêöèè ïî øàãàì";
            if (i==1)
                strName="Ãðàôèê ðàññòîÿíèÿ îò òåêóùåé òî÷êè äî òî÷êè îïòèìóìà";            
            NameSize=pDC->GetTextExtent(strName);
            pDC->TextOut((xmax[i]+xmin[i]-NameSize.cx)/2,ymin[i]+30,strName);
            pDC->TextOut(xmin[i]+10,ymin[i],"X2");
            pDC->TextOut(xmax[i]-15,ymax[i]-25, "X1");        
        }
//////////////////////////////
        // ñîáñòâåííî ãðàôèêè
        CPen pengreen(PS_SOLID, 5, RGB(0,255,0));
        CPen penred(PS_SOLID, 5, RGB(255,0,0));

        pDC->SelectObject(penred);
        pDC->MoveTo(morphX+(xmax[2]+xmin[2])/2, morphY+(ymax[2]+ymin[2])/2);
        pDC->LineTo(morphX+(xmax[2]+xmin[2])/2, morphY+(ymax[2]+ymin[2])/2);

        pDC->SelectObject(pengreen);
        pDC->MoveTo(pDoc->XInst[0]*morphX+(xmax[2]+xmin[2])/2, pDoc->XInst[1]*morphY+(ymax[2]+ymin[2])/2);
        pDC->LineTo(pDoc->XInst[0]*morphX+(xmax[2]+xmin[2])/2, pDoc->XInst[1]*morphY+(ymax[2]+ymin[2])/2);

        size.cx= xmax[0]+30;
        size.cy= ymax[0]+10;
    }
    else
    {
        pDC->TextOut(0, 0, "Ôóíêöèÿ (x2 - x1^2 )^2 + (1 - x1 )^2");
        str="Íà÷àëüíàÿ òî÷êà ("+pDoc->Coord+')';
        pDC->TextOut(0, Metric.tmHeight, str);
        pDC->TextOut(0, 2*Metric.tmHeight, "Òåîðåòè÷åñêàÿ òî÷êà îïòèìóìà (1;1)");

        CString tmp;
        for (int k=0; k<pDoc->Iter; k++)
        {
            str.Format("%d",k+1);
            str="Ñèìïëåêñ "+str;
            pDC->TextOut(0,(4+6*k)*Metric.tmHeight, str);
            for (int i=0;i<3;i++)
            {
                tmp.Format("%d",i);
                str=" òî÷êå "+tmp+" (";
                for (int j=0;j<2;j++)
                {
                    tmp.Format("%.3f",pDoc->X[k][i][j]);
                    str+=tmp+';';
                }
                tmp.Format("%.3f",pDoc->Fx[k][i]);
                str=str.Left(str.GetLength()-1);
                str+=") ôóíêöèÿ ðàâíà "+tmp;
                pDC->TextOut(0,(5+i+6*k)*Metric.tmHeight, str);
            }
            tmp.Format("%d",pDoc->MaxF[k]);
            str="Ìàêñèìàëüíîå çíà÷åíèå ôóíêöèè íàáëþäàëîñü â òî÷êå "+tmp;
            pDC->TextOut(0,(8+6*k)*Metric.tmHeight, str);
        }
        size.cx= 500;
        size.cy= (4+6*pDoc->Iter)*Metric.tmHeight;
    }
    SetScrollSizes(MM_TEXT,size);
}

void CSimplexView::OnInitialUpdate()
{
    CScrollView::OnInitialUpdate();

    CSize sizeTotal;
    // TODO: calculate the total size of this view
    sizeTotal.cx = sizeTotal.cy = 100;
    SetScrollSizes(MM_TEXT, sizeTotal);
}

/////////////////////////////////////////////////////////////////////////////
// CSimplexView printing

BOOL CSimplexView::OnPreparePrinting(CPrintInfo* pInfo)
{
    // default preparation
    return DoPreparePrinting(pInfo);
}

void CSimplexView::OnBeginPrinting(CDC* /*pDC*/, CPrintInfo* /*pInfo*/)
{
    // TODO: add extra initialization before printing
}

void CSimplexView::OnEndPrinting(CDC* /*pDC*/, CPrintInfo* /*pInfo*/)
{
    // TODO: add cleanup after printing
}

/////////////////////////////////////////////////////////////////////////////
// CSimplexView diagnostics

#ifdef _DEBUG
void CSimplexView::AssertValid() const
{
    CScrollView::AssertValid();
}

void CSimplexView::Dump(CDumpContext& dc) const
{
    CScrollView::Dump(dc);
}

CSimplexDoc* CSimplexView::GetDocument() // non-debug version is inline
{
    ASSERT(m_pDocument->IsKindOf(RUNTIME_CLASS(CSimplexDoc)));
    return (CSimplexDoc*)m_pDocument;
}
#endif //_DEBUG

/////////////////////////////////////////////////////////////////////////////
// CSimplexView message handlers

void CSimplexView::OnViewGraph() 
{
    // TODO: Add your command handler code here
    if (ViewCheck==0)
    {
        Invalidate ();
        ViewCheck=1;
    }
}

void CSimplexView::OnViewTable() 
{
    // TODO: Add your command handler code here
    if (ViewCheck==1)
    {
        Invalidate ();
        ViewCheck=0;
    }
}

int CSimplexView::OnCreate(LPCREATESTRUCT lpCreateStruct) 
{
    if (CScrollView::OnCreate(lpCreateStruct) == -1)
        return -1;
    
    // TODO: Add your specialized creation code here
    m_pDC = new CClientDC(this);    // ïîëó÷åíèå óêàçàòåëÿ íà êîíòåêñò îêíà    
    return 0;
}

void CSimplexView::OnDestroy() 
{
    
    // TODO: Add your message handler code here
    m_bWorking=false;
//    Sleep(m_nThreadCounter*20);    // çàñíóòü íà 20 ìèëëèñåêóíä äëÿ êàæäîãî ïîòîêà
//    m_nThreadCounter=0;
    delete m_pDC;
    m_pDC = 0;
    CView::OnDestroy();

}

void CSimplexView::OnUpdateViewSearchprocess(CCmdUI* pCmdUI) 
{
    // TODO: Add your command update UI handler code here
    if (ViewCheck==0 || m_bWorking==true)
        pCmdUI->Enable(false);
    else
        pCmdUI->Enable(true);

}

void CSimplexView::OnViewSearchprocess() 
{
    // TODO: Add your command handler code here
    Invalidate ();
    AfxBeginThread(SearchThread, this, THREAD_PRIORITY_IDLE);
//    m_nThreadCounter++;
}


PS. Visual C++ 6.0
PM MAIL   Вверх
Earnest
Дата 11.12.2007, 19:43 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Экс. модератор
Сообщений: 5962
Регистрация: 17.6.2005
Где: Рязань

Репутация: 87
Всего: 183



ИМХО, неправильный подход. Рисовать лучше в одном потоке - в главном. Рабочий поток пусть обсчитывает данные.
Не разбиралась, что у тебя за данные, это не существенно, существеннен подход: данные для рисования отдельно, рисование - отдельно.
Т.е. рабочий поток считает данные, главный поток - рисует, что получилось на данный момент.
Анимация обеспечивается таймером: перерисовка происходит каждые столько-то миллисекунд. 
Чтобы не дергалось, рисуем во внеэкранный буфер, потом быстренько копируем на экран.

Простой пример: рассчитываем гистограмму а-а-громного растра. Данные - 3 массива по 256 для каждого канало (например). Создаем класс, куда запихиваем эти 3 массива + методы set\get + критическая секция для синхронизации. Поток сканирует растр и обновляет гистограмму. Рабочий поток, получив сигнал таймера, делает окну Invalidate, а рисует всегда в методе OnPaint - это принципиально! Тогда никаких проблем с позицией не будет.
Рисует то, что находится в наст. момент в гистограмме.
Чтобы абстрагироваться от текущей позиции скролла, введи логическую систему координат: все поле рисунка. Кстати, это тем более полезно, что данные у тебя наверняка считаются как double. При рисовании пересчтывай в координаты окна - это будет элементарный сдвиг. Рисуй все, если не тормозит. Если тормозит - отсекай, перед началом прорисовки определив зону отсечения в логических координатах.

Главное - точка рисования должна быть ровно одна - и вызываться из OnPaint.

Можно также предложить второй вариант - если общий размер поля не слишком превышает размер окна. Заведи внеэкранный буфер полного размера и рисуй в него - тогда никакого отсечения и никакой зависимости от позиции скроллинга. Тогда операции OnPaint, OnScroll И собственно рисование в буфер можно несколько разделить. OnPaint - просто копирует нужную часть буфера в окно. OnScroll - прокручивает окно + инвалидэйтит новые области (вылезающие из-за границы), которые тут же перерисуются OnPaint (который скопирует туда кусок буфера smile ). А по получению сигнала от таймера - перерисовываем буфер и делаем инвалидэйт. 

Но в обих слуачаях нужно отделить рисование от получения данных. 


--------------------
...
PM   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Visual C++/MFC/WTL | Следующая тема »


 




[ Время генерации скрипта: 0.0978 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.