Adding some logic to Objective-C++ wrapper
This commit is contained in:
parent
83bb16b28b
commit
be7d432f6d
24
NesKit/NesLayer.h
Normal file
24
NesKit/NesLayer.h
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
//
|
||||||
|
// NesLayer.h
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Created by Мустафаев Селим Мустафаевич on 28.09.2023.
|
||||||
|
//
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#import <Foundation/Foundation.h>
|
||||||
|
#import <QuartzCore/QuartzCore.h>
|
||||||
|
#import "NesSystem.h"
|
||||||
|
|
||||||
|
NS_ASSUME_NONNULL_BEGIN
|
||||||
|
|
||||||
|
@interface NesLayer : CALayer
|
||||||
|
|
||||||
|
@property NesSystem* system;
|
||||||
|
|
||||||
|
- (instancetype)initWithNesSystem:(NesSystem*)system;
|
||||||
|
|
||||||
|
@end
|
||||||
|
|
||||||
|
NS_ASSUME_NONNULL_END
|
||||||
27
NesKit/NesLayer.m
Normal file
27
NesKit/NesLayer.m
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
//
|
||||||
|
// NesLayer.m
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Created by Мустафаев Селим Мустафаевич on 28.09.2023.
|
||||||
|
//
|
||||||
|
|
||||||
|
#import "NesLayer.h"
|
||||||
|
|
||||||
|
@implementation NesLayer {
|
||||||
|
NSTimer* _timer;
|
||||||
|
}
|
||||||
|
|
||||||
|
- (instancetype)initWithNesSystem:(NesSystem*)system {
|
||||||
|
if(self = [super init]) {
|
||||||
|
self.system = system;
|
||||||
|
_timer = [NSTimer timerWithTimeInterval:1.0/60.0 repeats:YES block:^(NSTimer * _Nonnull timer) {
|
||||||
|
if(self.system) {
|
||||||
|
self.contents = self.system.frame;
|
||||||
|
[self.system stepToNextFrame];
|
||||||
|
}
|
||||||
|
}];
|
||||||
|
}
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
|
||||||
|
@end
|
||||||
@ -6,12 +6,17 @@
|
|||||||
//
|
//
|
||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
#import <Foundation/Foundation.h>
|
||||||
|
#import <CoreGraphics/CoreGraphics.h>
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
NS_ASSUME_NONNULL_BEGIN
|
||||||
|
|
||||||
@interface NesSystem : NSObject
|
@interface NesSystem : NSObject
|
||||||
|
|
||||||
|
@property CGImageRef frame;
|
||||||
|
|
||||||
- (instancetype)init;
|
- (instancetype)init;
|
||||||
|
- (void)runRom:(NSString*)path;
|
||||||
|
- (void)stepToNextFrame;
|
||||||
|
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
|||||||
@ -1,5 +1,5 @@
|
|||||||
//
|
//
|
||||||
// NesSystem.m
|
// NesSystem.mm
|
||||||
//
|
//
|
||||||
//
|
//
|
||||||
// Created by Selim Mustafaev on 27.09.2023.
|
// Created by Selim Mustafaev on 27.09.2023.
|
||||||
@ -16,13 +16,62 @@
|
|||||||
|
|
||||||
@implementation NesSystem {
|
@implementation NesSystem {
|
||||||
std::unique_ptr<nes::System> _system;
|
std::unique_ptr<nes::System> _system;
|
||||||
|
NSCondition* _condition;
|
||||||
|
BOOL _runEmulation;
|
||||||
}
|
}
|
||||||
|
|
||||||
- (instancetype)init {
|
- (instancetype)init {
|
||||||
if(self = [super init]) {
|
if(self = [super init]) {
|
||||||
_system = std::make_unique<nes::System>();
|
_system = std::make_unique<nes::System>();
|
||||||
|
_condition = [NSCondition new];
|
||||||
|
_runEmulation = YES;
|
||||||
|
|
||||||
|
size_t frameBufferSize = nes::Ppu::SCREEN_WIDTH * nes::Ppu::SCREEN_HEIGHT * sizeof(nes::Pixel);
|
||||||
|
|
||||||
|
_system->setNewFrameCallback([&](auto frameBuffer) {
|
||||||
|
_runEmulation = NO;
|
||||||
|
|
||||||
|
CGDataProviderRef dataProvider = CGDataProviderCreateWithData(NULL, (void*)frameBuffer, frameBufferSize, NULL);
|
||||||
|
CGColorSpaceRef colorspace = CGColorSpaceCreateDeviceRGB();
|
||||||
|
_frame = CGImageCreate(nes::Ppu::SCREEN_WIDTH,
|
||||||
|
nes::Ppu::SCREEN_HEIGHT,
|
||||||
|
8,
|
||||||
|
sizeof(nes::Pixel)*8,
|
||||||
|
nes::Ppu::SCREEN_WIDTH * sizeof(nes::Pixel),
|
||||||
|
colorspace,
|
||||||
|
kCGBitmapByteOrderDefault,
|
||||||
|
dataProvider,
|
||||||
|
NULL,
|
||||||
|
true,
|
||||||
|
kCGRenderingIntentDefault);
|
||||||
|
CGDataProviderRelease(dataProvider);
|
||||||
|
CGColorSpaceRelease(colorspace);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
return self;
|
return self;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
- (void)runRom:(NSURL*)url {
|
||||||
|
_system->insertCartridge([url fileSystemRepresentation]);
|
||||||
|
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
|
||||||
|
[_condition lock];
|
||||||
|
while (!_runEmulation) {
|
||||||
|
[_condition wait];
|
||||||
|
}
|
||||||
|
|
||||||
|
while(_runEmulation) {
|
||||||
|
_system->tick();
|
||||||
|
}
|
||||||
|
|
||||||
|
[_condition unlock];
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
- (void)stepToNextFrame {
|
||||||
|
[_condition lock];
|
||||||
|
_runEmulation = YES;
|
||||||
|
[_condition signal];
|
||||||
|
[_condition unlock];
|
||||||
|
}
|
||||||
|
|
||||||
@end
|
@end
|
||||||
|
|||||||
@ -1,4 +1,4 @@
|
|||||||
// swift-tools-version: 5.9
|
// swift-tools-version: 5.8
|
||||||
// The swift-tools-version declares the minimum version of Swift required to build this package.
|
// The swift-tools-version declares the minimum version of Swift required to build this package.
|
||||||
|
|
||||||
import PackageDescription
|
import PackageDescription
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user