forked from flutter/engine
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathFlutterRenderer.mm
More file actions
129 lines (109 loc) · 5.32 KB
/
FlutterRenderer.mm
File metadata and controls
129 lines (109 loc) · 5.32 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
// Copyright 2013 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#import "flutter/shell/platform/darwin/macos/framework/Source/FlutterRenderer.h"
#import "flutter/shell/platform/darwin/macos/framework/Source/FlutterEngine_Internal.h"
#import "flutter/shell/platform/darwin/macos/framework/Source/FlutterExternalTexture.h"
#import "flutter/shell/platform/darwin/macos/framework/Source/FlutterViewController_Internal.h"
#import "flutter/shell/platform/darwin/macos/framework/Source/FlutterViewEngineProvider.h"
#include "flutter/shell/platform/embedder/embedder.h"
#pragma mark - Static callbacks that require the engine.
static FlutterMetalTexture OnGetNextDrawableForDefaultView(FlutterEngine* engine,
const FlutterFrameInfo* frameInfo) {
// TODO(dkwingsmt): This callback only supports single-view, therefore it only
// operates on the default view. To support multi-view, we need a new callback
// that also receives a view ID, or pass the ID via FlutterFrameInfo.
FlutterViewId viewId = kFlutterDefaultViewId;
CGSize size = CGSizeMake(frameInfo->size.width, frameInfo->size.height);
return [engine.renderer createTextureForView:viewId size:size];
}
static bool OnPresentDrawableOfDefaultView(FlutterEngine* engine,
const FlutterMetalTexture* texture) {
// TODO(dkwingsmt): This callback only supports single-view, therefore it only
// operates on the default view. To support multi-view, we need a new callback
// that also receives a view ID.
FlutterViewId viewId = kFlutterDefaultViewId;
return [engine.renderer present:viewId texture:texture];
}
static bool OnAcquireExternalTexture(FlutterEngine* engine,
int64_t textureIdentifier,
size_t width,
size_t height,
FlutterMetalExternalTexture* metalTexture) {
return [engine.renderer populateTextureWithIdentifier:textureIdentifier
metalTexture:metalTexture];
}
#pragma mark - FlutterRenderer implementation
@implementation FlutterRenderer {
FlutterViewEngineProvider* _viewProvider;
FlutterDarwinContextMetalSkia* _darwinMetalContext;
}
- (instancetype)initWithFlutterEngine:(nonnull FlutterEngine*)flutterEngine {
self = [super initWithDelegate:self engine:flutterEngine];
if (self) {
_viewProvider = [[FlutterViewEngineProvider alloc] initWithEngine:flutterEngine];
_device = MTLCreateSystemDefaultDevice();
if (!_device) {
NSLog(@"Could not acquire Metal device.");
return nil;
}
_commandQueue = [_device newCommandQueue];
if (!_commandQueue) {
NSLog(@"Could not create Metal command queue.");
return nil;
}
_darwinMetalContext = [[FlutterDarwinContextMetalSkia alloc] initWithMTLDevice:_device
commandQueue:_commandQueue];
}
return self;
}
- (FlutterRendererConfig)createRendererConfig {
FlutterRendererConfig config = {
.type = FlutterRendererType::kMetal,
.metal.struct_size = sizeof(FlutterMetalRendererConfig),
.metal.device = (__bridge FlutterMetalDeviceHandle)_device,
.metal.present_command_queue = (__bridge FlutterMetalCommandQueueHandle)_commandQueue,
.metal.get_next_drawable_callback =
reinterpret_cast<FlutterMetalTextureCallback>(OnGetNextDrawableForDefaultView),
.metal.present_drawable_callback =
reinterpret_cast<FlutterMetalPresentCallback>(OnPresentDrawableOfDefaultView),
.metal.external_texture_frame_callback =
reinterpret_cast<FlutterMetalTextureFrameCallback>(OnAcquireExternalTexture),
};
return config;
}
#pragma mark - Embedder callback implementations.
- (FlutterMetalTexture)createTextureForView:(FlutterViewId)viewId size:(CGSize)size {
FlutterView* view = [_viewProvider viewForId:viewId];
NSAssert(view != nil, @"Can't create texture on a non-existent view 0x%llx.", viewId);
if (view == nil) {
// FlutterMetalTexture has texture `null`, therefore is discarded.
return FlutterMetalTexture{};
}
return [view.surfaceManager surfaceForSize:size].asFlutterMetalTexture;
}
- (BOOL)present:(FlutterViewId)viewId texture:(const FlutterMetalTexture*)texture {
FlutterView* view = [_viewProvider viewForId:viewId];
if (view == nil) {
return NO;
}
FlutterSurface* surface = [FlutterSurface fromFlutterMetalTexture:texture];
if (surface == nil) {
return NO;
}
FlutterSurfacePresentInfo* info = [[FlutterSurfacePresentInfo alloc] init];
info.surface = surface;
[view.surfaceManager present:@[ info ] notify:nil];
return YES;
}
#pragma mark - FlutterTextureRegistrar methods.
- (BOOL)populateTextureWithIdentifier:(int64_t)textureID
metalTexture:(FlutterMetalExternalTexture*)textureOut {
FlutterExternalTexture* texture = [self getTextureWithID:textureID];
return [texture populateTexture:textureOut];
}
- (FlutterExternalTexture*)onRegisterTexture:(id<FlutterTexture>)texture {
return [[FlutterExternalTexture alloc] initWithFlutterTexture:texture
darwinMetalContext:_darwinMetalContext];
}
@end