Giter VIP home page Giter VIP logo

Comments (13)

zeux avatar zeux commented on July 21, 2024 5

Yeah - you need to change the layer on the NSView to be a CAMetalLayer. It might be worthwhile to make MoltenVK do this automatically (it's only possible to do on macOS, not iOS). Just run this code:

static void makeViewMetalCompatible(void* handle)
{
    NSView* view = (NSView*)handle;
    assert([view isKindOfClass:[NSView class]]);

    if (![view.layer isKindOfClass:[CAMetalLayer class]])
    {
        [view setLayer:[CAMetalLayer layer]];
        [view setWantsLayer:YES];
    }
}

(note: you need to compile this in an ObjC translation unit; not sure if it's possible to do the same from just C/C++)

from moltenvk.

jbltx avatar jbltx commented on July 21, 2024

@zeux your method works like a charm, thank you !

I just made a small .mm wrapper file for the surface creation for the moment, it will surely grow later...

I'm a total newbie with ObjC so it's really helpful for me, and I hope it will be also helpful for other people using Qt !

Thank you again.

from moltenvk.

mellinoe avatar mellinoe commented on July 21, 2024

It might be worthwhile to make MoltenVK do this automatically

I'd also like to see that. It can also be done on an iOS UIView by adding the CAMetalLayer as a new sublayer. This is what I'm doing in my code for Metal, at least.

from moltenvk.

billhollings avatar billhollings commented on July 21, 2024

@zeux & @mellinoe

Hmmm...interesting suggestion...and thanks for the solutions.

But I'm not so sure that MoltenVK...as a graphics driver...should be taking it upon itself to reach into an app and change the app's windowing composition. That seems a bit like a recipe for confusion and complaints from (especially newbie) app devs who are otherwise expecting to be able to do normal app stuff to that window or view.

For instance...what if Qt (or equivalent) has a requirement that it NOT be a CAMetalLayer...maybe its expecting to run OpenGL on that view? It seems to be me better to let the app handle arbitration in those circumstances.

Perhaps as a convenience...the MoltenVK API could include your solutions into some kind of helper function (eg- mvkMakeMeCompatible(NS/UIView* view))?

from moltenvk.

zeux avatar zeux commented on July 21, 2024

@billhollings yeah - I'm not sure how I feel about automatically doing this, especially for iOS (not sure what the implications are about adding another layer). Adding a mvk function would be great though - as it stands you basically need to write Objective C code to use MoltenVK since these APIs aren't accessible from C AFAICT.

from moltenvk.

mellinoe avatar mellinoe commented on July 21, 2024

as it stands you basically need to write Objective C code to use MoltenVK since these APIs aren't accessible from C AFAICT.

They are accessible, you just need to be familiar with the Objective-C Runtime and message passing. I'm doing what was described above from C#/.NET, through its C interop capabilities.

from moltenvk.

billhollings avatar billhollings commented on July 21, 2024

@mellinoe

Similar to @zeux's macOS example...would you mind submitting a code snippet that implements the sublayer approach on iOS...for a future implementation of such a convenience function, please?

Or if anyone wants to take on implementing that function for fun...and submit a PR...please feel free! ;^)

from moltenvk.

mellinoe avatar mellinoe commented on July 21, 2024

@billhollings Sure, here's what I do in my library. It should be understandable although it is in C#:

CAMetalLayer = CAMetalLayer.New(); // Calls alloc + init
UIView uiView = ...; // From swapchain create info

CGSize viewSize = uiView.frame.size;
metalLayer.frame = uiView.frame;
metalLayer.opaque = true;
uiView.layer.addSublayer(metalLayer.NativePtr); // This is just your CAMetalLayer* in C/C++
metalLayer.device = device; // My MTLDevice instance
metalLayer.pixelFormat = MTLPixelFormat.BGRA8Unorm; // Aka MTLPixelFormatBGRA8Unorm
metalLayer.framebufferOnly = true;
metalLayer.drawableSize = viewSize;

Some of the above is probably already done by MoltenVK (like setting the device, etc.).

from moltenvk.

oscarbg avatar oscarbg commented on July 21, 2024

Hi guys thanks to this thread I have been able to add support for surface info to a simple port I had done last week of VulkanCapsViewer to MacOS and IOS..
you can see the diff here:
SaschaWillems/VulkanCapsViewer#45
I unified @zeux and @mellinoe solutions in one function

#ifdef BUILD_FOR_MAC
#import <Cocoa/Cocoa.h>
#else
#import <UIKit/UIKit.h>
#import <Metal/Metal.h>
#endif

extern "C" void makeViewMetalCompatible(void* handle)
{
#ifdef BUILD_FOR_MAC
    NSView* view = (NSView*)handle;
    assert([view isKindOfClass:[NSView class]]);

    if (![view.layer isKindOfClass:[CAMetalLayer class]])
    {
        orilayer=[view layer];
        [view setLayer:[CAMetalLayer layer]];
        //[view setWantsLayer:NO];
    }
#else
    UIView* view = (UIView*)handle;
    assert([view isKindOfClass:[UIView class]]);

    CAMetalLayer *metalLayer = [CAMetalLayer new]; // Calls alloc + init
    //UIView uiView = ...; // From swapchain create info

    CGSize viewSize = view.frame.size;
    metalLayer.frame = view.frame;
   metalLayer.opaque = true;
    metalLayer.framebufferOnly = true;
    metalLayer.drawableSize = viewSize;
    metalLayer.pixelFormat = (MTLPixelFormat)80;//BGRA8Unorm==80
    [view.layer addSublayer:metalLayer];
#endif
}

notes:
as VulkanCapsviewer is special Qt+Vulkan app as calls VkCreateSurface for getting surface info but also doesn't up rendering to it.. so I need after getting the info to call some other function (unmakeViewMetalCompatible below) to restore the original layer (that I saved previously as oriLayer) so I can see the app render correctly..

void unmakeViewMetalCompatible(void* handle)
{
#ifdef BUILD_FOR_MAC
    NSView* view = (NSView*)handle;
    assert([view isKindOfClass:[NSView class]]);
#else
  UIView* view = (UIView*)handle;
    assert([view isKindOfClass:[UIView class]]);
#endif

    if ([view.layer isKindOfClass:[CAMetalLayer class]])
    {
        [view setLayer:orilayer];
    }
}

it seems to work on MacOS without any strange messages with debugging enabled so nice..

code with ifdefs compiles also on IOS and in the form I share doesn't crash on it (as it was if using the original approach shader for MacOS)..
on IOS still MoltenVK complains that the view should be CAMetalLayer..
on IOS, with the sublayer approach, original view still seems to be EAGLLayer but seems the addSublayer should have added the Metal sublayer as shared here..
so seems now the ball is on MoltenVK to support that scenario, right @billhollings?
then will fix the unmakeViewMetalCompatible call on IOS which is not ready or perhaps it's already it is if I save the original layer on IOS case and restore later..
Also note I know on MacOS there is a leak on code as restoring original layer I should delete the CAMetalLayer I created, right?

thanks..

from moltenvk.

mellinoe avatar mellinoe commented on July 21, 2024

I should delete the CAMetalLayer I created, right?

I'm not really an Objective-C expert, but yes, you need to release the object if you created it yourself (with the "new" function).

from moltenvk.

ikryukov avatar ikryukov commented on July 21, 2024

Made simple solution for Qt + Vulkan on OSX using MoltenVK with qmake. Work in progress now, but I think it could be useful for some one: https://github.com/ikryukov/QtVulkan

from moltenvk.

msorvig avatar msorvig commented on July 21, 2024

We've now also added experimental support in Qt itself, see http://blog.qt.io/blog/2018/05/30/vulkan-for-qt-on-macos .

In Qt 5.12, setting the surface type of the window to QSurface::VulkanSurface will configure the QWindow/NSView to backed by a CAMetalLayer layer which should be usable by MoltenVK.

from moltenvk.

billhollings avatar billhollings commented on July 21, 2024

@msorvig

Wonderful news! Thanks very much for letting us know!

And with that news...I am going to close this issue here!

from moltenvk.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.