React Native for macOS で新しく追加されたファイル

# React Native と React Native for macOS の差分

2020年5月19日、MicrosoftからReact Native for macOS公開についてブログでアナウンスがありました。

[Announcing React Native for macOS and more · React Native for Windows \+ macOS](https://microsoft.github.io/react-native-windows/blog/2020/05/19/rn4mupdadates)

Microsoftは2019年5月7日に多くのコンポーネントをC++で書き直した[React Native for Windows](https://jp.techcrunch.com/2019/05/07/2019-05-06-microsoft-launches-react-native-for-windows/)を公開しており、今回はmacOS用のネイティブライブラリなどが追加されています。

今回、本家[FacebookのReact Native](https://github.com/facebook/react-native)と比べてどのようなファイルがコミットされているかを調べてみました。

調査は2020年5月29日のmasterで行いました。

- https://github.com/facebook/react-native/tree/f438a6e8f60a5cd10b06f19bc5248f5805fbb739
- https://github.com/microsoft/react-native-macos/tree/9232ace99d095a793bddf00ffda3238cc7078820

# トップディレクトリの差分

```diff
+ .ado
+ .appveyor
+ Folly
+ ReactApple
+ android-patches
+ danger
- docs
+ double-conversion
+ follybuild
+ glog
+ jsc
+ metadata
+ processor
+ stubs/glog
+ v8-docker-build
+ website/server
+ flowconfig.macos
+ Brewfile
+ CHANGELOG.json
+ CODE_OF_CONDUCT.md
+ KeepingRecent.md
- index.js
- interface.js
```

## 概要

トップディレクトリの主な差分は

1. ライブラリの追加
2. Microsoftの管理用と思われるファイル

の2つです。

## 1. ライブラリの追加

React Native for macOSには以下のライブラリが追加されてました。

ライブラリ名 | 開発チーム | 概要
---- | ---- | ----
[Folly](https://github.com/facebook/folly) | Facebook | C++ ライブラリ
[Infer annotations](https://github.com/facebook/infer/tree/master/infer/annotations) | Facebook | Java アノテーションライブラリ
[glog](https://github.com/google/glog) | Google | C++ ロギングライブラリ
[double-conversion](https://github.com/google/double-conversion) | Google | C++ binary-decimal convertライブラリ

## 2. Microsoftの管理用と思われるファイル

ファイル / ディレクトリ | 概要
---- | ----
[.appveyor/config.yml](https://github.com/microsoft/react-native-macos/blob/9232ace99d095a793bddf00ffda3238cc7078820/.appveyor/config.yml) | OSにWindowsを使っていることを特徴としたCI、AppVeyorの設定ファイル 
[ReactApple/ReactApple.nuspec](https://github.com/microsoft/react-native-macos/blob/9232ace99d095a793bddf00ffda3238cc7078820/ReactApple/ReactApple.nuspec) | .NET用パッケージNuGetのメタファイル
[android-patches](https://github.com/microsoft/react-native-macos/tree/9232ace99d095a793bddf00ffda3238cc7078820/android-patches) | "patches-droid-office-grouped" というディレクトリから推測すると、AndroidのOffice用のパッチファイルか。
[metadata/repo.json](https://github.com/microsoft/react-native-macos/blob/9232ace99d095a793bddf00ffda3238cc7078820/metadata/repo.json) | リポジトリ管理用のjsonファイル。
[docsList.js](https://github.com/microsoft/react-native-macos/blob/9232ace99d095a793bddf00ffda3238cc7078820/website/server/docsList.js) | Websiteのドキュメント管理用？

### 補足: metadata/repo.json

[metadata/repo.json](https://github.com/microsoft/react-native-macos/blob/9232ace99d095a793bddf00ffda3238cc7078820/metadata/repo.json)

```json
{
  "description": "Fork of facebook's react-native implementation.  Include additional platform implementations for Mac, Win32 and UWP.  And implementation of the JS bridge against Chakra.",
  "schema": {
    "office": "1.0.0"
  },
  "deployedToProduction": true,
  "complianceTypes": [],
  "inventoryId": ["684c3345-709f-474d-9f83-726e63a64237"],
  "contacts": ["acoates@microsoft.com"]
}
```

"description": "Fork of facebook's react-native implementation.  Include additional platform implementations for Mac, Win32 and UWP.  And implementation of the JS bridge against Chakra."

[Chakra](https://github.com/microsoft/ChakraCore)はIEなどで使われていたJSエンジン。Microsoft EdgeはChromiumベースなのでV8なはず。WindowsのJSエンジンとしてのChakraと思われる。

## その他追加されているファイル

ファイル / ディレクトリ | 概要
---- | ----
[danger/dangerfile.js](https://github.com/microsoft/react-native-macos/blob/9232ace99d095a793bddf00ffda3238cc7078820/danger/dangerfile.js) | GitHub拡張用のJSファイル。bots/dangerfile.js のバックアップ?
[jsc](https://github.com/microsoft/react-native-macos/tree/9232ace99d095a793bddf00ffda3238cc7078820/jsc) | Appleが開発したJSエンジンである[JSC ( JavaScriptCore )](https://developer.apple.com/documentation/javascriptcore) のヘッダーファイルたち。initial コミットから修正なし。
[.ado](https://github.com/microsoft/react-native-macos/tree/9232ace99d095a793bddf00ffda3238cc7078820/.ado) | ローカルにnpmレジストリを作成できる [Verdaccio](https://github.com/verdaccio/verdaccio) とCI関連のファイル

# Reactディレクトリ以下の差分

```bash
% diff -rq react-native/React/ react-native-macos/React/ | grep 'Only in react-native-macos'
Only in react-native-macos/React/Base: RCTBridge+Cxx.h
Only in react-native-macos/React/Base: RCTBridge+Cxx.mm
Only in react-native-macos/React/Base: RCTPlatformDisplayLink.h
Only in react-native-macos/React/Base: RCTUIKit.h
Only in react-native-macos/React/Base: macOS
Only in react-native-macos/React/CoreModules: RCTImageEditingManager.h
Only in react-native-macos/React/CoreModules: RCTImageEditingManager.m
Only in react-native-macos/React/CoreModules: RCTImageLoader.h
Only in react-native-macos/React/CoreModules: RCTImageLoader.mm
Only in react-native-macos/React/CoreModules: RCTImageStoreManager.h
Only in react-native-macos/React/CoreModules: RCTImageStoreManager.m
Only in react-native-macos/React/DevSupport: RCTDevLoadingView.h
Only in react-native-macos/React/DevSupport: RCTDevLoadingView.m
Only in react-native-macos/React/DevSupport: RCTDevMenu.h
Only in react-native-macos/React/DevSupport: RCTDevMenu.m
Only in react-native-macos/React/Modules: RCTAccessibilityManager.h
Only in react-native-macos/React/Modules: RCTAccessibilityManager.m
Only in react-native-macos/React/Modules: RCTAlertManager.h
Only in react-native-macos/React/Modules: RCTAlertManager.m
Only in react-native-macos/React/Modules: RCTAppState.h
Only in react-native-macos/React/Modules: RCTAppState.m
Only in react-native-macos/React/Modules: RCTAsyncLocalStorage.h
Only in react-native-macos/React/Modules: RCTAsyncLocalStorage.m
Only in react-native-macos/React/Modules: RCTClipboard.h
Only in react-native-macos/React/Modules: RCTClipboard.m
Only in react-native-macos/React/Modules: RCTDevSettings.h
Only in react-native-macos/React/Modules: RCTDevSettings.mm
Only in react-native-macos/React/Modules: RCTDeviceInfo.h
Only in react-native-macos/React/Modules: RCTDeviceInfo.m
Only in react-native-macos/React/Modules: RCTI18nManager.h
Only in react-native-macos/React/Modules: RCTI18nManager.m
Only in react-native-macos/React/Modules: RCTKeyboardObserver.h
Only in react-native-macos/React/Modules: RCTKeyboardObserver.m
Only in react-native-macos/React/Modules: RCTRedBox.h
Only in react-native-macos/React/Modules: RCTRedBox.m
Only in react-native-macos/React/Modules: RCTSourceCode.h
Only in react-native-macos/React/Modules: RCTSourceCode.m
Only in react-native-macos/React/Modules: RCTStatusBarManager.h
Only in react-native-macos/React/Modules: RCTStatusBarManager.m
Only in react-native-macos/React/Modules: RCTTVNavigationEventEmitter.h
Only in react-native-macos/React/Modules: RCTTVNavigationEventEmitter.m
Only in react-native-macos/React/Modules: RCTTiming.h
Only in react-native-macos/React/Modules: RCTTiming.m
Only in react-native-macos/React/Profiler: RCTFPSGraph.h
Only in react-native-macos/React/Profiler: RCTFPSGraph.m
Only in react-native-macos/React/Profiler: RCTPerfMonitor.m
Only in react-native-macos/React/Views: RCTFontSmoothing.h
Only in react-native-macos/React/Views: RCTModalManager.h
Only in react-native-macos/React/Views: RCTModalManager.m
Only in react-native-macos/React/Views: RCTProgressView.h
Only in react-native-macos/React/Views: RCTProgressView.m
Only in react-native-macos/React/Views: RCTRefreshControl.h
Only in react-native-macos/React/Views: RCTRefreshControl.m
Only in react-native-macos/React/Views: RCTRefreshControlManager.h
Only in react-native-macos/React/Views: RCTRefreshControlManager.m
```

## 概要

macOS用のネイティブライブラリ群が追加されてます。macOSプラットフォーム関連として [React/Base/macOS](https://github.com/microsoft/react-native-macos/tree/9232ace99d095a793bddf00ffda3238cc7078820/React/Base/macOS) ディレクトリが追加されました。


```bash
% ls React/Base/macOS
RCTDynamicColor.h
RCTDynamicColor.m
RCTPlatform.m
RCTPlatformDisplayLink.m
RCTUIKit.m
```

## RCTUIKit.m

React Native はUI描画のOSによる差分を吸収し、同じレイアウト構成(YogaによるFlexbox)を構築することが大きな特徴の一つです。

macOSのUIクラスであるUIKitについて、UIImage / NSImageを扱うために書かれたファイル。

```objective_c
NSImage *UIGraphicsGetImageFromCurrentImageContext(void)
{
	NSImage *image = nil;
	NSGraphicsContext *graphicsContext = [NSGraphicsContext currentContext];

	NSValue *sizeValue = objc_getAssociatedObject(graphicsContext, &RCTGraphicsContextSizeKey);
	if (sizeValue != nil) {
		CGImageRef cgImage = CGBitmapContextCreateImage([graphicsContext CGContext]);

		if (cgImage != NULL) {
			image = [[NSImage alloc] initWithCGImage:cgImage size:[sizeValue sizeValue]];
			CFRelease(cgImage);
		}
	}

	return image;
}

CGFloat UIImageGetScale(NSImage *image)
{
  if (image == nil) {
    return 0.0;
  }
  
  RCTAssert(image.representations.count == 1, @"The scale can only be derived if the image has one representation.");

  NSImageRep *imageRep = image.representations.firstObject;
  if (imageRep != nil) {
    NSSize imageSize = image.size;
    NSSize repSize = CGSizeMake(imageRep.pixelsWide, imageRep.pixelsHigh);

    return round(fmax(repSize.width / imageSize.width, repSize.height / imageSize.height));
  }

  return 1.0;
}
```


# React Native for macOS の歴史

年月 | 出来ごと
---- | ----
2019年3月6日 | [v0.0.1-microsoft.0](https://github.com/microsoft/react-native-macos/releases/tag/v0.0.1-microsoft.0)がリリース
2019年5月7日 | Microsoftが[React Native for Windows](https://jp.techcrunch.com/2019/05/07/2019-05-06-microsoft-launches-react-native-for-windows/)を公開
2020年5月19日 | MicrosoftのReact Native Blogで[React Native for macOSをアナウンス](https://microsoft.github.io/react-native-windows/blog/2020/05/19/rn4mupdadates)