# 👷♂️ Classes and Shared Objects
## Navigation
- [🏡 Native modules made easy with Expo](/gYH9xz-oR2ai0Yih8if50w)
- [👶 First Steps](/ANE6NSUlTSimTIrN-gMsBw)
- [⚙️ Native Module](/mAIt0ctDTvSL5xV4uE9nWQ)
- [📈 Passing data to view](/_gWWp8uoQwGkqKcEyfk8Tg)
- [📚 View Props](/96IjlLNDRvydILdkbfaA5A)
- [🔥 View Events](/PQWXYmxLRCebmLfx3Fh_gg)
- [🏞️ View Functions](/DcjStCFdT6euzWqnJqCL6w)
- [👉 👷♂️ Classes and Shared Objects](/__42gVw8RqiIgfSbVseIvw)
- [📊 Views and shared object](/IgHyIAHQQPCbeBD74Ri4BA)
---
## Classes
### Task 1
Export from `ChartModule` an empty native class the is called `Class`.
:::spoiler :robot_face: Android
:open_file_folder: File `android/src/main/java/expo/modules/workshopscharts/ChartsModule.kt`
```kotlin
Class("Class") {
}
```
:::
:::spoiler :apple: iOS
:open_file_folder: File `ios/ChartsModule.swift`
```swift
Class("Class") {
}
```
:::
<br />
📝 Full changelog: [open GitHub Commit](https://github.com/software-mansion-labs/appjs-2023-workshop-expo-modules/commit/7e91e3e291eec8019af6b4bc9343c0ace588f9c5)
---
### Task 2
Add a native constructor to the exported class. This constructor should have the option to receive an integer parameter and also set the property (named `property`). If no value is provided, the default value of `10` should be used.
:::spoiler :robot_face: Android
:open_file_folder: File `android/src/main/java/expo/modules/workshopscharts/ChartsModule.kt`
```kotlin
Constructor { self: JavaScriptObject, value: Int? ->
self.setProperty("property", value ?: 10)
}
```
:::
:::spoiler :apple: iOS
:open_file_folder: File `ios/ChartsModule.swift`
```swift
Constructor { (this: JavaScriptObject, value: Int?) in
this.setProperty("property", value: value ?? 10)
}
```
:::
<br />
📝 Full changelog: [open GitHub Commit](https://github.com/software-mansion-labs/appjs-2023-workshop-expo-modules/commit/f1b3120006a917079817ea38d4d097df859255a6)
---
### Task 3
Add an async function named `modifyProperty` that will multiply the value of the previously set property by itself.
:::spoiler :robot_face: Android
:open_file_folder: File `android/src/main/java/expo/modules/workshopscharts/ChartsModule.kt`
```kotlin
Function("modifyProperty") { self: JavaScriptObject ->
val p = self.getProperty("property").getInt()
self.setProperty("property", p * p)
}
```
:::
:::spoiler :apple: iOS
:open_file_folder: File `ios/ChartsModule.swift`
```swift
Function("modifyProperty") { (this: JavaScriptObject) in
let p = this.getProperty("property").getInt()
this.setProperty("property", value: p * p)
}
```
:::
<br />
📝 Full changelog: [open GitHub Commit](https://github.com/software-mansion-labs/appjs-2023-workshop-expo-modules/commit/ce81903864c6b8866d8df905f6dad24d8aa8bd55)
---
### Task 4
Create a duplicate of the `modifyProperty` function and make it asynchronous.
:::spoiler :robot_face: Android
:open_file_folder: File `android/src/main/java/expo/modules/workshopscharts/ChartsModule.kt`
```kotlin
AsyncFunction("modifyPropertyAsync") { self: JavaScriptObject, promise: Promise ->
appContext.executeOnJavaScriptThread {
val p = self.getProperty("property").getInt()
self.setProperty("property", p * p)
promise.resolve(null)
}
}
```
:::
:::spoiler :apple: iOS
:open_file_folder: File `ios/ChartsModule.swift`
```swift
AsyncFunction("modifyPropertyAsync") { (this: JavaScriptObject, promise: Promise) in
guard let context = appContext else {
throw Exceptions.AppContextLost()
}
context.executeOnJavaScriptThread {
let p = this.getProperty("property").getInt()
this.setProperty("property", value: p * p)
promise.resolve()
}
}
```
:::
<br />
📝 Full changelog: [open GitHub Commit](https://github.com/software-mansion-labs/appjs-2023-workshop-expo-modules/commit/c89c325700d85eb2546b3917d02c0deebdf60460)
---
### Task 5
Add a function that returns an anonymous object. This object should contain a function called `calculate`, which receives three integers and returns their sum.
:::spoiler :robot_face: Android
:open_file_folder: File `android/src/main/java/expo/modules/workshopscharts/ChartsModule.kt`
```kotlin
Function("createAnonymousObject") {
return@Function Object {
Function("calculate") { a: Int, b: Int, c: Int ->
a + b + c
}
}
}
```
:::
:::spoiler :apple: iOS
:open_file_folder: File `ios/ChartsModule.swift`
```swift
Function("createAnonymousObject") {
Object {
Function("calculate") { (a: Int, b: Int, c: Int) in
a + b + c
}
}
}
```
:::
<br />
📝 Full changelog: [open GitHub Commit](https://github.com/software-mansion-labs/appjs-2023-workshop-expo-modules/commit/89c4e4f09065034c82730f78eb427adad44ff372)
---
## Shared Objects
### Task 6
Create a shared object that represents a list of integers. This object should allow for the addition and retrieval of elements, as well as checking its size.
:::spoiler :robot_face: Android
:open_file_folder: File `android/src/main/java/expo/modules/workshopscharts/ChartsModule.kt`
```kotlin
class SharedList<T> : SharedObject() {
private val data = mutableListOf<T>()
val size: Int
get() = data.size
fun add(newElement: T) {
data.add(newElement)
}
operator fun get(index: Int): T {
return data[index]
}
}
```
:::
:::spoiler :apple: iOS
:open_file_folder: File `ios/ChartsModule.swift`
```swift
class SharedList : SharedObject {
private var data: [Int] = []
var size: Int {
data.count
}
func add(_ newElement: Int) {
data.append(newElement)
}
subscript(index: Int) -> Int {
get {
return data[index]
}
}
}
```
:::
<br />
📝 Full changelog: [open GitHub Commit](https://github.com/software-mansion-labs/appjs-2023-workshop-expo-modules/commit/8d5d3cdebbb1affbf812e4fd853cc41f3eadc8f1)
---
### Task 7
Export a shared list within a native class. The exported structure's JavaScript representation must follow an interface:
```typescript
interface SharedList {
new (): SharedList;
readonly add: (newValue: number) => void;
readonly get: (index: number) => number;
readonly size: () => number;
readonly addAsync: (newValue: number) => Promise<void>;
readonly getAsync: (index: number) => Promise<number>;
readonly sizeAsync: () => Promise<number>;
}
```
:::spoiler :robot_face: Android
:open_file_folder: File `android/src/main/java/expo/modules/workshopscharts/ChartsModule.kt`
```kotlin
Class(SharedList::class) {
Constructor {
return@Constructor SharedList<Int>()
}
Function("add") { sharedObject: SharedList<Int>, newValue: Int ->
sharedObject.add(newValue)
}
Function("get") { sharedObject: SharedList<Int>, index: Int ->
sharedObject[index]
}
Function("size") { sharedObject: SharedList<Int> ->
sharedObject.size
}
AsyncFunction("addAsync") { sharedObject: SharedList<Int>, newValue: Int ->
sharedObject.add(newValue)
}
AsyncFunction("getAsync") { sharedObject: SharedList<Int>, index: Int ->
sharedObject[index]
}
AsyncFunction("sizeAsync") { sharedObject: SharedList<Int> ->
sharedObject.size
}
}
```
:::
:::spoiler :apple: iOS
:open_file_folder: File `ios/ChartsModule.swift`
```swift
Class(SharedList.self) {
Constructor {
return SharedList()
}
Function("add") { (sharedObject: SharedList, newValue: Int) in
sharedObject.add(newValue)
}
Function("get") { (sharedObject: SharedList, index: Int) in
sharedObject[index]
}
Function("size") { (sharedObject: SharedList) in
sharedObject.size
}
AsyncFunction("addAsync") { (sharedObject: SharedList, newValue: Int) in
sharedObject.add(newValue)
}
AsyncFunction("getAsync") { (sharedObject: SharedList, index: Int) in
sharedObject[index]
}
AsyncFunction("sizeAsync") { (sharedObject: SharedList) in
sharedObject.size
}
}
```
:::
<br />
📝 Full changelog: [open GitHub Commit](https://github.com/software-mansion-labs/appjs-2023-workshop-expo-modules/commit/bb42e64a68f83bc91c3876c796af548f8376d164)
---
## [📊 Views and shared object](/IgHyIAHQQPCbeBD74Ri4BA)