翻译过来后,在wglUseFontOutlines时,出错,错误信息为:存储空间不足,无法完成次操作。为什么?BCB代码,执行正确:
//---------------------------------------------------------------------------
#include <vcl.h>
#include <gl/gl.h>
#pragma hdrstop
#include "stdlib.h"
#include "main.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
void CreateFont(void);
 GLYPHMETRICSFLOAT pgmf[1];
int x,y,z;void glDrawString(unsigned char *str)
{
 HDC hDC=wglGetCurrentDC();
 DWORD dwChar;
 int ListNum;
 for(size_t i=0;i<strlen((char *)str);i++)
   {
     if(IsDBCSLeadByte(str[i]))
       {dwChar=(DWORD)((str[i]<<8)|str[i+1]);i++;}
     else dwChar=str[i];
     ListNum=glGenLists(1);
     wglUseFontOutlines(hDC,dwChar,1,ListNum,0.0,0.1,WGL_FONT_POLYGONS,pgmf);
     glCallList(ListNum);
     glDeleteLists(ListNum,1);
   }
}
void CreateFont(void)
{
 HFONT         HFont,HOldFont=0;
 LOGFONT       LogFont;
 GetObject(Form1->Font->Handle,sizeof(LOGFONT),&LogFont);
 HFont = CreateFontIndirect(&LogFont);
 HOldFont=SelectObject (Form1->hDC, HFont);
 DeleteObject(HOldFont);
}
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner)
    : TForm(Owner)
{
    hDC=GetDC(Handle);          //茆取一个DC,TForm1.Handle中保存有Form的窗口句柄
    SetDCPixelFormat(hDC);      //调整该DC的象素格式
    hRC=wglCreateContext(hDC);  //用这种DC去创建一个RC
    wglMakeCurrent(hDC,hRC);    //指定当前DC、当前RC为hDC、hRC
    glEnable(GL_COLOR_MATERIAL);
    randomize();
    glColor3f(random(255)/255.0,random(255)/255.0,random(255)/255.0);    CreateFont();
}
//---------------------------------------------------------------------------
void __fastcall TForm1::CreateParams(TCreateParams& Params)
{
    TForm::CreateParams(Params);                //调用原有函数预处理
    Params.Style|=WS_CLIPCHILDREN|WS_CLIPSIBLINGS;//加上必要的属性
}
//---------------------------------------------------------------------------
void __fastcall TForm1::SetDCPixelFormat(HDC hDC)
{   //本函数用于调整DC的象素格式,如缓冲区、颜色数等
    //先不深究,只要知道它的作用就行
int nPixelFormat;static PIXELFORMATDESCRIPTOR pfd = {
  sizeof(PIXELFORMATDESCRIPTOR), // Size of this structure
  1,        // Version of this structure
  PFD_DRAW_TO_WINDOW |   // Draw to Window (not to bitmap)
  PFD_SUPPORT_OPENGL |   // Support OpenGL calls in window
  PFD_DOUBLEBUFFER,    // Double buffered mode
  PFD_TYPE_RGBA,     // RGBA Color mode
  24,        // Want 24bit color
  0,0,0,0,0,0,     // Not used to select mode
  0,0,       // Not used to select mode
  0,0,0,0,0,      // Not used to select mode
  32,        // Size of depth buffer
  0,        // Not used to select mode
  0,        // Not used to select mode
  PFD_MAIN_PLANE,     // Draw in main plane
  0,        // Not used to select mode
  0,0,0 };      // Not used to select mode// Choose a pixel format that best matches that described in pfd
nPixelFormat = ChoosePixelFormat(hDC, &pfd);// Set the pixel format for the device context
SetPixelFormat(hDC, nPixelFormat, &pfd);
}
//---------------------------------------------------------------------------
void RenderScence(void)
{
//try to draw fonts.
byte cstr[]={"OpenGL测试"};
//glTranslatef(-1,-1,0);
glScalef(0.2,0.2,1);
glDrawString(cstr);
}//---------------------------------------------------------------------------
void __fastcall TForm1::FormPaint(TObject *Sender)
{   //该Form的绘制响应函数
    glClearColor(0.5,0.7,0.9,1.0); //指定背景颜色(依次为RGBA)
    glClear(GL_COLOR_BUFFER_BIT); //用背景色清窗口  glPushMatrix();
    glRotatef(x,1.0,0.0,0.0);
    glRotatef(y,0.0,1.0,0.0);
    glRotatef(z,0.0,0.0,1.0);
    RenderScence();
  glPopMatrix();    SwapBuffers(hDC);
      //切交缓冲区,这就是可以启动图形库处理流程并得相应结果的两条命令之一
      //如果当前RC相联DC具有DoubleBuffer的PixelFormat则用本命令
      //否则就是单缓冲DC,用glFlush(void)进行更新。
}
//---------------------------------------------------------------------------
void __fastcall TForm1::FormDestroy(TObject *Sender)
{
    wglMakeCurrent(NULL,NULL);  //取消当前RC和当前DC
    wglDeleteContext(hRC);      //删除该RC
//    DeleteObject(hDC);          //删除Windows DC。!!交给VCL系统自动完成。
}
//---------------------------------------------------------------------------void __fastcall TForm1::Button1Click(TObject *Sender)
{
 Timer1->Enabled=false;
 x=y=z=0;
 FormPaint(Sender);
 fd->Execute();
 Form1->Font=fd->Font;
 CreateFont();
 Timer1->Enabled=true;
}
//---------------------------------------------------------------------------void __fastcall TForm1::Timer1Timer(TObject *Sender)
{
  x=(x+random(10))%360;
  y=(y+random(10))%360;
  z=(z+random(5))%360;
  FormPaint(Sender);
}
//---------------------------------------------------------------------------

解决方案 »

  1.   

    翻译的代码:unit Unit1;interfaceuses
      Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
      Dialogs, OpenGL, StdCtrls;type
      TForm1 = class(TForm)
        Button1: TButton;
        FontDialog1: TFontDialog;
        procedure FormCreate(Sender: TObject);
        procedure FormPaint(Sender: TObject);
        procedure FormDestroy(Sender: TObject);
        procedure Button1Click(Sender: TObject);
      private
        m_RC: HGLRC;
        m_dc: HDC;
        pgmf : array [0..0] of GLYPHMETRICSFLOAT;
            procedure SetDCPixelFormat(_dc : HDC);
        procedure CreateFont;
        procedure glDrawString_2(const str: string);    
        { Private declarations }
      public
        { Public declarations }
      end;var
      Form1: TForm1;implementation{$R *.dfm}procedure TForm1.FormCreate(Sender: TObject);
    var
      h:HDC;
    begin
      h := GetDC(handle);
      //Canvas.Handle
      SetDCPixelFormat(h);      //调整该DC的象素格式
      m_RC :=wglCreateContext(h);  //用这种DC去创建一个RC
      wglMakeCurrent(h,m_RC);    //指定当前DC、当前RC为hDC、hRC
      glEnable(GL_COLOR_MATERIAL);
      CreateFont;
      //glViewPort(0, 0, 200, 200);
    end;
    procedure TForm1.SetDCPixelFormat(_dc: HDC);
    var
      nPixelFormat :integer;
      pfd: PIXELFORMATDESCRIPTOR ;
    begin
        with pfd do     // 告诉Windows 我们要什么
        begin
          nSize:= SizeOf( PIXELFORMATDESCRIPTOR ); // 象素格式描述表结构的大小
          nVersion:= 1; // 版本号?
          dwFlags:= PFD_DRAW_TO_WINDOW // 格式必须支持窗口
            or PFD_SUPPORT_OPENGL // 格式必须支持OpenGL
            or PFD_DOUBLEBUFFER; // 格式必须支持双缓存
          iPixelType:= PFD_TYPE_RGBA; // 请求RGBA格式
          cColorBits:= 24; // 选择颜色深度
          cRedBits:= 0; // 忽略颜色位
          cRedShift:= 0;
          cGreenBits:= 0;
          cGreenShift:= 0;
          cBlueBits:= 0;
          cBlueShift:= 0;
          cAlphaBits:= 0; // 不用Alpha 缓存
          cAlphaShift:= 0; // 忽略移位位
          cAccumBits:= 0; // 不用累积缓存
          cAccumRedBits:= 0; // 忽略累积位
          cAccumGreenBits:= 0;
          cAccumBlueBits:= 0;
          cAccumAlphaBits:= 0;
          cDepthBits:= 32; // 16位深度缓存
          cStencilBits:= 0; // 不用模板缓存
          cAuxBuffers:= 0; // 不用辅助缓存
          iLayerType:= PFD_MAIN_PLANE; // 主绘制层
          bReserved:= 0; // 保留
          dwLayerMask:= 0; // 忽略层掩码
          dwVisibleMask:= 0;
          dwDamageMask:= 0;
        end;
        nPixelFormat := ChoosePixelFormat(_dc, @pfd);
        SetPixelFormat(_dc, nPixelFormat, @pfd);
    end;procedure TForm1.CreateFont;
    var
      hf, old_hf: HFont;
      aLogFont: LOGFONT;
    begin
      // 取字体信息
      GetObject(Font.Handle, sizeof(LOGFONT), @aLogFont);
      // 建立字体
      hf := CreateFontIndirect(aLogFont);
      // 选用字体
      Old_hf := windows.SelectObject(Handle, hf);
      //Old_hf := windows.SelectObject(Canvas.Handle, hf);
      // 清除已经不用的字体
      DeleteObject(Old_HF);
    end;procedure TForm1.FormPaint(Sender: TObject);
    begin
        glClearColor(0,0,0,1.0); //指定背景颜色(依次为RGBA)
        glClear(GL_COLOR_BUFFER_BIT); //用背景色清窗口    glPushMatrix();
        {
        glRotatef(0,1.0,0.0,0.0);
        glRotatef(0,0.0,1.0,0.0);
        glRotatef(0,0.0,0.0,1.0);
        glScalef(0.2,0.2,1);
        }
        //RenderScence();
        
        glScalef(0.2,0.2,1);
        glDrawString_2('OpenGL测试');
        
        glPopMatrix();
        SwapBuffers(Canvas.Handle);
    end;
    procedure TForm1.glDrawString_2(const str: string);
    var
      h: HDC;
      dwChar : DWORD;
      i, ListNum: integer ;
      bln :boolean;
      err :DWORD;
      ss : string;
    begin
      h := wglGetCurrentDC();
      i := 1;
      
      while i <= Length(str) do begin
        if IsDBCSLeadByte(Ord(str[i])) then begin
          dwChar := ((Ord(str[i]) shl 8) or Ord(str[i + 1]));
          i :=i + 1 ;
        end
        else
          dwChar := Ord(str[i]);    ListNum :=glGenLists(1);
        err := GetLastError;
        //ShowMessage(SysErrorMessage(err));
        
        bln := wglUseFontOutlines(Handle,dwChar,1,ListNum,0.0,0.1,WGL_FONT_POLYGONS,@pgmf);    err := GetLastError;
        //ShowMessage(SysErrorMessage(err));
        ss := SysErrorMessage(err);    glCallList(ListNum);
        glDeleteLists(ListNum,1);
        break;
        i :=i + 1 ;
      end;
    end;procedure TForm1.FormDestroy(Sender: TObject);
    begin
     wglMakeCurrent(0,0);  //取消当前RC和当前DC
     wglDeleteContext(m_RC);
    end;procedure TForm1.Button1Click(Sender: TObject);
    begin
      if FontDialog1.Execute then begin
        Font := FontDialog1.Font;
        CreateFont;
        Repaint;
      end;
    end;end.
      

  2.   

    问题已解决。wglUseFontOutlines的handle传错了,应该传Canvas.Handle.
    结贴了,要分的快来啊。