Unverified Commit 21d7a12b authored by Ivan Matkov's avatar Ivan Matkov Committed by GitHub

Don't try to init D3D with zero size (#858)

* Don't try to init D3D with zero size

* Pass AWT size for swap chain initialization

* Avoid reading size twice
parent 03928d6a
...@@ -58,12 +58,7 @@ public: ...@@ -58,12 +58,7 @@ public:
device.reset(nullptr); device.reset(nullptr);
} }
void initSwapChain() { void initSwapChain(UINT width, UINT height) {
RECT windowRect;
GetClientRect(window, &windowRect);
UINT width = windowRect.right - windowRect.left;
UINT height = windowRect.bottom - windowRect.top;
gr_cp<IDXGIFactory4> swapChainFactory4; gr_cp<IDXGIFactory4> swapChainFactory4;
gr_cp<IDXGISwapChain1> swapChain1; gr_cp<IDXGISwapChain1> swapChain1;
CreateDXGIFactory2(0, IID_PPV_ARGS(&swapChainFactory4)); CreateDXGIFactory2(0, IID_PPV_ARGS(&swapChainFactory4));
...@@ -330,12 +325,12 @@ extern "C" ...@@ -330,12 +325,12 @@ extern "C"
} }
JNIEXPORT void JNICALL Java_org_jetbrains_skiko_redrawer_Direct3DRedrawer_initSwapChain( JNIEXPORT void JNICALL Java_org_jetbrains_skiko_redrawer_Direct3DRedrawer_initSwapChain(
JNIEnv *env, jobject redrawer, jlong devicePtr) JNIEnv *env, jobject redrawer, jlong devicePtr, jint width, jint height)
{ {
__try __try
{ {
DirectXDevice *d3dDevice = fromJavaPointer<DirectXDevice *>(devicePtr); DirectXDevice *d3dDevice = fromJavaPointer<DirectXDevice *>(devicePtr);
d3dDevice->initSwapChain(); d3dDevice->initSwapChain((UINT) width, (UINT) height);
} }
__except(EXCEPTION_EXECUTE_HANDLER) { __except(EXCEPTION_EXECUTE_HANDLER) {
auto code = GetExceptionCode(); auto code = GetExceptionCode();
......
...@@ -41,34 +41,38 @@ internal class Direct3DContextHandler(layer: SkiaLayer) : JvmContextHandler(laye ...@@ -41,34 +41,38 @@ internal class Direct3DContextHandler(layer: SkiaLayer) : JvmContextHandler(laye
} }
return false return false
} }
private var isD3DInited = false
override fun initCanvas() { override fun initCanvas() {
val context = context ?: return
val scale = layer.contentScale val scale = layer.contentScale
val w = (layer.width * scale).toInt().coerceAtLeast(0) val width = (layer.width * scale).toInt()
val h = (layer.height * scale).toInt().coerceAtLeast(0) val height = (layer.height * scale).toInt()
val surfaceProps = SurfaceProps(pixelGeometry = layer.pixelGeometry)
if (isSizeChanged(w, h) || isSurfacesNull()) { if (width <= 0 || height <= 0) {
return
}
if (isSizeChanged(width, height) || isSurfacesNull()) {
disposeCanvas() disposeCanvas()
context?.flush() context.flush()
if (!isD3DInited) { val justInitialized = directXRedrawer.changeSize(width, height)
directXRedrawer.initSwapChain()
} else {
directXRedrawer.resizeBuffers(w, h)
}
try { try {
for (bufferIndex in 0..bufferCount - 1) { val surfaceProps = SurfaceProps(pixelGeometry = layer.pixelGeometry)
surfaces[bufferIndex] = directXRedrawer.makeSurface(getPtr(context!!), w, h, surfaceProps, bufferIndex) for (bufferIndex in 0 until bufferCount) {
surfaces[bufferIndex] = directXRedrawer.makeSurface(
context = getPtr(context),
width = width,
height = height,
surfaceProps = surfaceProps,
index = bufferIndex
)
} }
} finally { } finally {
Reference.reachabilityFence(context!!) Reference.reachabilityFence(context)
} }
if (!isD3DInited) { if (justInitialized) {
isD3DInited = true
directXRedrawer.initFence() directXRedrawer.initFence()
} }
} }
...@@ -77,14 +81,13 @@ internal class Direct3DContextHandler(layer: SkiaLayer) : JvmContextHandler(laye ...@@ -77,14 +81,13 @@ internal class Direct3DContextHandler(layer: SkiaLayer) : JvmContextHandler(laye
} }
override fun flush() { override fun flush() {
val context = context ?: return
val surface = surface ?: return
try { try {
flush( flush(getPtr(context), getPtr(surface))
getPtr(context!!),
getPtr(surface!!)
)
} finally { } finally {
Reference.reachabilityFence(context!!) Reference.reachabilityFence(context)
Reference.reachabilityFence(surface!!) Reference.reachabilityFence(surface)
} }
} }
......
...@@ -19,6 +19,7 @@ internal class Direct3DRedrawer( ...@@ -19,6 +19,7 @@ internal class Direct3DRedrawer(
override val renderInfo: String get() = contextHandler.rendererInfo() override val renderInfo: String get() = contextHandler.rendererInfo()
private var drawLock = Any() private var drawLock = Any()
private var isSwapChainInitialized = false
private var device: Long = 0L private var device: Long = 0L
get() { get() {
...@@ -84,10 +85,11 @@ internal class Direct3DRedrawer( ...@@ -84,10 +85,11 @@ internal class Direct3DRedrawer(
} }
private fun drawAndSwap(withVsync: Boolean) = synchronized(drawLock) { private fun drawAndSwap(withVsync: Boolean) = synchronized(drawLock) {
if (!isDisposed) { if (isDisposed) {
contextHandler.draw() return
swap(device, withVsync)
} }
contextHandler.draw()
swap(withVsync)
} }
fun makeContext() = DirectContext( fun makeContext() = DirectContext(
...@@ -100,10 +102,25 @@ internal class Direct3DRedrawer( ...@@ -100,10 +102,25 @@ internal class Direct3DRedrawer(
} }
} }
fun resizeBuffers(width: Int, height: Int) = resizeBuffers(device, width, height) fun changeSize(width: Int, height: Int): Boolean {
return if (!isSwapChainInitialized) {
initSwapChain(device, width, height)
isSwapChainInitialized = true
true
} else {
resizeBuffers(device, width, height)
false
}
}
private fun swap(withVsync: Boolean) {
if (!isSwapChainInitialized) {
return
}
swap(device, withVsync)
}
fun getBufferIndex() = getBufferIndex(device) fun getBufferIndex() = getBufferIndex(device)
fun initSwapChain() = initSwapChain(device)
fun initFence() = initFence(device) fun initFence() = initFence(device)
// Called from native code // Called from native code
...@@ -117,7 +134,7 @@ internal class Direct3DRedrawer( ...@@ -117,7 +134,7 @@ internal class Direct3DRedrawer(
private external fun swap(device: Long, isVsyncEnabled: Boolean) private external fun swap(device: Long, isVsyncEnabled: Boolean)
private external fun disposeDevice(device: Long) private external fun disposeDevice(device: Long)
private external fun getBufferIndex(device: Long): Int private external fun getBufferIndex(device: Long): Int
private external fun initSwapChain(device: Long) private external fun initSwapChain(device: Long, width: Int, height: Int)
private external fun initFence(device: Long) private external fun initFence(device: Long)
private external fun getAdapterName(adapter: Long): String private external fun getAdapterName(adapter: Long): String
private external fun getAdapterMemorySize(adapter: Long): Long private external fun getAdapterMemorySize(adapter: Long): Long
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment