6725214: D3D: forward-port the new pipeline from 6u10

Forward port of the new Direct3D 9 rendering pipeline from 6u10. Also includes fixes for 6690659 6689025 6658398 6596234.

Reviewed-by: campbell, prr
This commit is contained in:
Dmitri Trembovetski 2008-07-18 10:48:44 -07:00
parent 6acd06f8b5
commit e4c9db984f
231 changed files with 36094 additions and 16894 deletions

View File

@ -1,5 +1,5 @@
#
# Copyright 1997-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -371,7 +371,7 @@ ifeq ($(PLATFORM), windows)
# ISHIELD_TEMP_MIN is the difference of an empty C:\TEMP vs. one after a
# bundles build on windows.
ISHIELD_TEMP_MIN=250000
REQUIRED_DXSDK_VER = 0x0700
REQUIRED_DXSDK_VER = 0x0900
OS_VENDOR = Microsoft
# How much RAM does this machine have:
ifeq ($(USING_CYGWIN),true)

View File

@ -1,5 +1,5 @@
#
# Copyright 2005-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 2005-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -91,7 +91,7 @@ ifeq ($(PLATFORM), windows)
else \
$(ECHO) "Unknown Windows Version"; \
fi)
DXSDK_VER := $(shell $(EGREP) DIRECTDRAW_VERSION $(DXSDK_INCLUDE_PATH)/ddraw.h 2>&1 | \
DXSDK_VER := $(shell $(EGREP) DIRECT3D_VERSION $(DXSDK_INCLUDE_PATH)/d3d9.h 2>&1 | \
$(EGREP) "\#define" | $(NAWK) '{print $$3}')
endif
@ -1257,7 +1257,7 @@ sane-unzip_version:
######################################################
sane-dxsdk:
ifeq ($(PLATFORM), windows)
@if [ ! -r $(DXSDK_INCLUDE_PATH)/ddraw.h ]; then \
@if [ ! -r $(DXSDK_INCLUDE_PATH)/d3d9.h ]; then \
$(ECHO) "ERROR: You do not have access to a valid DirectX SDK Include dir.\n" \
" The value of DXSDK_INCLUDE_PATH must point a valid DX SDK dir.\n" \
" Please check your access to \n" \
@ -1286,7 +1286,7 @@ ifeq ($(PLATFORM), windows)
" This may result in a build failure.\n" \
" The DirectX SDK Include dir was obtained from the following location:\n" \
" $(DXSDK_INCLUDE_PATH) \n" \
" Please change your DirectX SDK to version 7 or 9 (Summer 2004 Update or newer).\n" \
" Please change your DirectX SDK to version 9 (Summer 2004 Update or newer).\n" \
" Microsoft DirectX 9 SDK can be downloaded from the following location:\n" \
" http://msdn.microsoft.com/library/default.asp?url=/downloads/list/directx.asp\n" \
" Or http://www.microsoft.com/directx\n" \

View File

@ -1,5 +1,5 @@
#
# Copyright 1997-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -112,29 +112,11 @@ FILES_cpp = \
GDIHashtable.cpp \
Devices.cpp \
ObjectList.cpp \
DDBlitLoops.cpp \
DDRenderer.cpp \
GDIBlitLoops.cpp \
GDIRenderer.cpp \
Win32OffScreenSurfaceData.cpp \
Win32SurfaceData.cpp \
WinBackBufferSurfaceData.cpp \
GDIWindowSurfaceData.cpp \
WindowsFlags.cpp \
WBufferStrategy.cpp \
WPrinterJob.cpp \
ddrawUtils.cpp \
dxCapabilities.cpp \
dxInit.cpp \
RegistryKey.cpp \
D3DBlitLoops.cpp \
D3DContext.cpp \
D3DMaskFill.cpp \
D3DRenderer.cpp \
D3DRuntimeTest.cpp \
D3DSurfaceData.cpp \
D3DTextRenderer_md.cpp \
D3DUtils.cpp \
ddrawObject.cpp \
awt_AWTEvent.cpp \
awt_BitmapUtil.cpp \
awt_Brush.cpp \
@ -199,6 +181,23 @@ FILES_cpp = \
awt_Mlib.cpp \
awt_new.cpp \
awt_TrayIcon.cpp \
ShaderList.cpp \
D3DBlitLoops.cpp \
D3DBufImgOps.cpp \
D3DContext.cpp \
D3DGlyphCache.cpp \
D3DGraphicsDevice.cpp \
D3DMaskBlit.cpp \
D3DMaskCache.cpp \
D3DMaskFill.cpp \
D3DPipelineManager.cpp \
D3DPaints.cpp \
D3DRenderer.cpp \
D3DRenderQueue.cpp \
D3DResourceManager.cpp \
D3DSurfaceData.cpp \
D3DTextRenderer.cpp \
D3DVertexCacher.cpp \
ShellFolder2.cpp \
ThemeReader.cpp \
ComCtl32Util.cpp \

View File

@ -1,5 +1,5 @@
#
# Copyright 2000-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 2000-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -49,6 +49,9 @@ FILES_export = \
sun/java2d/loops/TransformHelper.java \
sun/java2d/loops/GraphicsPrimitiveMgr.java \
sun/java2d/loops/GraphicsPrimitive.java \
sun/java2d/pipe/hw/AccelSurface.java \
sun/java2d/pipe/hw/AccelDeviceEventNotifier.java \
sun/java2d/pipe/hw/ContextCapabilities.java \
sun/awt/image/ImagingLib.java \
sun/java2d/SurfaceData.java \
sun/java2d/SunGraphics2D.java \
@ -107,6 +110,7 @@ FILES_export = \
sun/java2d/pipe/BufferedContext.java \
sun/java2d/pipe/BufferedMaskBlit.java \
sun/java2d/pipe/BufferedOpCodes.java \
sun/java2d/pipe/BufferedMaskBlit.java \
sun/java2d/pipe/BufferedPaints.java \
sun/java2d/pipe/BufferedRenderPipe.java \
sun/java2d/pipe/BufferedTextPipe.java \

View File

@ -1,5 +1,5 @@
#
# Copyright 2000-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 2000-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -125,14 +125,9 @@ FILES_export2 = \
sun/awt/image/BufImgSurfaceData.java \
sun/awt/image/DataBufferNative.java \
sun/awt/shell/Win32ShellFolder2.java \
sun/java2d/windows/DDBlitLoops.java \
sun/java2d/windows/DDRenderer.java \
sun/java2d/windows/DDScaleLoops.java \
sun/java2d/windows/GDIBlitLoops.java \
sun/java2d/windows/GDIRenderer.java \
sun/java2d/windows/Win32OffScreenSurfaceData.java \
sun/java2d/windows/Win32SurfaceData.java \
sun/java2d/windows/WinBackBufferSurfaceData.java \
sun/java2d/windows/GDIWindowSurfaceData.java \
sun/java2d/windows/WindowsFlags.java \
sun/java2d/loops/Blit.java \
sun/java2d/loops/BlitBg.java \
@ -219,6 +214,9 @@ FILES_export3 = \
sun/awt/windows/WBufferStrategy.java \
sun/awt/windows/WTrayIconPeer.java \
sun/awt/image/ImagingLib.java \
sun/java2d/pipe/hw/AccelSurface.java \
sun/java2d/pipe/hw/AccelDeviceEventNotifier.java \
sun/java2d/pipe/hw/ContextCapabilities.java \
sun/java2d/pipe/BufferedContext.java \
sun/java2d/pipe/BufferedMaskBlit.java \
sun/java2d/pipe/BufferedOpCodes.java \
@ -229,13 +227,6 @@ FILES_export3 = \
sun/java2d/pipe/ShapeSpanIterator.java \
sun/java2d/pipe/SpanClipRenderer.java \
sun/java2d/pipe/RegionIterator.java \
sun/java2d/d3d/D3DBlitLoops.java \
sun/java2d/d3d/D3DMaskFill.java \
sun/java2d/d3d/D3DRenderer.java \
sun/java2d/d3d/D3DContext.java \
sun/java2d/d3d/D3DSurfaceData.java \
sun/java2d/d3d/D3DBackBufferSurfaceData.java \
sun/java2d/d3d/D3DTextRenderer.java \
sun/java2d/opengl/OGLBlitLoops.java \
sun/java2d/opengl/OGLContext.java \
sun/java2d/opengl/OGLMaskFill.java \
@ -245,4 +236,13 @@ FILES_export3 = \
sun/java2d/opengl/OGLSurfaceData.java \
sun/java2d/opengl/OGLTextRenderer.java \
sun/java2d/opengl/WGLGraphicsConfig.java \
sun/java2d/opengl/WGLSurfaceData.java
sun/java2d/opengl/WGLSurfaceData.java \
sun/java2d/d3d/D3DBlitLoops.java \
sun/java2d/d3d/D3DGraphicsDevice.java \
sun/java2d/d3d/D3DSurfaceData.java \
sun/java2d/d3d/D3DMaskFill.java \
sun/java2d/d3d/D3DPaints.java \
sun/java2d/d3d/D3DRenderQueue.java \
sun/java2d/d3d/D3DRenderer.java \
sun/java2d/d3d/D3DTextRenderer.java \
sun/java2d/d3d/D3DContext.java

View File

@ -1,5 +1,5 @@
#
# Copyright 1995-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 1995-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -69,7 +69,6 @@ include FILES_export_windows.gmk
#
AUTO_JAVA_PRUNE += RemoteOffScreenImage.java
OTHER_CXXFLAGS += -DD3D_OVERLOADS
OTHER_CFLAGS += $(GX_OPTION) -DMLIB_NO_LIBSUNMATH -DUNICODE -D_UNICODE
OTHER_CXXFLAGS += $(GX_OPTION) -DUNICODE -D_UNICODE
@ -448,7 +447,7 @@ OTHER_INCLUDES += -I$(CLASSHDRDIR)/../../java/jvm \
-I$(SHARE_SRC)/native/sun/dc/path \
-I$(SHARE_SRC)/native/sun/dc/doe \
-I$(SHARE_SRC)/native/sun/awt/debug \
-I$(PLATFORM_SRC)/native/sun/awt \
-I$(PLATFORM_SRC)/native/sun/awt
# -I$(WINAWT_COMMON_native)
# this is only required for compiling )/native/sun/awt/medialib/*.c files

File diff suppressed because one or more lines are too long

View File

@ -1,5 +1,5 @@
#
# Copyright 2001-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 2001-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -417,12 +417,14 @@ SUNWprivate_1.1 {
Java_sun_java2d_x11_X11SurfaceData_XSetForeground;
Java_sun_java2d_x11_X11SurfaceData_XSetGraphicsExposures;
Java_sun_java2d_opengl_OGLContext_getOGLIdString;
Java_sun_java2d_opengl_OGLMaskFill_maskFill;
Java_sun_java2d_opengl_OGLRenderer_drawPoly;
Java_sun_java2d_opengl_OGLRenderQueue_flushBuffer;
Java_sun_java2d_opengl_OGLSurfaceData_initTexture;
Java_sun_java2d_opengl_OGLSurfaceData_initFBObject;
Java_sun_java2d_opengl_OGLSurfaceData_initFlipBackbuffer;
Java_sun_java2d_opengl_OGLSurfaceData_getTextureID;
Java_sun_java2d_opengl_OGLSurfaceData_getTextureTarget;
Java_sun_java2d_opengl_OGLTextRenderer_drawGlyphList;
Java_sun_java2d_opengl_GLXGraphicsConfig_getGLXConfigInfo;
@ -511,6 +513,7 @@ SUNWprivate_1.1 {
AWTCharAscent;
AWTCharDescent;
AWTDrawGlyphList;
AccelGlyphCache_RemoveAllCellInfos;
local:
*;

View File

@ -1,5 +1,5 @@
#
# Copyright 1997-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -137,7 +137,6 @@ SUNWprivate_1.1 {
RegionToYXBandedRectangles;
GrPrim_CompGetXorInfo;
GrPrim_CompGetAlphaInfo;
GrPrim_ColorGetRGB;
J2dTraceImpl;
J2dTraceInit;
img_makePalette;

View File

@ -1,5 +1,5 @@
#
# Copyright 2002-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 2002-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -568,6 +568,7 @@ SUNWprivate_1.1 {
AWTCharAscent;
AWTCharDescent;
AWTDrawGlyphList;
AccelGlyphCache_RemoveAllCellInfos;
local:
*;

View File

@ -1,5 +1,5 @@
#
# Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -116,7 +116,7 @@ ifeq ($(PLATFORM),windows)
FILES_c_platform = fontpath.c \
lcdglyph.c
FILES_cpp_platform = D3DTextRenderer.cpp
FILES_cpp_platform =
else
FILES_c_platform = X11FontScaler.c \
X11TextRenderer.c

View File

@ -1,5 +1,5 @@
#
# Copyright 1997-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -85,8 +85,6 @@ ifeq ($(PLATFORM), windows)
OTHER_CFLAGS += -DCC_NOEX
OTHER_CXXFLAGS += -DCC_NOEX
FILES_export += sun/java2d/d3d/D3DTextRenderer.java
else # PLATFORM unix
FILES_export += \
@ -171,7 +169,6 @@ endif
ifeq ($(PLATFORM), windows)
vpath %.cpp $(PLATFORM_SRC)/native/sun/windows
vpath %.cpp $(PLATFORM_SRC)/native/sun/java2d/d3d
else # PLATFORM
#
@ -206,7 +203,6 @@ CPPFLAGS += -I$(SHARE_SRC)/native/$(PKGDIR) \
-I$(TEMPDIR)/../../sun.awt/awt/CClassHeaders
ifeq ($(PLATFORM), windows)
CPPFLAGS += -I$(PLATFORM_SRC)/native/sun/windows \
-I$(PLATFORM_SRC)/native/sun/java2d/d3d
CPPFLAGS += -I$(PLATFORM_SRC)/native/sun/windows
endif

View File

@ -1,5 +1,5 @@
#
# Copyright 2001-2006 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 2001-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -99,6 +99,7 @@ SUNWprivate_1.1 {
AWTCharAscent;
AWTCharDescent;
AWTDrawGlyphList;
AccelGlyphCache_RemoveAllCellInfos;
local:

View File

@ -1 +1 @@
$(OBJDIR)/jawt.obj:: $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_AlphaComposite.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_AWTEvent.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_Component.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_Dimension.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_event_FocusEvent.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_Event.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_event_KeyEvent.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_event_MouseEvent.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_event_WindowEvent.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_Font.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_FontDescriptor.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_PlatformFont.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_windows_WComponentPeer.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_windows_WFontMetrics.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_windows_WObjectPeer.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_windows_WToolkit.h ../../../src/share/javavm/export/jawt.h ../../../src/share/javavm/export/jni.h ../../../src/share/javavm/export/jvm.h ../../../src/share/native/common/gdefs.h ../../../src/share/native/common/jni_util.h ../../../src/share/native/sun/awt/debug/debug_assert.h ../../../src/share/native/sun/awt/debug/debug_mem.h ../../../src/share/native/sun/awt/debug/debug_trace.h ../../../src/share/native/sun/awt/debug/debug_util.h ../../../src/share/native/sun/awt/image/cvutils/img_globals.h ../../../src/share/native/sun/java2d/loops/AlphaMath.h ../../../src/share/native/sun/java2d/loops/GlyphImageRef.h ../../../src/share/native/sun/java2d/loops/GraphicsPrimitiveMgr.h ../../../src/share/native/sun/java2d/pipe/SpanIterator.h ../../../src/share/native/sun/java2d/SurfaceData.h ../../../src/share/native/sun/java2d/Trace.h ../../../src/windows/javavm/export/jawt_md.h ../../../src/windows/javavm/export/jni_md.h ../../../src/windows/javavm/export/jvm_md.h ../../../src/windows/native/common/gdefs_md.h ../../../src/windows/native/sun/java2d/j2d_md.h ../../../src/windows/native/sun/java2d/windows/ddrawObject.h ../../../src/windows/native/sun/java2d/windows/dxCapabilities.h ../../../src/windows/native/sun/java2d/windows/RegistryKey.h ../../../src/windows/native/sun/java2d/windows/Win32SurfaceData.h ../../../src/windows/native/sun/windows/alloc.h ../../../src/windows/native/sun/windows/awt_Brush.h ../../../src/windows/native/sun/windows/awt_Component.h ../../../src/windows/native/sun/windows/awt_Debug.h ../../../src/windows/native/sun/windows/awt_DrawingSurface.h ../../../src/windows/native/sun/windows/awt_Font.h ../../../src/windows/native/sun/windows/awt_GDIObject.h ../../../src/windows/native/sun/windows/awt.h ../../../src/windows/native/sun/windows/awt_MMStub.h ../../../src/windows/native/sun/windows/awtmsg.h ../../../src/windows/native/sun/windows/awt_Multimon.h ../../../src/windows/native/sun/windows/awt_Object.h ../../../src/windows/native/sun/windows/awt_Palette.h ../../../src/windows/native/sun/windows/awt_Pen.h ../../../src/windows/native/sun/windows/awt_Toolkit.h ../../../src/windows/native/sun/windows/awt_Unicode.h ../../../src/windows/native/sun/windows/awt_Win32GraphicsDevice.h ../../../src/windows/native/sun/windows/colordata.h ../../../src/windows/native/sun/windows/Devices.h ../../../src/windows/native/sun/windows/GDIHashtable.h ../../../src/windows/native/sun/windows/Hashtable.h ../../../src/windows/native/sun/windows/ObjectList.h ../../../src/windows/native/sun/windows/stdhdrs.h ../../../src/windows/native/sun/windows/UnicowsLoader.h
$(OBJDIR)/jawt.obj:: $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_AWTEvent.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_Component.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_Dimension.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_Event.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_Font.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_event_FocusEvent.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_event_KeyEvent.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_event_MouseEvent.h $(CLASSHDRDIR)/../../awt/CClassHeaders/java_awt_event_WindowEvent.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_FontDescriptor.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_PlatformFont.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_windows_WComponentPeer.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_windows_WFontMetrics.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_windows_WObjectPeer.h $(CLASSHDRDIR)/../../awt/CClassHeaders/sun_awt_windows_WToolkit.h ../../../src/share/javavm/export/jawt.h ../../../src/share/javavm/export/jni.h ../../../src/share/javavm/export/jvm.h ../../../src/share/native/common/jlong.h ../../../src/share/native/common/jni_util.h ../../../src/share/native/sun/awt/debug/debug_assert.h ../../../src/share/native/sun/awt/debug/debug_mem.h ../../../src/share/native/sun/awt/debug/debug_trace.h ../../../src/share/native/sun/awt/debug/debug_util.h ../../../src/share/native/sun/awt/image/cvutils/img_globals.h ../../../src/share/native/sun/java2d/SurfaceData.h ../../../src/share/native/sun/java2d/Trace.h ../../../src/windows/javavm/export/jawt_md.h ../../../src/windows/javavm/export/jni_md.h ../../../src/windows/javavm/export/jvm_md.h ../../../src/windows/native/common/jlong_md.h ../../../src/windows/native/sun/java2d/windows/GDIWindowSurfaceData.h ../../../src/windows/native/sun/windows/Devices.h ../../../src/windows/native/sun/windows/GDIHashtable.h ../../../src/windows/native/sun/windows/Hashtable.h ../../../src/windows/native/sun/windows/ObjectList.h ../../../src/windows/native/sun/windows/UnicowsLoader.h ../../../src/windows/native/sun/windows/alloc.h ../../../src/windows/native/sun/windows/awt.h ../../../src/windows/native/sun/windows/awt_Brush.h ../../../src/windows/native/sun/windows/awt_Component.h ../../../src/windows/native/sun/windows/awt_Debug.h ../../../src/windows/native/sun/windows/awt_DrawingSurface.h ../../../src/windows/native/sun/windows/awt_Font.h ../../../src/windows/native/sun/windows/awt_GDIObject.h ../../../src/windows/native/sun/windows/awt_MMStub.h ../../../src/windows/native/sun/windows/awt_Multimon.h ../../../src/windows/native/sun/windows/awt_Object.h ../../../src/windows/native/sun/windows/awt_Palette.h ../../../src/windows/native/sun/windows/awt_Pen.h ../../../src/windows/native/sun/windows/awt_Toolkit.h ../../../src/windows/native/sun/windows/awt_Unicode.h ../../../src/windows/native/sun/windows/awt_Win32GraphicsDevice.h ../../../src/windows/native/sun/windows/awtmsg.h ../../../src/windows/native/sun/windows/colordata.h ../../../src/windows/native/sun/windows/stdhdrs.h

View File

@ -1,5 +1,5 @@
#
# Copyright 2002-2007 Sun Microsystems, Inc. All Rights Reserved.
# Copyright 2002-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -242,6 +242,7 @@ SUNWprivate_1.1 {
AWTCharAscent;
AWTCharDescent;
AWTDrawGlyphList;
AccelGlyphCache_RemoveAllCellInfos;
Java_sun_awt_X11_XToolkit_waitForEvents;
Java_java_awt_Event_initIDs;

View File

@ -74,7 +74,11 @@ import sun.awt.dnd.SunDropTargetEvent;
import sun.awt.im.CompositionArea;
import sun.java2d.SunGraphics2D;
import sun.java2d.pipe.Region;
import sun.awt.image.VSyncedBSManager;
import sun.java2d.pipe.hw.ExtendedBufferCapabilities;
import static sun.java2d.pipe.hw.ExtendedBufferCapabilities.VSyncType.*;
import sun.awt.RequestFocusController;
import sun.java2d.SunGraphicsEnvironment;
/**
* A <em>component</em> is an object having a graphical representation
@ -3508,6 +3512,11 @@ public abstract class Component implements ImageObserver, MenuContainer,
if (numBuffers == 1) {
bufferStrategy = new SingleBufferStrategy(caps);
} else {
SunGraphicsEnvironment sge = (SunGraphicsEnvironment)
GraphicsEnvironment.getLocalGraphicsEnvironment();
if (!caps.isPageFlipping() && sge.isFlipStrategyPreferred(peer)) {
caps = new ProxyCapabilities(caps);
}
// assert numBuffers > 1;
if (caps.isPageFlipping()) {
bufferStrategy = new FlipSubRegionBufferStrategy(numBuffers, caps);
@ -3517,6 +3526,25 @@ public abstract class Component implements ImageObserver, MenuContainer,
}
}
/**
* This is a proxy capabilities class used when a FlipBufferStrategy
* is created instead of the requested Blit strategy.
*
* @see sun.awt.SunGraphicsEnvironment#isFlipStrategyPreferred(ComponentPeer)
*/
private class ProxyCapabilities extends ExtendedBufferCapabilities {
private BufferCapabilities orig;
private ProxyCapabilities(BufferCapabilities orig) {
super(orig.getFrontBufferCapabilities(),
orig.getBackBufferCapabilities(),
orig.getFlipContents() ==
BufferCapabilities.FlipContents.BACKGROUND ?
BufferCapabilities.FlipContents.BACKGROUND :
BufferCapabilities.FlipContents.COPIED);
this.orig = orig;
}
}
/**
* @return the buffer strategy used by this component
* @see Window#createBufferStrategy
@ -3646,16 +3674,30 @@ public abstract class Component implements ImageObserver, MenuContainer,
width = getWidth();
height = getHeight();
if (drawBuffer == null) {
peer.createBuffers(numBuffers, caps);
} else {
if (drawBuffer != null) {
// dispose the existing backbuffers
drawBuffer = null;
drawVBuffer = null;
destroyBuffers();
// ... then recreate the backbuffers
peer.createBuffers(numBuffers, caps);
}
if (caps instanceof ExtendedBufferCapabilities) {
ExtendedBufferCapabilities ebc =
(ExtendedBufferCapabilities)caps;
if (ebc.getVSync() == VSYNC_ON) {
// if this buffer strategy is not allowed to be v-synced,
// change the caps that we pass to the peer but keep on
// trying to create v-synced buffers;
// do not throw IAE here in case it is disallowed, see
// ExtendedBufferCapabilities for more info
if (!VSyncedBSManager.vsyncAllowed(this)) {
caps = ebc.derive(VSYNC_DEFAULT);
}
}
}
peer.createBuffers(numBuffers, caps);
updateInternalBuffers();
}
@ -3700,7 +3742,23 @@ public abstract class Component implements ImageObserver, MenuContainer,
*/
protected void flip(BufferCapabilities.FlipContents flipAction) {
if (peer != null) {
peer.flip(flipAction);
Image backBuffer = getBackBuffer();
if (backBuffer != null) {
peer.flip(0, 0,
backBuffer.getWidth(null),
backBuffer.getHeight(null), flipAction);
}
} else {
throw new IllegalStateException(
"Component must have a valid peer");
}
}
void flipSubRegion(int x1, int y1, int x2, int y2,
BufferCapabilities.FlipContents flipAction)
{
if (peer != null) {
peer.flip(x1, y1, x2, y2, flipAction);
} else {
throw new IllegalStateException(
"Component must have a valid peer");
@ -3711,6 +3769,7 @@ public abstract class Component implements ImageObserver, MenuContainer,
* Destroys the buffers created through this object
*/
protected void destroyBuffers() {
VSyncedBSManager.releaseVsync(this);
if (peer != null) {
peer.destroyBuffers();
} else {
@ -3723,7 +3782,11 @@ public abstract class Component implements ImageObserver, MenuContainer,
* @return the buffering capabilities of this strategy
*/
public BufferCapabilities getCapabilities() {
return caps;
if (caps instanceof ProxyCapabilities) {
return ((ProxyCapabilities)caps).orig;
} else {
return caps;
}
}
/**
@ -3810,6 +3873,14 @@ public abstract class Component implements ImageObserver, MenuContainer,
flip(caps.getFlipContents());
}
/**
* Makes specified region of the the next available buffer visible
* by either blitting or flipping.
*/
void showSubRegion(int x1, int y1, int x2, int y2) {
flipSubRegion(x1, y1, x2, y2, caps.getFlipContents());
}
/**
* {@inheritDoc}
* @since 1.6
@ -4080,8 +4151,6 @@ public abstract class Component implements ImageObserver, MenuContainer,
/**
* Private class to perform sub-region flipping.
* REMIND: this subclass currently punts on subregions and
* flips the entire buffer.
*/
private class FlipSubRegionBufferStrategy extends FlipBufferStrategy
implements SubRegionShowable
@ -4095,14 +4164,13 @@ public abstract class Component implements ImageObserver, MenuContainer,
}
public void show(int x1, int y1, int x2, int y2) {
show();
showSubRegion(x1, y1, x2, y2);
}
// This is invoked by Swing on the toolkit thread.
public boolean validateAndShow(int x1, int y1, int x2, int y2) {
revalidate(false);
if (!contentsRestored() && !contentsLost()) {
show();
public boolean showIfNotLost(int x1, int y1, int x2, int y2) {
if (!contentsLost()) {
showSubRegion(x1, y1, x2, y2);
return !contentsLost();
}
return false;
@ -4130,9 +4198,8 @@ public abstract class Component implements ImageObserver, MenuContainer,
}
// This method is called by Swing on the toolkit thread.
public boolean validateAndShow(int x1, int y1, int x2, int y2) {
revalidate(false);
if (!contentsRestored() && !contentsLost()) {
public boolean showIfNotLost(int x1, int y1, int x2, int y2) {
if (!contentsLost()) {
showSubRegion(x1, y1, x2, y2);
return !contentsLost();
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 1997-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -236,6 +236,10 @@ public abstract class GraphicsDevice {
*/
public void setFullScreenWindow(Window w) {
if (fullScreenWindow != null && windowedModeBounds != null) {
// if the window went into fs mode before it was realized it may
// have (0,0) dimensions
if (windowedModeBounds.width == 0) windowedModeBounds.width = 1;
if (windowedModeBounds.height == 0) windowedModeBounds.height = 1;
fullScreenWindow.setBounds(windowedModeBounds);
}
// Set the full screen window

View File

@ -1,5 +1,5 @@
/*
* Copyright 1999-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1999-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -25,12 +25,18 @@
package java.awt;
import java.awt.peer.*;
import java.awt.image.*;
import java.awt.event.*;
import java.awt.event.InputEvent;
import java.awt.event.KeyEvent;
import java.awt.image.BufferedImage;
import java.awt.image.DataBufferInt;
import java.awt.image.DirectColorModel;
import java.awt.image.Raster;
import java.awt.image.WritableRaster;
import java.awt.peer.RobotPeer;
import java.lang.reflect.InvocationTargetException;
import sun.awt.ComponentFactory;
import sun.awt.SunToolkit;
import sun.awt.image.SunWritableRaster;
import sun.security.util.SecurityConstants;
/**
@ -335,6 +341,10 @@ public class Robot {
/* blue mask */ 0x000000FF);
}
// need to sync the toolkit prior to grabbing the pixels since in some
// cases rendering to the screen may be delayed
Toolkit.getDefaultToolkit().sync();
int pixels[];
int[] bandmasks = new int[3];
@ -346,6 +356,7 @@ public class Robot {
bandmasks[2] = screenCapCM.getBlueMask();
raster = Raster.createPackedRaster(buffer, translatedRect.width, translatedRect.height, translatedRect.width, bandmasks, null);
SunWritableRaster.makeTrackable(buffer);
image = new BufferedImage(screenCapCM, raster, false, null);

View File

@ -1,5 +1,5 @@
/*
* Portions Copyright 1997-2007 Sun Microsystems, Inc. All Rights Reserved.
* Portions Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -530,6 +530,12 @@ public abstract class DataBuffer {
public StateTrackableDelegate getTrackable(DataBuffer db) {
return db.theTrackable;
}
public void setTrackable(DataBuffer db,
StateTrackableDelegate trackable)
{
db.theTrackable = trackable;
}
});
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 1995-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1995-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -88,7 +88,7 @@ public interface ComponentPeer {
boolean handlesWheelScrolling();
void createBuffers(int numBuffers, BufferCapabilities caps) throws AWTException;
Image getBackBuffer();
void flip(BufferCapabilities.FlipContents flipAction);
void flip(int x1, int y1, int x2, int y2, BufferCapabilities.FlipContents flipAction);
void destroyBuffers();
/**

View File

@ -1,5 +1,5 @@
/*
* Copyright 2005-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2005-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -263,7 +263,7 @@ class BufferStrategyPaintManager extends RepaintManager.PaintManager {
(SubRegionShowable)bufferStrategy;
boolean paintAllOnExpose = info.getPaintAllOnExpose();
info.setPaintAllOnExpose(false);
if (bsSubRegion.validateAndShow(x, y, (x + w), (y + h))) {
if (bsSubRegion.showIfNotLost(x, y, (x + w), (y + h))) {
return !paintAllOnExpose;
}
// Mark the buffer as needing to be repainted. We don't

View File

@ -1,5 +1,5 @@
/*
* Copyright 2000-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2000-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -255,7 +255,9 @@ public class NullComponentPeer implements LightweightPeer,
throw new IllegalStateException(
"Page-flipping is not allowed on a lightweight component");
}
public void flip(BufferCapabilities.FlipContents flipAction) {
public void flip(int x1, int y1, int x2, int y2,
BufferCapabilities.FlipContents flipAction)
{
throw new IllegalStateException(
"Page-flipping is not allowed on a lightweight component");
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2005 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2005-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -39,10 +39,11 @@ public interface SubRegionShowable {
public void show(int x1, int y1, int x2, int y2);
/**
* Validates the buffer and if successful shows the specified region.
* Shows the specified region if the buffer is not lost and the dimensions
* of the back-buffer match those of the component.
*
* @return true if successful
*/
// NOTE: this is invoked by swing on the toolkit thread!
public boolean validateAndShow(int x1, int y1, int x2, int y2);
public boolean showIfNotLost(int x1, int y1, int x2, int y2);
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2000-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2000-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -29,19 +29,18 @@ import java.awt.AlphaComposite;
import java.awt.Color;
import java.awt.Component;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.GraphicsConfiguration;
import java.awt.ImageCapabilities;
import java.awt.Transparency;
import java.awt.image.BufferedImage;
import java.awt.image.ColorModel;
import java.awt.image.ImageObserver;
import java.awt.image.VolatileImage;
import java.awt.image.WritableRaster;
import sun.java2d.SunGraphics2D;
import sun.java2d.SurfaceData;
import sun.java2d.SurfaceManagerFactory;
import sun.java2d.DestSurfaceProvider;
import sun.java2d.Surface;
import static sun.java2d.pipe.hw.AccelSurface.*;
/**
* This class is the base implementation of the VolatileImage
@ -52,23 +51,28 @@ import sun.java2d.SurfaceManagerFactory;
* appropriate VolatileSurfaceManager for the GraphicsConfiguration
* under which this SunVolatileImage was created.
*/
public class SunVolatileImage extends VolatileImage {
public class SunVolatileImage extends VolatileImage
implements DestSurfaceProvider
{
protected VolatileSurfaceManager volSurfaceManager;
protected Component comp;
private GraphicsConfiguration graphicsConfig;
private Font defaultFont;
private int width, height;
private int forcedAccelSurfaceType;
private SunVolatileImage(Component comp,
GraphicsConfiguration graphicsConfig,
int width, int height, Object context,
int transparency, ImageCapabilities caps)
protected SunVolatileImage(Component comp,
GraphicsConfiguration graphicsConfig,
int width, int height, Object context,
int transparency, ImageCapabilities caps,
int accType)
{
this.comp = comp;
this.graphicsConfig = graphicsConfig;
this.width = width;
this.height = height;
this.forcedAccelSurfaceType = accType;
if (!(transparency == Transparency.OPAQUE ||
transparency == Transparency.BITMASK ||
transparency == Transparency.TRANSLUCENT))
@ -92,7 +96,7 @@ public class SunVolatileImage extends VolatileImage {
ImageCapabilities caps)
{
this(comp, graphicsConfig,
width, height, context, Transparency.OPAQUE, caps);
width, height, context, Transparency.OPAQUE, caps, UNDEFINED);
}
public SunVolatileImage(Component comp, int width, int height) {
@ -110,7 +114,8 @@ public class SunVolatileImage extends VolatileImage {
int width, int height, int transparency,
ImageCapabilities caps)
{
this(null, graphicsConfig, width, height, null, transparency, caps);
this(null, graphicsConfig, width, height, null, transparency,
caps, UNDEFINED);
}
public int getWidth() {
@ -144,6 +149,10 @@ public class SunVolatileImage extends VolatileImage {
return comp;
}
public int getForcedAccelSurfaceType() {
return forcedAccelSurfaceType;
}
protected VolatileSurfaceManager createSurfaceManager(Object context,
ImageCapabilities caps)
{
@ -248,4 +257,14 @@ public class SunVolatileImage extends VolatileImage {
public ImageCapabilities getCapabilities() {
return volSurfaceManager.getCapabilities(graphicsConfig);
}
/**
* {@inheritDoc}
*
* @see sun.java2d.DestSurfaceProvider#getDestSurface
*/
@Override
public Surface getDestSurface() {
return volSurfaceManager.getPrimarySurfaceData();
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2001-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2001-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -35,6 +35,7 @@ import java.awt.image.DataBufferInt;
import java.awt.image.SampleModel;
import java.awt.image.WritableRaster;
import sun.java2d.StateTrackable.State;
import sun.java2d.SurfaceData;
import sun.java2d.StateTrackableDelegate;
@ -54,6 +55,7 @@ public class SunWritableRaster extends WritableRaster {
public short[] getData(DataBufferUShort dbus, int bank);
public int[] getData(DataBufferInt dbi, int bank);
public StateTrackableDelegate getTrackable(DataBuffer db);
public void setTrackable(DataBuffer db, StateTrackableDelegate trackable);
}
public static void setDataStealer(DataStealer ds) {
@ -79,6 +81,14 @@ public class SunWritableRaster extends WritableRaster {
return stealer.getTrackable(db);
}
public static void setTrackable(DataBuffer db, StateTrackableDelegate trackable) {
stealer.setTrackable(db, trackable);
}
public static void makeTrackable(DataBuffer db) {
stealer.setTrackable(db, StateTrackableDelegate.createInstance(State.STABLE));
}
public static void markDirty(DataBuffer db) {
stealer.getTrackable(db).markDirty();
}

View File

@ -0,0 +1,121 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.awt.image;
import java.awt.image.BufferStrategy;
import java.lang.ref.WeakReference;
/**
* Manages v-synced buffer strategies.
*/
public abstract class VSyncedBSManager {
private static VSyncedBSManager theInstance;
private static final boolean vSyncLimit =
Boolean.valueOf((String)java.security.AccessController.doPrivileged(
new sun.security.action.GetPropertyAction(
"sun.java2d.vsynclimit", "true")));
private static VSyncedBSManager getInstance(boolean create) {
if (theInstance == null && create) {
theInstance =
vSyncLimit ? new SingleVSyncedBSMgr() : new NoLimitVSyncBSMgr();
}
return theInstance;
}
abstract boolean checkAllowed(BufferStrategy bs);
abstract void relinquishVsync(BufferStrategy bs);
/**
* Returns true if the buffer strategy is allowed to be created
* v-synced.
*
* @return true if the bs is allowed to be v-synced, false otherwise
*/
public static boolean vsyncAllowed(BufferStrategy bs) {
VSyncedBSManager bsm = getInstance(true);
return bsm.checkAllowed(bs);
}
/**
* Lets the manager know that this buffer strategy is no longer interested
* in being v-synced.
*/
public static synchronized void releaseVsync(BufferStrategy bs) {
VSyncedBSManager bsm = getInstance(false);
if (bsm != null) {
bsm.relinquishVsync(bs);
}
}
/**
* An instance of the manager which allows any buffer strategy to be
* v-synced.
*/
private static final class NoLimitVSyncBSMgr extends VSyncedBSManager {
@Override
boolean checkAllowed(BufferStrategy bs) {
return true;
}
@Override
void relinquishVsync(BufferStrategy bs) {
}
}
/**
* An instance of the manager which allows only one buffer strategy to
* be v-synced at any give moment in the vm.
*/
private static final class SingleVSyncedBSMgr extends VSyncedBSManager {
private WeakReference<BufferStrategy> strategy;
@Override
public synchronized boolean checkAllowed(BufferStrategy bs) {
if (strategy != null) {
BufferStrategy current = strategy.get();
if (current != null) {
return (current == bs);
}
}
strategy = new WeakReference<BufferStrategy>(bs);
return true;
}
@Override
public synchronized void relinquishVsync(BufferStrategy bs) {
if (strategy != null) {
BufferStrategy b = strategy.get();
if (b == bs) {
strategy.clear();
strategy = null;
}
}
}
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -37,6 +37,7 @@ import sun.awt.image.SunVolatileImage;
import sun.java2d.SunGraphicsEnvironment;
import sun.java2d.SurfaceData;
import sun.java2d.loops.CompositeType;
import static sun.java2d.pipe.hw.AccelSurface.*;
/**
* This SurfaceManager variant manages an accelerated volatile surface, if it
@ -117,7 +118,11 @@ public abstract class VolatileSurfaceManager
sdCurrent = sdAccel;
}
}
if (sdCurrent == null) {
// only initialize the backup surface for images with unforced
// acceleration type
if (sdCurrent == null &&
vImg.getForcedAccelSurfaceType() == UNDEFINED)
{
sdCurrent = getBackupSurface();
}
}
@ -270,9 +275,13 @@ public abstract class VolatileSurfaceManager
* the background).
*/
public void initContents() {
Graphics g = vImg.createGraphics();
g.clearRect(0, 0, vImg.getWidth(), vImg.getHeight());
g.dispose();
// images with forced acceleration type may have a null sdCurrent
// because we do not create a backup surface for them
if (sdCurrent != null) {
Graphics g = vImg.createGraphics();
g.clearRect(0, 0, vImg.getWidth(), vImg.getHeight());
g.dispose();
}
}
/**

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -25,16 +25,17 @@
package sun.font;
import java.awt.GraphicsConfiguration;
import java.awt.GraphicsEnvironment;
import java.lang.ref.Reference;
import java.lang.ref.ReferenceQueue;
import java.lang.ref.SoftReference;
import java.lang.ref.WeakReference;
import java.awt.Font;
import java.awt.FontFormatException;
import java.util.logging.Level;
import java.util.logging.Logger;
import sun.java2d.Disposer;
import sun.java2d.pipe.BufferedContext;
import sun.java2d.pipe.RenderQueue;
import sun.java2d.pipe.hw.AccelGraphicsConfig;
import sun.misc.Unsafe;
/**
@ -192,13 +193,13 @@ public final class StrikeCache {
recentStrikeIndex = index;
}
static void disposeStrike(FontStrikeDisposer disposer) {
private static final void doDispose(FontStrikeDisposer disposer) {
if (disposer.intGlyphImages != null) {
freeIntMemory(disposer.intGlyphImages,
disposer.pScalerContext);
disposer.pScalerContext);
} else if (disposer.longGlyphImages != null) {
freeLongMemory(disposer.longGlyphImages,
disposer.pScalerContext);
disposer.pScalerContext);
} else if (disposer.segIntGlyphImages != null) {
/* NB Now making multiple JNI calls in this case.
* But assuming that there's a reasonable amount of locality
@ -207,7 +208,7 @@ public final class StrikeCache {
for (int i=0; i<disposer.segIntGlyphImages.length; i++) {
if (disposer.segIntGlyphImages[i] != null) {
freeIntMemory(disposer.segIntGlyphImages[i],
disposer.pScalerContext);
disposer.pScalerContext);
/* native will only free the scaler context once */
disposer.pScalerContext = 0L;
disposer.segIntGlyphImages[i] = null;
@ -223,7 +224,7 @@ public final class StrikeCache {
for (int i=0; i<disposer.segLongGlyphImages.length; i++) {
if (disposer.segLongGlyphImages[i] != null) {
freeLongMemory(disposer.segLongGlyphImages[i],
disposer.pScalerContext);
disposer.pScalerContext);
disposer.pScalerContext = 0L;
disposer.segLongGlyphImages[i] = null;
}
@ -234,6 +235,44 @@ public final class StrikeCache {
}
}
static void disposeStrike(final FontStrikeDisposer disposer) {
// we need to execute the strike disposal on the rendering thread
// because they may be accessed on that thread at the time of the
// disposal (for example, when the accel. cache is invalidated)
// REMIND: this look a bit heavyweight, but should be ok
// because strike disposal is a relatively infrequent operation,
// more worrisome is the necessity of getting a GC here.
RenderQueue rq = null;
GraphicsEnvironment ge =
GraphicsEnvironment.getLocalGraphicsEnvironment();
if (!ge.isHeadless()) {
GraphicsConfiguration gc =
ge.getDefaultScreenDevice().getDefaultConfiguration();
if (gc instanceof AccelGraphicsConfig) {
AccelGraphicsConfig agc = (AccelGraphicsConfig)gc;
BufferedContext bc = agc.getContext();
if (bc != null) {
rq = bc.getRenderQueue();
}
}
}
if (rq != null) {
rq.lock();
try {
rq.flushAndInvokeNow(new Runnable() {
public void run() {
doDispose(disposer);
}
});
} finally {
rq.unlock();
}
} else {
doDispose(disposer);
}
}
static native void freeIntPointer(int ptr);
static native void freeLongPointer(long ptr);
private static native void freeIntMemory(int[] glyphPtrs, long pContext);

View File

@ -0,0 +1,41 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d;
import sun.java2d.pipe.hw.*;
/**
* Classes implementing this interface provide access to their
* destination surfaces.
*/
public interface DestSurfaceProvider {
/**
* Returns a surface currently used as a destination surface for rendering.
*
* @return destination surface
*/
public Surface getDestSurface();
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 1996-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1996-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -41,24 +41,17 @@ import java.awt.image.renderable.RenderableImage;
import java.awt.image.renderable.RenderContext;
import java.awt.image.AffineTransformOp;
import java.awt.image.Raster;
import java.awt.image.SampleModel;
import java.awt.image.VolatileImage;
import java.awt.image.WritableRaster;
import java.awt.Image;
import java.awt.Composite;
import java.awt.Color;
import java.awt.color.ColorSpace;
import java.awt.image.DataBuffer;
import java.awt.image.ColorModel;
import java.awt.image.IndexColorModel;
import java.awt.image.DirectColorModel;
import java.awt.GraphicsConfiguration;
import java.awt.Paint;
import java.awt.GradientPaint;
import java.awt.LinearGradientPaint;
import java.awt.RadialGradientPaint;
import java.awt.TexturePaint;
import java.awt.geom.Point2D;
import java.awt.geom.Rectangle2D;
import java.awt.geom.PathIterator;
import java.awt.geom.GeneralPath;
@ -69,19 +62,16 @@ import java.awt.Rectangle;
import java.text.AttributedCharacterIterator;
import java.awt.Font;
import java.awt.image.ImageObserver;
import java.awt.image.ColorConvertOp;
import java.awt.Transparency;
import java.awt.font.GlyphVector;
import java.awt.font.TextLayout;
import sun.font.FontDesignMetrics;
import sun.font.StandardGlyphVector;
import sun.java2d.pipe.PixelDrawPipe;
import sun.java2d.pipe.PixelFillPipe;
import sun.java2d.pipe.ShapeDrawPipe;
import sun.java2d.pipe.ValidatePipe;
import sun.java2d.pipe.ShapeSpanIterator;
import sun.java2d.pipe.Region;
import sun.java2d.pipe.RegionIterator;
import sun.java2d.pipe.TextPipe;
import sun.java2d.pipe.DrawImagePipe;
import sun.java2d.pipe.LoopPipe;
@ -90,7 +80,6 @@ import sun.java2d.loops.RenderLoops;
import sun.java2d.loops.CompositeType;
import sun.java2d.loops.SurfaceType;
import sun.java2d.loops.Blit;
import sun.java2d.loops.BlitBg;
import sun.java2d.loops.MaskFill;
import sun.font.FontManager;
import java.awt.font.FontRenderContext;
@ -99,7 +88,7 @@ import sun.awt.ConstrainableGraphics;
import sun.awt.SunHints;
import java.util.Map;
import java.util.Iterator;
import sun.awt.image.OffScreenImage;
import sun.java2d.DestSurfaceProvider;
import sun.misc.PerformanceLogger;
/**
@ -113,7 +102,7 @@ import sun.misc.PerformanceLogger;
*/
public final class SunGraphics2D
extends Graphics2D
implements ConstrainableGraphics, Cloneable
implements ConstrainableGraphics, Cloneable, DestSurfaceProvider
{
/*
* Attribute States
@ -3306,4 +3295,14 @@ public final class SunGraphics2D
public Object getDestination() {
return surfaceData.getDestination();
}
/**
* {@inheritDoc}
*
* @see sun.java2d.DestSurfaceProvider#getDestSurface
*/
@Override
public Surface getDestSurface() {
return surfaceData;
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 1997-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -36,6 +36,7 @@ import java.awt.Rectangle;
import java.awt.Toolkit;
import java.awt.font.TextAttribute;
import java.awt.image.BufferedImage;
import java.awt.peer.ComponentPeer;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
@ -1313,4 +1314,18 @@ public abstract class SunGraphicsEnvironment extends GraphicsEnvironment
/*
* ----END DISPLAY CHANGE SUPPORT----
*/
/**
* Returns true if FlipBufferStrategy with COPIED buffer contents
* is preferred for this peer's GraphicsConfiguration over
* BlitBufferStrategy, false otherwise.
*
* The reason FlipBS could be preferred is that in some configurations
* an accelerated copy to the screen is supported (like Direct3D 9)
*
* @return true if flip strategy should be used, false otherwise
*/
public boolean isFlipStrategyPreferred(ComponentPeer peer) {
return false;
}
}

View File

@ -0,0 +1,34 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d;
/**
* This is a tag interface for a surface.
* @see sun.java2d.SurfaceData
* @see sun.java2d.pipe.hw.AccelSurface
*/
public interface Surface {
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 1999-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1999-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -93,7 +93,7 @@ import sun.awt.image.SurfaceManager;
* retrieved the tracker.
*/
public abstract class SurfaceData
implements Transparency, DisposerTarget, StateTrackable
implements Transparency, DisposerTarget, StateTrackable, Surface
{
private long pData;
private boolean valid;

View File

@ -1,5 +1,5 @@
/*
* Copyright 2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -521,7 +521,7 @@ public abstract class SurfaceDataProxy
CompositeType.SrcNoEa,
dstType);
blitbg.BlitBg(srcData, dstData,
AlphaComposite.Src, null, bgColor,
AlphaComposite.Src, null, bgColor.getRGB(),
0, 0, 0, 0, w, h);
dstData.markDirty();
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 1999-2004 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1999-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -109,7 +109,7 @@ public class BlitBg extends GraphicsPrimitive
*/
public native void BlitBg(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
Color bgColor,
int bgColor,
int srcx, int srcy,
int dstx, int dsty,
int width, int height);
@ -142,19 +142,19 @@ public class BlitBg extends GraphicsPrimitive
compositeType = comptype;
}
@Override
public void BlitBg(SurfaceData srcData,
SurfaceData dstData,
Composite comp,
Region clip,
Color bgColor,
int bgArgb,
int srcx, int srcy,
int dstx, int dsty,
int width, int height)
{
ColorModel dstModel = dstData.getColorModel();
if (!dstModel.hasAlpha() &&
bgColor.getTransparency() != Transparency.OPAQUE)
{
boolean bgHasAlpha = (bgArgb >>> 24) != 0xff;
if (!dstModel.hasAlpha() && bgHasAlpha) {
dstModel = ColorModel.getRGBdefault();
}
WritableRaster wr =
@ -163,6 +163,7 @@ public class BlitBg extends GraphicsPrimitive
BufferedImage bimg =
new BufferedImage(dstModel, wr, isPremult, null);
SurfaceData tmpData = BufImgSurfaceData.createData(bimg);
Color bgColor = new Color(bgArgb, bgHasAlpha);
SunGraphics2D sg2d = new SunGraphics2D(tmpData, bgColor, bgColor,
defaultFont);
FillRect fillop = FillRect.locate(SurfaceType.AnyColor,
@ -201,9 +202,10 @@ public class BlitBg extends GraphicsPrimitive
return this;
}
@Override
public void BlitBg(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
Color bgColor,
int bgColor,
int srcx, int srcy, int dstx, int dsty,
int width, int height)
{

View File

@ -1,5 +1,5 @@
/*
* Copyright 1998-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1998-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -159,6 +159,10 @@ public final class GeneralRenderer {
{
int mx, my, x1, y1;
int[] tmp = null;
if (nPoints <= 0) {
return;
}
mx = x1 = xPoints[off] + transx;
my = y1 = yPoints[off] + transy;
while (--nPoints > 0) {

View File

@ -1,5 +1,5 @@
/*
* Copyright 2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -35,6 +35,7 @@ import sun.java2d.SunGraphics2D;
import sun.java2d.SurfaceData;
import sun.java2d.loops.CompositeType;
import sun.java2d.pipe.BufferedBufImgOps;
import static sun.java2d.opengl.OGLContext.OGLContextCaps.*;
class OGLBufImgOps extends BufferedBufImgOps {
@ -94,7 +95,7 @@ class OGLBufImgOps extends BufferedBufImgOps {
OGLSurfaceData oglSrc = (OGLSurfaceData)srcData;
OGLGraphicsConfig gc = oglSrc.getOGLGraphicsConfig();
if (oglSrc.getType() != OGLSurfaceData.TEXTURE ||
!gc.isCapPresent(OGLContext.CAPS_EXT_BIOP_SHADER))
!gc.isCapPresent(CAPS_EXT_BIOP_SHADER))
{
return false;
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2004-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2004-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -25,91 +25,24 @@
package sun.java2d.opengl;
import java.awt.AlphaComposite;
import java.awt.Composite;
import java.awt.Paint;
import java.awt.geom.AffineTransform;
import sun.java2d.SunGraphics2D;
import sun.java2d.pipe.BufferedContext;
import sun.java2d.pipe.Region;
import sun.java2d.pipe.RenderBuffer;
import sun.java2d.pipe.RenderQueue;
import sun.java2d.pipe.hw.ContextCapabilities;
import static sun.java2d.pipe.BufferedOpCodes.*;
import static sun.java2d.pipe.hw.ContextCapabilities.*;
/**
* Note that the RenderQueue lock must be acquired before calling any of
* the methods in this class.
*/
class OGLContext extends BufferedContext {
public class OGLContext extends BufferedContext {
/** Indicates that the context has no capabilities. */
static final int CAPS_EMPTY = (0 << 0);
/** Indicates that the context is doublebuffered. */
static final int CAPS_DOUBLEBUFFERED = (1 << 0);
/** Indicates that the context supports a stored alpha channel. */
static final int CAPS_STORED_ALPHA = (1 << 1);
/** Indicates the presence of the GL_ARB_multitexture extension. */
static final int CAPS_EXT_MULTITEXTURE = (1 << 2);
/** Indicates the presence of the GL_ARB_texture_non_power_of_two ext. */
static final int CAPS_EXT_TEXNONPOW2 = (1 << 3);
/**
* Indicates the presence of the GL_EXT_framebuffer_object extension.
* This cap will only be set if the fbobject system property has been
* enabled and we are able to create an FBO with depth buffer.
*/
static final int CAPS_EXT_FBOBJECT = (1 << 4);
/**
* Indicates the presence of the GL_ARB_fragment_shader extension.
* This cap will only be set if the lcdshader system property has been
* enabled and the hardware supports the minimum number of texture units.
*/
static final int CAPS_EXT_LCD_SHADER = (1 << 5);
/** Indicates the presence of the GL_ARB_texture_rectangle extension. */
static final int CAPS_EXT_TEXRECT = (1 << 6);
/**
* Indicates the presence of the GL_ARB_fragment_shader extension.
* This cap will only be set if the biopshader system property has been
* enabled and the hardware meets our minimum requirements.
*/
static final int CAPS_EXT_BIOP_SHADER = (1 << 7);
/**
* Indicates the presence of the GL_ARB_fragment_shader extension.
* This cap will only be set if the gradshader system property has been
* enabled and the hardware meets our minimum requirements.
*/
static final int CAPS_EXT_GRAD_SHADER = (1 << 8);
private final OGLGraphicsConfig config;
OGLContext(RenderQueue rq) {
OGLContext(RenderQueue rq, OGLGraphicsConfig config) {
super(rq);
}
/**
* Fetches the OGLContext associated with the current GraphicsConfig
* and validates the context using the given parameters. Most rendering
* operations will call this method first in order to set the necessary
* state before issuing rendering commands.
*/
static void validateContext(OGLSurfaceData srcData,
OGLSurfaceData dstData,
Region clip, Composite comp,
AffineTransform xform,
Paint paint, SunGraphics2D sg2d,
int flags)
{
// assert rq.lock.isHeldByCurrentThread();
OGLContext oglc = dstData.getContext();
oglc.validate(srcData, dstData,
clip, comp, xform, paint, sg2d, flags);
}
/**
* Simplified version of validateContext() that disables all context
* state settings.
*/
static void validateContext(OGLSurfaceData dstData) {
// assert rq.lock.isHeldByCurrentThread();
validateContext(dstData, dstData,
null, null, null, null, null, NO_CONTEXT_FLAGS);
this.config = config;
}
/**
@ -160,19 +93,128 @@ class OGLContext extends BufferedContext {
static void invalidateCurrentContext() {
// assert OGLRenderQueue.getInstance().lock.isHeldByCurrentThread();
// first invalidate the context reference at the native level, and
// invalidate the current Java-level context so that we
// revalidate everything the next time around
if (currentContext != null) {
currentContext.invalidateContext();
currentContext = null;
}
// invalidate the context reference at the native level, and
// then flush the queue so that we have no pending operations
// dependent on the current context
OGLRenderQueue rq = OGLRenderQueue.getInstance();
rq.ensureCapacity(4);
rq.getBuffer().putInt(INVALIDATE_CONTEXT);
rq.flushNow();
}
// then invalidate the current Java-level context so that we
// revalidate everything the next time around
if (currentContext != null) {
currentContext.invalidateSurfaces();
currentContext = null;
public RenderQueue getRenderQueue() {
return OGLRenderQueue.getInstance();
}
/**
* Returns a string representing adapter id (vendor, renderer, version).
* Must be called on the rendering thread.
*
* @return an id string for the adapter
*/
static final native String getOGLIdString();
@Override
public void saveState() {
// assert rq.lock.isHeldByCurrentThread();
// reset all attributes of this and current contexts
invalidateContext();
invalidateCurrentContext();
setScratchSurface(config);
// save the state on the native level
rq.ensureCapacity(4);
buf.putInt(SAVE_STATE);
rq.flushNow();
}
@Override
public void restoreState() {
// assert rq.lock.isHeldByCurrentThread();
// reset all attributes of this and current contexts
invalidateContext();
invalidateCurrentContext();
setScratchSurface(config);
// restore the state on the native level
rq.ensureCapacity(4);
buf.putInt(RESTORE_STATE);
rq.flushNow();
}
static class OGLContextCaps extends ContextCapabilities {
/**
* Indicates the presence of the GL_EXT_framebuffer_object extension.
* This cap will only be set if the fbobject system property has been
* enabled and we are able to create an FBO with depth buffer.
*/
static final int CAPS_EXT_FBOBJECT =
(CAPS_RT_TEXTURE_ALPHA | CAPS_RT_TEXTURE_OPAQUE);
/** Indicates that the context supports a stored alpha channel. */
static final int CAPS_STORED_ALPHA = CAPS_RT_PLAIN_ALPHA;
/** Indicates that the context is doublebuffered. */
static final int CAPS_DOUBLEBUFFERED = (FIRST_PRIVATE_CAP << 0);
/**
* Indicates the presence of the GL_ARB_fragment_shader extension.
* This cap will only be set if the lcdshader system property has been
* enabled and the hardware supports the minimum number of texture units
*/
static final int CAPS_EXT_LCD_SHADER = (FIRST_PRIVATE_CAP << 1);
/**
* Indicates the presence of the GL_ARB_fragment_shader extension.
* This cap will only be set if the biopshader system property has been
* enabled and the hardware meets our minimum requirements.
*/
static final int CAPS_EXT_BIOP_SHADER = (FIRST_PRIVATE_CAP << 2);
/**
* Indicates the presence of the GL_ARB_fragment_shader extension.
* This cap will only be set if the gradshader system property has been
* enabled and the hardware meets our minimum requirements.
*/
static final int CAPS_EXT_GRAD_SHADER = (FIRST_PRIVATE_CAP << 3);
/** Indicates the presence of the GL_ARB_texture_rectangle extension. */
static final int CAPS_EXT_TEXRECT = (FIRST_PRIVATE_CAP << 4);
OGLContextCaps(int caps, String adapterId) {
super(caps, adapterId);
}
@Override
public String toString() {
StringBuffer buf = new StringBuffer(super.toString());
if ((caps & CAPS_EXT_FBOBJECT) != 0) {
buf.append("CAPS_EXT_FBOBJECT|");
}
if ((caps & CAPS_STORED_ALPHA) != 0) {
buf.append("CAPS_STORED_ALPHA|");
}
if ((caps & CAPS_DOUBLEBUFFERED) != 0) {
buf.append("CAPS_DOUBLEBUFFERED|");
}
if ((caps & CAPS_EXT_LCD_SHADER) != 0) {
buf.append("CAPS_EXT_LCD_SHADER|");
}
if ((caps & CAPS_EXT_BIOP_SHADER) != 0) {
buf.append("CAPS_BIOP_SHADER|");
}
if ((caps & CAPS_EXT_GRAD_SHADER) != 0) {
buf.append("CAPS_EXT_GRAD_SHADER|");
}
if ((caps & CAPS_EXT_TEXRECT) != 0) {
buf.append("CAPS_EXT_TEXRECT|");
}
return buf.toString();
}
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2005-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2005-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -27,13 +27,16 @@ package sun.java2d.opengl;
import sun.java2d.SurfaceData;
import sun.awt.image.SurfaceManager;
import sun.java2d.pipe.hw.AccelGraphicsConfig;
/**
* This interface collects the methods that are provided by both
* GLXGraphicsConfig and WGLGraphicsConfig, making it easier to invoke these
* methods directly from OGLSurfaceData.
*/
interface OGLGraphicsConfig extends SurfaceManager.ProxiedGraphicsConfig {
interface OGLGraphicsConfig extends
AccelGraphicsConfig, SurfaceManager.ProxiedGraphicsConfig
{
OGLContext getContext();
long getNativeConfigInfo();
boolean isCapPresent(int cap);

View File

@ -1,5 +1,5 @@
/*
* Copyright 2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -39,6 +39,7 @@ import sun.java2d.SunGraphics2D;
import sun.java2d.SurfaceData;
import sun.java2d.loops.CompositeType;
import static sun.java2d.pipe.BufferedPaints.*;
import static sun.java2d.opengl.OGLContext.OGLContextCaps.*;
abstract class OGLPaints {
@ -170,7 +171,7 @@ abstract class OGLPaints {
OGLSurfaceData dstData = (OGLSurfaceData)sg2d.surfaceData;
OGLGraphicsConfig gc = dstData.getOGLGraphicsConfig();
if (!gc.isCapPresent(OGLContext.CAPS_EXT_GRAD_SHADER)) {
if (!gc.isCapPresent(CAPS_EXT_GRAD_SHADER)) {
return false;
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -30,6 +30,7 @@ import java.awt.geom.Path2D;
import sun.java2d.SunGraphics2D;
import sun.java2d.loops.GraphicsPrimitive;
import sun.java2d.pipe.BufferedRenderPipe;
import sun.java2d.pipe.ParallelogramPipe;
import sun.java2d.pipe.RenderQueue;
import sun.java2d.pipe.SpanIterator;
import static sun.java2d.pipe.BufferedOpCodes.*;
@ -51,6 +52,15 @@ class OGLRenderer extends BufferedRenderPipe {
null, sg2d.paint, sg2d, ctxflags);
}
@Override
protected void validateContextAA(SunGraphics2D sg2d) {
int ctxflags = OGLContext.NO_CONTEXT_FLAGS;
OGLSurfaceData dstData = (OGLSurfaceData)sg2d.surfaceData;
OGLContext.validateContext(dstData, dstData,
sg2d.getCompClip(), sg2d.composite,
null, sg2d.paint, sg2d, ctxflags);
}
void copyArea(SunGraphics2D sg2d,
int x, int y, int w, int h, int dx, int dy)
{
@ -88,6 +98,31 @@ class OGLRenderer extends BufferedRenderPipe {
super(oglr.rq);
this.oglr = oglr;
}
public ParallelogramPipe getAAParallelogramPipe() {
final ParallelogramPipe realpipe = oglr.getAAParallelogramPipe();
return new ParallelogramPipe() {
public void fillParallelogram(SunGraphics2D sg2d,
double x, double y,
double dx1, double dy1,
double dx2, double dy2)
{
GraphicsPrimitive.tracePrimitive("OGLFillAAParallelogram");
realpipe.fillParallelogram(sg2d,
x, y, dx1, dy1, dx2, dy2);
}
public void drawParallelogram(SunGraphics2D sg2d,
double x, double y,
double dx1, double dy1,
double dx2, double dy2,
double lw1, double lw2)
{
GraphicsPrimitive.tracePrimitive("OGLDrawAAParallelogram");
realpipe.drawParallelogram(sg2d,
x, y, dx1, dy1, dx2, dy2,
lw1, lw2);
}
};
}
protected void validateContext(SunGraphics2D sg2d) {
oglr.validateContext(sg2d);
}
@ -130,6 +165,23 @@ class OGLRenderer extends BufferedRenderPipe {
GraphicsPrimitive.tracePrimitive("OGLFillSpans");
oglr.fillSpans(sg2d, si, transx, transy);
}
public void fillParallelogram(SunGraphics2D sg2d,
double x, double y,
double dx1, double dy1,
double dx2, double dy2)
{
GraphicsPrimitive.tracePrimitive("OGLFillParallelogram");
oglr.fillParallelogram(sg2d, x, y, dx1, dy1, dx2, dy2);
}
public void drawParallelogram(SunGraphics2D sg2d,
double x, double y,
double dx1, double dy1,
double dx2, double dy2,
double lw1, double lw2)
{
GraphicsPrimitive.tracePrimitive("OGLDrawParallelogram");
oglr.drawParallelogram(sg2d, x, y, dx1, dy1, dx2, dy2, lw1, lw2);
}
public void copyArea(SunGraphics2D sg2d,
int x, int y, int w, int h, int dx, int dy)
{

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -27,23 +27,26 @@ package sun.java2d.opengl;
import java.awt.AlphaComposite;
import java.awt.GraphicsEnvironment;
import java.awt.Rectangle;
import java.awt.Transparency;
import java.awt.image.ColorModel;
import java.awt.image.Raster;
import sun.awt.SunHints;
import sun.awt.image.PixelConverter;
import sun.java2d.pipe.hw.AccelSurface;
import sun.java2d.SunGraphics2D;
import sun.java2d.SurfaceData;
import sun.java2d.SurfaceDataProxy;
import sun.java2d.loops.CompositeType;
import sun.java2d.loops.GraphicsPrimitive;
import sun.java2d.loops.MaskFill;
import sun.java2d.loops.SurfaceType;
import sun.java2d.pipe.PixelToShapeConverter;
import sun.java2d.pipe.ParallelogramPipe;
import sun.java2d.pipe.PixelToParallelogramConverter;
import sun.java2d.pipe.RenderBuffer;
import sun.java2d.pipe.RenderQueue;
import sun.java2d.pipe.TextPipe;
import static sun.java2d.pipe.BufferedOpCodes.*;
import static sun.java2d.opengl.OGLContext.*;
import static sun.java2d.opengl.OGLContext.OGLContextCaps.*;
/**
* This class describes an OpenGL "surface", that is, a region of pixels
@ -92,17 +95,16 @@ import static sun.java2d.opengl.OGLContext.*;
* FLIP_BACKBUFFER OpenGLSurface
* FBOBJECT OpenGLSurfaceRTT
*/
public abstract class OGLSurfaceData extends SurfaceData {
public abstract class OGLSurfaceData extends SurfaceData
implements AccelSurface {
/**
* OGL-specific surface types
*
* @see sun.java2d.pipe.hw.AccelSurface
*/
public static final int UNDEFINED = 0;
public static final int WINDOW = 1;
public static final int PBUFFER = 2;
public static final int TEXTURE = 3;
public static final int FLIP_BACKBUFFER = 4;
public static final int FBOBJECT = 5;
public static final int PBUFFER = RT_PLAIN;
public static final int FBOBJECT = RT_TEXTURE;
/**
* Pixel formats
@ -148,11 +150,14 @@ public abstract class OGLSurfaceData extends SurfaceData {
private static boolean isGradShaderEnabled;
private OGLGraphicsConfig graphicsConfig;
private int textureTarget;
protected int type;
// these fields are set from the native code when the surface is
// initialized
private int nativeWidth, nativeHeight;
protected static OGLRenderer oglRenderPipe;
protected static PixelToShapeConverter oglTxRenderPipe;
protected static PixelToParallelogramConverter oglTxRenderPipe;
protected static ParallelogramPipe oglAAPgramPipe;
protected static OGLTextRenderer oglTextPipe;
protected static OGLDrawImage oglImagePipe;
@ -170,6 +175,7 @@ public abstract class OGLSurfaceData extends SurfaceData {
int width, int height);
private native int getTextureTarget(long pData);
private native int getTextureID(long pData);
static {
if (!GraphicsEnvironment.isHeadless()) {
@ -203,9 +209,14 @@ public abstract class OGLSurfaceData extends SurfaceData {
oglRenderPipe = new OGLRenderer(rq);
if (GraphicsPrimitive.tracingEnabled()) {
oglTextPipe = oglTextPipe.traceWrap();
oglRenderPipe = oglRenderPipe.traceWrap();
//The wrapped oglRenderPipe will wrap the AA pipe as well...
//oglAAPgramPipe = oglRenderPipe.traceWrap();
}
oglTxRenderPipe = new PixelToShapeConverter(oglRenderPipe);
oglAAPgramPipe = oglRenderPipe.getAAParallelogramPipe();
oglTxRenderPipe =
new PixelToParallelogramConverter(oglRenderPipe,
oglRenderPipe,
1.0, 0.25, true);
OGLBlitLoops.register();
OGLMaskFill.register();
@ -282,9 +293,7 @@ public abstract class OGLSurfaceData extends SurfaceData {
break;
}
if (success) {
textureTarget = getTextureTarget(getNativeOps());
} else {
if (!success) {
throw new OutOfMemoryError("can't create offscreen surface");
}
}
@ -323,7 +332,7 @@ public abstract class OGLSurfaceData extends SurfaceData {
* Returns the OGLContext for the GraphicsConfig associated with this
* surface.
*/
final OGLContext getContext() {
public final OGLContext getContext() {
return graphicsConfig.getContext();
}
@ -337,7 +346,7 @@ public abstract class OGLSurfaceData extends SurfaceData {
/**
* Returns one of the surface type constants defined above.
*/
final int getType() {
public final int getType() {
return type;
}
@ -346,8 +355,41 @@ public abstract class OGLSurfaceData extends SurfaceData {
* for that texture (either GL_TEXTURE_2D or GL_TEXTURE_RECTANGLE_ARB).
* Otherwise, this method will return zero.
*/
final int getTextureTarget() {
return textureTarget;
public final int getTextureTarget() {
return getTextureTarget(getNativeOps());
}
/**
* If this surface is backed by a texture object, returns the texture ID
* for that texture.
* Otherwise, this method will return zero.
*/
public final int getTextureID() {
return getTextureID(getNativeOps());
}
/**
* Returns native resource of specified {@code resType} associated with
* this surface.
*
* Specifically, for {@code OGLSurfaceData} this method returns the
* the following:
* <pre>
* TEXTURE - texture id
* </pre>
*
* Note: the resource returned by this method is only valid on the rendering
* thread.
*
* @return native resource of specified type or 0L if
* such resource doesn't exist or can not be retrieved.
* @see sun.java2d.pipe.hw.AccelSurface#getNativeResource
*/
public long getNativeResource(int resType) {
if (resType == TEXTURE) {
return getTextureID();
}
return 0L;
}
public Raster getRaster(int x, int y, int w, int h) {
@ -366,7 +408,7 @@ public abstract class OGLSurfaceData extends SurfaceData {
*/
public boolean canRenderLCDText(SunGraphics2D sg2d) {
return
graphicsConfig.isCapPresent(OGLContext.CAPS_EXT_LCD_SHADER) &&
graphicsConfig.isCapPresent(CAPS_EXT_LCD_SHADER) &&
sg2d.compositeState <= SunGraphics2D.COMP_ISCOPY &&
sg2d.paintState <= SunGraphics2D.PAINT_OPAQUECOLOR;
}
@ -405,7 +447,7 @@ public abstract class OGLSurfaceData extends SurfaceData {
validated = true;
}
PixelToShapeConverter txPipe = null;
PixelToParallelogramConverter txPipe = null;
OGLRenderer nonTxPipe = null;
if (sg2d.antialiasHint != SunHints.INTVAL_ANTIALIAS_ON) {
@ -422,12 +464,28 @@ public abstract class OGLSurfaceData extends SurfaceData {
// custom paints handled by super.validatePipe() below
}
} else {
if (sg2d.paintState <= sg2d.PAINT_ALPHACOLOR &&
sg2d.compositeState == sg2d.COMP_XOR)
{
// install the solid pipes when AA and XOR are both enabled
txPipe = oglTxRenderPipe;
nonTxPipe = oglRenderPipe;
if (sg2d.paintState <= sg2d.PAINT_ALPHACOLOR) {
if (graphicsConfig.isCapPresent(CAPS_PS30) &&
(sg2d.imageComp == CompositeType.SrcOverNoEa ||
sg2d.imageComp == CompositeType.SrcOver))
{
if (!validated) {
super.validatePipe(sg2d);
validated = true;
}
PixelToParallelogramConverter aaConverter =
new PixelToParallelogramConverter(sg2d.shapepipe,
oglAAPgramPipe,
1.0/8.0, 0.499,
false);
sg2d.drawpipe = aaConverter;
sg2d.fillpipe = aaConverter;
sg2d.shapepipe = aaConverter;
} else if (sg2d.compositeState == sg2d.COMP_XOR) {
// install the solid pipes when AA and XOR are both enabled
txPipe = oglTxRenderPipe;
nonTxPipe = oglRenderPipe;
}
}
// other cases handled by super.validatePipe() below
}
@ -443,7 +501,11 @@ public abstract class OGLSurfaceData extends SurfaceData {
sg2d.drawpipe = nonTxPipe;
sg2d.fillpipe = nonTxPipe;
}
sg2d.shapepipe = nonTxPipe;
// Note that we use the transforming pipe here because it
// will examine the shape and possibly perform an optimized
// operation if it can be simplified. The simplifications
// will be valid for all STROKE and TRANSFORM types.
sg2d.shapepipe = txPipe;
} else {
if (!validated) {
super.validatePipe(sg2d);
@ -472,7 +534,7 @@ public abstract class OGLSurfaceData extends SurfaceData {
* validation code will choose a more general software-based loop.
*/
if (!OGLPaints.isValid(sg2d) ||
!graphicsConfig.isCapPresent(CAPS_EXT_MULTITEXTURE))
!graphicsConfig.isCapPresent(CAPS_MULTITEXTURE))
{
return null;
}
@ -564,7 +626,7 @@ public abstract class OGLSurfaceData extends SurfaceData {
* when using the basic GL_TEXTURE_2D target.
*/
boolean isTexNonPow2Available() {
return graphicsConfig.isCapPresent(OGLContext.CAPS_EXT_TEXNONPOW2);
return graphicsConfig.isCapPresent(CAPS_TEXNONPOW2);
}
/**
@ -573,6 +635,16 @@ public abstract class OGLSurfaceData extends SurfaceData {
* GL_ARB_texture_rectangle extension is present).
*/
boolean isTexRectAvailable() {
return graphicsConfig.isCapPresent(OGLContext.CAPS_EXT_TEXRECT);
return graphicsConfig.isCapPresent(CAPS_EXT_TEXRECT);
}
public Rectangle getNativeBounds() {
OGLRenderQueue rq = OGLRenderQueue.getInstance();
rq.lock();
try {
return new Rectangle(nativeWidth, nativeHeight);
} finally {
rq.unlock();
}
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2005 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2005-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -26,12 +26,13 @@
package sun.java2d.pipe;
import java.awt.AlphaComposite;
import java.awt.Color;
import java.awt.Composite;
import java.awt.Paint;
import java.awt.geom.AffineTransform;
import sun.java2d.pipe.hw.AccelSurface;
import sun.java2d.InvalidPipeException;
import sun.java2d.SunGraphics2D;
import sun.java2d.SurfaceData;
import sun.java2d.loops.XORComposite;
import static sun.java2d.pipe.BufferedOpCodes.*;
import static sun.java2d.pipe.BufferedRenderPipe.BYTES_PER_SPAN;
@ -43,8 +44,10 @@ import static sun.java2d.pipe.BufferedRenderPipe.BYTES_PER_SPAN;
* single thread. Note that the RenderQueue lock must be acquired before
* calling the validate() method (or any other method in this class). See
* the RenderQueue class comments for a sample usage scenario.
*
* @see RenderQueue
*/
public class BufferedContext {
public abstract class BufferedContext {
/*
* The following flags help the internals of validate() determine
@ -82,19 +85,66 @@ public class BufferedContext {
*/
protected static BufferedContext currentContext;
private SurfaceData validatedSrcData;
private SurfaceData validatedDstData;
private AccelSurface validatedSrcData;
private AccelSurface validatedDstData;
private Region validatedClip;
private Composite validatedComp;
private Paint validatedPaint;
private boolean isValidatedPaintAColor;
private int validatedRGB;
private int validatedFlags;
private boolean xformInUse;
private int transX;
private int transY;
protected BufferedContext(RenderQueue rq) {
this.rq = rq;
this.buf = rq.getBuffer();
}
/**
* Fetches the BufferedContextContext associated with the dst. surface
* and validates the context using the given parameters. Most rendering
* operations will call this method first in order to set the necessary
* state before issuing rendering commands.
*
* Note: must be called while the RenderQueue lock is held.
*
* @throws InvalidPipeException if either src or dest surface is not valid
* or lost
* @see RenderQueue#lock
* @see RenderQueue#unlock
*/
public static void validateContext(AccelSurface srcData,
AccelSurface dstData,
Region clip, Composite comp,
AffineTransform xform,
Paint paint, SunGraphics2D sg2d,
int flags)
{
// assert rq.lock.isHeldByCurrentThread();
BufferedContext d3dc = dstData.getContext();
d3dc.validate(srcData, dstData,
clip, comp, xform, paint, sg2d, flags);
}
/**
* Fetches the BufferedContextassociated with the surface
* and disables all context state settings.
*
* Note: must be called while the RenderQueue lock is held.
*
* @throws InvalidPipeException if the surface is not valid
* or lost
* @see RenderQueue#lock
* @see RenderQueue#unlock
*/
public static void validateContext(AccelSurface surface) {
// assert rt.lock.isHeldByCurrentThread();
validateContext(surface, surface,
null, null, null, null, null, NO_CONTEXT_FLAGS);
}
/**
* Validates the given parameters against the current state for this
* context. If this context is not current, it will be made current
@ -106,19 +156,47 @@ public class BufferedContext {
* Note that the SunGraphics2D parameter is only used for the purposes
* of validating a (non-null) Paint parameter. In all other cases it
* is safe to pass a null SunGraphics2D and it will be ignored.
*
* Note: must be called while the RenderQueue lock is held.
*
* @throws InvalidPipeException if either src or dest surface is not valid
* or lost
*/
public void validate(SurfaceData srcData, SurfaceData dstData,
public void validate(AccelSurface srcData, AccelSurface dstData,
Region clip, Composite comp,
AffineTransform xform,
Paint paint, SunGraphics2D sg2d, int flags)
{
// assert rq.lock.isHeldByCurrentThread();
boolean updateClip = (clip != validatedClip);
boolean updatePaint = (paint != validatedPaint);
boolean updateClip = false;
boolean updatePaint = false;
if (!dstData.isValid()) {
throw new InvalidPipeException("bounds changed");
if (!dstData.isValid() ||
dstData.isSurfaceLost() || srcData.isSurfaceLost())
{
invalidateContext();
throw new InvalidPipeException("bounds changed or surface lost");
}
if (paint instanceof Color) {
// REMIND: not 30-bit friendly
int newRGB = ((Color)paint).getRGB();
if (isValidatedPaintAColor) {
if (newRGB != validatedRGB) {
validatedRGB = newRGB;
updatePaint = true;
}
} else {
validatedRGB = newRGB;
updatePaint = true;
isValidatedPaintAColor = true;
}
} else if (validatedPaint != paint) {
updatePaint = true;
// this should be set when we are switching from paint to color
// in which case this condition will be true
isValidatedPaintAColor = false;
}
if ((currentContext != this) ||
@ -147,9 +225,18 @@ public class BufferedContext {
}
// validate clip
if (updateClip) {
if ((clip != validatedClip) || updateClip) {
if (clip != null) {
setClip(clip);
if (updateClip ||
validatedClip == null ||
!(validatedClip.isRectangular() && clip.isRectangular()) ||
((clip.getLoX() != validatedClip.getLoX() ||
clip.getLoY() != validatedClip.getLoY() ||
clip.getHiX() != validatedClip.getHiX() ||
clip.getHiY() != validatedClip.getHiY())))
{
setClip(clip);
}
} else {
resetClip();
}
@ -173,14 +260,29 @@ public class BufferedContext {
}
// validate transform
boolean txChanged = false;
if (xform == null) {
if (xformInUse) {
resetTransform();
xformInUse = false;
txChanged = true;
} else if (sg2d != null) {
if (transX != sg2d.transX || transY != sg2d.transY) {
txChanged = true;
}
}
if (sg2d != null) {
transX = sg2d.transX;
transY = sg2d.transY;
}
} else {
setTransform(xform);
xformInUse = true;
txChanged = true;
}
// non-Color paints may require paint revalidation
if (!isValidatedPaintAColor && txChanged) {
updatePaint = true;
}
// validate paint
@ -194,6 +296,7 @@ public class BufferedContext {
}
// mark dstData dirty
// REMIND: is this really needed now? we do it in SunGraphics2D..
dstData.markDirty();
}
@ -201,13 +304,20 @@ public class BufferedContext {
* Invalidates the surfaces associated with this context. This is
* useful when the context is no longer needed, and we want to break
* the chain caused by these surface references.
*
* Note: must be called while the RenderQueue lock is held.
*
* @see RenderQueue#lock
* @see RenderQueue#unlock
*/
public void invalidateSurfaces() {
validatedSrcData = null;
validatedDstData = null;
}
private void setSurfaces(SurfaceData srcData, SurfaceData dstData) {
private void setSurfaces(AccelSurface srcData,
AccelSurface dstData)
{
// assert rq.lock.isHeldByCurrentThread();
rq.ensureCapacityAndAlignment(20, 4);
buf.putInt(SET_SURFACES);
@ -304,4 +414,54 @@ public class BufferedContext {
buf.putDouble(xform.getTranslateX());
buf.putDouble(xform.getTranslateY());
}
/**
* Resets this context's surfaces and all attributes.
*
* Note: must be called while the RenderQueue lock is held.
*
* @see RenderQueue#lock
* @see RenderQueue#unlock
*/
public void invalidateContext() {
resetTransform();
resetComposite();
resetClip();
invalidateSurfaces();
validatedComp = null;
validatedClip = null;
validatedPaint = null;
xformInUse = false;
}
/**
* Returns a singleton {@code RenderQueue} object used by the rendering
* pipeline.
*
* @return a render queue
* @see RenderQueue
*/
public abstract RenderQueue getRenderQueue();
/**
* Saves the the state of this context.
* It may reset the current context.
*
* Note: must be called while the RenderQueue lock is held.
*
* @see RenderQueue#lock
* @see RenderQueue#unlock
*/
public abstract void saveState();
/**
* Restores the native state of this context.
* It may reset the current context.
*
* Note: must be called while the RenderQueue lock is held.
*
* @see RenderQueue#lock
* @see RenderQueue#unlock
*/
public abstract void restoreState();
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2005-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2005-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -32,10 +32,14 @@ public class BufferedOpCodes {
public static final int DRAW_POLY = 12;
public static final int DRAW_PIXEL = 13;
public static final int DRAW_SCANLINES = 14;
public static final int DRAW_PARALLELOGRAM = 15;
public static final int DRAW_AAPARALLELOGRAM = 16;
// fill ops
public static final int FILL_RECT = 20;
public static final int FILL_SPANS = 21;
public static final int FILL_PARALLELOGRAM = 22;
public static final int FILL_AAPARALLELOGRAM = 23;
// copy-related ops
public static final int COPY_AREA = 30;
@ -67,6 +71,9 @@ public class BufferedOpCodes {
public static final int DISPOSE_CONFIG = 74;
public static final int INVALIDATE_CONTEXT = 75;
public static final int SYNC = 76;
public static final int RESTORE_DEVICES = 77;
public static final int SAVE_STATE = 78;
public static final int RESTORE_STATE = 79;
// multibuffering ops
public static final int SWAP_BUFFERS = 80;

View File

@ -1,5 +1,5 @@
/*
* Copyright 2005-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2005-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -25,6 +25,7 @@
package sun.java2d.pipe;
import java.awt.BasicStroke;
import java.awt.Polygon;
import java.awt.Shape;
import java.awt.geom.AffineTransform;
@ -33,6 +34,7 @@ import java.awt.geom.Ellipse2D;
import java.awt.geom.Path2D;
import java.awt.geom.IllegalPathStateException;
import java.awt.geom.PathIterator;
import java.awt.geom.Rectangle2D;
import java.awt.geom.RoundRectangle2D;
import sun.java2d.SunGraphics2D;
import sun.java2d.loops.ProcessPath;
@ -51,8 +53,10 @@ import static sun.java2d.pipe.BufferedOpCodes.*;
* simply delegate to draw(Shape) and fill(Shape), respectively.
*/
public abstract class BufferedRenderPipe
implements PixelDrawPipe, PixelFillPipe, ShapeDrawPipe
implements PixelDrawPipe, PixelFillPipe, ShapeDrawPipe, ParallelogramPipe
{
ParallelogramPipe aapgrampipe = new AAParallelogramPipe();
static final int BYTES_PER_POLY_POINT = 8;
static final int BYTES_PER_SCANLINE = 12;
static final int BYTES_PER_SPAN = 16;
@ -67,12 +71,17 @@ public abstract class BufferedRenderPipe
this.drawHandler = new BufferedDrawHandler();
}
public ParallelogramPipe getAAParallelogramPipe() {
return aapgrampipe;
}
/**
* Validates the state in the provided SunGraphics2D object and sets up
* any special resources for this operation (e.g. enabling gradient
* shading).
*/
protected abstract void validateContext(SunGraphics2D sg2d);
protected abstract void validateContextAA(SunGraphics2D sg2d);
public void drawLine(SunGraphics2D sg2d,
int x1, int y1, int x2, int y2)
@ -398,6 +407,98 @@ public abstract class BufferedRenderPipe
}
}
public void fillParallelogram(SunGraphics2D sg2d,
double x, double y,
double dx1, double dy1,
double dx2, double dy2)
{
rq.lock();
try {
validateContext(sg2d);
rq.ensureCapacity(28);
buf.putInt(FILL_PARALLELOGRAM);
buf.putFloat((float) x);
buf.putFloat((float) y);
buf.putFloat((float) dx1);
buf.putFloat((float) dy1);
buf.putFloat((float) dx2);
buf.putFloat((float) dy2);
} finally {
rq.unlock();
}
}
public void drawParallelogram(SunGraphics2D sg2d,
double x, double y,
double dx1, double dy1,
double dx2, double dy2,
double lw1, double lw2)
{
rq.lock();
try {
validateContext(sg2d);
rq.ensureCapacity(36);
buf.putInt(DRAW_PARALLELOGRAM);
buf.putFloat((float) x);
buf.putFloat((float) y);
buf.putFloat((float) dx1);
buf.putFloat((float) dy1);
buf.putFloat((float) dx2);
buf.putFloat((float) dy2);
buf.putFloat((float) lw1);
buf.putFloat((float) lw2);
} finally {
rq.unlock();
}
}
private class AAParallelogramPipe implements ParallelogramPipe {
public void fillParallelogram(SunGraphics2D sg2d,
double x, double y,
double dx1, double dy1,
double dx2, double dy2)
{
rq.lock();
try {
validateContextAA(sg2d);
rq.ensureCapacity(28);
buf.putInt(FILL_AAPARALLELOGRAM);
buf.putFloat((float) x);
buf.putFloat((float) y);
buf.putFloat((float) dx1);
buf.putFloat((float) dy1);
buf.putFloat((float) dx2);
buf.putFloat((float) dy2);
} finally {
rq.unlock();
}
}
public void drawParallelogram(SunGraphics2D sg2d,
double x, double y,
double dx1, double dy1,
double dx2, double dy2,
double lw1, double lw2)
{
rq.lock();
try {
validateContextAA(sg2d);
rq.ensureCapacity(36);
buf.putInt(DRAW_AAPARALLELOGRAM);
buf.putFloat((float) x);
buf.putFloat((float) y);
buf.putFloat((float) dx1);
buf.putFloat((float) dy1);
buf.putFloat((float) dx2);
buf.putFloat((float) dy2);
buf.putFloat((float) lw1);
buf.putFloat((float) lw2);
} finally {
rq.unlock();
}
}
}
public void draw(SunGraphics2D sg2d, Shape s) {
if (sg2d.strokeState == sg2d.STROKE_THIN) {
if (s instanceof Polygon) {

View File

@ -1,5 +1,5 @@
/*
* Copyright 2001-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2001-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -955,7 +955,7 @@ public class DrawImage implements DrawImagePipe
} else {
BlitBg blit = BlitBg.getFromCache(srcType, comp, dstType);
blit.BlitBg(srcData, dstData, sg.composite, clipRegion,
bgColor, sx, sy, dx, dy, w, h);
bgColor.getRGB(), sx, sy, dx, dy, w, h);
}
}

View File

@ -0,0 +1,66 @@
/*
* Copyright 2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.pipe;
import sun.java2d.SunGraphics2D;
/**
* This interface defines the set of calls that pipeline objects
* can use to pass on responsibility for drawing arbitrary
* parallelogram shapes.
* Six floating point numbers are provided and the parallelogram
* is defined as the quadrilateral with the following vertices:
* <pre>
* origin: (x, y)
* => (x+dx1, y+dy1)
* => (x+dx1+dx2, y+dy1+dy2)
* => (x+dx2, y+dy2)
* => origin
* </pre>
*/
public interface ParallelogramPipe {
public void fillParallelogram(SunGraphics2D sg,
double x, double y,
double dx1, double dy1,
double dx2, double dy2);
/**
* Draw a Parallelogram with the indicated line widths
* assuming a standard BasicStroke with MITER joins.
* lw1 specifies the width of the stroke along the dx1,dy1
* vector and lw2 specifies the width of the stroke along
* the dx2,dy2 vector.
* This is equivalent to outsetting the indicated
* parallelogram by lw/2 pixels, then insetting the
* same parallelogram by lw/2 pixels and filling the
* difference between the outer and inner parallelograms.
*/
public void drawParallelogram(SunGraphics2D sg,
double x, double y,
double dx1, double dy1,
double dx2, double dy2,
double lw1, double lw2);
}

View File

@ -0,0 +1,417 @@
/*
* Copyright 2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.pipe;
import java.awt.Shape;
import java.awt.BasicStroke;
import java.awt.geom.Line2D;
import java.awt.geom.Rectangle2D;
import java.awt.geom.AffineTransform;
import sun.java2d.SunGraphics2D;
import sun.awt.SunHints;
/**
* This class converts calls to the basic pixel rendering methods
* into calls to the methods on a ParallelogramPipe.
* Most calls are transformed into calls to the fill(Shape) method
* by the parent PixelToShapeConverter class, but some calls are
* transformed into calls to fill/drawParallelogram().
*/
public class PixelToParallelogramConverter extends PixelToShapeConverter
implements ShapeDrawPipe
{
ParallelogramPipe outrenderer;
double minPenSize;
double normPosition;
double normRoundingBias;
boolean adjustfill;
/**
* @param shapepipe pipeline to forward shape calls to
* @param pgrampipe pipeline to forward parallelogram calls to
* (and drawLine calls if possible)
* @param minPenSize minimum pen size for dropout control
* @param normPosition sub-pixel location to normalize endpoints
* for STROKE_NORMALIZE cases
* @param adjustFill boolean to control whethere normalization
* constants are also applied to fill operations
* (normally true for non-AA, false for AA)
*/
public PixelToParallelogramConverter(ShapeDrawPipe shapepipe,
ParallelogramPipe pgrampipe,
double minPenSize,
double normPosition,
boolean adjustfill)
{
super(shapepipe);
outrenderer = pgrampipe;
this.minPenSize = minPenSize;
this.normPosition = normPosition;
this.normRoundingBias = 0.5 - normPosition;
this.adjustfill = adjustfill;
}
public void drawLine(SunGraphics2D sg2d,
int x1, int y1, int x2, int y2)
{
if (!drawGeneralLine(sg2d, x1, y1, x2, y2)) {
super.drawLine(sg2d, x1, y1, x2, y2);
}
}
public void drawRect(SunGraphics2D sg2d,
int x, int y, int w, int h)
{
if (w >= 0 && h >= 0) {
if (sg2d.strokeState < SunGraphics2D.STROKE_CUSTOM) {
BasicStroke bs = ((BasicStroke) sg2d.stroke);
if (w > 0 && h > 0) {
if (bs.getLineJoin() == BasicStroke.JOIN_MITER &&
bs.getDashArray() == null)
{
double lw = bs.getLineWidth();
drawRectangle(sg2d, x, y, w, h, lw);
return;
}
} else {
// Note: This calls the integer version which
// will verify that the local drawLine optimizations
// work and call super.drawLine(), if not.
drawLine(sg2d, x, y, x+w, y+h);
return;
}
}
super.drawRect(sg2d, x, y, w, h);
}
}
public void fillRect(SunGraphics2D sg2d,
int x, int y, int w, int h)
{
if (w > 0 && h > 0) {
fillRectangle(sg2d, x, y, w, h);
}
}
public void draw(SunGraphics2D sg2d, Shape s) {
if (sg2d.strokeState < SunGraphics2D.STROKE_CUSTOM) {
BasicStroke bs = ((BasicStroke) sg2d.stroke);
if (s instanceof Rectangle2D) {
if (bs.getLineJoin() == BasicStroke.JOIN_MITER &&
bs.getDashArray() == null)
{
Rectangle2D r2d = (Rectangle2D) s;
double w = r2d.getWidth();
double h = r2d.getHeight();
double x = r2d.getX();
double y = r2d.getY();
if (w >= 0 && h >= 0) {
double lw = bs.getLineWidth();
drawRectangle(sg2d, x, y, w, h, lw);
}
return;
}
} else if (s instanceof Line2D) {
Line2D l2d = (Line2D) s;
if (drawGeneralLine(sg2d,
l2d.getX1(), l2d.getY1(),
l2d.getX2(), l2d.getY2()))
{
return;
}
}
}
outpipe.draw(sg2d, s);
}
public void fill(SunGraphics2D sg2d, Shape s) {
if (s instanceof Rectangle2D) {
Rectangle2D r2d = (Rectangle2D) s;
double w = r2d.getWidth();
double h = r2d.getHeight();
if (w > 0 && h > 0) {
double x = r2d.getX();
double y = r2d.getY();
fillRectangle(sg2d, x, y, w, h);
}
return;
}
outpipe.fill(sg2d, s);
}
static double len(double x, double y) {
return ((x == 0) ? Math.abs(y)
: ((y == 0) ? Math.abs(x)
: Math.sqrt(x * x + y * y)));
}
double normalize(double v) {
return Math.floor(v + normRoundingBias) + normPosition;
}
public boolean drawGeneralLine(SunGraphics2D sg2d,
double x1, double y1,
double x2, double y2)
{
if (sg2d.strokeState == SunGraphics2D.STROKE_CUSTOM ||
sg2d.strokeState == SunGraphics2D.STROKE_THINDASHED)
{
return false;
}
BasicStroke bs = (BasicStroke) sg2d.stroke;
int cap = bs.getEndCap();
if (cap == BasicStroke.CAP_ROUND || bs.getDashArray() != null) {
// TODO: we could construct the GeneralPath directly
// for CAP_ROUND and save a lot of processing in that case...
// And again, we would need to deal with dropout control...
return false;
}
double lw = bs.getLineWidth();
// Save the original dx, dy in case we need it to transform
// the linewidth as a perpendicular vector below
double dx = x2 - x1;
double dy = y2 - y1;
switch (sg2d.transformState) {
case SunGraphics2D.TRANSFORM_GENERIC:
case SunGraphics2D.TRANSFORM_TRANSLATESCALE:
{
double coords[] = {x1, y1, x2, y2};
sg2d.transform.transform(coords, 0, coords, 0, 2);
x1 = coords[0];
y1 = coords[1];
x2 = coords[2];
y2 = coords[3];
}
break;
case SunGraphics2D.TRANSFORM_ANY_TRANSLATE:
case SunGraphics2D.TRANSFORM_INT_TRANSLATE:
{
double tx = sg2d.transform.getTranslateX();
double ty = sg2d.transform.getTranslateY();
x1 += tx;
y1 += ty;
x2 += tx;
y2 += ty;
}
break;
case SunGraphics2D.TRANSFORM_ISIDENT:
break;
default:
throw new InternalError("unknown TRANSFORM state...");
}
if (sg2d.strokeHint != SunHints.INTVAL_STROKE_PURE) {
if (sg2d.strokeState == SunGraphics2D.STROKE_THIN &&
outrenderer instanceof PixelDrawPipe)
{
// PixelDrawPipes will add sg2d.transXY so we need to factor
// that out...
int ix1 = (int) Math.floor(x1 - sg2d.transX);
int iy1 = (int) Math.floor(y1 - sg2d.transY);
int ix2 = (int) Math.floor(x2 - sg2d.transX);
int iy2 = (int) Math.floor(y2 - sg2d.transY);
((PixelDrawPipe)outrenderer).drawLine(sg2d, ix1, iy1, ix2, iy2);
return true;
}
x1 = normalize(x1);
y1 = normalize(y1);
x2 = normalize(x2);
y2 = normalize(y2);
}
if (sg2d.transformState >= SunGraphics2D.TRANSFORM_TRANSLATESCALE) {
// Transform the linewidth...
// calculate the scaling factor for a unit vector
// perpendicular to the original user space line.
double len = len(dx, dy);
if (len == 0) {
dx = len = 1;
// dy = 0; already
}
// delta transform the transposed (90 degree rotated) unit vector
double unitvector[] = {dy/len, -dx/len};
sg2d.transform.deltaTransform(unitvector, 0, unitvector, 0, 1);
lw *= len(unitvector[0], unitvector[1]);
}
lw = Math.max(lw, minPenSize);
dx = x2 - x1;
dy = y2 - y1;
double len = len(dx, dy);
double udx, udy;
if (len == 0) {
if (cap == BasicStroke.CAP_BUTT) {
return true;
}
udx = lw;
udy = 0;
} else {
udx = lw * dx / len;
udy = lw * dy / len;
}
double px = x1 + udy / 2.0;
double py = y1 - udx / 2.0;
if (cap == BasicStroke.CAP_SQUARE) {
px -= udx / 2.0;
py -= udy / 2.0;
dx += udx;
dy += udy;
}
outrenderer.fillParallelogram(sg2d, px, py, -udy, udx, dx, dy);
return true;
}
public void fillRectangle(SunGraphics2D sg2d,
double rx, double ry,
double rw, double rh)
{
double px, py;
double dx1, dy1, dx2, dy2;
AffineTransform txform = sg2d.transform;
dx1 = txform.getScaleX();
dy1 = txform.getShearY();
dx2 = txform.getShearX();
dy2 = txform.getScaleY();
px = rx * dx1 + ry * dx2 + txform.getTranslateX();
py = rx * dy1 + ry * dy2 + txform.getTranslateY();
dx1 *= rw;
dy1 *= rw;
dx2 *= rh;
dy2 *= rh;
if (adjustfill &&
sg2d.strokeState < SunGraphics2D.STROKE_CUSTOM &&
sg2d.strokeHint != SunHints.INTVAL_STROKE_PURE)
{
double newx = normalize(px);
double newy = normalize(py);
dx1 = normalize(px + dx1) - newx;
dy1 = normalize(py + dy1) - newy;
dx2 = normalize(px + dx2) - newx;
dy2 = normalize(py + dy2) - newy;
px = newx;
py = newy;
}
outrenderer.fillParallelogram(sg2d, px, py, dx1, dy1, dx2, dy2);
}
public void drawRectangle(SunGraphics2D sg2d,
double rx, double ry,
double rw, double rh,
double lw)
{
double px, py;
double dx1, dy1, dx2, dy2;
double lw1, lw2;
AffineTransform txform = sg2d.transform;
dx1 = txform.getScaleX();
dy1 = txform.getShearY();
dx2 = txform.getShearX();
dy2 = txform.getScaleY();
px = rx * dx1 + ry * dx2 + txform.getTranslateX();
py = rx * dy1 + ry * dy2 + txform.getTranslateY();
// lw along dx1,dy1 scale by transformed length of dx2,dy2 vectors
// and vice versa
lw1 = len(dx1, dy1) * lw;
lw2 = len(dx2, dy2) * lw;
dx1 *= rw;
dy1 *= rw;
dx2 *= rh;
dy2 *= rh;
if (sg2d.strokeState < SunGraphics2D.STROKE_CUSTOM &&
sg2d.strokeHint != SunHints.INTVAL_STROKE_PURE)
{
double newx = normalize(px);
double newy = normalize(py);
dx1 = normalize(px + dx1) - newx;
dy1 = normalize(py + dy1) - newy;
dx2 = normalize(px + dx2) - newx;
dy2 = normalize(py + dy2) - newy;
px = newx;
py = newy;
}
lw1 = Math.max(lw1, minPenSize);
lw2 = Math.max(lw2, minPenSize);
double len1 = len(dx1, dy1);
double len2 = len(dx2, dy2);
if (lw1 >= len1 || lw2 >= len2) {
// The line widths are large enough to consume the
// entire hole in the middle of the parallelogram
// so we can just fill the outer parallelogram.
fillOuterParallelogram(sg2d,
px, py, dx1, dy1, dx2, dy2,
len1, len2, lw1, lw2);
} else {
outrenderer.drawParallelogram(sg2d,
px, py, dx1, dy1, dx2, dy2,
lw1 / len1, lw2 / len2);
}
}
/**
* This utility function handles the case where a drawRectangle
* operation discovered that the interior hole in the rectangle
* or parallelogram has been completely filled in by the stroke
* width. It calculates the outer parallelogram of the stroke
* and issues a single fillParallelogram request to fill it.
*/
public void fillOuterParallelogram(SunGraphics2D sg2d,
double px, double py,
double dx1, double dy1,
double dx2, double dy2,
double len1, double len2,
double lw1, double lw2)
{
double udx1 = dx1 / len1;
double udy1 = dy1 / len1;
double udx2 = dx2 / len2;
double udy2 = dy2 / len2;
if (len1 == 0) {
// len1 is 0, replace udxy1 with perpendicular of udxy2
if (len2 == 0) {
// both are 0, use a unit Y vector for udxy2
udx2 = 0;
udy2 = 1;
}
udx1 = udy2;
udy1 = -udx2;
} else if (len2 == 0) {
// len2 is 0, replace udxy2 with perpendicular of udxy1
udx2 = udy1;
udy2 = -udx1;
}
udx1 *= lw1;
udy1 *= lw1;
udx2 *= lw2;
udy2 *= lw2;
px -= (udx1 + udx2) / 2;
py -= (udy1 + udy2) / 2;
dx1 += udx1;
dy1 += udy1;
dx2 += udx2;
dy2 += udy2;
outrenderer.fillParallelogram(sg2d, px, py, dx1, dy1, dx2, dy2);
}
}

View File

@ -0,0 +1,59 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.pipe.hw;
/**
* An interface for receiving notifications about imminent accelerated device's
* events. Upon receiving such event appropriate actions can be taken (for
* example, resources associated with the device can be freed).
*/
public interface AccelDeviceEventListener {
/**
* Called when the device is about to be reset.
*
* One must release all native resources associated with the device which
* prevent the device from being reset (such as Default Pool resources for
* the D3D pipeline).
*
* It is safe to remove the listener while in the call back.
*
* Note: this method is called on the rendering thread,
* do not call into user code, do not take RQ lock!
*/
public void onDeviceReset();
/**
* Called when the device is about to be disposed of.
*
* One must release all native resources associated with the device.
*
* It is safe to remove the listener while in the call back.
*
* Note: this method is called on the rendering thread,
* do not call into user code, do not take RQ lock!
*/
public void onDeviceDispose();
}

View File

@ -0,0 +1,167 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.pipe.hw;
import java.util.Collections;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;
/**
* This class is used to notify listeners about accelerated device's
* events such as device reset or dispose that are about to occur.
*/
public class AccelDeviceEventNotifier {
private static AccelDeviceEventNotifier theInstance;
/**
* A device is about to be reset. The listeners have to release all
* resources associated with the device which are required for the device
* to be reset.
*/
public static final int DEVICE_RESET = 0;
/**
* A device is about to be disposed. The listeners have to release all
* resources associated with the device.
*/
public static final int DEVICE_DISPOSED = 1;
private final Map<AccelDeviceEventListener, Integer> listeners;
private AccelDeviceEventNotifier() {
listeners = Collections.synchronizedMap(
new HashMap<AccelDeviceEventListener, Integer>(1));
}
/**
* Returns a singleton of AccelDeviceEventNotifier if it exists. If the
* passed boolean is false and singleton doesn't exist yet, null is
* returned. If the passed boolean is {@code true} and singleton doesn't
* exist it will be created and returned.
*
* @param create whether to create a singleton instance if doesn't yet
* exist
* @return a singleton instance or null
*/
private static synchronized
AccelDeviceEventNotifier getInstance(boolean create)
{
if (theInstance == null && create) {
theInstance = new AccelDeviceEventNotifier();
}
return theInstance;
}
/**
* Called to indicate that a device event had occured.
* If a singleton exists, the listeners (those associated with
* the device) will be notified.
*
* @param screen a screen number of the device which is a source of
* the event
* @param eventType a type of the event
* @see #DEVICE_DISPOSED
* @see #DEVICE_RESET
*/
public static final void eventOccured(int screen, int eventType) {
AccelDeviceEventNotifier notifier = getInstance(false);
if (notifier != null) {
notifier.notifyListeners(eventType, screen);
}
}
/**
* Adds the listener associated with a device on particular screen.
*
* Note: the listener must be removed as otherwise it will forever
* be referenced by the notifier.
*
* @param l the listener
* @param screen the screen number indicating which device the listener is
* interested in.
*/
public static final void addListener(AccelDeviceEventListener l,int screen){
getInstance(true).add(l, screen);
}
/**
* Removes the listener.
*
* @param l the listener
*/
public static final void removeListener(AccelDeviceEventListener l) {
getInstance(true).remove(l);
}
private final void add(AccelDeviceEventListener theListener, int screen) {
listeners.put(theListener, screen);
}
private final void remove(AccelDeviceEventListener theListener) {
listeners.remove(theListener);
}
/**
* Notifies the listeners associated with the screen's device about the
* event.
*
* Implementation note: the current list of listeners is first duplicated
* which allows the listeners to remove themselves during the iteration.
*
* @param screen a screen number with which the device which is a source of
* the event is associated with
* @param eventType a type of the event
* @see #DEVICE_DISPOSED
* @see #DEVICE_RESET
*/
private final void notifyListeners(int deviceEventType, int screen) {
HashMap<AccelDeviceEventListener, Integer> listClone;
Set<AccelDeviceEventListener> cloneSet;
synchronized(listeners) {
listClone =
new HashMap<AccelDeviceEventListener, Integer>(listeners);
}
cloneSet = listClone.keySet();
Iterator<AccelDeviceEventListener> itr = cloneSet.iterator();
while (itr.hasNext()) {
AccelDeviceEventListener current = itr.next();
Integer i = listClone.get(current);
// only notify listeners which are interested in this device
if (i != null && i.intValue() != screen) {
continue;
}
if (deviceEventType == DEVICE_RESET) {
current.onDeviceReset();
} else if (deviceEventType == DEVICE_DISPOSED) {
current.onDeviceDispose();
}
}
}
}

View File

@ -0,0 +1,95 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.pipe.hw;
import java.awt.image.VolatileImage;
/**
* Implementors of this interface provida a way to create a
* {@code VolatileImage} whose destination surface is an
* {@link AccelSurface} of specified type.
*
* @see AccelSurface
*/
public interface AccelGraphicsConfig extends BufferedContextProvider {
/**
* Returns a VolatileImage with specified width, height, transparency
* and guaranteed accelerated surface type. If such image can not be created
* (out of vram error, specific surface type is not supported) null
* is returned.
*
* Note: if {@link AccelSurface#TEXTURE} type is requested, rendering
* to the image will be denied by throwing
* {@code UnsupportedOperationException }
* from {@link java.awt.image.VolatileImage#getGraphics} and
* {@link java.awt.image.VolatileImage#createGraphics}
*
* @param width the width of the returned {@code VolatileImage}
* @param height the height of the returned {@code VolatileImage}
* @param transparency the specified transparency mode
* @param type requested accelerated surface type as specified by constants
* in AccelSurface interface
* @return a {@code VolatileImage} backed up by requested accelerated
* surface type or null
* @throws IllegalArgumentException if the transparency is not a valid value
* @see AccelSurface#TEXTURE
* @see AccelSurface#RT_PLAIN
* @see AccelSurface#RT_TEXTURE
*/
public VolatileImage createCompatibleVolatileImage(int width, int height,
int transparency,
int type);
/**
* Returns object representing capabilities of the context associated
* with this {@code AccelGraphicsConfig}.
*
* @return ContextCapabilities object representing caps
* @see ContextCapabilities
*/
public ContextCapabilities getContextCapabilities();
/**
* Adds an {@code AccelDeviceEventListener} to listen to accelerated
* device's (which is associated with this {@code AccelGraphicsConfig})
* events.
*
* Note: a hard link to the listener may be kept so it must be explicitly
* removed via {@link #removeDeviceEventListener()}.
*
* @param l the listener
* @see AccelDeviceEventListener
*/
public void addDeviceEventListener(AccelDeviceEventListener l);
/**
* Removes an {@code AccelDeviceEventListener} from the list of listeners
* for this device's events.
*
* @param l the listener
* @see AccelDeviceEventListener
*/
public void removeDeviceEventListener(AccelDeviceEventListener l);
}

View File

@ -0,0 +1,136 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.pipe.hw;
import java.awt.Rectangle;
import sun.java2d.Surface;
/**
* Abstraction for a hardware accelerated surface.
*/
public interface AccelSurface extends BufferedContextProvider, Surface {
/**
* Undefined
*/
public static final int UNDEFINED = 0;
/**
* Window (or window substitute) surface
*/
public static final int WINDOW = 1;
/**
* Render-To Plain surface (pbuffer for OpenGL, Render Target surface
* for Direct3D)
*/
public static final int RT_PLAIN = 2;
/**
* Texture surface
*/
public static final int TEXTURE = 3;
/**
* A back-buffer surface (SwapChain surface for Direct3D, backbuffer for
* OpenGL)
*/
public static final int FLIP_BACKBUFFER = 4;
/**
* Render-To Texture surface (fbobject for OpenGL, texture with render-to
* attribute for Direct3D)
*/
public static final int RT_TEXTURE = 5;
/**
* Returns {@code int} representing surface's type as defined by constants
* in this interface.
*
* @return an integer representing this surface's type
* @see AccelSurface#UNDEFINED
* @see AccelSurface#WINDOW
* @see AccelSurface#RT_PLAIN
* @see AccelSurface#TEXTURE
* @see AccelSurface#FLIP_BACKBUFFER
* @see AccelSurface#RT_TEXTURE
*/
public int getType();
/**
* Returns a pointer to the native surface data associated with this
* surface.
* Note: this pointer is only valid on the rendering thread.
*
* @return pointer to the native surface's data
*/
public long getNativeOps();
/**
* Returns a pointer to the real native resource
* of the specified type associated with this AccelSurface.
* Note: this pointer is only valid on the rendering thread.
*
* @param resType the type of the requested resource
* @return a long containing a pointer to the native resource of the
* specified type or 0L if such resource doesn't exist for this surface
*/
public long getNativeResource(int resType);
/**
* Marks this surface dirty.
*/
public void markDirty();
/**
* Returns whether the pipeline considers this surface valid. A surface
* may become invalid if it is disposed of, or resized.
*
* @return true if valid, false otherwise
*/
public boolean isValid();
/**
* Returns whether this surface is lost. The return value is only valid
* on the render thread, meaning that even if this method returns
* {@code true} it could be lost in the next moment unless it is called
* on the rendering thread.
*
* @return true if the surface is known to be lost, false otherwise
*/
public boolean isSurfaceLost();
/**
* Returns the requested bounds of the destination surface. The real bounds
* of the native accelerated surface may differ. Use
* {@link #getNativeBounds} to get the bounds of the native surface.
*
* @return Rectangle representing java surface's bounds
*/
public Rectangle getBounds();
/**
* Returns real bounds of the native surface, which may differ from those
* returned by {@link #getBounds}.
*
* @return Rectangle representing native surface's bounds
*/
public Rectangle getNativeBounds();
}

View File

@ -0,0 +1,74 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.pipe.hw;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.GraphicsConfiguration;
import sun.awt.image.SunVolatileImage;
import static sun.java2d.pipe.hw.AccelSurface.*;
/**
* This is an image with forced type of the accelerated surface.
*/
public class AccelTypedVolatileImage extends SunVolatileImage {
/**
* Creates a volatile image with specified type of accelerated surface.
*
* @param graphicsConfig a GraphicsConfiguration for which this image should
* be created.
* @param width width
* @param height width
* @param transparency type of {@link java.awt.Transparency transparency}
* requested for the image
* @param accType type of the desired accelerated surface as defined in
* AccelSurface interface
* @see sun.java2d.pipe.hw.AccelSurface
*/
public AccelTypedVolatileImage(GraphicsConfiguration graphicsConfig,
int width, int height, int transparency,
int accType)
{
super(null, graphicsConfig, width, height, null, transparency,
null, accType);
}
/**
* {@inheritDoc}
*
* This method will throw {@code UnsupportedOperationException} if it this
* image's destination surface can not be rendered to.
*/
@Override
public Graphics2D createGraphics() {
if (getForcedAccelSurfaceType() == TEXTURE) {
throw new UnsupportedOperationException("Can't render " +
"to a non-RT Texture");
}
return super.createGraphics();
}
}

View File

@ -0,0 +1,45 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.pipe.hw;
import sun.java2d.pipe.BufferedContext;
/**
* Classes implementing this interface can provide the {@code BufferedContext}
* associated with or used by them.
*
* @see sun.java2d.pipe.BufferedContext
*/
public interface BufferedContextProvider {
/**
* Retrieves a context associated with object implementing this
* interface.
*
* @return associated context
* @see sun.java2d.pipe.BufferedContext
*/
public BufferedContext getContext();
}

View File

@ -0,0 +1,128 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.pipe.hw;
/**
* Represents a set of capabilities of a BufferedContext and associated
* AccelGraphicsConfig.
*
* @see AccelGraphicsConfig
*/
public class ContextCapabilities {
/** Indicates that the context has no capabilities. */
public static final int CAPS_EMPTY = (0 << 0);
/** Indicates that the context supports RT surfaces with alpha channel. */
public static final int CAPS_RT_PLAIN_ALPHA = (1 << 1);
/** Indicates that the context supports RT textures with alpha channel. */
public static final int CAPS_RT_TEXTURE_ALPHA = (1 << 2);
/** Indicates that the context supports opaque RT textures. */
public static final int CAPS_RT_TEXTURE_OPAQUE = (1 << 3);
/** Indicates that the context supports multitexturing. */
public static final int CAPS_MULTITEXTURE = (1 << 4);
/** Indicates that the context supports non-pow2 texture dimensions. */
public static final int CAPS_TEXNONPOW2 = (1 << 5);
/** Indicates that the context supports non-square textures. */
public static final int CAPS_TEXNONSQUARE = (1 << 6);
/** Indicates that the context supports pixel shader 2.0 or better. */
public static final int CAPS_PS20 = (1 << 7);
/** Indicates that the context supports pixel shader 3.0 or better. */
public static final int CAPS_PS30 = (1 << 8);
/*
* Pipeline contexts should use this for defining pipeline-specific
* capabilities, for example:
* int CAPS_D3D_1 = (FIRST_PRIVATE_CAP << 0);
* int CAPS_D3D_2 = (FIRST_PRIVATE_CAP << 1);
*/
protected static final int FIRST_PRIVATE_CAP = (1 << 16);
protected final int caps;
protected final String adapterId;
/**
* Constructs a {@code ContextCapabilities} object.
* @param caps an {@code int} representing the capabilities
* @param a {@code String} representing the name of the adapter, or null,
* in which case the adapterId will be set to "unknown adapter".
*/
protected ContextCapabilities(int caps, String adapterId) {
this.caps = caps;
this.adapterId = adapterId != null ? adapterId : "unknown adapter";
}
/**
* Returns a string representing the name of the graphics adapter if such
* could be determined. It is guaranteed to never return {@code null}.
* @return string representing adapter id
*/
public String getAdapterId() {
return adapterId;
}
/**
* Returns an {@code int} with capabilities (OR-ed constants defined in
* this class and its pipeline-specific subclasses).
* @return capabilities as {@code int}
*/
public int getCaps() {
return caps;
}
@Override
public String toString() {
StringBuffer buf =
new StringBuffer("ContextCapabilities: adapter=" +
adapterId+", caps=");
if (caps == CAPS_EMPTY) {
buf.append("CAPS_EMPTY");
} else {
if ((caps & CAPS_RT_PLAIN_ALPHA) != 0) {
buf.append("CAPS_RT_PLAIN_ALPHA|");
}
if ((caps & CAPS_RT_TEXTURE_ALPHA) != 0) {
buf.append("CAPS_RT_TEXTURE_ALPHA|");
}
if ((caps & CAPS_RT_TEXTURE_OPAQUE) != 0) {
buf.append("CAPS_RT_TEXTURE_OPAQUE|");
}
if ((caps & CAPS_MULTITEXTURE) != 0) {
buf.append("CAPS_MULTITEXTURE|");
}
if ((caps & CAPS_TEXNONPOW2) != 0) {
buf.append("CAPS_TEXNONPOW2|");
}
if ((caps & CAPS_TEXNONSQUARE) != 0) {
buf.append("CAPS_TEXNONSQUARE|");
}
if ((caps & CAPS_PS20) != 0) {
buf.append("CAPS_PS20|");
}
if ((caps & CAPS_PS30) != 0) {
buf.append("CAPS_PS30|");
}
}
return buf.toString();
}
}

View File

@ -0,0 +1,154 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.pipe.hw;
import java.awt.BufferCapabilities;
import java.awt.ImageCapabilities;
/**
* Provides extended BufferStrategy capabilities, allowing to specify
* the type of vertical refresh synchronization for a buffer strategy.
*
* This BS capability is always page flipping because v-sync is only relevant
* to flipping buffer strategies.
*
* Note that asking for a v-synced BS doesn't necessarily guarantee that it will
* be v-synced since the vsync capability may be disabled in the driver, or
* there may be other restriction (like a number of v-synced buffer strategies
* allowed per vm). Because of this {@code createBufferStrategy} doesn't
* throw {@code AWTException} when a v-synced BS could not be created when
* requested.
*
* @see java.awt.Canvas#createBufferStrategy(int, BufferCapabilities)
* @see java.awt.Window#createBufferStrategy(int, BufferCapabilities)
*/
public class ExtendedBufferCapabilities extends BufferCapabilities {
/**
* Type of synchronization on vertical retrace.
*/
public static enum VSyncType {
/**
* Use the default v-sync mode appropriate for given BufferStrategy
* and situation.
*/
VSYNC_DEFAULT(0),
/**
* Synchronize flip on vertical retrace.
*/
VSYNC_ON(1),
/**
* Do not synchronize flip on vertical retrace.
*/
VSYNC_OFF(2);
/**
* Used to identify the v-sync type (independent of the constants
* order as opposed to {@code ordinal()}).
*/
public int id() {
return id;
}
private VSyncType(int id) {
this.id = id;
}
private int id;
}
private VSyncType vsync;
/**
* Creates an ExtendedBufferCapabilities object with front/back/flip caps
* from the passed cap, and VSYNC_DEFAULT v-sync mode.
*/
public ExtendedBufferCapabilities(BufferCapabilities caps) {
super(caps.getFrontBufferCapabilities(),
caps.getBackBufferCapabilities(),
caps.getFlipContents());
this.vsync = VSyncType.VSYNC_DEFAULT;
}
/**
* Creates an ExtendedBufferCapabilities instance with front/back/flip caps
* from the passed caps, and VSYNC_DEFAULT v-sync mode.
*/
public ExtendedBufferCapabilities(ImageCapabilities front,
ImageCapabilities back, FlipContents flip)
{
super(front, back, flip);
this.vsync = VSyncType.VSYNC_DEFAULT;
}
/**
* Creates an ExtendedBufferCapabilities instance with front/back/flip caps
* from the passed image/flip caps, and the v-sync type.
*/
public ExtendedBufferCapabilities(ImageCapabilities front,
ImageCapabilities back, FlipContents flip,
VSyncType t)
{
super(front, back, flip);
this.vsync = t;
}
/**
* Creates an ExtendedBufferCapabilities instance with front/back/flip caps
* from the passed cap, and the passed v-sync mode.
*/
public ExtendedBufferCapabilities(BufferCapabilities caps, VSyncType t) {
super(caps.getFrontBufferCapabilities(),
caps.getBackBufferCapabilities(),
caps.getFlipContents());
this.vsync = t;
}
/**
* Creates an ExtendedBufferCapabilities instance with front/back/flip caps
* from the object, and passed v-sync mode.
*/
public ExtendedBufferCapabilities derive(VSyncType t) {
return new ExtendedBufferCapabilities(this, t);
}
/**
* Returns the type of v-sync requested by this capabilities instance.
*/
public VSyncType getVSync() {
return vsync;
}
@Override
public final boolean isPageFlipping() {
return true;
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -45,6 +45,19 @@
* list describing the cache as new glyphs are added. Platform specific
* glyph caching code is responsible for actually creating the accelerated
* memory surface that will contain the individual glyph images.
*
* Each glyph contains a reference to a list of cell infos - one per glyph
* cache. There may be multiple glyph caches (for example, one per graphics
* adapter), so if the glyph is cached on two devices its cell list will
* consists of two elements corresponding to different glyph caches.
*
* The platform-specific glyph caching code is supposed to use
* GetCellInfoForCache method for retrieving cache infos from the glyph's list.
*
* Note that if it is guaranteed that there will be only one global glyph
* cache then it one does not have to use AccelGlyphCache_GetCellInfoForCache
* for retrieving cell info for the glyph, but instead just use the struct's
* field directly.
*/
GlyphCacheInfo *
AccelGlyphCache_Init(jint width, jint height,
@ -86,8 +99,11 @@ AccelGlyphCache_Init(jint width, jint height,
* "virtual" glyph cache is available for the glyph image. Platform specific
* glyph caching code is responsible for actually caching the glyph image
* in the associated accelerated memory surface.
*
* Returns created cell info if it was successfully created and added to the
* cache and glyph's cell lists, NULL otherwise.
*/
void
CacheCellInfo *
AccelGlyphCache_AddGlyph(GlyphCacheInfo *cache, GlyphInfo *glyph)
{
CacheCellInfo *cellinfo = NULL;
@ -99,7 +115,7 @@ AccelGlyphCache_AddGlyph(GlyphCacheInfo *cache, GlyphInfo *glyph)
if ((glyph->width > cache->cellWidth) ||
(glyph->height > cache->cellHeight))
{
return;
return NULL;
}
if (!cache->isFull) {
@ -126,9 +142,8 @@ AccelGlyphCache_AddGlyph(GlyphCacheInfo *cache, GlyphInfo *glyph)
// create new CacheCellInfo
cellinfo = (CacheCellInfo *)malloc(sizeof(CacheCellInfo));
if (cellinfo == NULL) {
glyph->cellInfo = NULL;
J2dTraceLn(J2D_TRACE_ERROR, "could not allocate CellInfo");
return;
return NULL;
}
cellinfo->cacheInfo = cache;
@ -136,6 +151,8 @@ AccelGlyphCache_AddGlyph(GlyphCacheInfo *cache, GlyphInfo *glyph)
cellinfo->timesRendered = 0;
cellinfo->x = x;
cellinfo->y = y;
cellinfo->leftOff = 0;
cellinfo->rightOff = 0;
cellinfo->tx1 = (jfloat)cellinfo->x / cache->width;
cellinfo->ty1 = (jfloat)cellinfo->y / cache->height;
cellinfo->tx2 = cellinfo->tx1 + ((jfloat)w / cache->width);
@ -152,6 +169,7 @@ AccelGlyphCache_AddGlyph(GlyphCacheInfo *cache, GlyphInfo *glyph)
// add the new cell to the end of the list
cache->tail = cellinfo;
cellinfo->next = NULL;
cellinfo->nextGCI = NULL;
}
}
@ -210,9 +228,9 @@ AccelGlyphCache_AddGlyph(GlyphCacheInfo *cache, GlyphInfo *glyph)
cache->Flush();
}
// if the cell is occupied, notify the base glyph that its
// cached version is about to be kicked out
cellinfo->glyphInfo->cellInfo = NULL;
// if the cell is occupied, notify the base glyph that the
// cached version for this cache is about to be kicked out
AccelGlyphCache_RemoveCellInfo(cellinfo->glyphInfo, cellinfo);
}
// update cellinfo with glyph's occupied region information
@ -221,8 +239,9 @@ AccelGlyphCache_AddGlyph(GlyphCacheInfo *cache, GlyphInfo *glyph)
cellinfo->ty2 = cellinfo->ty1 + ((jfloat)h / cache->height);
}
// update the glyph's reference to its cache cell
glyph->cellInfo = cellinfo;
// add cache cell to the glyph's cells list
AccelGlyphCache_AddCellInfo(glyph, cellinfo);
return cellinfo;
}
/**
@ -251,10 +270,145 @@ AccelGlyphCache_Invalidate(GlyphCacheInfo *cache)
while (cellinfo != NULL) {
if (cellinfo->glyphInfo != NULL) {
// if the cell is occupied, notify the base glyph that its
// cached version is about to be invalidated
cellinfo->glyphInfo->cellInfo = NULL;
cellinfo->glyphInfo = NULL;
// cached version for this cache is about to be invalidated
AccelGlyphCache_RemoveCellInfo(cellinfo->glyphInfo, cellinfo);
}
cellinfo = cellinfo->next;
}
}
/**
* Invalidates and frees all cells and the cache itself. The "cache" pointer
* becomes invalid after this function returns.
*/
void
AccelGlyphCache_Free(GlyphCacheInfo *cache)
{
CacheCellInfo *cellinfo;
J2dTraceLn(J2D_TRACE_INFO, "AccelGlyphCache_Free");
if (cache == NULL) {
return;
}
// flush any pending vertices that may be depending on the current
// glyph cache
if (cache->Flush != NULL) {
cache->Flush();
}
while (cache->head != NULL) {
cellinfo = cache->head;
if (cellinfo->glyphInfo != NULL) {
// if the cell is occupied, notify the base glyph that its
// cached version for this cache is about to be invalidated
AccelGlyphCache_RemoveCellInfo(cellinfo->glyphInfo, cellinfo);
}
cache->head = cellinfo->next;
free(cellinfo);
}
free(cache);
}
/**
* Add cell info to the head of the glyph's list of cached cells.
*/
void
AccelGlyphCache_AddCellInfo(GlyphInfo *glyph, CacheCellInfo *cellInfo)
{
// assert (glyph != NULL && cellInfo != NULL)
J2dTraceLn(J2D_TRACE_INFO, "AccelGlyphCache_AddCellInfo");
J2dTraceLn2(J2D_TRACE_VERBOSE, " glyph 0x%x: adding cell 0x%x to the list",
glyph, cellInfo);
cellInfo->glyphInfo = glyph;
cellInfo->nextGCI = glyph->cellInfo;
glyph->cellInfo = cellInfo;
}
/**
* Removes cell info from the glyph's list of cached cells.
*/
void
AccelGlyphCache_RemoveCellInfo(GlyphInfo *glyph, CacheCellInfo *cellInfo)
{
CacheCellInfo *currCellInfo = glyph->cellInfo;
CacheCellInfo *prevInfo = NULL;
// assert (glyph!= NULL && glyph->cellInfo != NULL && cellInfo != NULL)
J2dTraceLn(J2D_TRACE_INFO, "AccelGlyphCache_RemoveCellInfo");
do {
if (currCellInfo == cellInfo) {
J2dTraceLn2(J2D_TRACE_VERBOSE,
" glyph 0x%x: removing cell 0x%x from glyph's list",
glyph, currCellInfo);
if (prevInfo == NULL) { // it's the head, chop-chop
glyph->cellInfo = currCellInfo->nextGCI;
} else {
prevInfo->nextGCI = currCellInfo->nextGCI;
}
currCellInfo->glyphInfo = NULL;
currCellInfo->nextGCI = NULL;
return;
}
prevInfo = currCellInfo;
currCellInfo = currCellInfo->nextGCI;
} while (currCellInfo != NULL);
J2dTraceLn2(J2D_TRACE_WARNING, "AccelGlyphCache_RemoveCellInfo: "\
"no cell 0x%x in glyph 0x%x's cell list",
cellInfo, glyph);
}
/**
* Removes cell info from the glyph's list of cached cells.
*/
JNIEXPORT void
AccelGlyphCache_RemoveAllCellInfos(GlyphInfo *glyph)
{
CacheCellInfo *currCell, *prevCell;
J2dTraceLn(J2D_TRACE_INFO, "AccelGlyphCache_RemoveAllCellInfos");
if (glyph == NULL || glyph->cellInfo == NULL) {
return;
}
// invalidate all of this glyph's accelerated cache cells
currCell = glyph->cellInfo;
do {
currCell->glyphInfo = NULL;
prevCell = currCell;
currCell = currCell->nextGCI;
prevCell->nextGCI = NULL;
} while (currCell != NULL);
glyph->cellInfo = NULL;
}
/**
* Returns cell info associated with particular cache from the glyph's list of
* cached cells.
*/
CacheCellInfo *
AccelGlyphCache_GetCellInfoForCache(GlyphInfo *glyph, GlyphCacheInfo *cache)
{
// assert (glyph != NULL && cache != NULL)
J2dTraceLn(J2D_TRACE_VERBOSE2, "AccelGlyphCache_GetCellInfoForCache");
if (glyph->cellInfo != NULL) {
CacheCellInfo *cellInfo = glyph->cellInfo;
do {
if (cellInfo->cacheInfo == cache) {
J2dTraceLn3(J2D_TRACE_VERBOSE2,
" glyph 0x%x: found cell 0x%x for cache 0x%x",
glyph, cellInfo, cache);
return cellInfo;
}
cellInfo = cellInfo->nextGCI;
} while (cellInfo != NULL);
}
J2dTraceLn2(J2D_TRACE_VERBOSE2, " glyph 0x%x: no cell for cache 0x%x",
glyph, cache);
return NULL;
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -26,6 +26,10 @@
#ifndef AccelGlyphCache_h_Included
#define AccelGlyphCache_h_Included
#ifdef __cplusplus
extern "C" {
#endif
#include "jni.h"
#include "fontscalerdefs.h"
@ -48,10 +52,18 @@ typedef struct {
struct _CacheCellInfo {
GlyphCacheInfo *cacheInfo;
struct GlyphInfo *glyphInfo;
// next cell info in the cache's list
CacheCellInfo *next;
// REMIND: find better name?
// next cell info in the glyph's cell list (next Glyph Cache Info)
CacheCellInfo *nextGCI;
jint timesRendered;
jint x;
jint y;
// number of pixels from the left or right edge not considered touched
// by the glyph
jint leftOff;
jint rightOff;
jfloat tx1;
jfloat ty1;
jfloat tx2;
@ -62,9 +74,24 @@ GlyphCacheInfo *
AccelGlyphCache_Init(jint width, jint height,
jint cellWidth, jint cellHeight,
FlushFunc *func);
void
CacheCellInfo *
AccelGlyphCache_AddGlyph(GlyphCacheInfo *cache, struct GlyphInfo *glyph);
void
AccelGlyphCache_Invalidate(GlyphCacheInfo *cache);
void
AccelGlyphCache_AddCellInfo(struct GlyphInfo *glyph, CacheCellInfo *cellInfo);
void
AccelGlyphCache_RemoveCellInfo(struct GlyphInfo *glyph, CacheCellInfo *cellInfo);
CacheCellInfo *
AccelGlyphCache_GetCellInfoForCache(struct GlyphInfo *glyph,
GlyphCacheInfo *cache);
JNIEXPORT void
AccelGlyphCache_RemoveAllCellInfos(struct GlyphInfo *glyph);
void
AccelGlyphCache_Free(GlyphCacheInfo *cache);
#ifdef __cplusplus
};
#endif
#endif /* AccelGlyphCache_h_Included */

View File

@ -1,5 +1,5 @@
/*
* Copyright 2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -35,6 +35,8 @@
#include "sun_font_StrikeCache.h"
static void *theNullScalerContext = NULL;
extern void AccelGlyphCache_RemoveAllCellInfos(GlyphInfo *glyph);
JNIEXPORT jlong JNICALL
Java_sun_font_NullFontScaler_getNullScalerContext
@ -294,7 +296,7 @@ JNIEXPORT void JNICALL Java_sun_font_StrikeCache_freeIntMemory
GlyphInfo *ginfo = (GlyphInfo *)ptrs[i];
if (ginfo->cellInfo != NULL) {
// invalidate this glyph's accelerated cache cell
ginfo->cellInfo->glyphInfo = NULL;
AccelGlyphCache_RemoveAllCellInfos(ginfo);
}
free((void*)ginfo);
}
@ -324,8 +326,7 @@ JNIEXPORT void JNICALL Java_sun_font_StrikeCache_freeLongMemory
if (ptrs[i] != 0L) {
GlyphInfo *ginfo = (GlyphInfo *) jlong_to_ptr(ptrs[i]);
if (ginfo->cellInfo != NULL) {
// invalidate this glyph's accelerated cache cell
ginfo->cellInfo->glyphInfo = NULL;
AccelGlyphCache_RemoveAllCellInfos(ginfo);
}
free((void*)ginfo);
}

View File

@ -0,0 +1,143 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
#include <malloc.h>
#include <string.h>
#include "ShaderList.h"
#include "Trace.h"
/**
* Creates a new ShaderInfo that wraps the given fragment program handle
* and related data and stores it at the front of the provided ShaderList.
* If the addition causes the ShaderList to outgrow its defined capacity,
* the least-recently used item in the list (including its fragment program
* object) will be disposed.
*/
void
ShaderList_AddProgram(ShaderList *programList,
jlong programID,
jint compType, jint compMode, jint flags)
{
ShaderInfo *info;
J2dTraceLn(J2D_TRACE_INFO, "ShaderList_AddProgram");
// create new ShaderInfo
info = (ShaderInfo *)malloc(sizeof(ShaderInfo));
if (info == NULL) {
J2dTraceLn(J2D_TRACE_ERROR,
"OGLContext_AddProgram: could not allocate ShaderInfo");
return;
}
// fill in the information
info->next = programList->head;
info->programID = programID;
info->compType = compType;
info->compMode = compMode;
info->flags = flags;
// insert it at the head of the list
programList->head = info;
// run through the list and see if we need to delete the least
// recently used item
{
int i = 1;
ShaderInfo *prev = NULL;
ShaderInfo *curr = info->next;
while (curr != NULL) {
if (i >= programList->maxItems) {
prev->next = NULL;
programList->dispose(curr->programID);
free(curr);
break;
}
i++;
prev = curr;
curr = curr->next;
}
}
}
/**
* Locates a fragment program handle given a list of shader programs
* (ShaderInfos), using the provided composite state and flags as search
* parameters. The "flags" parameter is a bitwise-or'd value that helps
* differentiate one program for another; the interpretation of this value
* varies depending on the type of shader (BufImgOp, Paint, etc) but here
* it is only used to find another ShaderInfo with that same "flags" value.
* If no matching program can be located, this method returns 0.
*/
jlong
ShaderList_FindProgram(ShaderList *programList,
jint compType, jint compMode, jint flags)
{
ShaderInfo *prev = NULL;
ShaderInfo *info = programList->head;
J2dTraceLn(J2D_TRACE_INFO, "ShaderList_FindProgram");
while (info != NULL) {
if (compType == info->compType &&
compMode == info->compMode &&
flags == info->flags)
{
// it's a match: move it to the front of the list (if it's not
// there already) and patch up the links
if (info != programList->head) {
prev->next = info->next;
info->next = programList->head;
programList->head = info;
}
return info->programID;
}
prev = info;
info = info->next;
}
return 0;
}
/**
* Disposes all entries (and their associated shader program objects)
* contained in the given ShaderList.
*/
void
ShaderList_Dispose(ShaderList *programList)
{
ShaderInfo *info = programList->head;
J2dTraceLn(J2D_TRACE_INFO, "ShaderList_Dispose");
while (info != NULL) {
ShaderInfo *tmp = info->next;
programList->dispose(info->programID);
free(info);
info = tmp;
}
programList->head = NULL;
}

View File

@ -0,0 +1,85 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
#ifndef ShaderList_h_Included
#define ShaderList_h_Included
#ifdef __cplusplus
extern "C" {
#endif
#include "jni.h"
#include "jlong.h"
typedef void (ShaderDisposeFunc)(jlong programID);
/**
* The following structures are used to maintain a list of fragment program
* objects and their associated attributes. Each logical shader (e.g.
* RadialGradientPaint shader, ConvolveOp shader) can have a number of
* different variants depending on a number of factors, such as whether
* antialiasing is enabled or the current composite mode. Since the number
* of possible combinations of these factors is in the hundreds, we need
* some way to create fragment programs on an as-needed basis, and also
* keep them in a limited sized cache to avoid creating too many objects.
*
* The ShaderInfo structure keeps a reference to the fragment program's
* handle, as well as some other values that help differentiate one ShaderInfo
* from another. ShaderInfos can be chained together to form a linked list.
*
* The ShaderList structure acts as a cache for ShaderInfos, placing
* most-recently used items at the front, and removing items from the
* cache when its size exceeds the "maxItems" limit.
*/
typedef struct _ShaderInfo ShaderInfo;
typedef struct {
ShaderInfo *head;
ShaderDisposeFunc *dispose;
jint maxItems;
} ShaderList;
struct _ShaderInfo {
ShaderInfo *next;
jlong programID;
jint compType;
jint compMode;
jint flags;
};
void ShaderList_AddProgram(ShaderList *programList,
jlong programID,
jint compType, jint compMode,
jint flags);
jlong ShaderList_FindProgram(ShaderList *programList,
jint compType, jint compMode,
jint flags);
void ShaderList_Dispose(ShaderList *programList);
#ifdef __cplusplus
};
#endif
#endif /* ShaderList_h_Included */

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -62,12 +62,18 @@ J2dTraceInit();
#define J2dTrace3(level, string, arg1, arg2, arg3)
#define J2dTrace4(level, string, arg1, arg2, arg3, arg4)
#define J2dTrace5(level, string, arg1, arg2, arg3, arg4, arg5)
#define J2dTrace6(level, string, arg1, arg2, arg3, arg4, arg5, arg6)
#define J2dTrace7(level, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7)
#define J2dTrace8(level, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8)
#define J2dTraceLn(level, string)
#define J2dTraceLn1(level, string, arg1)
#define J2dTraceLn2(level, string, arg1, arg2)
#define J2dTraceLn3(level, string, arg1, arg2, arg3)
#define J2dTraceLn4(level, string, arg1, arg2, arg3, arg4)
#define J2dTraceLn5(level, string, arg1, arg2, arg3, arg4, arg5)
#define J2dTraceLn6(level, string, arg1, arg2, arg3, arg4, arg5, arg6)
#define J2dTraceLn7(level, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7)
#define J2dTraceLn8(level, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8)
#else /* DEBUG */
#define J2dTrace(level, string) { \
J2dTraceImpl(level, JNI_FALSE, string); \
@ -87,6 +93,15 @@ J2dTraceInit();
#define J2dTrace5(level, string, arg1, arg2, arg3, arg4, arg5) { \
J2dTraceImpl(level, JNI_FALSE, string, arg1, arg2, arg3, arg4, arg5); \
}
#define J2dTrace6(level, string, arg1, arg2, arg3, arg4, arg5, arg6) { \
J2dTraceImpl(level, JNI_FALSE, string, arg1, arg2, arg3, arg4, arg5, arg6); \
}
#define J2dTrace7(level, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7) { \
J2dTraceImpl(level, JNI_FALSE, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7); \
}
#define J2dTrace8(level, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8) { \
J2dTraceImpl(level, JNI_FALSE, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8); \
}
#define J2dTraceLn(level, string) { \
J2dTraceImpl(level, JNI_TRUE, string); \
}
@ -105,6 +120,15 @@ J2dTraceInit();
#define J2dTraceLn5(level, string, arg1, arg2, arg3, arg4, arg5) { \
J2dTraceImpl(level, JNI_TRUE, string, arg1, arg2, arg3, arg4, arg5); \
}
#define J2dTraceLn6(level, string, arg1, arg2, arg3, arg4, arg5, arg6) { \
J2dTraceImpl(level, JNI_TRUE, string, arg1, arg2, arg3, arg4, arg5, arg6); \
}
#define J2dTraceLn7(level, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7) { \
J2dTraceImpl(level, JNI_TRUE, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7); \
}
#define J2dTraceLn8(level, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8) { \
J2dTraceImpl(level, JNI_TRUE, string, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8); \
}
#endif /* DEBUG */

View File

@ -1,5 +1,5 @@
/*
* Copyright 2000-2003 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2000-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -31,12 +31,12 @@
/*
* Class: sun_java2d_loops_BlitBg
* Method: BlitBg
* Signature: (Lsun/java2d/SurfaceData;Lsun/java2d/SurfaceData;Ljava/awt/Composite;Ljava/awt/Color;IIIIII)V
* Signature: (Lsun/java2d/SurfaceData;Lsun/java2d/SurfaceData;Ljava/awt/Composite;IIIIIII)V
*/
JNIEXPORT void JNICALL Java_sun_java2d_loops_BlitBg_BlitBg
(JNIEnv *env, jobject self,
jobject srcData, jobject dstData,
jobject comp, jobject clip, jobject bgColor,
jobject comp, jobject clip, jint bgColor,
jint srcx, jint srcy, jint dstx, jint dsty, jint width, jint height)
{
SurfaceDataOps *srcOps;
@ -93,7 +93,7 @@ JNIEXPORT void JNICALL Java_sun_java2d_loops_BlitBg_BlitBg
Region_IntersectBounds(&clipInfo, &dstInfo.bounds);
if (!Region_IsEmpty(&clipInfo)) {
jint bgpixel = GrPrim_ColorGetRGB(env, bgColor);
jint bgpixel = bgColor;
srcOps->GetRasInfo(env, srcOps, &srcInfo);
dstOps->GetRasInfo(env, dstOps, &dstInfo);
if (pPrim->pDstType->pixelFor) {

View File

@ -1,5 +1,5 @@
/*
* Copyright 2000-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2000-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -50,7 +50,6 @@ static jfieldID eargbID;
static jfieldID clipRegionID;
static jfieldID compositeID;
static jfieldID lcdTextContrastID;
static jfieldID valueID;
static jfieldID xorPixelID;
static jfieldID xorColorID;
static jfieldID alphaMaskID;
@ -64,6 +63,8 @@ static jfieldID m10ID;
static jfieldID m11ID;
static jfieldID m12ID;
static jmethodID getRgbID;
static jboolean InitPrimTypes(JNIEnv *env);
static jboolean InitSurfaceTypes(JNIEnv *env, jclass SurfaceType);
static jboolean InitCompositeTypes(JNIEnv *env, jclass CompositeType);
@ -114,7 +115,7 @@ Java_sun_java2d_loops_GraphicsPrimitiveMgr_initIDs
"Ljava/awt/Composite;");
lcdTextContrastID =
(*env)->GetFieldID(env, SG2D, "lcdTextContrast", "I");
valueID = (*env)->GetFieldID(env, Color, "value", "I");
getRgbID = (*env)->GetMethodID(env, Color, "getRGB", "()I");
xorPixelID = (*env)->GetFieldID(env, XORComp, "xorPixel", "I");
xorColorID = (*env)->GetFieldID(env, XORComp, "xorColor",
"Ljava/awt/Color;");
@ -138,7 +139,6 @@ Java_sun_java2d_loops_GraphicsPrimitiveMgr_initIDs
sg2dStrokeHintID = (*env)->GetFieldID(env, SG2D, "strokeHint", "I");
fid = (*env)->GetStaticFieldID(env, SHints, "INTVAL_STROKE_PURE", "I");
sunHints_INTVAL_STROKE_PURE = (*env)->GetStaticIntField(env, SHints, fid);
}
void GrPrim_RefineBounds(SurfaceDataBounds *bounds, jint transX, jint transY,
@ -467,7 +467,7 @@ GrPrim_CompGetXorColor(JNIEnv *env, jobject comp)
jint rgb;
color = (*env)->GetObjectField(env, comp, xorColorID);
rgb = (*env)->GetIntField(env, color, valueID);
rgb = (*env)->CallIntMethod(env, color, getRgbID);
(*env)->DeleteLocalRef(env, color);
return rgb;
@ -492,11 +492,6 @@ GrPrim_Sg2dGetEaRGB(JNIEnv *env, jobject sg2d)
return (*env)->GetIntField(env, sg2d, eargbID);
}
jint GrPrim_ColorGetRGB(JNIEnv *env, jobject color)
{
return (*env)->GetIntField(env, color, valueID);
}
JNIEXPORT jint JNICALL
GrPrim_Sg2dGetLCDTextContrast(JNIEnv *env, jobject sg2d)
{

View File

@ -1,5 +1,5 @@
/*
* Copyright 2000-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2000-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -501,7 +501,6 @@ extern JNIEXPORT jint JNICALL
GrPrim_Sg2dGetEaRGB(JNIEnv *env, jobject sg2d);
extern JNIEXPORT jint JNICALL
GrPrim_Sg2dGetLCDTextContrast(JNIEnv *env, jobject sg2d);
extern jint GrPrim_ColorGetRGB(JNIEnv *env, jobject color);
/*
* Data structure and functions to retrieve and use

View File

@ -1,5 +1,5 @@
/*
* Copyright 2004-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2004-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -852,28 +852,58 @@ OGLContext_GetExtensionInfo(JNIEnv *env, jint *caps)
J2dTraceLn(J2D_TRACE_INFO, "OGLContext_GetExtensionInfo");
*caps |= CAPS_TEXNONSQUARE;
if (OGLContext_IsExtensionAvailable(e, "GL_ARB_multitexture")) {
*caps |= sun_java2d_opengl_OGLContext_CAPS_EXT_MULTITEXTURE;
*caps |= CAPS_MULTITEXTURE;
}
if (OGLContext_IsExtensionAvailable(e, "GL_ARB_texture_non_power_of_two")){
*caps |= sun_java2d_opengl_OGLContext_CAPS_EXT_TEXNONPOW2;
*caps |= CAPS_TEXNONPOW2;
}
if (OGLContext_IsExtensionAvailable(e, "GL_ARB_texture_rectangle")) {
*caps |= sun_java2d_opengl_OGLContext_CAPS_EXT_TEXRECT;
// 6656574: Use of the GL_ARB_texture_rectangle extension by Java 2D
// complicates any third-party libraries that try to interact with
// the OGL pipeline (and we've run into driver bugs in the past related
// to this extension), so for now we will disable its use by default (unless
// forced). We will still make use of the GL_ARB_texture_non_power_of_two
// extension when available, which is the better choice going forward
// anyway.
if (OGLContext_IsExtensionAvailable(e, "GL_ARB_texture_rectangle") &&
getenv("J2D_OGL_TEXRECT") != NULL)
{
*caps |= CAPS_EXT_TEXRECT;
}
if (OGLContext_IsFBObjectExtensionAvailable(env, e)) {
*caps |= sun_java2d_opengl_OGLContext_CAPS_EXT_FBOBJECT;
*caps |= CAPS_EXT_FBOBJECT;
}
if (OGLContext_IsLCDShaderSupportAvailable(env, fragShaderAvail)) {
*caps |= sun_java2d_opengl_OGLContext_CAPS_EXT_LCD_SHADER;
*caps |= CAPS_EXT_LCD_SHADER | CAPS_PS20;
}
if (OGLContext_IsBIOpShaderSupportAvailable(env, fragShaderAvail)) {
*caps |= sun_java2d_opengl_OGLContext_CAPS_EXT_BIOP_SHADER;
*caps |= CAPS_EXT_BIOP_SHADER | CAPS_PS20;
}
if (OGLContext_IsGradShaderSupportAvailable(env, fragShaderAvail)) {
*caps |= sun_java2d_opengl_OGLContext_CAPS_EXT_GRAD_SHADER;
*caps |= CAPS_EXT_GRAD_SHADER | CAPS_PS20;
}
if (OGLContext_IsExtensionAvailable(e, "GL_NV_fragment_program")) {
// this is an Nvidia board, at least PS 2.0, but we can't
// use the "max instructions" heuristic since GeForce FX
// boards report 1024 even though they're only PS 2.0,
// so we'll check the following, which does imply PS 3.0
if (OGLContext_IsExtensionAvailable(e, "GL_NV_fragment_program2")) {
*caps |= CAPS_PS30;
}
} else {
// for all other boards, we look at the "max instructions"
// count reported by the GL_ARB_fragment_program extension
// as a heuristic for detecting PS 3.0 compatible hardware
if (OGLContext_IsExtensionAvailable(e, "GL_ARB_fragment_program")) {
GLint instr;
j2d_glGetProgramivARB(GL_FRAGMENT_PROGRAM_ARB,
GL_MAX_PROGRAM_INSTRUCTIONS_ARB, &instr);
if (instr > 512) {
*caps |= CAPS_PS30;
}
}
}
// stuff vendor descriptor in the upper bits of the caps
if (vendor != NULL) {
if (strncmp(vendor, "ATI", 3) == 0) {
@ -883,8 +913,10 @@ OGLContext_GetExtensionInfo(JNIEnv *env, jint *caps)
} else if (strncmp(vendor, "Sun", 3) == 0) {
vcap = OGLC_VENDOR_SUN;
}
// REMIND: new in 7 - check if needs fixing
*caps |= ((vcap & OGLC_VCAP_MASK) << OGLC_VCAP_OFFSET);
}
*caps |= ((vcap & OGLC_VCAP_MASK) << OGLC_VCAP_OFFSET);
}
/**
@ -983,4 +1015,49 @@ OGLContext_CreateFragmentProgram(const char *fragmentShaderSource)
return fragmentProgram;
}
/*
* Class: sun_java2d_opengl_OGLContext
* Method: getOGLIdString
* Signature: ()Ljava/lang/String;
*/
JNIEXPORT jstring JNICALL Java_sun_java2d_opengl_OGLContext_getOGLIdString
(JNIEnv *env, jclass oglcc)
{
char *vendor, *renderer, *version;
char *pAdapterId;
jobject ret = NULL;
int len;
J2dTraceLn(J2D_TRACE_INFO, "OGLContext_getOGLIdString");
vendor = (char*)j2d_glGetString(GL_VENDOR);
if (vendor == NULL) {
vendor = "Unknown Vendor";
}
renderer = (char*)j2d_glGetString(GL_RENDERER);
if (renderer == NULL) {
renderer = "Unknown Renderer";
}
version = (char*)j2d_glGetString(GL_VERSION);
if (version == NULL) {
version = "unknown version";
}
// 'vendor renderer (version)0'
len = strlen(vendor) + 1 + strlen(renderer) + 1 + 1+strlen(version)+1 + 1;
pAdapterId = malloc(len);
if (pAdapterId != NULL) {
jio_snprintf(pAdapterId, len, "%s %s (%s)", vendor, renderer, version);
J2dTraceLn1(J2D_TRACE_VERBOSE, " id=%s", pAdapterId);
ret = JNU_NewStringPlatform(env, pAdapterId);
free(pAdapterId);
}
return ret;
}
#endif /* !HEADLESS */

View File

@ -1,5 +1,5 @@
/*
* Copyright 2004-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2004-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -28,6 +28,7 @@
#include "sun_java2d_pipe_BufferedContext.h"
#include "sun_java2d_opengl_OGLContext.h"
#include "sun_java2d_opengl_OGLContext_OGLContextCaps.h"
#include "j2d_md.h"
#include "J2D_GL/gl.h"
@ -95,14 +96,51 @@ typedef struct {
#define OGLC_USE_MASK \
sun_java2d_pipe_BufferedContext_USE_MASK
/**
* See OGLContext.java for more on these flags.
*/
#define CAPS_EMPTY \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_EMPTY
#define CAPS_RT_PLAIN_ALPHA \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_RT_PLAIN_ALPHA
#define CAPS_RT_TEXTURE_ALPHA \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_RT_TEXTURE_ALPHA
#define CAPS_RT_TEXTURE_OPAQUE \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_RT_TEXTURE_OPAQUE
#define CAPS_MULTITEXTURE \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_MULTITEXTURE
#define CAPS_TEXNONPOW2 \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_TEXNONPOW2
#define CAPS_TEXNONSQUARE \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_TEXNONSQUARE
#define CAPS_PS20 \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_PS20
#define CAPS_PS30 \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_PS30
#define LAST_SHARED_CAP \
sun_java2d_opengl_OGLContext_OGLContextCaps_LAST_SHARED_CAP
#define CAPS_EXT_FBOBJECT \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_EXT_FBOBJECT
#define CAPS_STORED_ALPHA \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_STORED_ALPHA
#define CAPS_DOUBLEBUFFERED \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_DOUBLEBUFFERED
#define CAPS_EXT_LCD_SHADER \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_EXT_LCD_SHADER
#define CAPS_EXT_BIOP_SHADER \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_EXT_BIOP_SHADER
#define CAPS_EXT_GRAD_SHADER \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_EXT_GRAD_SHADER
#define CAPS_EXT_TEXRECT \
sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_EXT_TEXRECT
/**
* Evaluates to true if the given capability bitmask is present for the
* given OGLContext. Note that only the constant name needs to be passed as
* a parameter, as this macro will automatically prepend the full package
* and class name to the constant name.
*/
#define OGLC_IS_CAP_PRESENT(oglc, cap) \
(((oglc)->caps & (sun_java2d_opengl_OGLContext_##cap)) != 0)
#define OGLC_IS_CAP_PRESENT(oglc, cap) (((oglc)->caps & (cap)) != 0)
/**
* At startup we will embed one of the following values in the caps field

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -91,8 +91,12 @@ typedef void (GLAPIENTRY *glPixelStoreiType)(GLenum pname, GLint param);
typedef void (GLAPIENTRY *glPixelTransferfType)(GLenum pname, GLfloat param);
typedef void (GLAPIENTRY *glPixelZoomType)(GLfloat xfactor, GLfloat yfactor);
typedef void (GLAPIENTRY *glPolygonOffsetType)(GLfloat factor, GLfloat units);
typedef void (GLAPIENTRY *glPopAttribType)(void);
typedef void (GLAPIENTRY *glPopClientAttribType)(void);
typedef void (GLAPIENTRY *glPopMatrixType)(void);
typedef void (GLAPIENTRY *glPrioritizeTexturesType)(GLsizei n, const GLuint *textures, const GLclampf *priorities);
typedef void (GLAPIENTRY *glPushAttribType)(GLbitfield);
typedef void (GLAPIENTRY *glPushClientAttribType)(GLbitfield);
typedef void (GLAPIENTRY *glPushMatrixType)(void);
typedef void (GLAPIENTRY *glRasterPos2iType)(GLint x, GLint y);
typedef void (GLAPIENTRY *glReadBufferType)(GLenum mode);
@ -155,8 +159,10 @@ typedef void (GLAPIENTRY *glUniform2fARBType)(GLint, GLfloat, GLfloat);
typedef void (GLAPIENTRY *glUniform3fARBType)(GLint, GLfloat, GLfloat, GLfloat);
typedef void (GLAPIENTRY *glUniform3fvARBType)(GLint, GLsizei, const GLfloat *);
typedef void (GLAPIENTRY *glUniform4fARBType)(GLint, GLfloat, GLfloat, GLfloat, GLfloat);
typedef void (GLAPIENTRY *glUniform4fvARBType)(GLint, GLsizei, const GLfloat *);
typedef GLint (GLAPIENTRY *glGetUniformLocationARBType)(GLhandleARB, const GLcharARB *);
typedef void (GLAPIENTRY *glGetInfoLogARBType)(GLhandleARB, GLsizei, GLsizei *, GLcharARB *);
typedef void (GLAPIENTRY *glGetProgramivARBType)(GLenum, GLenum, GLint *);
typedef void (GLAPIENTRY *glGetObjectParameterivARBType)(GLhandleARB, GLenum, GLint *);
typedef GLhandleARB (GLAPIENTRY *glCreateProgramObjectARBType)(void);
typedef void (GLAPIENTRY *glAttachObjectARBType)(GLhandleARB, GLhandleARB);
@ -243,8 +249,12 @@ typedef void (GLAPIENTRY *glDeleteObjectARBType)(GLhandleARB);
OGL_##action##_FUNC(glPixelTransferf); \
OGL_##action##_FUNC(glPixelZoom); \
OGL_##action##_FUNC(glPolygonOffset); \
OGL_##action##_FUNC(glPopAttrib); \
OGL_##action##_FUNC(glPopClientAttrib); \
OGL_##action##_FUNC(glPopMatrix); \
OGL_##action##_FUNC(glPrioritizeTextures); \
OGL_##action##_FUNC(glPushAttrib); \
OGL_##action##_FUNC(glPushClientAttrib); \
OGL_##action##_FUNC(glPushMatrix); \
OGL_##action##_FUNC(glRasterPos2i); \
OGL_##action##_FUNC(glReadBuffer); \
@ -298,7 +308,9 @@ typedef void (GLAPIENTRY *glDeleteObjectARBType)(GLhandleARB);
OGL_##action##_EXT_FUNC(glUniform3fARB); \
OGL_##action##_EXT_FUNC(glUniform3fvARB); \
OGL_##action##_EXT_FUNC(glUniform4fARB); \
OGL_##action##_EXT_FUNC(glUniform4fvARB); \
OGL_##action##_EXT_FUNC(glGetUniformLocationARB); \
OGL_##action##_EXT_FUNC(glGetProgramivARB); \
OGL_##action##_EXT_FUNC(glGetInfoLogARB); \
OGL_##action##_EXT_FUNC(glGetObjectParameterivARB); \
OGL_##action##_EXT_FUNC(glDeleteObjectARB);

View File

@ -1,5 +1,5 @@
/*
* Copyright 2005-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2005-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -88,8 +88,9 @@ Java_sun_java2d_opengl_OGLRenderQueue_flushBuffer
while (b < end) {
jint opcode = NEXT_INT(b);
J2dTraceLn1(J2D_TRACE_VERBOSE,
"OGLRenderQueue_flushBuffer: opcode=%d", opcode);
J2dTraceLn2(J2D_TRACE_VERBOSE,
"OGLRenderQueue_flushBuffer: opcode=%d, rem=%d",
opcode, (end-b));
switch (opcode) {
@ -148,6 +149,40 @@ Java_sun_java2d_opengl_OGLRenderQueue_flushBuffer
SKIP_BYTES(b, count * BYTES_PER_SCANLINE);
}
break;
case sun_java2d_pipe_BufferedOpCodes_DRAW_PARALLELOGRAM:
{
jfloat x11 = NEXT_FLOAT(b);
jfloat y11 = NEXT_FLOAT(b);
jfloat dx21 = NEXT_FLOAT(b);
jfloat dy21 = NEXT_FLOAT(b);
jfloat dx12 = NEXT_FLOAT(b);
jfloat dy12 = NEXT_FLOAT(b);
jfloat lwr21 = NEXT_FLOAT(b);
jfloat lwr12 = NEXT_FLOAT(b);
OGLRenderer_DrawParallelogram(oglc,
x11, y11,
dx21, dy21,
dx12, dy12,
lwr21, lwr12);
}
break;
case sun_java2d_pipe_BufferedOpCodes_DRAW_AAPARALLELOGRAM:
{
jfloat x11 = NEXT_FLOAT(b);
jfloat y11 = NEXT_FLOAT(b);
jfloat dx21 = NEXT_FLOAT(b);
jfloat dy21 = NEXT_FLOAT(b);
jfloat dx12 = NEXT_FLOAT(b);
jfloat dy12 = NEXT_FLOAT(b);
jfloat lwr21 = NEXT_FLOAT(b);
jfloat lwr12 = NEXT_FLOAT(b);
OGLRenderer_DrawAAParallelogram(oglc, dstOps,
x11, y11,
dx21, dy21,
dx12, dy12,
lwr21, lwr12);
}
break;
// fill ops
case sun_java2d_pipe_BufferedOpCodes_FILL_RECT:
@ -166,6 +201,34 @@ Java_sun_java2d_opengl_OGLRenderQueue_flushBuffer
SKIP_BYTES(b, count * BYTES_PER_SPAN);
}
break;
case sun_java2d_pipe_BufferedOpCodes_FILL_PARALLELOGRAM:
{
jfloat x11 = NEXT_FLOAT(b);
jfloat y11 = NEXT_FLOAT(b);
jfloat dx21 = NEXT_FLOAT(b);
jfloat dy21 = NEXT_FLOAT(b);
jfloat dx12 = NEXT_FLOAT(b);
jfloat dy12 = NEXT_FLOAT(b);
OGLRenderer_FillParallelogram(oglc,
x11, y11,
dx21, dy21,
dx12, dy12);
}
break;
case sun_java2d_pipe_BufferedOpCodes_FILL_AAPARALLELOGRAM:
{
jfloat x11 = NEXT_FLOAT(b);
jfloat y11 = NEXT_FLOAT(b);
jfloat dx21 = NEXT_FLOAT(b);
jfloat dy21 = NEXT_FLOAT(b);
jfloat dx12 = NEXT_FLOAT(b);
jfloat dy12 = NEXT_FLOAT(b);
OGLRenderer_FillAAParallelogram(oglc, dstOps,
x11, y11,
dx21, dy21,
dx12, dy12);
}
break;
// text-related ops
case sun_java2d_pipe_BufferedOpCodes_DRAW_GLYPH_LIST:
@ -438,6 +501,31 @@ Java_sun_java2d_opengl_OGLRenderQueue_flushBuffer
dstOps = NULL;
}
break;
case sun_java2d_pipe_BufferedOpCodes_SAVE_STATE:
{
j2d_glPushAttrib(GL_ALL_ATTRIB_BITS);
j2d_glPushClientAttrib(GL_CLIENT_ALL_ATTRIB_BITS);
j2d_glMatrixMode(GL_MODELVIEW);
j2d_glPushMatrix();
j2d_glMatrixMode(GL_PROJECTION);
j2d_glPushMatrix();
j2d_glMatrixMode(GL_TEXTURE);
j2d_glPushMatrix();
}
break;
case sun_java2d_pipe_BufferedOpCodes_RESTORE_STATE:
{
j2d_glPopAttrib();
j2d_glPopClientAttrib();
j2d_glMatrixMode(GL_MODELVIEW);
j2d_glPopMatrix();
j2d_glMatrixMode(GL_PROJECTION);
j2d_glPopMatrix();
j2d_glMatrixMode(GL_TEXTURE);
j2d_glPopMatrix();
}
break;
case sun_java2d_pipe_BufferedOpCodes_SYNC:
{
sync = JNI_TRUE;
@ -691,6 +779,9 @@ OGLRenderQueue_CheckPreviousOp(jint op)
return;
}
J2dTraceLn1(J2D_TRACE_VERBOSE,
"OGLRenderQueue_CheckPreviousOp: new op=%d", op);
switch (previousOp) {
case GL_TEXTURE_2D:
case GL_TEXTURE_RECTANGLE_ARB:
@ -718,6 +809,9 @@ OGLRenderQueue_CheckPreviousOp(jint op)
case OGL_STATE_GLYPH_OP:
OGLTR_DisableGlyphVertexCache(oglc);
break;
case OGL_STATE_PGRAM_OP:
OGLRenderer_DisableAAParallelogramProgram();
break;
case OGL_STATE_RESET:
case OGL_STATE_CHANGE:
// No-op
@ -745,6 +839,9 @@ OGLRenderQueue_CheckPreviousOp(jint op)
case OGL_STATE_GLYPH_OP:
OGLTR_EnableGlyphVertexCache(oglc);
break;
case OGL_STATE_PGRAM_OP:
OGLRenderer_EnableAAParallelogramProgram();
break;
case OGL_STATE_RESET:
case OGL_STATE_CHANGE:
// No-op

View File

@ -1,5 +1,5 @@
/*
* Copyright 2005-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2005-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -89,6 +89,13 @@
*/
#define OGL_STATE_GLYPH_OP -4
/*
* Parameter passed to the CHECK_PREVIOUS_OP() macro to indicate that the
* following operation represents an operation that renders a
* parallelogram via a fragment program (see OGLRenderer).
*/
#define OGL_STATE_PGRAM_OP -5
/*
* Initializes the "previous operation" state to its default value.
*/

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -27,6 +27,7 @@
#include <jlong.h>
#include <jni_util.h>
#include <math.h>
#include "sun_java2d_opengl_OGLRenderer.h"
@ -326,4 +327,486 @@ OGLRenderer_FillSpans(OGLContext *oglc, jint spanCount, jint *spans)
}
}
#define FILL_PGRAM(fx11, fy11, dx21, dy21, dx12, dy12) \
do { \
j2d_glVertex2f(fx11, fy11); \
j2d_glVertex2f(fx11 + dx21, fy11 + dy21); \
j2d_glVertex2f(fx11 + dx21 + dx12, fy11 + dy21 + dy12); \
j2d_glVertex2f(fx11 + dx12, fy11 + dy12); \
} while (0)
void
OGLRenderer_FillParallelogram(OGLContext *oglc,
jfloat fx11, jfloat fy11,
jfloat dx21, jfloat dy21,
jfloat dx12, jfloat dy12)
{
J2dTraceLn6(J2D_TRACE_INFO,
"OGLRenderer_FillParallelogram "
"(x=%6.2f y=%6.2f "
"dx1=%6.2f dy1=%6.2f "
"dx2=%6.2f dy2=%6.2f)",
fx11, fy11,
dx21, dy21,
dx12, dy12);
RETURN_IF_NULL(oglc);
CHECK_PREVIOUS_OP(GL_QUADS);
FILL_PGRAM(fx11, fy11, dx21, dy21, dx12, dy12);
}
void
OGLRenderer_DrawParallelogram(OGLContext *oglc,
jfloat fx11, jfloat fy11,
jfloat dx21, jfloat dy21,
jfloat dx12, jfloat dy12,
jfloat lwr21, jfloat lwr12)
{
// dx,dy for line width in the "21" and "12" directions.
jfloat ldx21 = dx21 * lwr21;
jfloat ldy21 = dy21 * lwr21;
jfloat ldx12 = dx12 * lwr12;
jfloat ldy12 = dy12 * lwr12;
// calculate origin of the outer parallelogram
jfloat ox11 = fx11 - (ldx21 + ldx12) / 2.0f;
jfloat oy11 = fy11 - (ldy21 + ldy12) / 2.0f;
J2dTraceLn8(J2D_TRACE_INFO,
"OGLRenderer_DrawParallelogram "
"(x=%6.2f y=%6.2f "
"dx1=%6.2f dy1=%6.2f lwr1=%6.2f "
"dx2=%6.2f dy2=%6.2f lwr2=%6.2f)",
fx11, fy11,
dx21, dy21, lwr21,
dx12, dy12, lwr12);
RETURN_IF_NULL(oglc);
CHECK_PREVIOUS_OP(GL_QUADS);
// Only need to generate 4 quads if the interior still
// has a hole in it (i.e. if the line width ratio was
// less than 1.0)
if (lwr21 < 1.0f && lwr12 < 1.0f) {
// Note: "TOP", "BOTTOM", "LEFT" and "RIGHT" here are
// relative to whether the dxNN variables are positive
// and negative. The math works fine regardless of
// their signs, but for conceptual simplicity the
// comments will refer to the sides as if the dxNN
// were all positive. "TOP" and "BOTTOM" segments
// are defined by the dxy21 deltas. "LEFT" and "RIGHT"
// segments are defined by the dxy12 deltas.
// Each segment includes its starting corner and comes
// to just short of the following corner. Thus, each
// corner is included just once and the only lengths
// needed are the original parallelogram delta lengths
// and the "line width deltas". The sides will cover
// the following relative territories:
//
// T T T T T R
// L R
// L R
// L R
// L R
// L B B B B B
// TOP segment, to left side of RIGHT edge
// "width" of original pgram, "height" of hor. line size
fx11 = ox11;
fy11 = oy11;
FILL_PGRAM(fx11, fy11, dx21, dy21, ldx12, ldy12);
// RIGHT segment, to top of BOTTOM edge
// "width" of vert. line size , "height" of original pgram
fx11 = ox11 + dx21;
fy11 = oy11 + dy21;
FILL_PGRAM(fx11, fy11, ldx21, ldy21, dx12, dy12);
// BOTTOM segment, from right side of LEFT edge
// "width" of original pgram, "height" of hor. line size
fx11 = ox11 + dx12 + ldx21;
fy11 = oy11 + dy12 + ldy21;
FILL_PGRAM(fx11, fy11, dx21, dy21, ldx12, ldy12);
// LEFT segment, from bottom of TOP edge
// "width" of vert. line size , "height" of inner pgram
fx11 = ox11 + ldx12;
fy11 = oy11 + ldy12;
FILL_PGRAM(fx11, fy11, ldx21, ldy21, dx12, dy12);
} else {
// The line width ratios were large enough to consume
// the entire hole in the middle of the parallelogram
// so we can just issue one large quad for the outer
// parallelogram.
dx21 += ldx21;
dy21 += ldy21;
dx12 += ldx12;
dy12 += ldy12;
FILL_PGRAM(ox11, oy11, dx21, dy21, dx12, dy12);
}
}
static GLhandleARB aaPgramProgram = 0;
/*
* This shader fills the space between an outer and inner parallelogram.
* It can be used to draw an outline by specifying both inner and outer
* values. It fills pixels by estimating what portion falls inside the
* outer shape, and subtracting an estimate of what portion falls inside
* the inner shape. Specifying both inner and outer values produces a
* standard "wide outline". Specifying an inner shape that falls far
* outside the outer shape allows the same shader to fill the outer
* shape entirely since pixels that fall within the outer shape are never
* inside the inner shape and so they are filled based solely on their
* coverage of the outer shape.
*
* The setup code renders this shader over the bounds of the outer
* shape (or the only shape in the case of a fill operation) and
* sets the texture 0 coordinates so that 0,0=>0,1=>1,1=>1,0 in those
* texture coordinates map to the four corners of the parallelogram.
* Similarly the texture 1 coordinates map the inner shape to the
* unit square as well, but in a different coordinate system.
*
* When viewed in the texture coordinate systems the parallelograms
* we are filling are unit squares, but the pixels have then become
* tiny parallelograms themselves. Both of the texture coordinate
* systems are affine transforms so the rate of change in X and Y
* of the texture coordinates are essentially constants and happen
* to correspond to the size and direction of the slanted sides of
* the distorted pixels relative to the "square mapped" boundary
* of the parallelograms.
*
* The shader uses the dFdx() and dFdy() functions to measure the "rate
* of change" of these texture coordinates and thus gets an accurate
* measure of the size and shape of a pixel relative to the two
* parallelograms. It then uses the bounds of the size and shape
* of a pixel to intersect with the unit square to estimate the
* coverage of the pixel. Unfortunately, without a lot more work
* to calculate the exact area of intersection between a unit
* square (the original parallelogram) and a parallelogram (the
* distorted pixel), this shader only approximates the pixel
* coverage, but emperically the estimate is very useful and
* produces visually pleasing results, if not theoretically accurate.
*/
static const char *aaPgramShaderSource =
"void main() {"
// Calculate the vectors for the "legs" of the pixel parallelogram
// for the outer parallelogram.
" vec2 oleg1 = dFdx(gl_TexCoord[0].st);"
" vec2 oleg2 = dFdy(gl_TexCoord[0].st);"
// Calculate the bounds of the distorted pixel parallelogram.
" vec2 corner = gl_TexCoord[0].st - (oleg1+oleg2)/2.0;"
" vec2 omin = min(corner, corner+oleg1);"
" omin = min(omin, corner+oleg2);"
" omin = min(omin, corner+oleg1+oleg2);"
" vec2 omax = max(corner, corner+oleg1);"
" omax = max(omax, corner+oleg2);"
" omax = max(omax, corner+oleg1+oleg2);"
// Calculate the vectors for the "legs" of the pixel parallelogram
// for the inner parallelogram.
" vec2 ileg1 = dFdx(gl_TexCoord[1].st);"
" vec2 ileg2 = dFdy(gl_TexCoord[1].st);"
// Calculate the bounds of the distorted pixel parallelogram.
" corner = gl_TexCoord[1].st - (ileg1+ileg2)/2.0;"
" vec2 imin = min(corner, corner+ileg1);"
" imin = min(imin, corner+ileg2);"
" imin = min(imin, corner+ileg1+ileg2);"
" vec2 imax = max(corner, corner+ileg1);"
" imax = max(imax, corner+ileg2);"
" imax = max(imax, corner+ileg1+ileg2);"
// Clamp the bounds of the parallelograms to the unit square to
// estimate the intersection of the pixel parallelogram with
// the unit square. The ratio of the 2 rectangle areas is a
// reasonable estimate of the proportion of coverage.
" vec2 o1 = clamp(omin, 0.0, 1.0);"
" vec2 o2 = clamp(omax, 0.0, 1.0);"
" float oint = (o2.y-o1.y)*(o2.x-o1.x);"
" float oarea = (omax.y-omin.y)*(omax.x-omin.x);"
" vec2 i1 = clamp(imin, 0.0, 1.0);"
" vec2 i2 = clamp(imax, 0.0, 1.0);"
" float iint = (i2.y-i1.y)*(i2.x-i1.x);"
" float iarea = (imax.y-imin.y)*(imax.x-imin.x);"
// Proportion of pixel in outer shape minus the proportion
// of pixel in the inner shape == the coverage of the pixel
// in the area between the two.
" float coverage = oint/oarea - iint / iarea;"
" gl_FragColor = gl_Color * coverage;"
"}";
#define ADJUST_PGRAM(V1, DV, V2) \
do { \
if ((DV) >= 0) { \
(V2) += (DV); \
} else { \
(V1) += (DV); \
} \
} while (0)
// Invert the following transform:
// DeltaT(0, 0) == (0, 0)
// DeltaT(1, 0) == (DX1, DY1)
// DeltaT(0, 1) == (DX2, DY2)
// DeltaT(1, 1) == (DX1+DX2, DY1+DY2)
// TM00 = DX1, TM01 = DX2, (TM02 = X11)
// TM10 = DY1, TM11 = DY2, (TM12 = Y11)
// Determinant = TM00*TM11 - TM01*TM10
// = DX1*DY2 - DX2*DY1
// Inverse is:
// IM00 = TM11/det, IM01 = -TM01/det
// IM10 = -TM10/det, IM11 = TM00/det
// IM02 = (TM01 * TM12 - TM11 * TM02) / det,
// IM12 = (TM10 * TM02 - TM00 * TM12) / det,
#define DECLARE_MATRIX(MAT) \
jfloat MAT ## 00, MAT ## 01, MAT ## 02, MAT ## 10, MAT ## 11, MAT ## 12
#define GET_INVERTED_MATRIX(MAT, X11, Y11, DX1, DY1, DX2, DY2, RET_CODE) \
do { \
jfloat det = DX1*DY2 - DX2*DY1; \
if (det == 0) { \
RET_CODE; \
} \
MAT ## 00 = DY2/det; \
MAT ## 01 = -DX2/det; \
MAT ## 10 = -DY1/det; \
MAT ## 11 = DX1/det; \
MAT ## 02 = (DX2 * Y11 - DY2 * X11) / det; \
MAT ## 12 = (DY1 * X11 - DX1 * Y11) / det; \
} while (0)
#define TRANSFORM(MAT, TX, TY, X, Y) \
do { \
TX = (X) * MAT ## 00 + (Y) * MAT ## 01 + MAT ## 02; \
TY = (X) * MAT ## 10 + (Y) * MAT ## 11 + MAT ## 12; \
} while (0)
void
OGLRenderer_FillAAParallelogram(OGLContext *oglc, OGLSDOps *dstOps,
jfloat fx11, jfloat fy11,
jfloat dx21, jfloat dy21,
jfloat dx12, jfloat dy12)
{
DECLARE_MATRIX(om);
// parameters for parallelogram bounding box
jfloat bx11, by11, bx22, by22;
// parameters for uv texture coordinates of parallelogram corners
jfloat u11, v11, u12, v12, u21, v21, u22, v22;
J2dTraceLn6(J2D_TRACE_INFO,
"OGLRenderer_FillAAParallelogram "
"(x=%6.2f y=%6.2f "
"dx1=%6.2f dy1=%6.2f "
"dx2=%6.2f dy2=%6.2f)",
fx11, fy11,
dx21, dy21,
dx12, dy12);
RETURN_IF_NULL(oglc);
RETURN_IF_NULL(dstOps);
GET_INVERTED_MATRIX(om, fx11, fy11, dx21, dy21, dx12, dy12,
return);
CHECK_PREVIOUS_OP(OGL_STATE_PGRAM_OP);
bx11 = bx22 = fx11;
by11 = by22 = fy11;
ADJUST_PGRAM(bx11, dx21, bx22);
ADJUST_PGRAM(by11, dy21, by22);
ADJUST_PGRAM(bx11, dx12, bx22);
ADJUST_PGRAM(by11, dy12, by22);
bx11 = (jfloat) floor(bx11);
by11 = (jfloat) floor(by11);
bx22 = (jfloat) ceil(bx22);
by22 = (jfloat) ceil(by22);
TRANSFORM(om, u11, v11, bx11, by11);
TRANSFORM(om, u21, v21, bx22, by11);
TRANSFORM(om, u12, v12, bx11, by22);
TRANSFORM(om, u22, v22, bx22, by22);
j2d_glBegin(GL_QUADS);
j2d_glMultiTexCoord2fARB(GL_TEXTURE0_ARB, u11, v11);
j2d_glMultiTexCoord2fARB(GL_TEXTURE1_ARB, 5.f, 5.f);
j2d_glVertex2f(bx11, by11);
j2d_glMultiTexCoord2fARB(GL_TEXTURE0_ARB, u21, v21);
j2d_glMultiTexCoord2fARB(GL_TEXTURE1_ARB, 6.f, 5.f);
j2d_glVertex2f(bx22, by11);
j2d_glMultiTexCoord2fARB(GL_TEXTURE0_ARB, u22, v22);
j2d_glMultiTexCoord2fARB(GL_TEXTURE1_ARB, 6.f, 6.f);
j2d_glVertex2f(bx22, by22);
j2d_glMultiTexCoord2fARB(GL_TEXTURE0_ARB, u12, v12);
j2d_glMultiTexCoord2fARB(GL_TEXTURE1_ARB, 5.f, 6.f);
j2d_glVertex2f(bx11, by22);
j2d_glEnd();
}
void
OGLRenderer_FillAAParallelogramInnerOuter(OGLContext *oglc, OGLSDOps *dstOps,
jfloat ox11, jfloat oy11,
jfloat ox21, jfloat oy21,
jfloat ox12, jfloat oy12,
jfloat ix11, jfloat iy11,
jfloat ix21, jfloat iy21,
jfloat ix12, jfloat iy12)
{
DECLARE_MATRIX(om);
DECLARE_MATRIX(im);
// parameters for parallelogram bounding box
jfloat bx11, by11, bx22, by22;
// parameters for uv texture coordinates of outer parallelogram corners
jfloat ou11, ov11, ou12, ov12, ou21, ov21, ou22, ov22;
// parameters for uv texture coordinates of inner parallelogram corners
jfloat iu11, iv11, iu12, iv12, iu21, iv21, iu22, iv22;
RETURN_IF_NULL(oglc);
RETURN_IF_NULL(dstOps);
GET_INVERTED_MATRIX(im, ix11, iy11, ix21, iy21, ix12, iy12,
// inner parallelogram is degenerate
// therefore it encloses no area
// fill outer
OGLRenderer_FillAAParallelogram(oglc, dstOps,
ox11, oy11,
ox21, oy21,
ox12, oy12);
return);
GET_INVERTED_MATRIX(om, ox11, oy11, ox21, oy21, ox12, oy12,
return);
CHECK_PREVIOUS_OP(OGL_STATE_PGRAM_OP);
bx11 = bx22 = ox11;
by11 = by22 = oy11;
ADJUST_PGRAM(bx11, ox21, bx22);
ADJUST_PGRAM(by11, oy21, by22);
ADJUST_PGRAM(bx11, ox12, bx22);
ADJUST_PGRAM(by11, oy12, by22);
bx11 = (jfloat) floor(bx11);
by11 = (jfloat) floor(by11);
bx22 = (jfloat) ceil(bx22);
by22 = (jfloat) ceil(by22);
TRANSFORM(om, ou11, ov11, bx11, by11);
TRANSFORM(om, ou21, ov21, bx22, by11);
TRANSFORM(om, ou12, ov12, bx11, by22);
TRANSFORM(om, ou22, ov22, bx22, by22);
TRANSFORM(im, iu11, iv11, bx11, by11);
TRANSFORM(im, iu21, iv21, bx22, by11);
TRANSFORM(im, iu12, iv12, bx11, by22);
TRANSFORM(im, iu22, iv22, bx22, by22);
j2d_glBegin(GL_QUADS);
j2d_glMultiTexCoord2fARB(GL_TEXTURE0_ARB, ou11, ov11);
j2d_glMultiTexCoord2fARB(GL_TEXTURE1_ARB, iu11, iv11);
j2d_glVertex2f(bx11, by11);
j2d_glMultiTexCoord2fARB(GL_TEXTURE0_ARB, ou21, ov21);
j2d_glMultiTexCoord2fARB(GL_TEXTURE1_ARB, iu21, iv21);
j2d_glVertex2f(bx22, by11);
j2d_glMultiTexCoord2fARB(GL_TEXTURE0_ARB, ou22, ov22);
j2d_glMultiTexCoord2fARB(GL_TEXTURE1_ARB, iu22, iv22);
j2d_glVertex2f(bx22, by22);
j2d_glMultiTexCoord2fARB(GL_TEXTURE0_ARB, ou12, ov12);
j2d_glMultiTexCoord2fARB(GL_TEXTURE1_ARB, iu12, iv12);
j2d_glVertex2f(bx11, by22);
j2d_glEnd();
}
void
OGLRenderer_DrawAAParallelogram(OGLContext *oglc, OGLSDOps *dstOps,
jfloat fx11, jfloat fy11,
jfloat dx21, jfloat dy21,
jfloat dx12, jfloat dy12,
jfloat lwr21, jfloat lwr12)
{
// dx,dy for line width in the "21" and "12" directions.
jfloat ldx21, ldy21, ldx12, ldy12;
// parameters for "outer" parallelogram
jfloat ofx11, ofy11, odx21, ody21, odx12, ody12;
// parameters for "inner" parallelogram
jfloat ifx11, ify11, idx21, idy21, idx12, idy12;
J2dTraceLn8(J2D_TRACE_INFO,
"OGLRenderer_DrawAAParallelogram "
"(x=%6.2f y=%6.2f "
"dx1=%6.2f dy1=%6.2f lwr1=%6.2f "
"dx2=%6.2f dy2=%6.2f lwr2=%6.2f)",
fx11, fy11,
dx21, dy21, lwr21,
dx12, dy12, lwr12);
RETURN_IF_NULL(oglc);
RETURN_IF_NULL(dstOps);
// calculate true dx,dy for line widths from the "line width ratios"
ldx21 = dx21 * lwr21;
ldy21 = dy21 * lwr21;
ldx12 = dx12 * lwr12;
ldy12 = dy12 * lwr12;
// calculate coordinates of the outer parallelogram
ofx11 = fx11 - (ldx21 + ldx12) / 2.0f;
ofy11 = fy11 - (ldy21 + ldy12) / 2.0f;
odx21 = dx21 + ldx21;
ody21 = dy21 + ldy21;
odx12 = dx12 + ldx12;
ody12 = dy12 + ldy12;
// Only process the inner parallelogram if the line width ratio
// did not consume the entire interior of the parallelogram
// (i.e. if the width ratio was less than 1.0)
if (lwr21 < 1.0f && lwr12 < 1.0f) {
// calculate coordinates of the inner parallelogram
ifx11 = fx11 + (ldx21 + ldx12) / 2.0f;
ify11 = fy11 + (ldy21 + ldy12) / 2.0f;
idx21 = dx21 - ldx21;
idy21 = dy21 - ldy21;
idx12 = dx12 - ldx12;
idy12 = dy12 - ldy12;
OGLRenderer_FillAAParallelogramInnerOuter(oglc, dstOps,
ofx11, ofy11,
odx21, ody21,
odx12, ody12,
ifx11, ify11,
idx21, idy21,
idx12, idy12);
} else {
OGLRenderer_FillAAParallelogram(oglc, dstOps,
ofx11, ofy11,
odx21, ody21,
odx12, ody12);
}
}
void
OGLRenderer_EnableAAParallelogramProgram()
{
J2dTraceLn(J2D_TRACE_INFO, "OGLRenderer_EnableAAParallelogramProgram");
if (aaPgramProgram == 0) {
aaPgramProgram = OGLContext_CreateFragmentProgram(aaPgramShaderSource);
if (aaPgramProgram == 0) {
J2dRlsTraceLn(J2D_TRACE_ERROR,
"OGLRenderer_EnableAAParallelogramProgram: "
"error creating program");
return;
}
}
j2d_glUseProgramObjectARB(aaPgramProgram);
}
void
OGLRenderer_DisableAAParallelogramProgram()
{
J2dTraceLn(J2D_TRACE_INFO, "OGLRenderer_DisableAAParallelogramProgram");
j2d_glUseProgramObjectARB(0);
}
#endif /* !HEADLESS */

View File

@ -1,5 +1,5 @@
/*
* Copyright 2005-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2005-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -46,9 +46,31 @@ void OGLRenderer_DrawPoly(OGLContext *oglc,
jint *xPoints, jint *yPoints);
void OGLRenderer_DrawScanlines(OGLContext *oglc,
jint count, jint *scanlines);
void OGLRenderer_DrawParallelogram(OGLContext *oglc,
jfloat fx11, jfloat fy11,
jfloat dx21, jfloat dy21,
jfloat dx12, jfloat dy12,
jfloat lw21, jfloat lw12);
void OGLRenderer_DrawAAParallelogram(OGLContext *oglc, OGLSDOps *dstOps,
jfloat fx11, jfloat fy11,
jfloat dx21, jfloat dy21,
jfloat dx12, jfloat dy12,
jfloat lw21, jfloat lw12);
void OGLRenderer_FillRect(OGLContext *oglc,
jint x, jint y, jint w, jint h);
void OGLRenderer_FillSpans(OGLContext *oglc,
jint count, jint *spans);
void OGLRenderer_FillParallelogram(OGLContext *oglc,
jfloat fx11, jfloat fy11,
jfloat dx21, jfloat dy21,
jfloat dx12, jfloat dy12);
void OGLRenderer_FillAAParallelogram(OGLContext *oglc, OGLSDOps *dstOps,
jfloat fx11, jfloat fy11,
jfloat dx21, jfloat dy21,
jfloat dx12, jfloat dy12);
void OGLRenderer_EnableAAParallelogramProgram();
void OGLRenderer_DisableAAParallelogramProgram();
#endif /* OGLRenderer_h_Included */

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -41,6 +41,8 @@ extern jlong OGLSD_GetNativeConfigInfo(OGLSDOps *oglsdo);
extern jboolean OGLSD_InitOGLWindow(JNIEnv *env, OGLSDOps *oglsdo);
extern void OGLSD_DestroyOGLSurface(JNIEnv *env, OGLSDOps *oglsdo);
void OGLSD_SetNativeDimensions(JNIEnv *env, OGLSDOps *oglsdo, jint w, jint h);
/**
* This table contains the "pixel formats" for all system memory surfaces
* that OpenGL is capable of handling, indexed by the "PF_" constants defined
@ -269,6 +271,9 @@ Java_sun_java2d_opengl_OGLSurfaceData_initTexture
return JNI_FALSE;
}
OGLSD_SetNativeDimensions(env, oglsdo,
oglsdo->textureWidth, oglsdo->textureHeight);
oglsdo->drawableType = OGLSD_TEXTURE;
// other fields (e.g. width, height) are set in OGLSD_InitTextureObject()
@ -427,6 +432,9 @@ Java_sun_java2d_opengl_OGLSurfaceData_initFBObject
oglsdo->fbobjectID = fbobjectID;
oglsdo->depthID = depthID;
OGLSD_SetNativeDimensions(env, oglsdo,
oglsdo->textureWidth, oglsdo->textureHeight);
// framebuffer objects differ from other OpenGL surfaces in that the
// value passed to glRead/DrawBuffer() must be GL_COLOR_ATTACHMENTn_EXT,
// rather than GL_FRONT (or GL_BACK)
@ -476,6 +484,8 @@ Java_sun_java2d_opengl_OGLSurfaceData_initFlipBackbuffer
// explicitly use BACK_LEFT rather than BACK...
oglsdo->activeBuffer = GL_BACK_LEFT;
OGLSD_SetNativeDimensions(env, oglsdo, oglsdo->width, oglsdo->height);
return JNI_TRUE;
}
@ -497,6 +507,45 @@ Java_sun_java2d_opengl_OGLSurfaceData_getTextureTarget
return (jint)oglsdo->textureTarget;
}
JNIEXPORT jint JNICALL
Java_sun_java2d_opengl_OGLSurfaceData_getTextureID
(JNIEnv *env, jobject oglsd,
jlong pData)
{
OGLSDOps *oglsdo = (OGLSDOps *)jlong_to_ptr(pData);
J2dTraceLn(J2D_TRACE_INFO, "OGLSurfaceData_getTextureID");
if (oglsdo == NULL) {
J2dRlsTraceLn(J2D_TRACE_ERROR,
"OGLSurfaceData_getTextureID: ops are null");
return 0L;
}
return (jint)oglsdo->textureID;
}
/**
* Initializes nativeWidth/Height fields of the surfaceData object with
* passed arguments.
*/
void
OGLSD_SetNativeDimensions(JNIEnv *env, OGLSDOps *oglsdo,
jint width, jint height)
{
jobject sdObject;
sdObject = (*env)->NewLocalRef(env, oglsdo->sdOps.sdObject);
if (sdObject == NULL) {
return;
}
JNU_SetFieldByName(env, NULL, sdObject, "nativeWidth", "I", width);
JNU_SetFieldByName(env, NULL, sdObject, "nativeHeight", "I", height);
(*env)->DeleteLocalRef(env, sdObject);
}
/**
* Disposes of all native resources associated with this surface.
*/

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -28,6 +28,7 @@
#include "java_awt_image_AffineTransformOp.h"
#include "sun_java2d_opengl_OGLSurfaceData.h"
#include "sun_java2d_pipe_hw_AccelSurface.h"
#include "J2D_GL/gl.h"
#include "SurfaceData.h"
@ -215,12 +216,12 @@ struct _OGLSDOps {
* These are shorthand names for the surface type constants defined in
* OGLSurfaceData.java.
*/
#define OGLSD_UNDEFINED sun_java2d_opengl_OGLSurfaceData_UNDEFINED
#define OGLSD_WINDOW sun_java2d_opengl_OGLSurfaceData_WINDOW
#define OGLSD_PBUFFER sun_java2d_opengl_OGLSurfaceData_PBUFFER
#define OGLSD_TEXTURE sun_java2d_opengl_OGLSurfaceData_TEXTURE
#define OGLSD_FLIP_BACKBUFFER sun_java2d_opengl_OGLSurfaceData_FLIP_BACKBUFFER
#define OGLSD_FBOBJECT sun_java2d_opengl_OGLSurfaceData_FBOBJECT
#define OGLSD_UNDEFINED sun_java2d_pipe_hw_AccelSurface_UNDEFINED
#define OGLSD_WINDOW sun_java2d_pipe_hw_AccelSurface_WINDOW
#define OGLSD_PBUFFER sun_java2d_pipe_hw_AccelSurface_RT_PLAIN
#define OGLSD_TEXTURE sun_java2d_pipe_hw_AccelSurface_TEXTURE
#define OGLSD_FLIP_BACKBUFFER sun_java2d_pipe_hw_AccelSurface_FLIP_BACKBUFFER
#define OGLSD_FBOBJECT sun_java2d_pipe_hw_AccelSurface_RT_TEXTURE
/**
* These are shorthand names for the filtering method constants used by

View File

@ -1,5 +1,5 @@
/*
* Copyright 2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -59,7 +59,6 @@ Java_sun_java2d_pipe_BufferedMaskBlit_enqueueTile
{
SurfaceDataOps *srcOps = (SurfaceDataOps *)jlong_to_ptr(pSrcOps);
SurfaceDataRasInfo srcInfo;
unsigned char *pMask;
unsigned char *bbuf;
jint *pBuf;
@ -97,13 +96,6 @@ Java_sun_java2d_pipe_BufferedMaskBlit_enqueueTile
return bpos;
}
pMask = (*env)->GetPrimitiveArrayCritical(env, maskArray, 0);
if (pMask == NULL) {
J2dRlsTraceLn(J2D_TRACE_ERROR,
"BufferedMaskBlit_enqueueTile: cannot lock mask array");
return bpos;
}
srcInfo.bounds.x1 = srcx;
srcInfo.bounds.y1 = srcy;
srcInfo.bounds.x2 = srcx + width;
@ -112,8 +104,6 @@ Java_sun_java2d_pipe_BufferedMaskBlit_enqueueTile
if (srcOps->Lock(env, srcOps, &srcInfo, SD_LOCK_READ) != SD_SUCCESS) {
J2dRlsTraceLn(J2D_TRACE_WARNING,
"BufferedMaskBlit_enqueueTile: could not acquire lock");
(*env)->ReleasePrimitiveArrayCritical(env, maskArray,
pMask, JNI_ABORT);
return bpos;
}
@ -129,6 +119,15 @@ Java_sun_java2d_pipe_BufferedMaskBlit_enqueueTile
PtrCoord(srcInfo.rasBase,
srcInfo.bounds.x1, srcInfo.pixelStride,
srcInfo.bounds.y1, srcInfo.scanStride);
unsigned char *pMask =
(*env)->GetPrimitiveArrayCritical(env, maskArray, 0);
if (pMask == NULL) {
J2dRlsTraceLn(J2D_TRACE_ERROR,
"BufferedMaskBlit_enqueueTile: cannot lock mask array");
SurfaceData_InvokeRelease(env, srcOps, &srcInfo);
SurfaceData_InvokeUnlock(env, srcOps, &srcInfo);
return bpos;
}
width = srcInfo.bounds.x2 - srcInfo.bounds.x1;
height = srcInfo.bounds.y2 - srcInfo.bounds.y1;
@ -166,18 +165,22 @@ Java_sun_java2d_pipe_BufferedMaskBlit_enqueueTile
do {
jint w = width;
do {
jubyte pathA = *pMask++;
jint pathA = *pMask++;
if (!pathA) {
pBuf[0] = 0;
} else {
jint cr, cg, cb, ca;
jubyte r, g, b, a;
LoadIntArgbTo4ByteArgb(pSrc, c, 0, ca, cr, cg, cb);
a = MUL8(ca, pathA);
r = MUL8(cr, a);
g = MUL8(cg, a);
b = MUL8(cb, a);
pBuf[0] = (a << 24) | (r << 16) | (g << 8) | b;
jint pixel = pSrc[0];
if (pathA == 0xff && (pixel >> 24) + 1 == 0) {
pBuf[0] = pixel;
} else {
jint r, g, b, a;
ExtractIntDcmComponents1234(pixel, a, r, g, b);
a = MUL8(pathA, a);
r = MUL8(a, r);
g = MUL8(a, g);
b = MUL8(a, b);
pBuf[0] = (a << 24) | (r << 16) | (g << 8) | b;
}
}
pSrc = PtrAddBytes(pSrc, srcPixelStride);
pBuf++;
@ -191,17 +194,17 @@ Java_sun_java2d_pipe_BufferedMaskBlit_enqueueTile
do {
jint w = width;
do {
jubyte pathA = *pMask++;
jint pathA = *pMask++;
if (!pathA) {
pBuf[0] = 0;
} else if (pathA == 0xff) {
pBuf[0] = pSrc[0];
} else {
jubyte r, g, b, a;
a = MUL8((pSrc[0] >> 24) & 0xff, pathA);
r = MUL8((pSrc[0] >> 16) & 0xff, pathA);
g = MUL8((pSrc[0] >> 8) & 0xff, pathA);
b = MUL8((pSrc[0] >> 0) & 0xff, pathA);
jint r, g, b, a;
a = MUL8(pathA, (pSrc[0] >> 24) & 0xff);
r = MUL8(pathA, (pSrc[0] >> 16) & 0xff);
g = MUL8(pathA, (pSrc[0] >> 8) & 0xff);
b = MUL8(pathA, (pSrc[0] >> 0) & 0xff);
pBuf[0] = (a << 24) | (r << 16) | (g << 8) | b;
}
pSrc = PtrAddBytes(pSrc, srcPixelStride);
@ -216,17 +219,18 @@ Java_sun_java2d_pipe_BufferedMaskBlit_enqueueTile
do {
jint w = width;
do {
jubyte pathA = *pMask++;
jint pathA = *pMask++;
if (!pathA) {
pBuf[0] = 0;
} else if (pathA == 0xff) {
pBuf[0] = pSrc[0] | 0xff000000;
} else {
jint cr, cg, cb;
jubyte r, g, b, a;
LoadIntRgbTo3ByteRgb(pSrc, c, 0, cr, cg, cb);
jint r, g, b, a;
LoadIntRgbTo3ByteRgb(pSrc, c, 0, r, g, b);
a = pathA;
r = MUL8(cr, a);
g = MUL8(cg, a);
b = MUL8(cb, a);
r = MUL8(a, r);
g = MUL8(a, g);
b = MUL8(a, b);
pBuf[0] = (a << 24) | (r << 16) | (g << 8) | b;
}
pSrc = PtrAddBytes(pSrc, srcPixelStride);
@ -241,17 +245,16 @@ Java_sun_java2d_pipe_BufferedMaskBlit_enqueueTile
do {
jint w = width;
do {
jubyte pathA = *pMask++;
jint pathA = *pMask++;
if (!pathA) {
pBuf[0] = 0;
} else {
jint cr, cg, cb;
jubyte r, g, b, a;
LoadIntBgrTo3ByteRgb(pSrc, c, 0, cr, cg, cb);
jint r, g, b, a;
LoadIntBgrTo3ByteRgb(pSrc, c, 0, r, g, b);
a = pathA;
r = MUL8(cr, a);
g = MUL8(cg, a);
b = MUL8(cb, a);
r = MUL8(a, r);
g = MUL8(a, g);
b = MUL8(a, b);
pBuf[0] = (a << 24) | (r << 16) | (g << 8) | b;
}
pSrc = PtrAddBytes(pSrc, srcPixelStride);
@ -269,14 +272,14 @@ Java_sun_java2d_pipe_BufferedMaskBlit_enqueueTile
// increment current byte position
bpos += width * height * sizeof(jint);
(*env)->ReleasePrimitiveArrayCritical(env, maskArray,
pMask, JNI_ABORT);
}
SurfaceData_InvokeRelease(env, srcOps, &srcInfo);
}
SurfaceData_InvokeUnlock(env, srcOps, &srcInfo);
(*env)->ReleasePrimitiveArrayCritical(env, maskArray,
pMask, JNI_ABORT);
// return the current byte position
return bpos;
}

View File

@ -70,9 +70,12 @@ import sun.awt.*;
import sun.awt.event.IgnorePaintEvent;
import sun.awt.image.SunVolatileImage;
import sun.awt.image.ToolkitImage;
import sun.java2d.BackBufferCapsProvider;
import sun.java2d.pipe.Region;
public class XComponentPeer extends XWindow implements ComponentPeer, DropTargetPeer {
public class XComponentPeer extends XWindow implements ComponentPeer, DropTargetPeer,
BackBufferCapsProvider
{
/* FIX ME: these constants copied from java.awt.KeyboardFocusManager */
static final int SNFH_FAILURE = 0;
static final int SNFH_SUCCESS_HANDLED = 1;
@ -1274,25 +1277,37 @@ public class XComponentPeer extends XWindow implements ComponentPeer, DropTarget
* native windowing system specific actions.
*/
private BufferCapabilities backBufferCaps;
public void createBuffers(int numBuffers, BufferCapabilities caps)
throws AWTException
{
if (buffersLog.isLoggable(Level.FINE)) {
buffersLog.fine("createBuffers(" + numBuffers + ", " + caps + ")");
}
// set the caps first, they're used when creating the bb
backBufferCaps = caps;
backBuffer = graphicsConfig.createBackBuffer(this, numBuffers, caps);
xBackBuffer = graphicsConfig.createBackBufferImage(target,
backBuffer);
}
public void flip(BufferCapabilities.FlipContents flipAction) {
@Override
public BufferCapabilities getBackBufferCaps() {
return backBufferCaps;
}
public void flip(int x1, int y1, int x2, int y2,
BufferCapabilities.FlipContents flipAction)
{
if (buffersLog.isLoggable(Level.FINE)) {
buffersLog.fine("flip(" + flipAction + ")");
}
if (backBuffer == 0) {
throw new IllegalStateException("Buffers have not been created");
}
graphicsConfig.flip(this, target, xBackBuffer, flipAction);
graphicsConfig.flip(this, target, xBackBuffer,
x1, y1, x2, y2, flipAction);
}
public Image getBackBuffer() {

View File

@ -257,7 +257,7 @@ public class XEmbedChildProxyPeer implements ComponentPeer, XEventDispatcher{
public void createBuffers(int numBuffers, BufferCapabilities caps)
throws AWTException { }
public Image getBackBuffer() { return null; }
public void flip(BufferCapabilities.FlipContents flipAction) { }
public void flip(int x1, int y1, int x2, int y2, BufferCapabilities.FlipContents flipAction) { }
public void destroyBuffers() { }
/**

View File

@ -1,5 +1,5 @@
/*
* Copyright 1997-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -27,20 +27,17 @@ package sun.awt;
import java.awt.AWTException;
import java.awt.BufferCapabilities;
import java.awt.BufferCapabilities.FlipContents;
import java.awt.Component;
import java.awt.Toolkit;
import java.awt.GraphicsConfiguration;
import java.awt.GraphicsDevice;
import java.awt.Image;
import java.awt.ImageCapabilities;
import java.awt.image.DataBuffer;
import java.awt.Transparency;
import java.awt.image.BufferedImage;
import java.awt.image.ColorModel;
import java.awt.image.DirectColorModel;
import java.awt.image.ImageProducer;
import java.awt.image.IndexColorModel;
import java.awt.image.Raster;
import java.awt.image.VolatileImage;
import java.awt.image.WritableRaster;
import java.awt.geom.AffineTransform;
@ -429,6 +426,7 @@ public class X11GraphicsConfig extends GraphicsConfiguration
*/
public void flip(X11ComponentPeer peer,
Component target, VolatileImage xBackBuffer,
int x1, int y1, int x2, int y2,
BufferCapabilities.FlipContents flipAction)
{
long window = peer.getContentWindow();

View File

@ -1,5 +1,5 @@
/*
* Copyright 1997-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -385,6 +385,9 @@ public class X11GraphicsDevice
throw new IllegalStateException("Must be in fullscreen mode " +
"in order to set display mode");
}
if (getDisplayMode().equals(dm)) {
return;
}
if (dm == null ||
(dm = getMatchingDisplayMode(dm)) == null)
{

View File

@ -1,5 +1,5 @@
/*
* Copyright 1995-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1995-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -1138,11 +1138,14 @@ abstract class MComponentPeer implements ComponentPeer, DropTargetPeer, X11Compo
backBuffer);
}
public void flip(BufferCapabilities.FlipContents flipAction) {
public void flip(int x1, int y1, int x2, int y2,
BufferCapabilities.FlipContents flipAction)
{
if (backBuffer == 0) {
throw new IllegalStateException("Buffers have not been created");
}
graphicsConfig.flip(this, target, xBackBuffer, flipAction);
graphicsConfig.flip(this, target, xBackBuffer,
x1, y1, x2, y2, flipAction);
}
public Image getBackBuffer() {

View File

@ -0,0 +1,35 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d;
import java.awt.BufferCapabilities;
/**
* Provides access to back-buffer's BufferCapabilities.
*/
public interface BackBufferCapsProvider {
public BufferCapabilities getBackBufferCaps();
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -27,8 +27,11 @@ package sun.java2d.opengl;
import java.awt.AWTException;
import java.awt.BufferCapabilities;
import java.awt.BufferCapabilities.FlipContents;
import java.awt.Color;
import java.awt.Component;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.ImageCapabilities;
import java.awt.Transparency;
@ -45,7 +48,19 @@ import sun.awt.X11GraphicsDevice;
import sun.awt.X11GraphicsEnvironment;
import sun.awt.image.OffScreenImage;
import sun.awt.image.SunVolatileImage;
import sun.awt.image.SurfaceManager;
import sun.java2d.SunGraphics2D;
import sun.java2d.Surface;
import sun.java2d.SurfaceData;
import sun.java2d.pipe.hw.AccelSurface;
import sun.java2d.pipe.hw.AccelTypedVolatileImage;
import sun.java2d.pipe.hw.ContextCapabilities;
import static sun.java2d.opengl.OGLSurfaceData.*;
import static sun.java2d.opengl.OGLContext.*;
import static sun.java2d.opengl.OGLContext.OGLContextCaps.*;
import sun.java2d.opengl.GLXSurfaceData.GLXVSyncOffScreenSurfaceData;
import sun.java2d.pipe.hw.AccelDeviceEventListener;
import sun.java2d.pipe.hw.AccelDeviceEventNotifier;
public class GLXGraphicsConfig
extends X11GraphicsConfig
@ -54,7 +69,7 @@ public class GLXGraphicsConfig
private static ImageCapabilities imageCaps = new GLXImageCaps();
private BufferCapabilities bufferCaps;
private long pConfigInfo;
private int oglCaps;
private ContextCapabilities oglCaps;
private OGLContext context;
private static native long getGLXConfigInfo(int screennum, int visualnum);
@ -62,20 +77,22 @@ public class GLXGraphicsConfig
private native void initConfig(long aData, long ctxinfo);
private GLXGraphicsConfig(X11GraphicsDevice device, int visualnum,
long configInfo, int oglCaps)
long configInfo, ContextCapabilities oglCaps)
{
super(device, visualnum, 0, 0,
(oglCaps & OGLContext.CAPS_DOUBLEBUFFERED) != 0);
(oglCaps.getCaps() & CAPS_DOUBLEBUFFERED) != 0);
pConfigInfo = configInfo;
initConfig(getAData(), configInfo);
this.oglCaps = oglCaps;
context = new OGLContext(OGLRenderQueue.getInstance());
context = new OGLContext(OGLRenderQueue.getInstance(), this);
}
@Override
public Object getProxyKey() {
return this;
}
@Override
public SurfaceData createManagedSurface(int w, int h, int transparency) {
return GLXSurfaceData.createData(this, w, h,
getColorModel(transparency),
@ -91,6 +108,7 @@ public class GLXGraphicsConfig
}
long cfginfo = 0;
final String ids[] = new String[1];
OGLRenderQueue rq = OGLRenderQueue.getInstance();
rq.lock();
try {
@ -102,6 +120,12 @@ public class GLXGraphicsConfig
new GLXGetConfigInfo(device.getScreen(), visualnum);
rq.flushAndInvokeNow(action);
cfginfo = action.getConfigInfo();
OGLContext.setScratchSurface(cfginfo);
rq.flushAndInvokeNow(new Runnable() {
public void run() {
ids[0] = OGLContext.getOGLIdString();
}
});
} finally {
rq.unlock();
}
@ -110,8 +134,9 @@ public class GLXGraphicsConfig
}
int oglCaps = getOGLCapabilities(cfginfo);
ContextCapabilities caps = new OGLContextCaps(oglCaps, ids[0]);
return new GLXGraphicsConfig(device, visualnum, cfginfo, oglCaps);
return new GLXGraphicsConfig(device, visualnum, cfginfo, caps);
}
/**
@ -138,14 +163,22 @@ public class GLXGraphicsConfig
* Returns true if the provided capability bit is present for this config.
* See OGLContext.java for a list of supported capabilities.
*/
@Override
public final boolean isCapPresent(int cap) {
return ((oglCaps & cap) != 0);
return ((oglCaps.getCaps() & cap) != 0);
}
@Override
public final long getNativeConfigInfo() {
return pConfigInfo;
}
/**
* {@inheritDoc}
*
* @see sun.java2d.pipe.hw.BufferedContextProvider#getContext
*/
@Override
public final OGLContext getContext() {
return context;
}
@ -275,16 +308,36 @@ public class GLXGraphicsConfig
@Override
public void flip(X11ComponentPeer peer,
Component target, VolatileImage xBackBuffer,
int x1, int y1, int x2, int y2,
BufferCapabilities.FlipContents flipAction)
{
if (flipAction == BufferCapabilities.FlipContents.COPIED) {
Graphics g = peer.getGraphics();
try {
g.drawImage(xBackBuffer, 0, 0, null);
} finally {
g.dispose();
SurfaceManager vsm = SurfaceManager.getManager(xBackBuffer);
SurfaceData sd = vsm.getPrimarySurfaceData();
if (sd instanceof GLXVSyncOffScreenSurfaceData) {
GLXVSyncOffScreenSurfaceData vsd =
(GLXVSyncOffScreenSurfaceData)sd;
SurfaceData bbsd = vsd.getFlipSurface();
Graphics2D bbg =
new SunGraphics2D(bbsd, Color.black, Color.white, null);
try {
bbg.drawImage(xBackBuffer, 0, 0, null);
} finally {
bbg.dispose();
}
} else {
Graphics g = peer.getGraphics();
try {
g.drawImage(xBackBuffer,
x1, y1, x2, y2,
x1, y1, x2, y2,
null);
} finally {
g.dispose();
}
return;
}
return;
} else if (flipAction == BufferCapabilities.FlipContents.PRIOR) {
// not supported by GLX...
return;
@ -333,4 +386,64 @@ public class GLXGraphicsConfig
public ImageCapabilities getImageCapabilities() {
return imageCaps;
}
/**
* {@inheritDoc}
*
* @see sun.java2d.pipe.hw.AccelGraphicsConfig#createCompatibleVolatileImage
*/
@Override
public VolatileImage
createCompatibleVolatileImage(int width, int height,
int transparency, int type)
{
if (type == FLIP_BACKBUFFER || type == WINDOW || type == UNDEFINED ||
transparency == Transparency.BITMASK)
{
return null;
}
if (type == FBOBJECT) {
if (!isCapPresent(CAPS_EXT_FBOBJECT)) {
return null;
}
} else if (type == PBUFFER) {
boolean isOpaque = transparency == Transparency.OPAQUE;
if (!isOpaque && !isCapPresent(CAPS_STORED_ALPHA)) {
return null;
}
}
SunVolatileImage vi = new AccelTypedVolatileImage(this, width, height,
transparency, type);
Surface sd = vi.getDestSurface();
if (!(sd instanceof AccelSurface) ||
((AccelSurface)sd).getType() != type)
{
vi.flush();
vi = null;
}
return vi;
}
/**
* {@inheritDoc}
*
* @see sun.java2d.pipe.hw.AccelGraphicsConfig#getContextCapabilities
*/
@Override
public ContextCapabilities getContextCapabilities() {
return oglCaps;
}
@Override
public void addDeviceEventListener(AccelDeviceEventListener l) {
AccelDeviceEventNotifier.addListener(l, screen.getScreen());
}
@Override
public void removeDeviceEventListener(AccelDeviceEventListener l) {
AccelDeviceEventNotifier.removeListener(l);
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -73,13 +73,20 @@ public abstract class GLXSurfaceData extends OGLSurfaceData {
* double-buffered on-screen Window.
*/
public static GLXOffScreenSurfaceData createData(X11ComponentPeer peer,
Image image)
Image image,
int type)
{
GLXGraphicsConfig gc = getGC(peer);
Rectangle r = peer.getBounds();
return new GLXOffScreenSurfaceData(peer, gc, r.width, r.height,
image, peer.getColorModel(),
FLIP_BACKBUFFER);
if (type == FLIP_BACKBUFFER) {
return new GLXOffScreenSurfaceData(peer, gc, r.width, r.height,
image, peer.getColorModel(),
FLIP_BACKBUFFER);
} else {
return new GLXVSyncOffScreenSurfaceData(peer, gc, r.width, r.height,
image, peer.getColorModel(),
type);
}
}
/**
@ -134,6 +141,42 @@ public abstract class GLXSurfaceData extends OGLSurfaceData {
}
}
/**
* A surface which implements a v-synced flip back-buffer with COPIED
* FlipContents.
*
* This surface serves as a back-buffer to the outside world, while
* it is actually an offscreen surface. When the BufferStrategy this surface
* belongs to is showed, it is first copied to the real private
* FLIP_BACKBUFFER, which is then flipped.
*/
public static class GLXVSyncOffScreenSurfaceData extends
GLXOffScreenSurfaceData
{
private GLXOffScreenSurfaceData flipSurface;
public GLXVSyncOffScreenSurfaceData(X11ComponentPeer peer,
GLXGraphicsConfig gc,
int width, int height,
Image image, ColorModel cm,
int type)
{
super(peer, gc, width, height, image, cm, type);
flipSurface = GLXSurfaceData.createData(peer, image, FLIP_BACKBUFFER);
}
public SurfaceData getFlipSurface() {
return flipSurface;
}
@Override
public void flush() {
flipSurface.flush();
super.flush();
}
}
public static class GLXOffScreenSurfaceData extends GLXSurfaceData {
private Image offscreenImage;

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2005 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -25,16 +25,21 @@
package sun.java2d.opengl;
import java.awt.BufferCapabilities;
import static java.awt.BufferCapabilities.FlipContents.*;
import java.awt.Component;
import java.awt.GraphicsConfiguration;
import java.awt.ImageCapabilities;
import java.awt.Rectangle;
import java.awt.Transparency;
import java.awt.image.ColorModel;
import sun.awt.X11ComponentPeer;
import sun.awt.image.SunVolatileImage;
import sun.awt.image.VolatileSurfaceManager;
import sun.java2d.BackBufferCapsProvider;
import sun.java2d.SurfaceData;
import static sun.java2d.opengl.OGLContext.OGLContextCaps.*;
import sun.java2d.pipe.hw.ExtendedBufferCapabilities;
import static sun.java2d.pipe.hw.AccelSurface.*;
import static sun.java2d.pipe.hw.ExtendedBufferCapabilities.VSyncType.*;
public class GLXVolatileSurfaceManager extends VolatileSurfaceManager {
@ -56,8 +61,8 @@ public class GLXVolatileSurfaceManager extends VolatileSurfaceManager {
accelerationEnabled =
(transparency == Transparency.OPAQUE) ||
((transparency == Transparency.TRANSLUCENT) &&
(gc.isCapPresent(OGLContext.CAPS_EXT_FBOBJECT) ||
gc.isCapPresent(OGLContext.CAPS_STORED_ALPHA)));
(gc.isCapPresent(CAPS_EXT_FBOBJECT) ||
gc.isCapPresent(CAPS_STORED_ALPHA)));
}
protected boolean isAccelerationEnabled() {
@ -75,24 +80,49 @@ public class GLXVolatileSurfaceManager extends VolatileSurfaceManager {
(comp != null) ? (X11ComponentPeer)comp.getPeer() : null;
try {
boolean createVSynced = false;
boolean forceback = false;
if (context instanceof Boolean) {
forceback = ((Boolean)context).booleanValue();
if (forceback && peer instanceof BackBufferCapsProvider) {
BackBufferCapsProvider provider =
(BackBufferCapsProvider)peer;
BufferCapabilities caps = provider.getBackBufferCaps();
if (caps instanceof ExtendedBufferCapabilities) {
ExtendedBufferCapabilities ebc =
(ExtendedBufferCapabilities)caps;
if (ebc.getVSync() == VSYNC_ON &&
ebc.getFlipContents() == COPIED)
{
createVSynced = true;
forceback = false;
}
}
}
}
if (forceback) {
// peer must be non-null in this case
sData = GLXSurfaceData.createData(peer, vImg);
sData = GLXSurfaceData.createData(peer, vImg, FLIP_BACKBUFFER);
} else {
GLXGraphicsConfig gc =
(GLXGraphicsConfig)vImg.getGraphicsConfig();
ColorModel cm = gc.getColorModel(vImg.getTransparency());
int type = gc.isCapPresent(OGLContext.CAPS_EXT_FBOBJECT) ?
OGLSurfaceData.FBOBJECT : OGLSurfaceData.PBUFFER;
sData = GLXSurfaceData.createData(gc,
vImg.getWidth(),
vImg.getHeight(),
cm, vImg, type);
int type = vImg.getForcedAccelSurfaceType();
// if acceleration type is forced (type != UNDEFINED) then
// use the forced type, otherwise choose one based on caps
if (type == OGLSurfaceData.UNDEFINED) {
type = gc.isCapPresent(CAPS_EXT_FBOBJECT) ?
OGLSurfaceData.FBOBJECT : OGLSurfaceData.PBUFFER;
}
if (createVSynced) {
sData = GLXSurfaceData.createData(peer, vImg, type);
} else {
sData = GLXSurfaceData.createData(gc,
vImg.getWidth(),
vImg.getHeight(),
cm, vImg, type);
}
}
} catch (NullPointerException ex) {
sData = null;
@ -103,7 +133,15 @@ public class GLXVolatileSurfaceManager extends VolatileSurfaceManager {
return sData;
}
@Override
protected boolean isConfigValid(GraphicsConfiguration gc) {
return ((gc == null) || (gc == vImg.getGraphicsConfig()));
}
@Override
public void initContents() {
if (vImg.getForcedAccelSurfaceType() != OGLSurfaceData.TEXTURE) {
super.initContents();
}
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2001-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2001-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -79,15 +79,16 @@ public class X11PMBlitBgLoops extends BlitBg {
super(srcType, CompositeType.SrcNoEa, dstType);
}
@Override
public void BlitBg(SurfaceData src, SurfaceData dst,
Composite comp, Region clip, Color bgColor,
Composite comp, Region clip, int bgColor,
int sx, int sy,
int dx, int dy,
int w, int h)
{
SunToolkit.awtLock();
try {
int pixel = dst.pixelFor(bgColor.getRGB());
int pixel = dst.pixelFor(bgColor);
X11SurfaceData x11sd = (X11SurfaceData)dst;
// use false for needExposures since we clip to the pixmap
long xgc = x11sd.getBlitGC(clip, false);

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -471,7 +471,7 @@ Java_sun_java2d_opengl_GLXGraphicsConfig_getGLXConfigInfo(JNIEnv *env,
GLXContext context;
GLXPbuffer scratch;
GLXGraphicsConfigInfo *glxinfo;
jint caps = sun_java2d_opengl_OGLContext_CAPS_EMPTY;
jint caps = CAPS_EMPTY;
int db, alpha;
const unsigned char *versionstr;
@ -581,11 +581,11 @@ Java_sun_java2d_opengl_GLXGraphicsConfig_getGLXConfigInfo(JNIEnv *env,
// get config-specific capabilities
j2d_glXGetFBConfigAttrib(awt_display, fbconfig, GLX_DOUBLEBUFFER, &db);
if (db) {
caps |= sun_java2d_opengl_OGLContext_CAPS_DOUBLEBUFFERED;
caps |= CAPS_DOUBLEBUFFERED;
}
j2d_glXGetFBConfigAttrib(awt_display, fbconfig, GLX_ALPHA_SIZE, &alpha);
if (alpha > 0) {
caps |= sun_java2d_opengl_OGLContext_CAPS_STORED_ALPHA;
caps |= CAPS_STORED_ALPHA;
}
// initialize the OGLContext, which wraps the GLXFBConfig and GLXContext
@ -662,11 +662,11 @@ Java_sun_java2d_opengl_GLXGraphicsConfig_getOGLCapabilities(JNIEnv *env,
J2dTraceLn(J2D_TRACE_INFO, "GLXGraphicsConfig_getOGLCapabilities");
if (glxinfo == NULL || glxinfo->context == NULL) {
return sun_java2d_opengl_OGLContext_CAPS_EMPTY;
return CAPS_EMPTY;
}
return glxinfo->context->caps;
#else
return sun_java2d_opengl_OGLContext_CAPS_EMPTY;
return CAPS_EMPTY;
#endif /* !HEADLESS */
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2003-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -47,6 +47,9 @@ extern DisposeFunc OGLSD_Dispose;
extern struct MComponentPeerIDs mComponentPeerIDs;
extern void
OGLSD_SetNativeDimensions(JNIEnv *env, OGLSDOps *oglsdo, jint w, jint h);
jboolean surfaceCreationFailed = JNI_FALSE;
#endif /* !HEADLESS */
@ -460,6 +463,8 @@ Java_sun_java2d_opengl_GLXSurfaceData_initPbuffer
glxsdo->drawable = pbuffer;
glxsdo->xdrawable = 0;
OGLSD_SetNativeDimensions(env, oglsdo, width, height);
return JNI_TRUE;
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 1997-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -55,9 +55,7 @@ import sun.java2d.InvalidPipeException;
import sun.java2d.loops.RenderLoops;
import sun.java2d.loops.SurfaceType;
import sun.java2d.loops.CompositeType;
import sun.java2d.windows.Win32SurfaceData;
import sun.java2d.windows.WinBackBuffer;
import sun.java2d.windows.WindowsFlags;
import sun.java2d.windows.GDIWindowSurfaceData;
/**
* This is an implementation of a GraphicsConfiguration object for a
@ -72,8 +70,6 @@ public class Win32GraphicsConfig extends GraphicsConfiguration
protected Win32GraphicsDevice screen;
protected int visual; //PixelFormatID
protected RenderLoops solidloops;
private static BufferCapabilities bufferCaps;
private static ImageCapabilities imageCaps;
private static native void initIDs();
@ -170,32 +166,12 @@ public class Win32GraphicsConfig extends GraphicsConfiguration
case Transparency.BITMASK:
return new DirectColorModel(25, 0xff0000, 0xff00, 0xff, 0x1000000);
case Transparency.TRANSLUCENT:
return getTranslucentColorModel();
return ColorModel.getRGBdefault();
default:
return null;
}
}
private static final int DCM_4444_RED_MASK = 0x0f00;
private static final int DCM_4444_GRN_MASK = 0x00f0;
private static final int DCM_4444_BLU_MASK = 0x000f;
private static final int DCM_4444_ALP_MASK = 0xf000;
static ColorModel translucentCM = null;
public static ColorModel getTranslucentColorModel() {
if (WindowsFlags.getD3DTexBpp() == 16) {
if (translucentCM == null) {
translucentCM = new DirectColorModel(16,
DCM_4444_RED_MASK,
DCM_4444_GRN_MASK,
DCM_4444_BLU_MASK,
DCM_4444_ALP_MASK);
}
return translucentCM;
} else {
return ColorModel.getRGBdefault();
}
}
/**
* Returns the default Transform for this configuration. This
* Transform is typically the Identity transform for most normal
@ -246,44 +222,6 @@ public class Win32GraphicsConfig extends GraphicsConfiguration
return getBounds(screen.getScreen());
}
private static class DDrawBufferCapabilities extends BufferCapabilities {
public DDrawBufferCapabilities(ImageCapabilities imageCaps) {
super(imageCaps, imageCaps, FlipContents.PRIOR);
}
public boolean isFullScreenRequired() { return true; }
public boolean isMultiBufferAvailable() { return true; }
}
private static class DDrawImageCapabilities extends ImageCapabilities {
public DDrawImageCapabilities() {
super(true);
}
public boolean isTrueVolatile() { return true; }
}
public BufferCapabilities getBufferCapabilities() {
if (bufferCaps == null) {
if (WindowsFlags.isDDEnabled()) {
bufferCaps = new DDrawBufferCapabilities(
getImageCapabilities());
} else {
bufferCaps = super.getBufferCapabilities();
}
}
return bufferCaps;
}
public ImageCapabilities getImageCapabilities() {
if (imageCaps == null) {
if (WindowsFlags.isDDEnabled()) {
imageCaps = new DDrawImageCapabilities();
} else {
imageCaps = super.getImageCapabilities();
}
}
return imageCaps;
}
public synchronized void displayChanged() {
solidloops = null;
}
@ -305,11 +243,11 @@ public class Win32GraphicsConfig extends GraphicsConfiguration
public SurfaceData createSurfaceData(WComponentPeer peer,
int numBackBuffers)
{
return Win32SurfaceData.createData(peer, numBackBuffers);
return GDIWindowSurfaceData.createData(peer);
}
/**
* Creates a new hidden-acceleration image of the given width and height
* Creates a new managed image of the given width and height
* that is associated with the target Component.
*/
public Image createAcceleratedImage(Component target,
@ -327,15 +265,6 @@ public class Win32GraphicsConfig extends GraphicsConfiguration
* WComponentPeer.java...
*/
private boolean isFullScreenExclusive(Component target) {
Win32GraphicsDevice gd = (Win32GraphicsDevice)getDevice();
while (target != null && !(target instanceof Window)) {
target = target.getParent();
}
return (target == gd.getFullScreenWindow() &&
gd.isDDEnabledOnDevice());
}
/**
* Checks that the requested configuration is natively supported; if not,
* an AWTException is thrown.
@ -345,51 +274,61 @@ public class Win32GraphicsConfig extends GraphicsConfiguration
BufferCapabilities caps)
throws AWTException
{
if (!isFullScreenExclusive(target)) {
throw new AWTException(
"The operation requested is only supported on a full-screen" +
" exclusive window");
}
// the default pipeline doesn't support flip buffer strategy
throw new AWTException(
"The operation requested is not supported");
}
/**
* Creates a backbuffer for the given peer and returns the image wrapper.
* This method is called from WComponentPeer when a surface data is replaced
* REMIND: while the default pipeline doesn't support flipping, it may
* happen that the accelerated device may have this graphics config
* (like if the device restoration failed when one device exits fs mode
* while others remain).
*/
public VolatileImage createBackBuffer(WComponentPeer peer) {
// Create the back buffer object
return new WinBackBuffer((Component)peer.getTarget(),
(Win32SurfaceData)peer.getSurfaceData());
Component target = (Component)peer.getTarget();
return new SunVolatileImage(target,
target.getWidth(), target.getHeight(),
Boolean.TRUE);
}
/**
* Performs the native flip operation for the given target Component.
*
* REMIND: we should really not get here because that would mean that
* a FLIP BufferStrategy has been created, and one could only be created
* if accelerated pipeline is present but in some rare (and transitional)
* cases it may happen that the accelerated graphics device may have a
* default graphics configuraiton, so this is just a precaution.
*/
public void flip(WComponentPeer peer,
Component target, VolatileImage backBuffer,
int x1, int y1, int x2, int y2,
BufferCapabilities.FlipContents flipAction)
{
int width = target.getWidth();
int height = target.getHeight();
if (flipAction == BufferCapabilities.FlipContents.COPIED) {
Graphics g = target.getGraphics();
g.drawImage(backBuffer, 0, 0, width, height, null);
g.dispose();
return;
}
Win32SurfaceData sd = (Win32SurfaceData)peer.getSurfaceData();
try {
sd.flip(((WinBackBuffer)backBuffer).getHWSurfaceData());
} catch (sun.java2d.InvalidPipeException e) {
// copy software surface to the screen via gdi blit
Graphics g = target.getGraphics();
g.drawImage(backBuffer, 0, 0, width, height, null);
g.dispose();
}
if (flipAction == BufferCapabilities.FlipContents.BACKGROUND) {
if (flipAction == BufferCapabilities.FlipContents.COPIED ||
flipAction == BufferCapabilities.FlipContents.UNDEFINED) {
Graphics g = peer.getGraphics();
try {
g.drawImage(backBuffer,
x1, y1, x2, y2,
x1, y1, x2, y2,
null);
} finally {
g.dispose();
}
} else if (flipAction == BufferCapabilities.FlipContents.BACKGROUND) {
Graphics g = backBuffer.getGraphics();
g.setColor(target.getBackground());
g.fillRect(0, 0, width, height);
g.dispose();
try {
g.setColor(target.getBackground());
g.fillRect(0, 0,
backBuffer.getWidth(),
backBuffer.getHeight());
} finally {
g.dispose();
}
}
// the rest of the flip actions are not supported
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 1997-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -33,12 +33,14 @@ import java.awt.DisplayMode;
import java.awt.Frame;
import java.awt.Rectangle;
import java.awt.Window;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.awt.event.WindowListener;
import java.awt.image.ColorModel;
import java.util.ArrayList;
import java.util.Vector;
import java.awt.peer.WindowPeer;
import sun.awt.windows.WWindowPeer;
import sun.java2d.d3d.D3DContext;
import sun.java2d.opengl.WGLGraphicsConfig;
import sun.java2d.windows.WindowsFlags;
@ -54,13 +56,11 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
int screen;
ColorModel dynamicColorModel; // updated with dev changes
ColorModel colorModel; // static for device
GraphicsConfiguration[] configs;
GraphicsConfiguration defaultConfig;
boolean offscreenAccelerationEnabled = true;
private D3DContext d3dContext;
protected GraphicsConfiguration[] configs;
protected GraphicsConfiguration defaultConfig;
private final String idString;
private final String descString;
protected String descString;
// Note that we do not synchronize access to this variable - it doesn't
// really matter if a thread does an operation on graphics device which is
// about to become invalid (or already become) - we are prepared to deal
@ -69,12 +69,16 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
// keep track of top-level windows on this display
private SunDisplayChanger topLevels = new SunDisplayChanger();
private static boolean pfDisabled;
// REMIND: we may disable the use of pixel formats for some accelerated
// pipelines which are mutually exclusive with opengl, for which
// pixel formats were added in the first place
protected static boolean pfDisabled;
private static AWTPermission fullScreenExclusivePermission;
private Rectangle ownerWindowedModeBounds = null;
// the original display mode we had before entering the fullscreen
// mode
private DisplayMode defaultDisplayMode;
// activation/deactivation listener for the full-screen window
private WindowListener fsWindowListener;
static {
@ -91,16 +95,6 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
private static native void initIDs();
/**
* Acceleration can be disabled due to capabilities of the display
* device discovered during ddraw initialization. This is not the
* same as isDDEnabledOnDevice(), which returns false when ddraw
* was disabled by the user or had problems initializing.
*/
public boolean isOffscreenAccelerationEnabled() {
return offscreenAccelerationEnabled;
}
native void initDevice(int screen);
public Win32GraphicsDevice(int screennum) {
@ -109,6 +103,7 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
// to reflect the original screen number (which may change if the
// device is removed)
idString = "\\Display"+screen;
// REMIND: may be should use class name?
descString = "Win32GraphicsDevice[screen=" + screen;
valid = true;
@ -136,7 +131,7 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
* Returns whether this is a valid devicie. Device can become
* invalid as a result of device removal event.
*/
boolean isValid() {
public boolean isValid() {
return valid;
}
@ -145,7 +140,7 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
*
* @param defaultScreen the current default screen
*/
void invalidate(int defaultScreen) {
protected void invalidate(int defaultScreen) {
valid = false;
screen = defaultScreen;
}
@ -178,8 +173,7 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
int defaultPixID = getDefaultPixID(screen);
Vector v = new Vector( max );
if (defaultPixID == 0) {
// Workaround for failing GDI calls, or if DirectDraw
// is disabled
// Workaround for failing GDI calls
defaultConfig = Win32GraphicsConfig.getConfig(this,
defaultPixID);
v.addElement(defaultConfig);
@ -309,32 +303,6 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
getLocalGraphicsEnvironment().getDefaultScreenDevice());
}
private native boolean isDDEnabledOnDeviceNative(int screen);
public D3DContext getD3DContext() {
if (d3dContext == null) {
d3dContext = new D3DContext(this);
}
return d3dContext;
}
public boolean isDDEnabledOnDevice() {
return (WindowsFlags.isDDEnabled() && isValid() &&
isDDEnabledOnDeviceNative(screen));
}
public boolean isD3DEnabledOnDevice() {
// The conditions under which we enable the D3D pipeline for the device:
// - d3d is not disabled via a flag
// - either d3d is forced via property or we're in fullscreen mode
// - the hardware/drivers meet our requirements
return (WindowsFlags.isD3DEnabled() && isValid() &&
(WindowsFlags.isD3DSet() || getFullScreenWindow() != null) &&
((getD3DContext().getDeviceCaps() &
D3DContext.J2D_D3D_ENABLED_OK) != 0));
}
private static boolean isFSExclusiveModeAllowed() {
SecurityManager security = System.getSecurityManager();
if (security != null) {
@ -352,31 +320,14 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
}
/**
* We support the exclusive fullscreen mode in both ddraw and
* noddraw modes, so we return true unless we're not allowed to use
* fullscreen mode.
* returns true unless we're not allowed to use fullscreen mode.
*/
@Override
public boolean isFullScreenSupported() {
return isFSExclusiveModeAllowed();
}
/**
* Return the owning Frame for a given Window. Used in setFSWindow below
* to set the properties of the owning Frame when a Window goes
* into fullscreen mode.
*/
private Frame getToplevelOwner(Window w) {
Window owner = w;
while (owner != null) {
owner = owner.getOwner();
if (owner instanceof Frame) {
return (Frame) owner;
}
}
// Should not get here, but return something intelligent just in case
return null;
}
@Override
public synchronized void setFullScreenWindow(Window w) {
Window old = getFullScreenWindow();
if (w == old) {
@ -402,51 +353,25 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
}
WWindowPeer peer = (WWindowPeer)old.getPeer();
if (peer != null) {
// we used to destroy the buffers on exiting fs mode, this
// is no longer needed since fs change will cause a surface
// data replacement
synchronized(peer) {
peer.destroyBuffers();
exitFullScreenExclusive(isDDEnabledOnDevice(),
screen, peer);
exitFullScreenExclusive(screen, peer);
}
}
/**
* Bug 4933099: There is some funny-business to deal with when this
* method is called with a Window instead of a Frame. See 4836744
* for more information on this. One side-effect of our workaround
* for the problem is that the owning Frame of a Window may end
* up getting resized during the fullscreen process. When we
* return from fullscreen mode, we should resize the Frame to
* its original size (just like the Window is being resized
* to its original size in GraphicsDevice).
*/
if (!(old instanceof Frame)) {
Frame owner = getToplevelOwner(old);
if (owner != null && ownerWindowedModeBounds != null) {
owner.setBounds(ownerWindowedModeBounds);
}
ownerWindowedModeBounds = null;
}
removeFSWindowListener(old);
}
super.setFullScreenWindow(w);
if (w != null) {
// always record the default display mode prior to going
// fullscreen
defaultDisplayMode = getDisplayMode();
// Bug 4933099
if (!(w instanceof Frame)) {
Frame owner = getToplevelOwner(w);
if (owner != null) {
ownerWindowedModeBounds = owner.getBounds();
// These will get set for the native window in
// any case. Set them here so that resetting them
// later actually does the right thing
owner.setBounds(w.getBounds());
}
}
addFSWindowListener(w);
// Enter full screen exclusive mode.
WWindowPeer peer = (WWindowPeer)w.getPeer();
synchronized(peer) {
enterFullScreenExclusive(isDDEnabledOnDevice(),
screen, peer);
enterFullScreenExclusive(screen, peer);
// Note: removed replaceSurfaceData() call because
// changing the window size or making it visible
// will cause this anyway, and both of these events happen
@ -463,15 +388,18 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
// tree-lock and should never lock on any resources which are
// required by other threads which may have them and may require
// the tree-lock.
private native void enterFullScreenExclusive(boolean useDD,
int screen, WindowPeer w);
private native void exitFullScreenExclusive(boolean useDD,
int screen, WindowPeer w);
// REMIND: in the future these methods may need to become protected so that
// subclasses could override them and use appropriate api other than GDI
// for implementing these functions.
protected native void enterFullScreenExclusive(int screen, WindowPeer w);
protected native void exitFullScreenExclusive(int screen, WindowPeer w);
@Override
public boolean isDisplayChangeSupported() {
return (isFullScreenSupported() && getFullScreenWindow() != null);
}
@Override
public synchronized void setDisplayMode(DisplayMode dm) {
if (!isDisplayChangeSupported()) {
super.setDisplayMode(dm);
@ -501,22 +429,19 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
}
}
private native DisplayMode getCurrentDisplayMode(int screen);
private native void configDisplayMode(int screen, WindowPeer w, int width,
protected native DisplayMode getCurrentDisplayMode(int screen);
protected native void configDisplayMode(int screen, WindowPeer w, int width,
int height, int bitDepth,
int refreshRate);
private native void enumDisplayModes(int screen, ArrayList modes);
// This function is only available if DirectDraw is enabled, otherwise we
// have to do the work the hard way (enumerating all of the display modes
// and checking each one)
private native boolean isDisplayModeAvailable(int screen, int width, int height,
int bitDepth, int refreshRate);
protected native void enumDisplayModes(int screen, ArrayList modes);
@Override
public synchronized DisplayMode getDisplayMode() {
DisplayMode res = getCurrentDisplayMode(screen);
return res;
}
@Override
public synchronized DisplayMode[] getDisplayModes() {
ArrayList modes = new ArrayList();
enumDisplayModes(screen, modes);
@ -528,33 +453,22 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
return retArray;
}
private synchronized DisplayMode getMatchingDisplayMode(DisplayMode dm) {
protected synchronized DisplayMode getMatchingDisplayMode(DisplayMode dm) {
if (!isDisplayChangeSupported()) {
return null;
}
if (isDDEnabledOnDevice()) {
return
isDisplayModeAvailable(screen, dm.getWidth(), dm.getHeight(),
dm.getBitDepth(), dm.getRefreshRate())
? dm : null;
} else {
// The function isDisplayModeAvailable is only available if
// DirectDraw is enabled, otherwise we have to do the work the
// hard way (enumerating all of the display modes
// and checking each one)
DisplayMode[] modes = getDisplayModes();
for (DisplayMode mode : modes) {
if (dm.equals(mode) ||
(dm.getRefreshRate() == DisplayMode.REFRESH_RATE_UNKNOWN &&
dm.getWidth() == mode.getWidth() &&
dm.getHeight() == mode.getHeight() &&
dm.getBitDepth() == mode.getBitDepth()))
{
return mode;
}
DisplayMode[] modes = getDisplayModes();
for (DisplayMode mode : modes) {
if (dm.equals(mode) ||
(dm.getRefreshRate() == DisplayMode.REFRESH_RATE_UNKNOWN &&
dm.getWidth() == mode.getWidth() &&
dm.getHeight() == mode.getHeight() &&
dm.getBitDepth() == mode.getBitDepth()))
{
return mode;
}
return null;
}
return null;
}
/*
@ -563,7 +477,6 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
* changed.
*/
public void displayChanged() {
d3dContext = null;
dynamicColorModel = null;
defaultConfig = null;
configs = null;
@ -621,17 +534,93 @@ public class Win32GraphicsDevice extends GraphicsDevice implements
return colorModel;
}
private native int getDeviceMemoryNative(int screen);
/**
* WindowAdapter class responsible for de/iconifying full-screen window
* of this device.
*
* The listener restores the default display mode when window is iconified
* and sets it back to the one set by the user on de-iconification.
*/
private static class Win32FSWindowAdapter extends WindowAdapter {
private Win32GraphicsDevice device;
private DisplayMode dm;
Win32FSWindowAdapter(Win32GraphicsDevice device) {
this.device = device;
}
private void setFSWindowsState(Window other, int state) {
GraphicsDevice gds[] =
GraphicsEnvironment.getLocalGraphicsEnvironment().
getScreenDevices();
// check if the de/activation was caused by other
// fs window and ignore the event if that's the case
if (other != null) {
for (GraphicsDevice gd : gds) {
if (other == gd.getFullScreenWindow()) {
return;
}
}
}
// otherwise apply state to all fullscreen windows
for (GraphicsDevice gd : gds) {
Window fsw = gd.getFullScreenWindow();
if (fsw instanceof Frame) {
((Frame)fsw).setExtendedState(state);
}
}
}
@Override
public void windowDeactivated(WindowEvent e) {
setFSWindowsState(e.getOppositeWindow(), Frame.ICONIFIED);
}
@Override
public void windowActivated(WindowEvent e) {
setFSWindowsState(e.getOppositeWindow(), Frame.NORMAL);
}
@Override
public void windowIconified(WindowEvent e) {
// restore the default display mode for this device
DisplayMode ddm = device.defaultDisplayMode;
if (ddm != null) {
dm = device.getDisplayMode();
device.setDisplayMode(ddm);
}
}
@Override
public void windowDeiconified(WindowEvent e) {
// restore the user-set display mode for this device
if (dm != null) {
device.setDisplayMode(dm);
dm = null;
}
}
}
/**
* Returns number of bytes available in VRAM on this device.
* Adds a WindowListener to be used as
* activation/deactivation listener for the current full-screen window.
*
* @param w full-screen window
*/
public int getAvailableAcceleratedMemory() {
if (getDefaultConfiguration() instanceof WGLGraphicsConfig) {
// when OGL is enabled, there is no way to determine the amount
// of accelerated memory, so just return the default value
return super.getAvailableAcceleratedMemory();
}
return getDeviceMemoryNative(screen);
protected void addFSWindowListener(Window w) {
// Note: even though we create a listener for Window instances of
// fs windows they will not receive window events.
fsWindowListener = new Win32FSWindowAdapter(this);
w.addWindowListener(fsWindowListener);
}
/**
* Removes the fs window listener.
*
* @param w full-screen window
*/
protected void removeFSWindowListener(Window w) {
w.removeWindowListener(fsWindowListener);
fsWindowListener = null;
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 1997-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1997-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -25,9 +25,11 @@
package sun.awt;
import java.awt.GraphicsConfiguration;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.Toolkit;
import java.awt.peer.ComponentPeer;
import java.io.File;
import java.io.IOException;
import java.lang.ref.WeakReference;
@ -44,6 +46,7 @@ import sun.font.FontManager;
import sun.java2d.SunGraphicsEnvironment;
import sun.java2d.SurfaceManagerFactory;
import sun.java2d.WindowsSurfaceManagerFactory;
import sun.java2d.d3d.D3DGraphicsDevice;
import sun.java2d.windows.WindowsFlags;
/**
@ -333,7 +336,14 @@ public class Win32GraphicsEnvironment
protected static native void deRegisterFontWithPlatform(String fontName);
protected GraphicsDevice makeScreenDevice(int screennum) {
return new Win32GraphicsDevice(screennum);
GraphicsDevice device = null;
if (WindowsFlags.isD3DEnabled()) {
device = D3DGraphicsDevice.createDevice(screennum);
}
if (device == null) {
device = new Win32GraphicsDevice(screennum);
}
return device;
}
// Implements SunGraphicsEnvironment.createFontConfiguration.
@ -348,4 +358,39 @@ public class Win32GraphicsEnvironment
return new WFontConfiguration(this, preferLocaleFonts,preferPropFonts);
}
@Override
public boolean isFlipStrategyPreferred(ComponentPeer peer) {
GraphicsConfiguration gc;
if (peer != null && (gc = peer.getGraphicsConfiguration()) != null) {
GraphicsDevice gd = gc.getDevice();
if (gd instanceof D3DGraphicsDevice) {
return ((D3DGraphicsDevice)gd).isD3DEnabledOnDevice();
}
}
return false;
}
private static volatile boolean isDWMCompositionEnabled;
/**
* Returns true if dwm composition is currently enabled, false otherwise.
*
* @return true if dwm composition is enabled, false otherwise
*/
public static boolean isDWMCompositionEnabled() {
return isDWMCompositionEnabled;
}
/**
* Called from the native code when DWM composition state changed.
* May be called multiple times during the lifetime of the application.
* REMIND: we may want to create a listener mechanism for this.
*
* Note: called on the Toolkit thread, no user code or locks are allowed.
*
* @param enabled indicates the state of dwm composition
*/
private static void dwmCompositionChanged(boolean enabled) {
isDWMCompositionEnabled = enabled;
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 1996-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1996-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -40,8 +40,10 @@ import java.awt.event.InvocationEvent;
import java.awt.event.KeyEvent;
import sun.awt.Win32GraphicsConfig;
import sun.java2d.InvalidPipeException;
import sun.java2d.SunGraphics2D;
import sun.java2d.SurfaceData;
import sun.java2d.d3d.D3DScreenUpdateManager;
import static sun.java2d.d3d.D3DSurfaceData.*;
import sun.java2d.ScreenUpdateManager;
import sun.java2d.opengl.OGLSurfaceData;
import sun.awt.DisplayChangedListener;
import sun.awt.PaintEventDispatcher;
@ -51,7 +53,6 @@ import java.awt.dnd.DropTarget;
import java.awt.dnd.peer.DropTargetPeer;
import sun.awt.ComponentAccessor;
import java.util.logging.*;
import java.util.logging.*;
@ -87,6 +88,7 @@ public abstract class WComponentPeer extends WObjectPeer
int oldHeight = -1;
private int numBackBuffers = 0;
private VolatileImage backBuffer = null;
private BufferCapabilities backBufferCaps = null;
// foreground, background and color are cached to avoid calling back
// into the Component.
@ -191,10 +193,12 @@ public abstract class WComponentPeer extends WObjectPeer
cont.invalidate();
cont.validate();
if (surfaceData instanceof OGLSurfaceData) {
// 6290245: When OGL is enabled, it is necessary to
if (surfaceData instanceof D3DWindowSurfaceData ||
surfaceData instanceof OGLSurfaceData)
{
// When OGL or D3D is enabled, it is necessary to
// replace the SurfaceData for each dynamic layout
// request so that the OGL viewport stays in sync
// request so that the viewport stays in sync
// with the window bounds.
try {
replaceSurfaceData();
@ -377,7 +381,7 @@ public abstract class WComponentPeer extends WObjectPeer
* just call that version with our current numBackBuffers.
*/
public void replaceSurfaceData() {
replaceSurfaceData(this.numBackBuffers);
replaceSurfaceData(this.numBackBuffers, this.backBufferCaps);
}
/**
@ -386,35 +390,51 @@ public abstract class WComponentPeer extends WObjectPeer
* order, but also needs to perform additional functions inside the
* locks.
*/
public void replaceSurfaceData(int newNumBackBuffers) {
public void replaceSurfaceData(int newNumBackBuffers,
BufferCapabilities caps)
{
SurfaceData oldData = null;
VolatileImage oldBB = null;
synchronized(((Component)target).getTreeLock()) {
synchronized(this) {
if (pData == 0) {
return;
}
numBackBuffers = newNumBackBuffers;
SurfaceData oldData = surfaceData;
Win32GraphicsConfig gc =
(Win32GraphicsConfig)getGraphicsConfiguration();
surfaceData = gc.createSurfaceData(this, numBackBuffers);
(Win32GraphicsConfig)getGraphicsConfiguration();
ScreenUpdateManager mgr = ScreenUpdateManager.getInstance();
oldData = surfaceData;
mgr.dropScreenSurface(oldData);
surfaceData =
mgr.createScreenSurface(gc, this, numBackBuffers, true);
if (oldData != null) {
oldData.invalidate();
// null out the old data to make it collected faster
oldData = null;
}
if (backBuffer != null) {
// this will remove the back buffer from the
// display change notification list
backBuffer.flush();
oldBB = backBuffer;
if (numBackBuffers > 0) {
// set the caps first, they're used when creating the bb
backBufferCaps = caps;
backBuffer = gc.createBackBuffer(this);
} else if (backBuffer != null) {
backBufferCaps = null;
backBuffer = null;
}
if (numBackBuffers > 0) {
backBuffer = gc.createBackBuffer(this);
}
}
}
// it would be better to do this before we create new ones,
// but then we'd run into deadlock issues
if (oldData != null) {
oldData.flush();
// null out the old data to make it collected faster
oldData = null;
}
if (oldBB != null) {
oldBB.flush();
// null out the old data to make it collected faster
oldData = null;
}
}
public void replaceSurfaceDataLater() {
@ -518,7 +538,10 @@ public abstract class WComponentPeer extends WObjectPeer
if (font == null) {
font = defaultFont;
}
return new SunGraphics2D(surfaceData, fgColor, bgColor, font);
ScreenUpdateManager mgr =
ScreenUpdateManager.getInstance();
return mgr.createGraphics(surfaceData, this, fgColor,
bgColor, font);
}
return null;
}
@ -530,6 +553,7 @@ public abstract class WComponentPeer extends WObjectPeer
protected void disposeImpl() {
SurfaceData oldData = surfaceData;
surfaceData = null;
ScreenUpdateManager.getInstance().dropScreenSurface(oldData);
oldData.invalidate();
// remove from updater before calling targetDisposedPeer
WToolkit.targetDisposedPeer(target, this);
@ -546,6 +570,16 @@ public abstract class WComponentPeer extends WObjectPeer
_setBackground(c.getRGB());
}
/**
* This method is intentionally not synchronized as it is called while
* holding other locks.
*
* @see sun.java2d.d3d.D3DScreenUpdateManager#validate(D3DWindowSurfaceData)
*/
public Color getBackgroundNoSync() {
return background;
}
public native void _setForeground(int rgb);
public native void _setBackground(int rgb);
@ -617,8 +651,9 @@ public abstract class WComponentPeer extends WObjectPeer
checkCreation();
this.winGraphicsConfig =
(Win32GraphicsConfig)getGraphicsConfiguration();
this.surfaceData =
winGraphicsConfig.createSurfaceData(this, numBackBuffers);
ScreenUpdateManager mgr = ScreenUpdateManager.getInstance();
this.surfaceData = mgr.createScreenSurface(winGraphicsConfig, this,
numBackBuffers, false);
initialize();
start(); // Initialize enable/disable state, turn on callbacks
}
@ -793,6 +828,7 @@ public abstract class WComponentPeer extends WObjectPeer
* native windowing system specific actions.
*/
@Override
public void createBuffers(int numBuffers, BufferCapabilities caps)
throws AWTException
{
@ -802,39 +838,44 @@ public abstract class WComponentPeer extends WObjectPeer
// Re-create the primary surface with the new number of back buffers
try {
replaceSurfaceData(numBuffers - 1);
replaceSurfaceData(numBuffers - 1, caps);
} catch (InvalidPipeException e) {
throw new AWTException(e.getMessage());
}
}
public synchronized void destroyBuffers() {
disposeBackBuffer();
numBackBuffers = 0;
@Override
public void destroyBuffers() {
replaceSurfaceData(0, null);
}
private synchronized void disposeBackBuffer() {
if (backBuffer == null) {
return;
}
backBuffer = null;
}
public synchronized void flip(BufferCapabilities.FlipContents flipAction) {
@Override
public void flip(int x1, int y1, int x2, int y2,
BufferCapabilities.FlipContents flipAction)
{
VolatileImage backBuffer = this.backBuffer;
if (backBuffer == null) {
throw new IllegalStateException("Buffers have not been created");
}
Win32GraphicsConfig gc =
(Win32GraphicsConfig)getGraphicsConfiguration();
gc.flip(this, (Component)target, backBuffer, flipAction);
gc.flip(this, (Component)target, backBuffer, x1, y1, x2, y2, flipAction);
}
@Override
public synchronized Image getBackBuffer() {
Image backBuffer = this.backBuffer;
if (backBuffer == null) {
throw new IllegalStateException("Buffers have not been created");
}
return backBuffer;
}
public BufferCapabilities getBackBufferCaps() {
return backBufferCaps;
}
public int getBackBuffersNum() {
return numBackBuffers;
}
/* override and return false on components that DO NOT require
a clearRect() before painting (i.e. native components) */
@ -866,6 +907,51 @@ public abstract class WComponentPeer extends WObjectPeer
sun.java2d.pipe.Region region);
// REMIND: Temp workaround for issues with using HW acceleration
// in the browser on Vista when DWM is enabled.
// @return true if the toplevel container is not an EmbeddedFrame or
// if this EmbeddedFrame is acceleration capable, false otherwise
private static final boolean isContainingTopLevelAccelCapable(Component c) {
while (c != null && !(c instanceof WEmbeddedFrame)) {
c = c.getParent();
}
if (c == null) {
return true;
}
return ((WEmbeddedFramePeer)c.getPeer()).isAccelCapable();
}
/**
* Returns whether this component is capable of being hw accelerated.
* More specifically, whether rendering to this component or a
* BufferStrategy's back-buffer for this component can be hw accelerated.
*
* Conditions which could prevent hw acceleration include the toplevel
* window containing this component being
* {@link com.sun.awt.AWTUtilities.Translucency#TRANSLUCENT TRANSLUCENT}.
*
* @return {@code true} if this component is capable of being hw
* accelerated, {@code false} otherwise
* @see com.sun.awt.AWTUtilities.Translucency#TRANSLUCENT
*/
public boolean isAccelCapable() {
// REMIND: Temp workaround for issues with using HW acceleration
// in the browser on Vista when DWM is enabled
if (!isContainingTopLevelAccelCapable((Component)target)) {
return false;
}
// REMIND: translucent windows support-related
/*
boolean isTranslucent =
SunToolkit.isContainingTopLevelTranslucent((Component)target);
// D3D/OGL and translucent windows interacted poorly in Windows XP;
// these problems are no longer present in Vista
return !isTranslucent || Win32GraphicsEnvironment.isVistaOS();
*/
return true;
}
/**
* Applies the shape to the native component window.
* @since 1.7

View File

@ -1,5 +1,5 @@
/*
* Copyright 1996-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1996-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -30,6 +30,7 @@ import java.awt.Graphics;
import java.awt.Rectangle;
import sun.awt.EmbeddedFrame;
import sun.awt.Win32GraphicsEnvironment;
public class WEmbeddedFramePeer extends WFramePeer {
@ -71,4 +72,13 @@ public class WEmbeddedFramePeer extends WFramePeer {
// We don't constrain the bounds of the EmbeddedFrames
return new Rectangle(x, y, width, height);
}
@Override
public boolean isAccelCapable() {
// REMIND: Temp workaround for issues with using HW acceleration
// in the browser on Vista when DWM is enabled
// Note: isDWMCompositionEnabled is only relevant on Vista, returns
// false on other systems.
return !Win32GraphicsEnvironment.isDWMCompositionEnabled();
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 1996-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1996-2008 Sun Microsystems Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -40,6 +40,7 @@ import sun.awt.AWTAutoShutdown;
import sun.awt.SunToolkit;
import sun.awt.Win32GraphicsDevice;
import sun.awt.Win32GraphicsEnvironment;
import sun.java2d.d3d.D3DRenderQueue;
import sun.java2d.opengl.OGLRenderQueue;
import sun.print.PrintJob2D;
@ -591,6 +592,8 @@ public class WToolkit extends SunToolkit implements Runnable {
nativeSync();
// now flush the OGL pipeline (this is a no-op if OGL is not enabled)
OGLRenderQueue.sync();
// now flush the D3D pipeline (this is a no-op if D3D is not enabled)
D3DRenderQueue.sync();
}
public PrintJob getPrintJob(Frame frame, String doctitle,
@ -910,8 +913,31 @@ public class WToolkit extends SunToolkit implements Runnable {
return toolkit;
}
/**
* There are two reasons why we don't use buffer per window when
* Vista's DWM (aka Aero) is enabled:
* - since with DWM all windows are already double-buffered, the application
* doesn't get expose events so we don't get to use our true back-buffer,
* wasting memory and performance (this is valid for both d3d and gdi
* pipelines)
* - in some cases with buffer per window enabled it is possible for the
* paint manager to redirect rendering to the screen for some operations
* (like copyArea), and since bpw uses its own BufferStrategy the
* d3d onscreen rendering support is disabled and rendering goes through
* GDI. This doesn't work well with Vista's DWM since one
* can not perform GDI and D3D operations on the same surface
* (see 6630702 for more info)
*
* Note: even though DWM composition state can change during the lifetime
* of the application it is a rare event, and it is more often that it
* is temporarily disabled (because of some app) than it is getting
* permanently enabled so we can live with this approach without the
* complexity of dwm state listeners and such. This can be revisited if
* proved otherwise.
*/
@Override
public boolean useBufferPerWindow() {
return true;
return !Win32GraphicsEnvironment.isDWMCompositionEnabled();
}
public void grab(Window w) {

View File

@ -0,0 +1,131 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics2D;
import sun.awt.Win32GraphicsConfig;
import sun.awt.windows.WComponentPeer;
import sun.java2d.d3d.D3DScreenUpdateManager;
import sun.java2d.windows.WindowsFlags;
/**
* This class handles the creation of on-screen surfaces and
* corresponding graphics objects.
*
* By default it delegates the surface creation to the
* particular GraphicsConfiguration classes.
*/
public class ScreenUpdateManager {
private static ScreenUpdateManager theInstance;
protected ScreenUpdateManager() {
}
/**
* Creates a SunGraphics2D object for the surface,
* given the parameters.
*
* @param sd surface data for which a graphics is to be created
* @param peer peer which owns the surface
* @param fgColor fg color to be used in the graphics
* @param bgColor bg color to be used in the graphics
* @param font font to be used in the graphics
* @return a SunGraphics2D object for rendering to the passed surface
*/
public synchronized Graphics2D createGraphics(SurfaceData sd,
WComponentPeer peer, Color fgColor, Color bgColor, Font font)
{
return new SunGraphics2D(sd, fgColor, bgColor, font);
}
/**
* Creates and returns the surface for the peer. This surface becomes
* managed by this manager. To remove the surface from the managed list
* {@code}dropScreenSurface(SurfaceData){@code} will need to be called.
*
* The default implementation delegates surface creation
* to the passed in GraphicsConfiguration object.
*
* @param gc graphics configuration for which the surface is to be created
* @param peer peer for which the onscreen surface is to be created
* @param bbNum number of back-buffers requested for this peer
* @param isResize whether this surface is being created in response to
* a component resize event
* @return a SurfaceData to be used for on-screen rendering for this peer.
* @see #dropScreenSurface(SurfaceData)
*/
public SurfaceData createScreenSurface(Win32GraphicsConfig gc,
WComponentPeer peer, int bbNum,
boolean isResize)
{
return gc.createSurfaceData(peer, bbNum);
}
/**
* Drops the passed surface from the list of managed surfaces.
*
* Nothing happens if the surface wasn't managed by this manager.
*
* @param sd SurfaceData to be removed from the list of managed surfaces
*/
public void dropScreenSurface(SurfaceData sd) {}
/**
* Returns a replacement SurfaceData for the invalid passed one.
*
* This method should be used by SurfaceData's created by
* the ScreenUpdateManager for providing replacement surfaces.
*
* @param peer to which the old surface belongs
* @param oldsd the old (invalid) surface to get replaced
* @return a replacement surface
* @see sun.java2d.d3d.D3DSurfaceData.D3DWindowSurfaceData#getReplacement()
* @see sun.java2d.windows.GDIWindowSurfaceData#getReplacement()
*/
public SurfaceData getReplacementScreenSurface(WComponentPeer peer,
SurfaceData oldsd)
{
return peer.getSurfaceData();
}
/**
* Returns an (singleton) instance of the screen surfaces
* manager class.
* @return instance of onscreen surfaces manager
*/
public static synchronized ScreenUpdateManager getInstance() {
if (theInstance == null) {
if (WindowsFlags.isD3DEnabled()) {
theInstance = new D3DScreenUpdateManager();
} else {
theInstance = new ScreenUpdateManager();
}
}
return theInstance;
}
}

View File

@ -26,14 +26,13 @@
package sun.java2d;
import java.awt.GraphicsConfiguration;
import java.awt.image.BufferedImage;
import sun.awt.image.BufImgVolatileSurfaceManager;
import sun.awt.image.SunVolatileImage;
import sun.awt.image.SurfaceManager;
import sun.awt.image.VolatileSurfaceManager;
import sun.java2d.d3d.D3DGraphicsConfig;
import sun.java2d.d3d.D3DVolatileSurfaceManager;
import sun.java2d.opengl.WGLGraphicsConfig;
import sun.java2d.opengl.WGLVolatileSurfaceManager;
import sun.java2d.windows.WindowsFlags;
import sun.java2d.windows.WinVolatileSurfaceManager;
/**
* The SurfaceManagerFactory that creates VolatileSurfaceManager
@ -54,10 +53,12 @@ public class WindowsSurfaceManagerFactory extends SurfaceManagerFactory {
Object context)
{
GraphicsConfiguration gc = vImg.getGraphicsConfig();
if (gc instanceof WGLGraphicsConfig) {
if (gc instanceof D3DGraphicsConfig) {
return new D3DVolatileSurfaceManager(vImg, context);
} else if (gc instanceof WGLGraphicsConfig) {
return new WGLVolatileSurfaceManager(vImg, context);
} else {
return new WinVolatileSurfaceManager(vImg, context);
return new BufImgVolatileSurfaceManager(vImg, context);
}
}

View File

@ -1,87 +0,0 @@
/*
* Copyright 2005 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.d3d;
import java.awt.GraphicsConfiguration;
import java.awt.Image;
import java.awt.Transparency;
import java.awt.image.ColorModel;
import sun.awt.Win32GraphicsDevice;
import sun.java2d.loops.SurfaceType;
import sun.java2d.windows.Win32SurfaceData;
public class D3DBackBufferSurfaceData extends D3DSurfaceData {
private Win32SurfaceData parentData;
/**
* Private constructor. Use createData() to create an object.
*/
private D3DBackBufferSurfaceData(int width, int height,
SurfaceType sType, ColorModel cm,
GraphicsConfiguration gc,
Image image, int screen,
Win32SurfaceData parentData)
{
super(width, height, D3DSurfaceData.D3D_ATTACHED_SURFACE,
sType, cm, gc, image, Transparency.OPAQUE);
this.parentData = parentData;
initSurface(width, height, screen, parentData);
}
private native void restoreDepthBuffer();
@Override
public void restoreSurface() {
parentData.restoreSurface();
// The above call restores the primary surface
// to which this backbuffer is attached. But
// we need to explicitly restore the depth buffer
// associated with this backbuffer surface, because it's not
// part of a 'complex' primary surface, and thus will not be
// restored as part of the primary surface restoration.
restoreDepthBuffer();
}
public static D3DBackBufferSurfaceData
createData(int width, int height,
ColorModel cm, GraphicsConfiguration gc,
Image image,
Win32SurfaceData parentData)
{
Win32GraphicsDevice gd = (Win32GraphicsDevice)gc.getDevice();
if (!gd.isD3DEnabledOnDevice()) {
return null;
}
SurfaceType sType = getSurfaceType(cm, Transparency.OPAQUE);
return new
D3DBackBufferSurfaceData(width, height,
getSurfaceType(gc, cm,
D3DSurfaceData.D3D_ATTACHED_SURFACE),
cm, gc, image,
gd.getScreen(), parentData);
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2002-2005 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -29,130 +29,777 @@ import java.awt.Composite;
import java.awt.Transparency;
import java.awt.geom.AffineTransform;
import java.awt.image.AffineTransformOp;
import java.awt.image.BufferedImage;
import java.awt.image.BufferedImageOp;
import java.lang.ref.WeakReference;
import sun.java2d.ScreenUpdateManager;
import sun.java2d.SurfaceData;
import sun.java2d.loops.Blit;
import sun.java2d.loops.CompositeType;
import sun.java2d.loops.GraphicsPrimitive;
import sun.java2d.loops.GraphicsPrimitiveMgr;
import sun.java2d.loops.CompositeType;
import sun.java2d.loops.SurfaceType;
import sun.java2d.loops.Blit;
import sun.java2d.loops.ScaledBlit;
import sun.java2d.loops.SurfaceType;
import sun.java2d.loops.TransformBlit;
import sun.java2d.pipe.Region;
import sun.java2d.SurfaceData;
import sun.java2d.pipe.RenderBuffer;
import sun.java2d.pipe.RenderQueue;
import static sun.java2d.pipe.BufferedOpCodes.*;
import sun.java2d.windows.GDIWindowSurfaceData;
import static sun.java2d.d3d.D3DSurfaceData.*;
class D3DBlitLoops {
/**
* This class contains accelerated blits/scales/transforms
* between textures and DD surfaces.
*/
public class D3DBlitLoops {
static void register() {
Blit blitIntArgbPreToSurface =
new D3DSwToSurfaceBlit(SurfaceType.IntArgbPre,
D3DSurfaceData.ST_INT_ARGB_PRE);
Blit blitIntArgbPreToTexture =
new D3DSwToTextureBlit(SurfaceType.IntArgbPre,
D3DSurfaceData.ST_INT_ARGB_PRE);
static void register()
{
GraphicsPrimitive[] primitives = {
new D3DTextureToSurfaceBlit(IntRgbD3D),
new D3DTextureToSurfaceBlit(Ushort565RgbD3D),
new D3DTextureToSurfaceBlit(IntRgbxD3D),
new D3DTextureToSurfaceBlit(Ushort555RgbD3D),
new D3DTextureToSurfaceBlit(ThreeByteBgrD3D),
// prevent D3DSurface -> Screen blits
new D3DSurfaceToGDIWindowSurfaceBlit(),
new D3DSurfaceToGDIWindowSurfaceScale(),
new D3DSurfaceToGDIWindowSurfaceTransform(),
new D3DTextureToSurfaceScale(IntRgbD3D),
new D3DTextureToSurfaceScale(Ushort565RgbD3D),
new D3DTextureToSurfaceScale(IntRgbxD3D),
new D3DTextureToSurfaceScale(Ushort555RgbD3D),
new D3DTextureToSurfaceScale(ThreeByteBgrD3D),
// surface->surface ops
new D3DSurfaceToSurfaceBlit(),
new D3DSurfaceToSurfaceScale(),
new D3DSurfaceToSurfaceTransform(),
new D3DTextureToSurfaceTransform(D3DTexture, IntRgbD3D),
new D3DTextureToSurfaceTransform(D3DTexture, Ushort565RgbD3D),
new D3DTextureToSurfaceTransform(D3DTexture, IntRgbxD3D),
new D3DTextureToSurfaceTransform(D3DTexture, Ushort555RgbD3D),
new D3DTextureToSurfaceTransform(D3DTexture, ThreeByteBgrD3D),
// render-to-texture surface->surface ops
new D3DRTTSurfaceToSurfaceBlit(),
new D3DRTTSurfaceToSurfaceScale(),
new D3DRTTSurfaceToSurfaceTransform(),
new DelegateSwToTextureLoop(),
// surface->sw ops
new D3DSurfaceToSwBlit(SurfaceType.IntArgb,
D3DSurfaceData.ST_INT_ARGB),
// sw->surface ops
blitIntArgbPreToSurface,
new D3DSwToSurfaceBlit(SurfaceType.IntArgb,
D3DSurfaceData.ST_INT_ARGB),
new D3DSwToSurfaceBlit(SurfaceType.IntRgb,
D3DSurfaceData.ST_INT_RGB),
new D3DSwToSurfaceBlit(SurfaceType.IntBgr,
D3DSurfaceData.ST_INT_BGR),
new D3DSwToSurfaceBlit(SurfaceType.Ushort565Rgb,
D3DSurfaceData.ST_USHORT_565_RGB),
new D3DSwToSurfaceBlit(SurfaceType.Ushort555Rgb,
D3DSurfaceData.ST_USHORT_555_RGB),
new D3DSwToSurfaceBlit(SurfaceType.ByteIndexed,
D3DSurfaceData.ST_BYTE_INDEXED),
// REMIND: we don't have a native sw loop to back this loop up
// new D3DSwToSurfaceBlit(SurfaceType.ByteIndexedBm,
// D3DSurfaceData.ST_BYTE_INDEXED_BM),
new D3DGeneralBlit(D3DSurfaceData.D3DSurface,
CompositeType.AnyAlpha,
blitIntArgbPreToSurface),
new D3DSwToSurfaceScale(SurfaceType.IntArgb,
D3DSurfaceData.ST_INT_ARGB),
new D3DSwToSurfaceScale(SurfaceType.IntArgbPre,
D3DSurfaceData.ST_INT_ARGB_PRE),
new D3DSwToSurfaceScale(SurfaceType.IntRgb,
D3DSurfaceData.ST_INT_RGB),
new D3DSwToSurfaceScale(SurfaceType.IntBgr,
D3DSurfaceData.ST_INT_BGR),
new D3DSwToSurfaceScale(SurfaceType.Ushort565Rgb,
D3DSurfaceData.ST_USHORT_565_RGB),
new D3DSwToSurfaceScale(SurfaceType.Ushort555Rgb,
D3DSurfaceData.ST_USHORT_555_RGB),
new D3DSwToSurfaceScale(SurfaceType.ByteIndexed,
D3DSurfaceData.ST_BYTE_INDEXED),
// REMIND: we don't have a native sw loop to back this loop up
// new D3DSwToSurfaceScale(SurfaceType.ByteIndexedBm,
// D3DSurfaceData.ST_BYTE_INDEXED_BM),
new D3DSwToSurfaceTransform(SurfaceType.IntArgb,
D3DSurfaceData.ST_INT_ARGB),
new D3DSwToSurfaceTransform(SurfaceType.IntArgbPre,
D3DSurfaceData.ST_INT_ARGB_PRE),
new D3DSwToSurfaceTransform(SurfaceType.IntRgb,
D3DSurfaceData.ST_INT_RGB),
new D3DSwToSurfaceTransform(SurfaceType.IntBgr,
D3DSurfaceData.ST_INT_BGR),
new D3DSwToSurfaceTransform(SurfaceType.Ushort565Rgb,
D3DSurfaceData.ST_USHORT_565_RGB),
new D3DSwToSurfaceTransform(SurfaceType.Ushort555Rgb,
D3DSurfaceData.ST_USHORT_555_RGB),
new D3DSwToSurfaceTransform(SurfaceType.ByteIndexed,
D3DSurfaceData.ST_BYTE_INDEXED),
// REMIND: we don't have a native sw loop to back this loop up
// new D3DSwToSurfaceTransform(SurfaceType.ByteIndexedBm,
// D3DSurfaceData.ST_BYTE_INDEXED_BM),
// texture->surface ops
new D3DTextureToSurfaceBlit(),
new D3DTextureToSurfaceScale(),
new D3DTextureToSurfaceTransform(),
// sw->texture ops
blitIntArgbPreToTexture,
new D3DSwToTextureBlit(SurfaceType.IntRgb,
D3DSurfaceData.ST_INT_RGB),
new D3DSwToTextureBlit(SurfaceType.IntArgb,
D3DSurfaceData.ST_INT_ARGB),
new D3DSwToTextureBlit(SurfaceType.IntBgr,
D3DSurfaceData.ST_INT_BGR),
new D3DSwToTextureBlit(SurfaceType.Ushort565Rgb,
D3DSurfaceData.ST_USHORT_565_RGB),
new D3DSwToTextureBlit(SurfaceType.Ushort555Rgb,
D3DSurfaceData.ST_USHORT_555_RGB),
new D3DSwToTextureBlit(SurfaceType.ByteIndexed,
D3DSurfaceData.ST_BYTE_INDEXED),
// REMIND: we don't have a native sw loop to back this loop up
// new D3DSwToTextureBlit(SurfaceType.ByteIndexedBm,
// D3DSurfaceData.ST_BYTE_INDEXED_BM),
new D3DGeneralBlit(D3DSurfaceData.D3DTexture,
CompositeType.SrcNoEa,
blitIntArgbPreToTexture),
};
GraphicsPrimitiveMgr.register(primitives);
}
static native void doTransform(long pSrc, long pDst, long pCtx,
int hint,
int sx1, int sy1, int sx2, int sy2,
float dx1, float dy1,
float dx2, float dy2);
static long getContext(SurfaceData src, SurfaceData dst,
Region clip, Composite comp, AffineTransform at)
/**
* The following offsets are used to pack the parameters in
* createPackedParams(). (They are also used at the native level when
* unpacking the params.)
*/
private static final int OFFSET_SRCTYPE = 16;
private static final int OFFSET_HINT = 8;
private static final int OFFSET_TEXTURE = 3;
private static final int OFFSET_RTT = 2;
private static final int OFFSET_XFORM = 1;
private static final int OFFSET_ISOBLIT = 0;
/**
* Packs the given parameters into a single int value in order to save
* space on the rendering queue.
*/
private static int createPackedParams(boolean isoblit, boolean texture,
boolean rtt, boolean xform,
int hint, int srctype)
{
int ctxFlags;
if (src.getTransparency() == Transparency.OPAQUE) {
ctxFlags = D3DContext.SRC_IS_OPAQUE;
} else {
ctxFlags = D3DContext.NO_CONTEXT_FLAGS;
}
return D3DContext.getContext(src, dst, clip, comp, at,
0xffffffff /* rgb */, ctxFlags);
}
}
class D3DTextureToSurfaceBlit extends Blit {
D3DTextureToSurfaceBlit(SurfaceType dstType) {
super(D3DTexture, CompositeType.AnyAlpha , dstType);
return
((srctype << OFFSET_SRCTYPE) |
(hint << OFFSET_HINT ) |
((texture ? 1 : 0) << OFFSET_TEXTURE) |
((rtt ? 1 : 0) << OFFSET_RTT ) |
((xform ? 1 : 0) << OFFSET_XFORM ) |
((isoblit ? 1 : 0) << OFFSET_ISOBLIT));
}
/**
* Blit
* This native method is where all of the work happens in the
* accelerated Blit.
* Enqueues a BLIT operation with the given parameters. Note that the
* RenderQueue lock must be held before calling this method.
*/
@Override
private static void enqueueBlit(RenderQueue rq,
SurfaceData src, SurfaceData dst,
int packedParams,
int sx1, int sy1,
int sx2, int sy2,
double dx1, double dy1,
double dx2, double dy2)
{
// assert rq.lock.isHeldByCurrentThread();
RenderBuffer buf = rq.getBuffer();
rq.ensureCapacityAndAlignment(72, 24);
buf.putInt(BLIT);
buf.putInt(packedParams);
buf.putInt(sx1).putInt(sy1);
buf.putInt(sx2).putInt(sy2);
buf.putDouble(dx1).putDouble(dy1);
buf.putDouble(dx2).putDouble(dy2);
buf.putLong(src.getNativeOps());
buf.putLong(dst.getNativeOps());
}
static void Blit(SurfaceData srcData, SurfaceData dstData,
Composite comp, Region clip,
AffineTransform xform, int hint,
int sx1, int sy1,
int sx2, int sy2,
double dx1, double dy1,
double dx2, double dy2,
int srctype, boolean texture)
{
int ctxflags = 0;
if (srcData.getTransparency() == Transparency.OPAQUE) {
ctxflags |= D3DContext.SRC_IS_OPAQUE;
}
D3DSurfaceData d3dDst = (D3DSurfaceData)dstData;
D3DRenderQueue rq = D3DRenderQueue.getInstance();
rq.lock();
try {
// make sure the RenderQueue keeps a hard reference to the
// source (sysmem) SurfaceData to prevent it from being
// disposed while the operation is processed on the QFT
rq.addReference(srcData);
if (texture) {
// make sure we have a current context before uploading
// the sysmem data to the texture object
D3DContext.setScratchSurface(d3dDst.getContext());
} else {
D3DContext.validateContext(d3dDst, d3dDst,
clip, comp, xform, null, null,
ctxflags);
}
int packedParams = createPackedParams(false, texture,
false, xform != null,
hint, srctype);
enqueueBlit(rq, srcData, dstData,
packedParams,
sx1, sy1, sx2, sy2,
dx1, dy1, dx2, dy2);
// always flush immediately, since we (currently) have no means
// of tracking changes to the system memory surface
rq.flushNow();
} finally {
rq.unlock();
}
if (d3dDst.getType() == D3DSurfaceData.WINDOW) {
// flush immediately when copying to the screen to improve
// responsiveness of applications using VI or BI backbuffers
D3DScreenUpdateManager mgr =
(D3DScreenUpdateManager)ScreenUpdateManager.getInstance();
mgr.runUpdateNow();
}
}
/**
* Note: The srcImg and biop parameters are only used when invoked
* from the D3DBufImgOps.renderImageWithOp() method; in all other cases,
* this method can be called with null values for those two parameters,
* and they will be effectively ignored.
*/
static void IsoBlit(SurfaceData srcData, SurfaceData dstData,
BufferedImage srcImg, BufferedImageOp biop,
Composite comp, Region clip,
AffineTransform xform, int hint,
int sx1, int sy1,
int sx2, int sy2,
double dx1, double dy1,
double dx2, double dy2,
boolean texture)
{
int ctxflags = 0;
if (srcData.getTransparency() == Transparency.OPAQUE) {
ctxflags |= D3DContext.SRC_IS_OPAQUE;
}
D3DSurfaceData d3dDst = (D3DSurfaceData)dstData;
D3DRenderQueue rq = D3DRenderQueue.getInstance();
boolean rtt = false;
rq.lock();
try {
D3DSurfaceData d3dSrc = (D3DSurfaceData)srcData;
int srctype = d3dSrc.getType();
D3DSurfaceData srcCtxData = d3dSrc;
if (srctype == D3DSurfaceData.TEXTURE) {
rtt = false;
} else {
// the source is a backbuffer, or render-to-texture
// surface; we set rtt to true to differentiate this kind
// of surface from a regular texture object
rtt = true;
}
D3DContext.validateContext(srcCtxData, d3dDst,
clip, comp, xform, null, null,
ctxflags);
if (biop != null) {
D3DBufImgOps.enableBufImgOp(rq, d3dSrc, srcImg, biop);
}
int packedParams = createPackedParams(true, texture,
rtt, xform != null,
hint, 0 /*unused*/);
enqueueBlit(rq, srcData, dstData,
packedParams,
sx1, sy1, sx2, sy2,
dx1, dy1, dx2, dy2);
if (biop != null) {
D3DBufImgOps.disableBufImgOp(rq, biop);
}
} finally {
rq.unlock();
}
if (rtt && (d3dDst.getType() == D3DSurfaceData.WINDOW)) {
// we only have to flush immediately when copying from a
// (non-texture) surface to the screen; otherwise Swing apps
// might appear unresponsive until the auto-flush completes
D3DScreenUpdateManager mgr =
(D3DScreenUpdateManager)ScreenUpdateManager.getInstance();
mgr.runUpdateNow();
}
}
}
class D3DSurfaceToSurfaceBlit extends Blit {
D3DSurfaceToSurfaceBlit() {
super(D3DSurfaceData.D3DSurface,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
}
public void Blit(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx, int sy, int dx, int dy, int w, int h)
{
synchronized (D3DContext.LOCK) {
long pCtx = D3DBlitLoops.getContext(src, dst, clip, comp, null);
D3DBlitLoops.doTransform(src.getNativeOps(), dst.getNativeOps(),
pCtx,
AffineTransformOp.TYPE_NEAREST_NEIGHBOR,
sx, sy, sx+w, sy+h,
(float)dx, (float)dy,
(float)(dx+w), (float)(dy+h));
}
D3DBlitLoops.IsoBlit(src, dst,
null, null,
comp, clip, null,
AffineTransformOp.TYPE_NEAREST_NEIGHBOR,
sx, sy, sx+w, sy+h,
dx, dy, dx+w, dy+h,
false);
}
}
class D3DTextureToSurfaceTransform extends TransformBlit {
class D3DSurfaceToSurfaceScale extends ScaledBlit {
D3DTextureToSurfaceTransform(SurfaceType srcType,
SurfaceType dstType)
{
super(srcType, CompositeType.AnyAlpha, dstType);
D3DSurfaceToSurfaceScale() {
super(D3DSurfaceData.D3DSurface,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
}
public void Scale(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx1, int sy1,
int sx2, int sy2,
double dx1, double dy1,
double dx2, double dy2)
{
D3DBlitLoops.IsoBlit(src, dst,
null, null,
comp, clip, null,
AffineTransformOp.TYPE_NEAREST_NEIGHBOR,
sx1, sy1, sx2, sy2,
dx1, dy1, dx2, dy2,
false);
}
}
class D3DSurfaceToSurfaceTransform extends TransformBlit {
D3DSurfaceToSurfaceTransform() {
super(D3DSurfaceData.D3DSurface,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
}
@Override
public void Transform(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
AffineTransform at, int hint,
int sx, int sy, int dx, int dy,
int w, int h)
{
synchronized (D3DContext.LOCK) {
long pCtx = D3DBlitLoops.getContext(src, dst, clip, comp, at);
D3DBlitLoops.doTransform(src.getNativeOps(), dst.getNativeOps(),
pCtx, hint,
sx, sy, sx+w, sy+h,
(float)dx, (float)dy,
(float)(dx+w), (float)(dy+h));
D3DBlitLoops.IsoBlit(src, dst,
null, null,
comp, clip, at, hint,
sx, sy, sx+w, sy+h,
dx, dy, dx+w, dy+h,
false);
}
}
class D3DRTTSurfaceToSurfaceBlit extends Blit {
D3DRTTSurfaceToSurfaceBlit() {
super(D3DSurfaceData.D3DSurfaceRTT,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
}
public void Blit(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx, int sy, int dx, int dy, int w, int h)
{
D3DBlitLoops.IsoBlit(src, dst,
null, null,
comp, clip, null,
AffineTransformOp.TYPE_NEAREST_NEIGHBOR,
sx, sy, sx+w, sy+h,
dx, dy, dx+w, dy+h,
true);
}
}
class D3DRTTSurfaceToSurfaceScale extends ScaledBlit {
D3DRTTSurfaceToSurfaceScale() {
super(D3DSurfaceData.D3DSurfaceRTT,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
}
public void Scale(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx1, int sy1,
int sx2, int sy2,
double dx1, double dy1,
double dx2, double dy2)
{
D3DBlitLoops.IsoBlit(src, dst,
null, null,
comp, clip, null,
AffineTransformOp.TYPE_NEAREST_NEIGHBOR,
sx1, sy1, sx2, sy2,
dx1, dy1, dx2, dy2,
true);
}
}
class D3DRTTSurfaceToSurfaceTransform extends TransformBlit {
D3DRTTSurfaceToSurfaceTransform() {
super(D3DSurfaceData.D3DSurfaceRTT,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
}
public void Transform(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
AffineTransform at, int hint,
int sx, int sy, int dx, int dy, int w, int h)
{
D3DBlitLoops.IsoBlit(src, dst,
null, null,
comp, clip, at, hint,
sx, sy, sx+w, sy+h,
dx, dy, dx+w, dy+h,
true);
}
}
class D3DSurfaceToSwBlit extends Blit {
private int typeval;
// REMIND: destination will actually be opaque/premultiplied...
D3DSurfaceToSwBlit(SurfaceType dstType, int typeval) {
super(D3DSurfaceData.D3DSurface,
CompositeType.SrcNoEa,
dstType);
this.typeval = typeval;
}
public void Blit(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx, int sy, int dx, int dy,
int w, int h)
{
D3DRenderQueue rq = D3DRenderQueue.getInstance();
rq.lock();
try {
// make sure the RenderQueue keeps a hard reference to the
// destination (sysmem) SurfaceData to prevent it from being
// disposed while the operation is processed on the QFT
rq.addReference(dst);
RenderBuffer buf = rq.getBuffer();
D3DContext.setScratchSurface(((D3DSurfaceData)src).getContext());
rq.ensureCapacityAndAlignment(48, 32);
buf.putInt(SURFACE_TO_SW_BLIT);
buf.putInt(sx).putInt(sy);
buf.putInt(dx).putInt(dy);
buf.putInt(w).putInt(h);
buf.putInt(typeval);
buf.putLong(src.getNativeOps());
buf.putLong(dst.getNativeOps());
// always flush immediately
rq.flushNow();
} finally {
rq.unlock();
}
}
}
class D3DSwToSurfaceBlit extends Blit {
private int typeval;
D3DSwToSurfaceBlit(SurfaceType srcType, int typeval) {
super(srcType,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
this.typeval = typeval;
}
public void Blit(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx, int sy, int dx, int dy, int w, int h)
{
D3DBlitLoops.Blit(src, dst,
comp, clip, null,
AffineTransformOp.TYPE_NEAREST_NEIGHBOR,
sx, sy, sx+w, sy+h,
dx, dy, dx+w, dy+h,
typeval, false);
}
}
class D3DSwToSurfaceScale extends ScaledBlit {
private int typeval;
D3DSwToSurfaceScale(SurfaceType srcType, int typeval) {
super(srcType,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
this.typeval = typeval;
}
public void Scale(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx1, int sy1,
int sx2, int sy2,
double dx1, double dy1,
double dx2, double dy2)
{
D3DBlitLoops.Blit(src, dst,
comp, clip, null,
AffineTransformOp.TYPE_NEAREST_NEIGHBOR,
sx1, sy1, sx2, sy2,
dx1, dy1, dx2, dy2,
typeval, false);
}
}
class D3DSwToSurfaceTransform extends TransformBlit {
private int typeval;
D3DSwToSurfaceTransform(SurfaceType srcType, int typeval) {
super(srcType,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
this.typeval = typeval;
}
public void Transform(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
AffineTransform at, int hint,
int sx, int sy, int dx, int dy, int w, int h)
{
D3DBlitLoops.Blit(src, dst,
comp, clip, at, hint,
sx, sy, sx+w, sy+h,
dx, dy, dx+w, dy+h,
typeval, false);
}
}
class D3DSwToTextureBlit extends Blit {
private int typeval;
D3DSwToTextureBlit(SurfaceType srcType, int typeval) {
super(srcType,
CompositeType.SrcNoEa,
D3DSurfaceData.D3DTexture);
this.typeval = typeval;
}
public void Blit(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx, int sy, int dx, int dy, int w, int h)
{
D3DBlitLoops.Blit(src, dst,
comp, clip, null,
AffineTransformOp.TYPE_NEAREST_NEIGHBOR,
sx, sy, sx+w, sy+h,
dx, dy, dx+w, dy+h,
typeval, true);
}
}
class D3DTextureToSurfaceBlit extends Blit {
D3DTextureToSurfaceBlit() {
super(D3DSurfaceData.D3DTexture,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
}
public void Blit(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx, int sy, int dx, int dy, int w, int h)
{
D3DBlitLoops.IsoBlit(src, dst,
null, null,
comp, clip, null,
AffineTransformOp.TYPE_NEAREST_NEIGHBOR,
sx, sy, sx+w, sy+h,
dx, dy, dx+w, dy+h,
true);
}
}
class D3DTextureToSurfaceScale extends ScaledBlit {
D3DTextureToSurfaceScale(SurfaceType dstType) {
super(D3DTexture, CompositeType.AnyAlpha, dstType);
D3DTextureToSurfaceScale() {
super(D3DSurfaceData.D3DTexture,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
}
public void Scale(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx1, int sy1,
int sx2, int sy2,
double dx1, double dy1,
double dx2, double dy2)
{
D3DBlitLoops.IsoBlit(src, dst,
null, null,
comp, clip, null,
AffineTransformOp.TYPE_NEAREST_NEIGHBOR,
sx1, sy1, sx2, sy2,
dx1, dy1, dx2, dy2,
true);
}
}
class D3DTextureToSurfaceTransform extends TransformBlit {
D3DTextureToSurfaceTransform() {
super(D3DSurfaceData.D3DTexture,
CompositeType.AnyAlpha,
D3DSurfaceData.D3DSurface);
}
public void Transform(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
AffineTransform at, int hint,
int sx, int sy, int dx, int dy,
int w, int h)
{
D3DBlitLoops.IsoBlit(src, dst,
null, null,
comp, clip, at, hint,
sx, sy, sx+w, sy+h,
dx, dy, dx+w, dy+h,
true);
}
}
/**
* This general Blit implemenation converts any source surface to an
* intermediate IntArgbPre surface, and then uses the more specific
* IntArgbPre->D3DSurface/Texture loop to get the intermediate
* (premultiplied) surface down to D3D.
*/
class D3DGeneralBlit extends Blit {
private Blit performop;
private WeakReference srcTmp;
D3DGeneralBlit(SurfaceType dstType,
CompositeType compType,
Blit performop)
{
super(SurfaceType.Any, compType, dstType);
this.performop = performop;
}
public synchronized void Blit(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx, int sy, int dx, int dy,
int w, int h)
{
Blit convertsrc = Blit.getFromCache(src.getSurfaceType(),
CompositeType.SrcNoEa,
SurfaceType.IntArgbPre);
SurfaceData cachedSrc = null;
if (srcTmp != null) {
// use cached intermediate surface, if available
cachedSrc = (SurfaceData)srcTmp.get();
}
// convert source to IntArgbPre
src = convertFrom(convertsrc, src, sx, sy, w, h,
cachedSrc, BufferedImage.TYPE_INT_ARGB_PRE);
// copy IntArgbPre intermediate surface to D3D surface
performop.Blit(src, dst, comp, clip,
0, 0, dx, dy, w, h);
if (src != cachedSrc) {
// cache the intermediate surface
srcTmp = new WeakReference(src);
}
}
}
/*
* The following classes prohibit copying D3DSurfaces to the screen
* (the D3D->sysmem->GDI path is known to be very very slow).
*
* Note: we used to disable hw acceleration for the surafce manager associated
* with the source surface in these loops but it proved to be too cautious.
*
* In most cases d3d->screen copy happens only during some transitional
* period where the accelerated destination surface is being recreated or
* restored (for example, when Swing's backbuffer VI is copied to the screen
* but the D3DScreenSurfaceManager couldn't restore its surface).
*
* An exception is if for some reason we could not enable accelerated on-screen
* rendering for this window for some permanent reason (like window being too
* small, or a present BufferStrategy).
*
* This meant that we'd disable hw acceleration after the first failure
* completely (at least until the src image is recreated which in case of
* Swing back-buffer happens only after resize).
*
* Now we delegate to the VISM to figure out if the acceleration needs to
* be disabled or if we can wait for a while until the onscreen accelerated
* can resume (by marking the source surface lost and making sure the
* VISM has a chance to use the backup surface).
*
*/
class D3DSurfaceToGDIWindowSurfaceBlit extends Blit {
D3DSurfaceToGDIWindowSurfaceBlit() {
super(D3DSurfaceData.D3DSurface,
CompositeType.AnyAlpha,
GDIWindowSurfaceData.AnyGdi);
}
@Override
public void Blit(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx, int sy, int dx, int dy, int w, int h)
{
// see comment above
D3DVolatileSurfaceManager.handleVItoScreenOp(src, dst);
}
}
class D3DSurfaceToGDIWindowSurfaceScale extends ScaledBlit {
D3DSurfaceToGDIWindowSurfaceScale() {
super(D3DSurfaceData.D3DSurface,
CompositeType.AnyAlpha,
GDIWindowSurfaceData.AnyGdi);
}
@Override
public void Scale(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
@ -161,65 +808,26 @@ class D3DTextureToSurfaceScale extends ScaledBlit {
double dx1, double dy1,
double dx2, double dy2)
{
synchronized (D3DContext.LOCK) {
long pCtx = D3DBlitLoops.getContext(src, dst, clip, comp, null);
D3DBlitLoops.doTransform(src.getNativeOps(), dst.getNativeOps(),
pCtx,
AffineTransformOp.TYPE_NEAREST_NEIGHBOR,
sx1, sy1, sx2, sy2,
(float)dx1, (float)dy1,
(float)dx2, (float)dy2);
}
// see comment above
D3DVolatileSurfaceManager.handleVItoScreenOp(src, dst);
}
}
class DelegateSwToTextureLoop extends Blit {
class D3DSurfaceToGDIWindowSurfaceTransform extends TransformBlit {
DelegateSwToTextureLoop() {
super(SurfaceType.Any, CompositeType.SrcNoEa, D3DTexture);
D3DSurfaceToGDIWindowSurfaceTransform() {
super(D3DSurfaceData.D3DSurface,
CompositeType.AnyAlpha,
GDIWindowSurfaceData.AnyGdi);
}
@Override
public void Blit(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
int sx, int sy, int dx, int dy, int w, int h)
public void Transform(SurfaceData src, SurfaceData dst,
Composite comp, Region clip,
AffineTransform at, int hint,
int sx, int sy, int dx, int dy,
int w, int h)
{
Blit realBlit = null;
int pf = ((D3DSurfaceData)dst).getPixelFormat();
switch (pf) {
case PF_INT_ARGB:
realBlit = Blit.getFromCache(src.getSurfaceType(),
CompositeType.SrcNoEa,
SurfaceType.IntArgbPre);
break;
case PF_INT_RGB:
realBlit = Blit.getFromCache(src.getSurfaceType(),
CompositeType.SrcNoEa,
SurfaceType.IntRgb);
break;
case PF_USHORT_565_RGB:
realBlit = Blit.getFromCache(src.getSurfaceType(),
CompositeType.SrcNoEa,
SurfaceType.Ushort565Rgb);
break;
case PF_USHORT_555_RGB:
realBlit = Blit.getFromCache(src.getSurfaceType(),
CompositeType.SrcNoEa,
SurfaceType.Ushort555Rgb);
break;
case PF_USHORT_4444_ARGB:
// REMIND: this should really be premultiplied!
realBlit = Blit.getFromCache(src.getSurfaceType(),
CompositeType.SrcNoEa,
SurfaceType.Ushort4444Argb);
break;
default:
throw
new InternalError("Can't yet handle dest pixel format: "+pf);
}
if (realBlit != null) {
realBlit.Blit(src, dst, comp, clip, sx, sy, dx, dy, w, h);
}
// see comment above
D3DVolatileSurfaceManager.handleVItoScreenOp(src, dst);
}
}

View File

@ -0,0 +1,116 @@
/*
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Sun designates this
* particular file as subject to the "Classpath" exception as provided
* by Sun in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*/
package sun.java2d.d3d;
import java.awt.image.AffineTransformOp;
import java.awt.image.BufferedImage;
import java.awt.image.BufferedImageOp;
import java.awt.image.ConvolveOp;
import java.awt.image.LookupOp;
import java.awt.image.RescaleOp;
import sun.java2d.SunGraphics2D;
import sun.java2d.SurfaceData;
import sun.java2d.loops.CompositeType;
import sun.java2d.pipe.BufferedBufImgOps;
import static sun.java2d.d3d.D3DContext.D3DContextCaps.*;
class D3DBufImgOps extends BufferedBufImgOps {
/**
* This method is called from D3DDrawImage.transformImage() only. It
* validates the provided BufferedImageOp to determine whether the op
* is one that can be accelerated by the D3D pipeline. If the operation
* cannot be completed for any reason, this method returns false;
* otherwise, the given BufferedImage is rendered to the destination
* using the provided BufferedImageOp and this method returns true.
*/
static boolean renderImageWithOp(SunGraphics2D sg, BufferedImage img,
BufferedImageOp biop, int x, int y)
{
// Validate the provided BufferedImage (make sure it is one that
// is supported, and that its properties are acceleratable)
if (biop instanceof ConvolveOp) {
if (!isConvolveOpValid((ConvolveOp)biop)) {
return false;
}
} else if (biop instanceof RescaleOp) {
if (!isRescaleOpValid((RescaleOp)biop, img)) {
return false;
}
} else if (biop instanceof LookupOp) {
if (!isLookupOpValid((LookupOp)biop, img)) {
return false;
}
} else {
// No acceleration for other BufferedImageOps (yet)
return false;
}
SurfaceData dstData = sg.surfaceData;
if (!(dstData instanceof D3DSurfaceData) ||
(sg.interpolationType == AffineTransformOp.TYPE_BICUBIC) ||
(sg.compositeState > SunGraphics2D.COMP_ALPHA))
{
return false;
}
SurfaceData srcData =
dstData.getSourceSurfaceData(img, sg.TRANSFORM_ISIDENT,
CompositeType.SrcOver, null);
if (!(srcData instanceof D3DSurfaceData)) {
// REMIND: this hack tries to ensure that we have a cached texture
srcData =
dstData.getSourceSurfaceData(img, sg.TRANSFORM_ISIDENT,
CompositeType.SrcOver, null);
if (!(srcData instanceof D3DSurfaceData)) {
return false;
}
}
// Verify that the source surface is actually a texture and that
// shaders are supported
D3DSurfaceData d3dSrc = (D3DSurfaceData)srcData;
D3DGraphicsDevice gd =
(D3DGraphicsDevice)d3dSrc.getDeviceConfiguration().getDevice();
if (d3dSrc.getType() != D3DSurfaceData.TEXTURE ||
!gd.isCapPresent(CAPS_LCD_SHADER))
{
return false;
}
int sw = img.getWidth();
int sh = img.getHeight();
D3DBlitLoops.IsoBlit(srcData, dstData,
img, biop,
sg.composite, sg.getCompClip(),
sg.transform, sg.interpolationType,
0, 0, sw, sh,
x, y, x+sw, y+sh,
true);
return true;
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2005-2006 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -25,392 +25,165 @@
package sun.java2d.d3d;
import java.awt.AlphaComposite;
import java.awt.Composite;
import java.awt.GraphicsEnvironment;
import java.awt.geom.AffineTransform;
import sun.awt.Win32GraphicsDevice;
import sun.java2d.InvalidPipeException;
import sun.java2d.SurfaceData;
import sun.java2d.pipe.Region;
import sun.java2d.windows.WindowsFlags;
import sun.java2d.pipe.BufferedContext;
import sun.java2d.pipe.RenderBuffer;
import sun.java2d.pipe.RenderQueue;
import sun.java2d.pipe.hw.ContextCapabilities;
import static sun.java2d.pipe.BufferedOpCodes.*;
import static sun.java2d.pipe.hw.ContextCapabilities.*;
import static sun.java2d.d3d.D3DContext.D3DContextCaps.*;
public class D3DContext {
/**
* Note that the RenderQueue lock must be acquired before calling any of
* the methods in this class.
*/
class D3DContext extends BufferedContext {
public static final int NO_CONTEXT_FLAGS = 0;
/**
* Used in D3DBlitLoops: if the source surface is opaque
* alpha blending can be turned off on the native level
* (if there's no ea), thus improving performance.
*/
public static final int SRC_IS_OPAQUE = 1;
private final D3DGraphicsDevice device;
D3DContext(RenderQueue rq, D3DGraphicsDevice device) {
super(rq);
this.device = device;
}
/**
* This is a list of capabilities supported by the device this
* context is associated with.
* @see getDeviceCaps
* Invalidates the currentContext field to ensure that we properly
* revalidate the D3DContext (make it current, etc.) next time through
* the validate() method. This is typically invoked from methods
* that affect the current context state (e.g. disposing a context or
* surface).
*/
public static final int J2D_D3D_FAILURE = (0 << 0);
/**
* Device supports depth buffer for d3d render targets
*/
public static final int J2D_D3D_DEPTH_SURFACE_OK = (1 << 0);
/**
* Device supports creation of plain d3d surfaces
*/
public static final int J2D_D3D_PLAIN_SURFACE_OK = (1 << 1);
/**
* Device supports creation of opaque textures
*/
public static final int J2D_D3D_OP_TEXTURE_SURFACE_OK = (1 << 2);
/**
* Device supports creation of bitmask textures
*/
public static final int J2D_D3D_BM_TEXTURE_SURFACE_OK = (1 << 3);
/**
* Device supports creation of translucent textures
*/
public static final int J2D_D3D_TR_TEXTURE_SURFACE_OK = (1 << 4);
/**
* Device supports creation of opaque render-to-textures
*/
public static final int J2D_D3D_OP_RTT_SURFACE_OK = (1 << 5);
/**
* Device can render lines correctly (no pixelization issues)
*/
public static final int J2D_D3D_LINES_OK = (1 << 6);
/**
* Device supports texture mapping (no pixelization issues)
*/
public static final int J2D_D3D_TEXTURE_BLIT_OK = (1 << 7);
/**
* Device supports texture mapping with transforms (no pixelization issues)
*/
public static final int J2D_D3D_TEXTURE_TRANSFORM_OK = (1 << 8);
/**
* Device can render clipped lines correctly.
*/
public static final int J2D_D3D_LINE_CLIPPING_OK = (1 << 9);
/**
* Device has all hw capabilities the d3d pipeline requires
*/
public static final int J2D_D3D_DEVICE_OK = (1 <<10);
/**
* Device supports all necessary texture formats required by d3d pipeline
*/
public static final int J2D_D3D_PIXEL_FORMATS_OK = (1 <<11);
/**
* Device supports geometry transformations
*/
public static final int J2D_D3D_SET_TRANSFORM_OK = (1 <<12);
/**
* The device is not from a list of known bad devices
* (see D3DRuntimeTest.cpp)
*/
public static final int J2D_D3D_HW_OK = (1 <<13);
/**
* Direct3D pipeline is enabled on this device
*/
public static final int J2D_D3D_ENABLED_OK = (1 <<14);
static void invalidateCurrentContext() {
// assert D3DRenderQueue.getInstance().lock.isHeldByCurrentThread();
/**
* The lock object used to synchronize access to the native windowing
* system layer. Note that rendering methods should always synchronize on
* D3DContext.LOCK before calling the D3DContext.getContext() method,
* or any other method that invokes native D3d commands.
* REMIND: in D3D case we should really be synchronizing on per-device
* basis.
*/
static Object LOCK;
private Win32GraphicsDevice gd;
private boolean valid;
protected long nativeContext;
private SurfaceData validatedDstData;
private Region validatedClip;
private Composite validatedComp;
private int validatedPixel;
private int validatedFlags;
private boolean xformInUse;
// validated transform's data
private double vScaleX, vScaleY, vShearX, vShearY, vTransX, vTransY;
private int deviceCaps;
private native void setRenderTarget(long pCtx, long pDst);
private native void setClip(long pCtx, long pDst, Region clip, boolean isRect,
int x1, int y1, int x2, int y2);
private native void resetClip(long pCtx, long pDst);
private native void resetComposite(long pCtx);
private native void setAlphaComposite(long pCtx, int rule,
float extraAlpha, int flags);
private native void setTransform(long pCtx, long pDst,
AffineTransform xform,
double m00, double m10, double m01,
double m11, double m02, double m12);
private native void resetTransform(long pCtx, long pDst);
private native void setColor(long pCtx, int pixel, int flags);
private native long initNativeContext(int screen);
private native int getNativeDeviceCaps(long pCtx);
static {
if (!GraphicsEnvironment.isHeadless()) {
LOCK = D3DContext.class;
// invalidate the current Java-level context so that we
// revalidate everything the next time around
if (currentContext != null) {
currentContext.invalidateContext();
currentContext = null;
}
}
public D3DContext(Win32GraphicsDevice gd) {
this.gd = gd;
reinitNativeContext();
// invalidate the context reference at the native level, and
// then flush the queue so that we have no pending operations
// dependent on the current context
D3DRenderQueue rq = D3DRenderQueue.getInstance();
rq.ensureCapacity(4);
rq.getBuffer().putInt(INVALIDATE_CONTEXT);
rq.flushNow();
}
/**
* Reinitializes the context by retrieving a pointer to the native
* D3DContext object, and resetting the device caps.
*/
void reinitNativeContext() {
nativeContext = initNativeContext(gd.getScreen());
deviceCaps = nativeContext != 0L ?
getNativeDeviceCaps(nativeContext) : J2D_D3D_FAILURE;
valid = ((deviceCaps & J2D_D3D_ENABLED_OK) != 0);
if (WindowsFlags.isD3DVerbose()) {
if (valid) {
System.out.println("Direct3D pipeline enabled on screen " +
gd.getScreen());
} else {
System.out.println("Could not enable Direct3D pipeline on " +
"screen " + gd.getScreen() +
". Device Caps: " +
Integer.toHexString(deviceCaps));
}
}
}
/**
* Invalidates this context by resetting its status: the validated
* destination surface, and a pointer to the native context.
* This method is called in the following cases:
* - if a surface loss situation is detected at the native level
* during any of the validation methods (setClip, setRenderTarget etc)
* and an InvalidPipeException is thrown.
* This situation happens when there was a surface loss, but
* there were no display change event (like in case of command prompt
* going fullscreen).
* - as part of surface restoration when a surface is the current
* target surface for this context. Since surface restoration
* resets the depth buffer contents, we need to make sure the clip
* is reset, and since the target surface is reset, we'll set a new
* clip the next time we attempt to render to the target surface.
* - when a display change occurs, the native D3DContext object is
* released and recreated as part of primary surface recreation.
* At the time of the release, the java D3DContext object need to be
* invalidated because a new D3D device is created and the target
* surface will need to be reset.
* Sets the current context on the native level to be the one passed as
* the argument.
* If the context is not the same as the defaultContext the latter
* will be reset to null.
*
* Invalidation of the context causes its revalidation the next time
* someone tries to get the D3DContext for rendering or creating a new
* surface.
* This call is needed when copying from a SW surface to a Texture
* (the upload test) or copying from d3d to SW surface to make sure we
* have the correct current context.
*
* @see #reinitNativeContext
* @param d3dc the context to be made current on the native level
*/
private void invalidateContext() {
valid = false;
nativeContext = 0L;
validatedDstData = null;
// We don't set deviceCaps to J2D_D3D_FAILURE here because
// it will prevent from creating d3d surfaces, which means that
// we'll never get a chance to continue using d3d after a single
// invalidation event (for example, a display change).
}
static void setScratchSurface(D3DContext d3dc) {
// assert D3DRenderQueue.getInstance().lock.isHeldByCurrentThread();
/**
* Fetches the D3DContext associated with the current
* thread/GraphicsConfig pair, validates the context using the given
* parameters, then returns the handle to the native context object.
* Most rendering operations will call this method first in order to
* prepare the native D3d layer before issuing rendering commands.
*/
static long getContext(SurfaceData srcData,
SurfaceData dstData,
Region clip, Composite comp,
AffineTransform xform,
int pixel, int flags)
{
if (dstData instanceof D3DSurfaceData == false) {
throw new InvalidPipeException("Incorrect destination surface");
// invalidate the current context
if (d3dc != currentContext) {
currentContext = null;
}
D3DContext d3dc = ((D3DSurfaceData)dstData).getContext();
try {
d3dc.validate(srcData, dstData, clip, comp, xform, pixel, flags);
} catch (InvalidPipeException e) {
d3dc.invalidateContext();
// note that we do not propagate the exception. Once the context
// is invalidated, any d3d rendering operations are noops, and
// we are waiting for the primary surface restoration, which
// happens when VolatileImage is validated. At this point
// the native D3DContext will be reinitialized, and the next
// time around validation of the context will succeed.
// Throwing the exception here will do no good, since the
// destination surface (which is associated with a VolatileImage
// or a BufferStrategy) will not be restored until VI.validate()
// is called by the rendering thread.
}
return d3dc.getNativeContext();
// set the scratch context
D3DRenderQueue rq = D3DRenderQueue.getInstance();
RenderBuffer buf = rq.getBuffer();
rq.ensureCapacity(8);
buf.putInt(SET_SCRATCH_SURFACE);
buf.putInt(d3dc.getDevice().getScreen());
}
public int getDeviceCaps() {
return deviceCaps;
public RenderQueue getRenderQueue() {
return D3DRenderQueue.getInstance();
}
boolean isRTTSupported() {
return ((deviceCaps & J2D_D3D_OP_RTT_SURFACE_OK) != 0);
@Override
public void saveState() {
// assert rq.lock.isHeldByCurrentThread();
// reset all attributes of this and current contexts
invalidateContext();
invalidateCurrentContext();
setScratchSurface(this);
// save the state on the native level
rq.ensureCapacity(4);
buf.putInt(SAVE_STATE);
rq.flushNow();
}
/**
* Returns a handle to the native D3DContext structure associated with
* this object.
*/
long getNativeContext() {
return nativeContext;
@Override
public void restoreState() {
// assert rq.lock.isHeldByCurrentThread();
// reset all attributes of this and current contexts
invalidateContext();
invalidateCurrentContext();
setScratchSurface(this);
// restore the state on the native level
rq.ensureCapacity(4);
buf.putInt(RESTORE_STATE);
rq.flushNow();
}
/**
* Validates the given parameters against the current state for this
* context. If this context is not current, it will be made current
* for the given source and destination surfaces, and the viewport will
* be updated. Then each part of the context state (clip, composite,
* etc.) is checked against the previous value. If the value has changed
* since the last call to validate(), it will be updated accordingly.
*/
private void validate(SurfaceData srcData, SurfaceData dstData,
Region clip, Composite comp, AffineTransform xform,
int pixel, int flags)
{
boolean updateClip = false;
D3DGraphicsDevice getDevice() {
return device;
}
if ((srcData != null && !srcData.isValid()) || !dstData.isValid() ||
dstData.getNativeOps() == 0L || dstData.isSurfaceLost())
{
throw new InvalidPipeException("Invalid surface");
static class D3DContextCaps extends ContextCapabilities {
/**
* Indicates the presence of pixel shaders (v2.0 or greater).
* This cap will only be set if the hardware supports the minimum number
* of texture units.
*/
static final int CAPS_LCD_SHADER = (FIRST_PRIVATE_CAP << 0);
/**
* Indicates the presence of pixel shaders (v2.0 or greater).
* This cap will only be set if the hardware meets our
* minimum requirements.
*/
static final int CAPS_BIOP_SHADER = (FIRST_PRIVATE_CAP << 1);
/**
* Indicates that the device was successfully initialized and can
* be safely used.
*/
static final int CAPS_DEVICE_OK = (FIRST_PRIVATE_CAP << 2);
/**
* Indicates that the device has all of the necessary capabilities
* to support the Antialiasing Pixel Shader program.
*/
static final int CAPS_AA_SHADER = (FIRST_PRIVATE_CAP << 3);
D3DContextCaps(int caps, String adapterId) {
super(caps, adapterId);
}
if (!valid) {
// attempt to reinitialize the context. If the device has been
// reset, the following calls to setRenderTarget/setClip will
// succeed and not throw InvalidPipeException.
reinitNativeContext();
}
if (dstData != validatedDstData) {
// invalidate pixel and clip (so they will be updated below)
validatedPixel = ~pixel;
updateClip = true;
// update the viewport
long pDst = dstData.getNativeOps();
setRenderTarget(nativeContext, pDst);
// keep the reference to the old data until we set the
// new one on the native level, preventing it from being disposed
SurfaceData tmpData = dstData;
validatedDstData = dstData;
tmpData = null;
}
// it's better to use dstData instead of validatedDstData because
// the latter may be set to null via invalidateContext at any moment.
long pDest = dstData.getNativeOps();
// validate clip
if ((clip != validatedClip) || updateClip) {
if (clip != null) {
/**
* It's cheaper to make this check than set clip every time.
*
* Set the new clip only if:
* - we were asked to do it (updateClip == true)
* - no clip was set before
* - if both the old and the new clip are shapes
* - if they're both rectangular but don't represent
* the same rectangle
*/
if (updateClip ||
validatedClip == null ||
!(validatedClip.isRectangular() && clip.isRectangular()) ||
((clip.getLoX() != validatedClip.getLoX() ||
clip.getLoY() != validatedClip.getLoY() ||
clip.getHiX() != validatedClip.getHiX() ||
clip.getHiY() != validatedClip.getHiY())))
{
setClip(nativeContext, pDest,
clip, clip.isRectangular(),
clip.getLoX(), clip.getLoY(),
clip.getHiX(), clip.getHiY());
}
} else {
resetClip(nativeContext, pDest);
@Override
public String toString() {
StringBuffer buf = new StringBuffer(super.toString());
if ((caps & CAPS_LCD_SHADER) != 0) {
buf.append("CAPS_LCD_SHADER|");
}
validatedClip = clip;
}
if ((comp != validatedComp) || (flags != validatedFlags)) {
// invalidate pixel
validatedPixel = ~pixel;
validatedComp = comp;
if (comp != null) {
AlphaComposite ac = (AlphaComposite)comp;
setAlphaComposite(nativeContext, ac.getRule(),
ac.getAlpha(), flags);
} else {
resetComposite(nativeContext);
if ((caps & CAPS_BIOP_SHADER) != 0) {
buf.append("CAPS_BIOP_SHADER|");
}
}
// validate transform
if (xform == null) {
if (xformInUse) {
resetTransform(nativeContext, pDest);
xformInUse = false;
vScaleX = vScaleY = 1.0;
vShearX = vShearY = vTransX = vTransY = 0.0;
if ((caps & CAPS_AA_SHADER) != 0) {
buf.append("CAPS_AA_SHADER|");
}
} else {
double nScaleX = xform.getScaleX();
double nScaleY = xform.getScaleY();
double nShearX = xform.getShearX();
double nShearY = xform.getShearY();
double nTransX = xform.getTranslateX();
double nTransY = xform.getTranslateY();
if (nTransX != vTransX || nTransY != vTransY ||
nScaleX != vScaleX || nScaleY != vScaleY ||
nShearX != vShearX || nShearY != vShearY)
{
setTransform(nativeContext, pDest,
xform,
nScaleX, nShearY, nShearX, nScaleY,
nTransX, nTransY);
vScaleX = nScaleX;
vScaleY = nScaleY;
vShearX = nShearX;
vShearY = nShearY;
vTransX = nTransY;
vTransY = nTransY;
xformInUse = true;
if ((caps & CAPS_DEVICE_OK) != 0) {
buf.append("CAPS_DEVICE_OK|");
}
return buf.toString();
}
// validate pixel
if (pixel != validatedPixel) {
validatedPixel = pixel;
setColor(nativeContext, pixel, flags);
}
// save flags for later comparison
validatedFlags = flags;
// mark dstData dirty
dstData.markDirty();
}
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2005-2007 Sun Microsystems, Inc. All Rights Reserved.
* Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -29,6 +29,8 @@ import java.awt.Color;
import java.awt.Image;
import java.awt.geom.AffineTransform;
import java.awt.image.AffineTransformOp;
import java.awt.image.BufferedImage;
import java.awt.image.BufferedImageOp;
import sun.java2d.SunGraphics2D;
import sun.java2d.SurfaceData;
import sun.java2d.loops.SurfaceType;
@ -36,6 +38,8 @@ import sun.java2d.loops.TransformBlit;
import sun.java2d.pipe.DrawImage;
public class D3DDrawImage extends DrawImage {
@Override
protected void renderImageXform(SunGraphics2D sg, Image img,
AffineTransform tx, int interpType,
int sx1, int sy1, int sx2, int sy2,
@ -44,7 +48,6 @@ public class D3DDrawImage extends DrawImage {
// punt to the MediaLib-based transformImage() in the superclass if:
// - bicubic interpolation is specified
// - a background color is specified and will be used
// - the source surface is not a texture
// - an appropriate TransformBlit primitive could not be found
if (interpType != AffineTransformOp.TYPE_BICUBIC) {
SurfaceData dstData = sg.surfaceData;
@ -54,10 +57,7 @@ public class D3DDrawImage extends DrawImage {
sg.imageComp,
bgColor);
if (srcData != null &&
!isBgOperation(srcData, bgColor) &&
srcData.getSurfaceType() == D3DSurfaceData.D3DTexture)
{
if (srcData != null && !isBgOperation(srcData, bgColor)) {
SurfaceType srcType = srcData.getSurfaceType();
SurfaceType dstType = dstData.getSurfaceType();
TransformBlit blit = TransformBlit.getFromCache(srcType,
@ -77,4 +77,25 @@ public class D3DDrawImage extends DrawImage {
super.renderImageXform(sg, img, tx, interpType,
sx1, sy1, sx2, sy2, bgColor);
}
@Override
public void transformImage(SunGraphics2D sg, BufferedImage img,
BufferedImageOp op, int x, int y)
{
if (op != null) {
if (op instanceof AffineTransformOp) {
AffineTransformOp atop = (AffineTransformOp) op;
transformImage(sg, img, x, y,
atop.getTransform(),
atop.getInterpolationType());
return;
} else {
if (D3DBufImgOps.renderImageWithOp(sg, img, op, x, y)) {
return;
}
}
img = op.filter(img, null);
}
copyImage(sg, img, x, y, null);
}
}

Some files were not shown because too many files have changed in this diff Show More