opengl32: Implement wglUseFontOutlines.
This commit is contained in:
parent
89b3191c7c
commit
4eb4546f21
|
@ -8013,7 +8013,8 @@ fi
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
for ac_header in GL/gl.h GL/glx.h GL/glext.h
|
|
||||||
|
for ac_header in GL/gl.h GL/glx.h GL/glext.h GL/glu.h
|
||||||
do
|
do
|
||||||
as_ac_Header=`echo "ac_cv_header_$ac_header" | $as_tr_sh`
|
as_ac_Header=`echo "ac_cv_header_$ac_header" | $as_tr_sh`
|
||||||
echo "$as_me:$LINENO: checking for $ac_header" >&5
|
echo "$as_me:$LINENO: checking for $ac_header" >&5
|
||||||
|
|
|
@ -373,7 +373,7 @@ then
|
||||||
dnl Check for the presence of OpenGL
|
dnl Check for the presence of OpenGL
|
||||||
if test "x$with_opengl" != "xno"
|
if test "x$with_opengl" != "xno"
|
||||||
then
|
then
|
||||||
AC_CHECK_HEADERS(GL/gl.h GL/glx.h GL/glext.h,,,
|
AC_CHECK_HEADERS(GL/gl.h GL/glx.h GL/glext.h GL/glu.h,,,
|
||||||
[#ifdef HAVE_GL_GLX_H
|
[#ifdef HAVE_GL_GLX_H
|
||||||
# include <GL/glx.h>
|
# include <GL/glx.h>
|
||||||
#endif])
|
#endif])
|
||||||
|
|
|
@ -397,4 +397,4 @@
|
||||||
@ stdcall wglUseFontBitmapsA(long long long long)
|
@ stdcall wglUseFontBitmapsA(long long long long)
|
||||||
@ stdcall wglUseFontBitmapsW(long long long long)
|
@ stdcall wglUseFontBitmapsW(long long long long)
|
||||||
@ stdcall wglUseFontOutlinesA(long long long long long long long ptr)
|
@ stdcall wglUseFontOutlinesA(long long long long long long long ptr)
|
||||||
@ stub wglUseFontOutlinesW
|
@ stdcall wglUseFontOutlinesW(long long long long long long long ptr)
|
||||||
|
|
|
@ -34,6 +34,11 @@
|
||||||
|
|
||||||
#include "wgl_ext.h"
|
#include "wgl_ext.h"
|
||||||
#include "opengl_ext.h"
|
#include "opengl_ext.h"
|
||||||
|
#ifdef HAVE_GL_GLU_H
|
||||||
|
#undef far
|
||||||
|
#undef near
|
||||||
|
#include <GL/glu.h>
|
||||||
|
#endif
|
||||||
#include "wine/library.h"
|
#include "wine/library.h"
|
||||||
#include "wine/debug.h"
|
#include "wine/debug.h"
|
||||||
|
|
||||||
|
@ -864,6 +869,212 @@ BOOL WINAPI wglUseFontBitmapsW(HDC hdc,
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef HAVE_GL_GLU_H
|
||||||
|
|
||||||
|
static void fixed_to_double(POINTFX fixed, UINT em_size, GLdouble vertex[3])
|
||||||
|
{
|
||||||
|
vertex[0] = (fixed.x.value + (GLdouble)fixed.x.fract / (1 << 16)) / em_size;
|
||||||
|
vertex[1] = (fixed.y.value + (GLdouble)fixed.y.fract / (1 << 16)) / em_size;
|
||||||
|
vertex[2] = 0.0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tess_callback_vertex(GLvoid *vertex)
|
||||||
|
{
|
||||||
|
GLdouble *dbl = vertex;
|
||||||
|
TRACE("%f, %f, %f\n", dbl[0], dbl[1], dbl[2]);
|
||||||
|
glVertex3dv(vertex);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tess_callback_begin(GLenum which)
|
||||||
|
{
|
||||||
|
TRACE("%d\n", which);
|
||||||
|
glBegin(which);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tess_callback_end(void)
|
||||||
|
{
|
||||||
|
TRACE("\n");
|
||||||
|
glEnd();
|
||||||
|
}
|
||||||
|
|
||||||
|
/***********************************************************************
|
||||||
|
* wglUseFontOutlines_common
|
||||||
|
*/
|
||||||
|
BOOL WINAPI wglUseFontOutlines_common(HDC hdc,
|
||||||
|
DWORD first,
|
||||||
|
DWORD count,
|
||||||
|
DWORD listBase,
|
||||||
|
FLOAT deviation,
|
||||||
|
FLOAT extrusion,
|
||||||
|
int format,
|
||||||
|
LPGLYPHMETRICSFLOAT lpgmf,
|
||||||
|
BOOL unicode)
|
||||||
|
{
|
||||||
|
UINT glyph;
|
||||||
|
const MAT2 identity = {{0,1},{0,0},{0,0},{0,1}};
|
||||||
|
GLUtesselator *tess;
|
||||||
|
LOGFONTW lf;
|
||||||
|
HFONT old_font, unscaled_font;
|
||||||
|
UINT em_size = 1024;
|
||||||
|
RECT rc;
|
||||||
|
|
||||||
|
TRACE("(%p, %ld, %ld, %ld, %f, %f, %d, %p, %s)\n", hdc, first, count,
|
||||||
|
listBase, deviation, extrusion, format, lpgmf, unicode ? "W" : "A");
|
||||||
|
|
||||||
|
|
||||||
|
ENTER_GL();
|
||||||
|
tess = gluNewTess();
|
||||||
|
if(tess)
|
||||||
|
{
|
||||||
|
gluTessCallback(tess, GLU_TESS_VERTEX, (_GLUfuncptr)tess_callback_vertex);
|
||||||
|
gluTessCallback(tess, GLU_TESS_BEGIN, (_GLUfuncptr)tess_callback_begin);
|
||||||
|
gluTessCallback(tess, GLU_TESS_END, tess_callback_end);
|
||||||
|
}
|
||||||
|
LEAVE_GL();
|
||||||
|
|
||||||
|
if(!tess) return FALSE;
|
||||||
|
|
||||||
|
GetObjectW(GetCurrentObject(hdc, OBJ_FONT), sizeof(lf), &lf);
|
||||||
|
rc.left = rc.right = rc.bottom = 0;
|
||||||
|
rc.top = em_size;
|
||||||
|
DPtoLP(hdc, (POINT*)&rc, 2);
|
||||||
|
lf.lfHeight = -abs(rc.top - rc.bottom);
|
||||||
|
lf.lfOrientation = lf.lfEscapement = 0;
|
||||||
|
unscaled_font = CreateFontIndirectW(&lf);
|
||||||
|
old_font = SelectObject(hdc, unscaled_font);
|
||||||
|
|
||||||
|
for (glyph = first; glyph < first + count; glyph++)
|
||||||
|
{
|
||||||
|
DWORD needed;
|
||||||
|
GLYPHMETRICS gm;
|
||||||
|
BYTE *buf;
|
||||||
|
TTPOLYGONHEADER *pph;
|
||||||
|
TTPOLYCURVE *ppc;
|
||||||
|
GLdouble *vertices;
|
||||||
|
|
||||||
|
if(unicode)
|
||||||
|
needed = GetGlyphOutlineW(hdc, glyph, GGO_NATIVE, &gm, 0, NULL, &identity);
|
||||||
|
else
|
||||||
|
needed = GetGlyphOutlineA(hdc, glyph, GGO_NATIVE, &gm, 0, NULL, &identity);
|
||||||
|
|
||||||
|
if(needed == GDI_ERROR)
|
||||||
|
goto error;
|
||||||
|
|
||||||
|
buf = HeapAlloc(GetProcessHeap(), 0, needed);
|
||||||
|
vertices = HeapAlloc(GetProcessHeap(), 0, needed / sizeof(POINTFX) * 3 * sizeof(GLdouble));
|
||||||
|
|
||||||
|
if(unicode)
|
||||||
|
GetGlyphOutlineW(hdc, glyph, GGO_NATIVE, &gm, needed, buf, &identity);
|
||||||
|
else
|
||||||
|
GetGlyphOutlineA(hdc, glyph, GGO_NATIVE, &gm, needed, buf, &identity);
|
||||||
|
|
||||||
|
TRACE("glyph %d\n", glyph);
|
||||||
|
|
||||||
|
if(lpgmf)
|
||||||
|
{
|
||||||
|
lpgmf->gmfBlackBoxX = gm.gmBlackBoxX / em_size;
|
||||||
|
lpgmf->gmfBlackBoxY = gm.gmBlackBoxY / em_size;
|
||||||
|
lpgmf->gmfptGlyphOrigin.x = gm.gmptGlyphOrigin.x / em_size;
|
||||||
|
lpgmf->gmfptGlyphOrigin.y = gm.gmptGlyphOrigin.y / em_size;
|
||||||
|
lpgmf->gmfCellIncX = gm.gmCellIncX / em_size;
|
||||||
|
lpgmf->gmfCellIncY = gm.gmCellIncY / em_size;
|
||||||
|
TRACE("%fx%f at %f,%f inc %f,%f\n", lpgmf->gmfBlackBoxX, lpgmf->gmfBlackBoxY,
|
||||||
|
lpgmf->gmfptGlyphOrigin.x, lpgmf->gmfptGlyphOrigin.y, lpgmf->gmfCellIncX, lpgmf->gmfCellIncY);
|
||||||
|
lpgmf++;
|
||||||
|
}
|
||||||
|
|
||||||
|
ENTER_GL();
|
||||||
|
glNewList(listBase++, GL_COMPILE);
|
||||||
|
gluTessBeginPolygon(tess, NULL);
|
||||||
|
|
||||||
|
pph = (TTPOLYGONHEADER*)buf;
|
||||||
|
while((BYTE*)pph < buf + needed)
|
||||||
|
{
|
||||||
|
TRACE("\tstart %d, %d\n", pph->pfxStart.x.value, pph->pfxStart.y.value);
|
||||||
|
|
||||||
|
gluTessBeginContour(tess);
|
||||||
|
|
||||||
|
fixed_to_double(pph->pfxStart, em_size, vertices);
|
||||||
|
gluTessVertex(tess, vertices, vertices);
|
||||||
|
vertices += 3;
|
||||||
|
|
||||||
|
ppc = (TTPOLYCURVE*)((char*)pph + sizeof(*pph));
|
||||||
|
while((char*)ppc < (char*)pph + pph->cb)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
switch(ppc->wType) {
|
||||||
|
case TT_PRIM_LINE:
|
||||||
|
for(i = 0; i < ppc->cpfx; i++)
|
||||||
|
{
|
||||||
|
TRACE("\t\tline to %d, %d\n", ppc->apfx[i].x.value, ppc->apfx[i].y.value);
|
||||||
|
fixed_to_double(ppc->apfx[i], em_size, vertices);
|
||||||
|
gluTessVertex(tess, vertices, vertices);
|
||||||
|
vertices += 3;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case TT_PRIM_QSPLINE:
|
||||||
|
for(i = 0; i < ppc->cpfx/2; i++)
|
||||||
|
{
|
||||||
|
/* FIXME just connecting the control points for now */
|
||||||
|
TRACE("\t\tcurve %d,%d %d,%d\n",
|
||||||
|
ppc->apfx[i * 2].x.value, ppc->apfx[i * 3].y.value,
|
||||||
|
ppc->apfx[i * 2 + 1].x.value, ppc->apfx[i * 3 + 1].y.value);
|
||||||
|
fixed_to_double(ppc->apfx[i * 2], em_size, vertices);
|
||||||
|
gluTessVertex(tess, vertices, vertices);
|
||||||
|
vertices += 3;
|
||||||
|
fixed_to_double(ppc->apfx[i * 2 + 1], em_size, vertices);
|
||||||
|
gluTessVertex(tess, vertices, vertices);
|
||||||
|
vertices += 3;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
ERR("\t\tcurve type = %d\n", ppc->wType);
|
||||||
|
gluTessEndContour(tess);
|
||||||
|
goto error_in_list;
|
||||||
|
}
|
||||||
|
|
||||||
|
ppc = (TTPOLYCURVE*)((char*)ppc + sizeof(*ppc) +
|
||||||
|
(ppc->cpfx - 1) * sizeof(POINTFX));
|
||||||
|
}
|
||||||
|
gluTessEndContour(tess);
|
||||||
|
pph = (TTPOLYGONHEADER*)((char*)pph + pph->cb);
|
||||||
|
}
|
||||||
|
|
||||||
|
error_in_list:
|
||||||
|
gluTessEndPolygon(tess);
|
||||||
|
glEndList();
|
||||||
|
LEAVE_GL();
|
||||||
|
HeapFree(GetProcessHeap(), 0, buf);
|
||||||
|
HeapFree(GetProcessHeap(), 0, vertices);
|
||||||
|
}
|
||||||
|
|
||||||
|
error:
|
||||||
|
DeleteObject(SelectObject(hdc, old_font));
|
||||||
|
gluDeleteTess(tess);
|
||||||
|
return TRUE;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#else /* HAVE_GL_GLU_H */
|
||||||
|
|
||||||
|
BOOL WINAPI wglUseFontOutlines_common(HDC hdc,
|
||||||
|
DWORD first,
|
||||||
|
DWORD count,
|
||||||
|
DWORD listBase,
|
||||||
|
FLOAT deviation,
|
||||||
|
FLOAT extrusion,
|
||||||
|
int format,
|
||||||
|
LPGLYPHMETRICSFLOAT lpgmf,
|
||||||
|
BOOL unicode)
|
||||||
|
{
|
||||||
|
FIXME("Unable to compile in wglUseFontOutlines support without GL/glu.h\n");
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif /* HAVE_GL_GLU_H */
|
||||||
|
|
||||||
/***********************************************************************
|
/***********************************************************************
|
||||||
* wglUseFontOutlinesA (OPENGL32.@)
|
* wglUseFontOutlinesA (OPENGL32.@)
|
||||||
*/
|
*/
|
||||||
|
@ -874,10 +1085,24 @@ BOOL WINAPI wglUseFontOutlinesA(HDC hdc,
|
||||||
FLOAT deviation,
|
FLOAT deviation,
|
||||||
FLOAT extrusion,
|
FLOAT extrusion,
|
||||||
int format,
|
int format,
|
||||||
LPGLYPHMETRICSFLOAT lpgmf) {
|
LPGLYPHMETRICSFLOAT lpgmf)
|
||||||
FIXME("(): stub !\n");
|
{
|
||||||
|
return wglUseFontOutlines_common(hdc, first, count, listBase, deviation, extrusion, format, lpgmf, FALSE);
|
||||||
|
}
|
||||||
|
|
||||||
return FALSE;
|
/***********************************************************************
|
||||||
|
* wglUseFontOutlinesW (OPENGL32.@)
|
||||||
|
*/
|
||||||
|
BOOL WINAPI wglUseFontOutlinesW(HDC hdc,
|
||||||
|
DWORD first,
|
||||||
|
DWORD count,
|
||||||
|
DWORD listBase,
|
||||||
|
FLOAT deviation,
|
||||||
|
FLOAT extrusion,
|
||||||
|
int format,
|
||||||
|
LPGLYPHMETRICSFLOAT lpgmf)
|
||||||
|
{
|
||||||
|
return wglUseFontOutlines_common(hdc, first, count, listBase, deviation, extrusion, format, lpgmf, TRUE);
|
||||||
}
|
}
|
||||||
|
|
||||||
const GLubyte * internal_glGetString(GLenum name) {
|
const GLubyte * internal_glGetString(GLenum name) {
|
||||||
|
|
|
@ -206,6 +206,9 @@
|
||||||
/* Define to 1 if you have the <GL/glext.h> header file. */
|
/* Define to 1 if you have the <GL/glext.h> header file. */
|
||||||
#undef HAVE_GL_GLEXT_H
|
#undef HAVE_GL_GLEXT_H
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <GL/glu.h> header file. */
|
||||||
|
#undef HAVE_GL_GLU_H
|
||||||
|
|
||||||
/* Define to 1 if you have the <GL/glx.h> header file. */
|
/* Define to 1 if you have the <GL/glx.h> header file. */
|
||||||
#undef HAVE_GL_GLX_H
|
#undef HAVE_GL_GLX_H
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue