Browse Source

implement copy_texture

cxgeorge 23 years ago
parent
commit
72e396f06d
2 changed files with 33 additions and 293 deletions
  1. 33 51
      panda/src/dxgsg8/dxGraphicsStateGuardian8.cxx
  2. 0 242
      panda/src/dxgsg8/dxTextureContext8.cxx

+ 33 - 51
panda/src/dxgsg8/dxGraphicsStateGuardian8.cxx

@@ -397,7 +397,7 @@ read_vertex_shader(string &filename) {
    hr = scrn.pD3DDevice->CreateVertexShader((DWORD*)ShaderDeclHeader,
                                      (DWORD*) ((pD3DXBuf_CompiledShader!=NULL) ? pD3DXBuf_CompiledShader->GetBufferPointer() : pShaderBytes),
                                      &hShader, UsageFlags);
-   if (FAILED(hr)) {
+   if(FAILED(hr)) {
         dxgsg_cat.error() << "CreateVertexShader failed for '"<< filename << "' " << D3DERRORSTRING(hr);
         hShader=NULL;
    }
@@ -3237,68 +3237,50 @@ release_texture(TextureContext *tc) {
     delete gtc;
 }
 
-#if 1
-
+// copies current display region in framebuffer to the texture
 void DXGraphicsStateGuardian::
 copy_texture(TextureContext *tc, const DisplayRegion *dr) {
-    dxgsg_cat.fatal() << "DX copy_texture unimplemented!!!";
-}
 
-#else
-static int logs[] = { 1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 1024, 2048,
-    4096, 0};
-
-// This function returns the smallest power of two greater than or
-// equal to x.
-static int binary_log_cap(const int x) {
-    int i = 0;
-    for (; (x > logs[i]) && (logs[i] != 0); ++i);
-    if (logs[i] == 0)
-        return 4096;
-    return logs[i];
-}
+  HRESULT hr;
+  int xo, yo, w, h;
+  dr->get_region_pixels(xo, yo, w, h);
 
-////////////////////////////////////////////////////////////////////
-//     Function: DXGraphicsStateGuardian::copy_texture
-//       Access: Public, Virtual
-//  Description: Copy the pixel region indicated by the display
-//       region from the framebuffer into texture memory
-////////////////////////////////////////////////////////////////////
-void DXGraphicsStateGuardian::
-copy_texture(TextureContext *tc, const DisplayRegion *dr) {
+  DXTextureContext *dtc = DCAST(DXTextureContext, tc);
+  PixelBuffer *pb = dtc->_tex->_pbuffer;
+  pb->set_size(0,0,w-xo,h-yo);
 
-    nassertv(tc != NULL && dr != NULL);
+  IDirect3DSurface8 *pTexSurfaceLev0,*pCurRenderTarget;
+  hr = dtc->_pD3DTexture8->GetSurfaceLevel(0,&pTexSurfaceLev0);
+  if(FAILED(hr)) {
+    dxgsg_cat.error() << "GetSurfaceLev failed in copy_texture" << D3DERRORSTRING(hr);
+    exit(1);
+  }
 
-    Texture *tex = tc->_texture;
+  hr = scrn.pD3DDevice->GetRenderTarget(&pCurRenderTarget);
+  if(FAILED(hr)) {
+    dxgsg_cat.error() << "GetRenderTgt failed in copy_texture" << D3DERRORSTRING(hr);
+    exit(1);
+  }
 
-    // Determine the size of the grab from the given display region
-    // If the requested region is not a power of two, grab a region that is
-    // a power of two that contains the requested region
-    int xo, yo, req_w, req_h;
-    dr->get_region_pixels(xo, yo, req_w, req_h);
-    int w = binary_log_cap(req_w);
-    int h = binary_log_cap(req_h);
-    if (w != req_w || h != req_h) {
-        tex->_requested_w = req_w;
-        tex->_requested_h = req_h;
-        tex->_has_requested_size = true;
-    }
 
-    PixelBuffer *pb = tex->_pbuffer;
+  RECT SrcRect;
 
-    pb->set_xorg(xo);
-    pb->set_yorg(yo);
-    pb->set_xsize(w);
-    pb->set_ysize(h);
+  SrcRect.left = xo;
+  SrcRect.right = xo+w;
+  SrcRect.top = yo;
+  SrcRect.bottom = yo+h;
 
+  // now copy from fb to tex
+  hr = scrn.pD3DDevice->CopyRects(pCurRenderTarget,&SrcRect,1,pTexSurfaceLev0,NULL);
+  if(FAILED(hr)) {
+    dxgsg_cat.error() << "CopyRects failed in copy_texture" << D3DERRORSTRING(hr);
+    exit(1);
+  }
 
-    bind_texture(tc);
-    glCopyTexImage2D( GL_TEXTURE_2D, tex->get_level(),
-                      get_internal_image_format(pb->get_format()),
-                      pb->get_xorg(), pb->get_yorg(),
-                      pb->get_xsize(), pb->get_ysize(), pb->get_border() );
+  SAFE_RELEASE(pCurRenderTarget);
+  SAFE_RELEASE(pTexSurfaceLev0);
 }
-#endif
+
 
 ////////////////////////////////////////////////////////////////////
 //     Function: DXGraphicsStateGuardian::copy_texture

+ 0 - 242
panda/src/dxgsg8/dxTextureContext8.cxx

@@ -1530,248 +1530,6 @@ FillDDSurfTexturePixels(void) {
     }
     RELEASE(pMipLevel0,dxgsg,"texture",RELEASE_ONCE);
     return hr;
-
-/*  old, custom conversion and mipmap-generation stuff
-
-
-    HRESULT hr = ConvertPixBuftoDDSurf((ConversionType)_PixBufConversionType,pbuf->_image.p(),_surface);
-    if(FAILED(hr)) {
-        return hr;
-    }
-
-    DX_DECLARE_CLEAN(DDSURFACEDESC2, ddsd);
-
-    _surface->GetSurfaceDesc(&ddsd);
-
-    if(_bHasMipMaps) {
-        DWORD i,oldcurxsize,oldcurysize,curxsize,curysize,cMipMapCount=ddsd.dwMipMapCount;
-        assert(ddsd.dwMipMapCount<20);
-
-        DWORD cNumColorChannels = pbuf->get_num_components();
-
-        curxsize=ddsd.dwWidth; curysize=ddsd.dwHeight;
-
-        assert(pbuf->get_image_type()==PixelBuffer::T_unsigned_byte);    // cant handle anything else now
-
-        // all mipmap sublevels require 1/3 of total original space. alloc 1/2 for safety
-        BYTE *pMipMapPixBufSpace = new BYTE[((curxsize*curysize*cNumColorChannels)/2)+1024];
-
-        LPDIRECTDRAWSURFACE7 pCurDDSurf=_surface;
-        pCurDDSurf->AddRef();  // so final release doesnt release the surface
-
-        BYTE *pDstWord = pMipMapPixBufSpace;
-        BYTE *pLastMipLevelStart  = (BYTE *) pbuf->_image.p();
-//    clock_t  start1,finish1;
-//    start1=clock();
-        for(i=1;i<ddsd.dwMipMapCount;i++) {
-            oldcurxsize=curxsize; oldcurysize=curysize;
-            curysize = max(curysize>>1,1);
-            curxsize = max(curxsize>>1,1);
-
-            assert(!((oldcurxsize==1)&&(oldcurysize==1)));
-
-            BYTE *pSrcWord;
-            BYTE *pSrcLineStart=pLastMipLevelStart;
-
-            // inc img start to DWORD boundary
-            while(((DWORD)pDstWord) & 0x11)
-                pDstWord++;
-
-            pLastMipLevelStart = pDstWord;
-
-            DWORD x,y,cPixelSize=cNumColorChannels;
-            DWORD src_row_bytelength=oldcurxsize*cPixelSize;
-            DWORD two_src_row_bytelength=2*src_row_bytelength;
-
-        #define GENMIPMAP_DO_INTEGER_DIV    // should be a little faster, but no rounding up
-        #ifdef GENMIPMAP_DO_INTEGER_DIV
-            DWORD DivShift=2;
-            if((oldcurxsize==1)||(oldcurysize==1))
-                DivShift = 1;
-        #else
-            float numpixels_per_filter=4.0f;
-            if((oldcurxsize==1)||(oldcurysize==1))
-                numpixels_per_filter=2.0f;                
-        #endif
-
-            DWORD x_srcptr_inc = ((oldcurxsize==1)? cPixelSize: (2*cPixelSize));
-
-            // box-filter shrink down, avg 4 pixels at a time
-            for(y=0; y<curysize; y++,pSrcLineStart+=two_src_row_bytelength) {
-                pSrcWord=pSrcLineStart;
-                for(x=0; x<curxsize; x++,pSrcWord+=x_srcptr_inc,pDstWord+=cPixelSize) {
-                  // fetches, stores byte at a time.
-                  // inefficient, but works for all channel sizes
-
-                    for(int c=0;c<cPixelSize;c++) {
-                        DWORD colr;
-                        colr =  *(pSrcWord+c);
-                        if(oldcurxsize>1)  // handle 1x[X], [X]x1 cases
-                            colr += *(pSrcWord+cPixelSize+c);
-                        if(oldcurysize>1) {
-                            colr += *(pSrcWord+src_row_bytelength+c);
-                            if(oldcurxsize>1)
-                                colr += *(pSrcWord+src_row_bytelength+cPixelSize+c);
-                        }
-                        #ifdef GENMIPMAP_DO_INTEGER_DIV
-                           colr >>= DivShift;
-                        #else
-                           colr = (DWORD) ((((float)colr)/numpixels_per_filter)+0.5f);
-                        #endif
-
-                        *(pDstWord+c)=(BYTE)colr;
-                    }
-                }
-            }
-
-            // now copy pixbuf to final DD surf
-
-            DDSCAPS2 ddsCaps;
-            LPDIRECTDRAWSURFACE7 pMipLevel_DDSurf;
-            ZeroMemory(&ddsCaps,sizeof(DDSCAPS2));
-            ddsCaps.dwCaps = DDSCAPS_TEXTURE | DDSCAPS_MIPMAP;
-            ddsCaps.dwCaps2 = DDSCAPS2_MIPMAPSUBLEVEL;
-
-            hr = pCurDDSurf->GetAttachedSurface(&ddsCaps, &pMipLevel_DDSurf);
-            if(FAILED(hr)) {
-                dxgsg_cat.error() << "CreateTexture failed creating mipmaps: GetAttachedSurf hr = " << D3DERRORSTRING(hr);
-                delete [] pMipMapPixBufSpace;
-                pCurDDSurf->Release();
-                return hr;
-            }
-
-            hr = ConvertPixBuftoDDSurf((ConversionType)_PixBufConversionType,pLastMipLevelStart,pMipLevel_DDSurf);
-            if(FAILED(hr)) {
-                delete [] pMipMapPixBufSpace;
-                pCurDDSurf->Release();
-                return hr;
-            }
-
-            pCurDDSurf->Release();
-            pCurDDSurf=pMipLevel_DDSurf;
-        }
-
-        //   finish1=clock();
-        //   double elapsed_time  = (double)(finish1 - start1) / CLOCKS_PER_SEC;
-        //   cerr <<  "mipmap gen takes " << elapsed_time << " secs for this texture\n";
-
-        delete [] pMipMapPixBufSpace;
-        pCurDDSurf->Release();
-
-#ifdef _DEBUG
-        if(dx_debug_view_mipmaps) {
-#if 0
-            if(!(ddcaps.dwCaps & DDCAPS_BLTSTRETCH)) {
-                dxgsg_cat.error() << "CreateTexture failed debug-viewing mipmaps, BLT stretching not supported!  ( we need to do SW stretch) \n";
-                return hr;
-            }
-#endif
-
-            // display mipmaps on primary surf
-            HDC hTexDC;
-            LPDIRECTDRAWSURFACE7 pTextureCurrent,pTexturePrev = _surface;
-            int cury,curx;
-            HDC hScreenDC;
-            RECT scrnrect;
-            hScreenDC=GetDC(NULL);
-
-            scrnrect.left=scrnrect.top=0;
-            scrnrect.bottom=GetDeviceCaps(hScreenDC,VERTRES);
-            scrnrect.right=GetDeviceCaps(hScreenDC,HORZRES);
-            char msg[500];
-
-            pTexturePrev->AddRef();
-
-            for(i = 0,curx=scrnrect.left,cury=scrnrect.top; i < ddsd.dwMipMapCount; i++) {
-
-                DX_DECLARE_CLEAN(DDSURFACEDESC2, ddsd_cur);
-                pTexturePrev->GetSurfaceDesc(&ddsd_cur);
-
-                hr = pTexturePrev->GetDC(&hTexDC);
-                if(FAILED(hr)) {
-                    dxgsg_cat.error() << "GetDC failed hr = " << D3DERRORSTRING(hr);
-                    break;
-                }
-
-                BOOL res;
-                        // res = BitBlt(_dxgsg->_hdc,0,0,ddsd.dwWidth,ddsd.dwHeight, TexDC,0,0,SRCCOPY);
-                        // loader inverts y, so use StretchBlt to re-invert it
-                        // res = StretchBlt(_dxgsg->hdc,0,ddsd_cur.dwHeight+cury,ddsd_cur.dwWidth,-ddsd_cur.dwHeight, TexDC,0,0,ddsd_cur.dwWidth,ddsd_cur.dwHeight,SRCCOPY);
-#if 0
-                if(cNumAlphaBits>0) {
-                    BLENDFUNCTION  bf;
-                    bf.BlendOp = AC_SRC_OVER;  bf.BlendFlags=0;
-                    bf.SourceConstantAlpha=255; bf.AlphaFormat=AC_SRC_ALPHA;
-                    res = AlphaBlend(hScreenDC,curx,cury,ddsd_cur.dwWidth,ddsd_cur.dwHeight, TexDC,0,0,ddsd_cur.dwWidth,ddsd_cur.dwHeight,bf);
-                    if(!res) {
-                        PrintLastError(msg);
-                        dxgsg_cat.error() << "AlphaBlend BLT failed: "<<msg<<"\n";
-                    }
-
-                } else
-#endif
-                {
-                    res = StretchBlt(hScreenDC,curx,ddsd_cur.dwHeight+cury,ddsd_cur.dwWidth,-((int)ddsd_cur.dwHeight), hTexDC,0,0,ddsd_cur.dwWidth,ddsd_cur.dwHeight,SRCCOPY);
-                    if(!res) {
-                        PrintLastError(msg);
-                        dxgsg_cat.error() << "StretchBLT failed: "<<msg<<"\n";
-
-                    }
-                }
-        //                SetBkMode(hScreenDC, TRANSPARENT);
-                sprintf(msg,"%d",i);
-                TextOut(hScreenDC,curx+(ddsd_cur.dwWidth)/2,5+cury+ddsd_cur.dwHeight,msg,strlen(msg));
-
-                curx+=max(20,ddsd_cur.dwWidth+10);
-
-                if(curx>scrnrect.right) {
-                    curx=0;  cury+=(scrnrect.bottom-scrnrect.top)/2;
-                }
-
-                hr = pTexturePrev->ReleaseDC(hTexDC);
-
-                if(FAILED(hr)) {
-                    dxgsg_cat.error() << "tex ReleaseDC failed for mip "<<i<<" hr = " << D3DERRORSTRING(hr);
-                    break;
-                }
-
-                if(i==ddsd.dwMipMapCount-1) {
-                    pTexturePrev->Release();
-                    continue;
-                }
-
-                DDSCAPS2 ddsCaps;
-                ZeroMemory(&ddsCaps,sizeof(DDSCAPS2));
-                ddsCaps.dwCaps = DDSCAPS_TEXTURE | DDSCAPS_MIPMAP;
-                ddsCaps.dwCaps2 = DDSCAPS2_MIPMAPSUBLEVEL;
-                hr = pTexturePrev->GetAttachedSurface(&ddsCaps, &pTextureCurrent);
-                if(FAILED(hr)) {
-                    dxgsg_cat.error() << " failed displaying mipmaps: GetAttachedSurf hr = " << D3DERRORSTRING(hr);
-                }
-                        // done with the previous texture
-                pTexturePrev->Release();
-                pTexturePrev = pTextureCurrent;
-            }
-
-            ReleaseDC(0,hScreenDC);
-
-            HANDLE hArr[1];
-            MSG winmsg;
-            hArr[0]=GetStdHandle(STD_INPUT_HANDLE);
-            GetMessage(&winmsg,NULL,0,0);
-
-            int val=MsgWaitForMultipleObjects(1,hArr,TRUE,INFINITE,QS_KEY);
-            if(val==-1) {
-                PrintLastError(msg);
-                dxgsg_cat.error() << " MsgWaitForMultipleObjects returns " << val << "  " <<msg << endl;
-            } else {
-                dxgsg_cat.error() << " MsgWaitForMultipleObjects returns " << val << endl;
-            }
-        }
-#endif
-    }
-    return S_OK;    
-*/  
 }