blob: 533b4153af061ba77bf1551d52dbede9e8ad7cc6 [file] [log] [blame]
// 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/Flutter.h>
#import <XCTest/XCTest.h>
#import "AppDelegate.h"
FLUTTER_ASSERT_ARC
@interface FlutterViewControllerTest : XCTestCase
@property(nonatomic, strong) FlutterViewController* flutterViewController;
@end
@implementation FlutterViewControllerTest
- (void)setUp {
[super setUp];
self.continueAfterFailure = NO;
}
- (void)tearDown {
if (self.flutterViewController) {
XCTestExpectation* vcDismissed = [self expectationWithDescription:@"dismiss"];
[self.flutterViewController dismissViewControllerAnimated:NO
completion:^{
[vcDismissed fulfill];
}];
[self waitForExpectationsWithTimeout:10.0 handler:nil];
}
[super tearDown];
}
- (void)testFirstFrameCallback {
XCTestExpectation* firstFrameRendered = [self expectationWithDescription:@"firstFrameRendered"];
FlutterEngine* engine = [[FlutterEngine alloc] initWithName:@"test" project:nil];
[engine runWithEntrypoint:nil];
self.flutterViewController = [[FlutterViewController alloc] initWithEngine:engine
nibName:nil
bundle:nil];
XCTAssertFalse(self.flutterViewController.isDisplayingFlutterUI);
XCTestExpectation* displayingFlutterUIExpectation =
[self keyValueObservingExpectationForObject:self.flutterViewController
keyPath:@"displayingFlutterUI"
expectedValue:@YES];
displayingFlutterUIExpectation.assertForOverFulfill = YES;
[self.flutterViewController setFlutterViewDidRenderCallback:^{
[firstFrameRendered fulfill];
}];
AppDelegate* appDelegate = (AppDelegate*)UIApplication.sharedApplication.delegate;
UIViewController* rootVC = appDelegate.window.rootViewController;
[rootVC presentViewController:self.flutterViewController animated:NO completion:nil];
[self waitForExpectationsWithTimeout:30.0 handler:nil];
}
- (void)testDrawLayer {
XCTestExpectation* firstFrameRendered = [self expectationWithDescription:@"firstFrameRendered"];
XCTestExpectation* imageRendered = [self expectationWithDescription:@"imageRendered"];
FlutterEngine* engine = [[FlutterEngine alloc] initWithName:@"test" project:nil];
[engine runWithEntrypoint:nil];
[engine.binaryMessenger
setMessageHandlerOnChannel:@"waiting_for_status"
binaryMessageHandler:^(NSData* _Nullable message, FlutterBinaryReply _Nonnull reply) {
FlutterMethodChannel* channel = [FlutterMethodChannel
methodChannelWithName:@"driver"
binaryMessenger:engine.binaryMessenger
codec:[FlutterJSONMethodCodec sharedInstance]];
[channel invokeMethod:@"set_scenario" arguments:@{@"name" : @"solid_blue"}];
}];
self.flutterViewController = [[FlutterViewController alloc] initWithEngine:engine
nibName:nil
bundle:nil];
XCTAssertFalse(self.flutterViewController.isDisplayingFlutterUI);
[self.flutterViewController setFlutterViewDidRenderCallback:^{
[firstFrameRendered fulfill];
}];
AppDelegate* appDelegate = (AppDelegate*)UIApplication.sharedApplication.delegate;
UIViewController* rootVC = appDelegate.window.rootViewController;
[rootVC presentViewController:self.flutterViewController animated:NO completion:nil];
CGColorSpaceRef color_space = CGColorSpaceCreateDeviceRGB();
__block dispatch_block_t callback;
callback = ^{
size_t width = 300u;
CGContextRef context =
CGBitmapContextCreate(nil, width, width, 8, 4 * width, color_space,
kCGBitmapByteOrder32Little | kCGImageAlphaPremultipliedFirst);
[appDelegate.window.layer renderInContext:context];
uint32_t* image_data = (uint32_t*)CGBitmapContextGetData(context);
if (image_data[20] == 0xFF0000FF) {
[imageRendered fulfill];
return;
}
CGContextRelease(context);
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, NSEC_PER_SEC), dispatch_get_main_queue(),
callback);
};
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, NSEC_PER_SEC), dispatch_get_main_queue(),
callback);
[self waitForExpectationsWithTimeout:30.0 handler:nil];
CGColorSpaceRelease(color_space);
}
@end