@thelacanians/vue-native-cli 0.4.2 → 0.4.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (172) hide show
  1. package/dist/cli.js +43 -23
  2. package/native/android/README.md +205 -0
  3. package/native/android/VueNativeCore/build.gradle.kts +100 -0
  4. package/native/android/VueNativeCore/consumer-rules.pro +12 -0
  5. package/native/android/VueNativeCore/proguard-rules.pro +33 -0
  6. package/native/android/VueNativeCore/src/main/AndroidManifest.xml +17 -0
  7. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Bridge/ErrorOverlayView.kt +94 -0
  8. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Bridge/HotReloadManager.kt +105 -0
  9. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Bridge/JSPolyfills.kt +652 -0
  10. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Bridge/JSRuntime.kt +207 -0
  11. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Bridge/NativeBridge.kt +417 -0
  12. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/ComponentRegistry.kt +76 -0
  13. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VActionSheetFactory.kt +78 -0
  14. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VActivityIndicatorFactory.kt +46 -0
  15. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VAlertDialogFactory.kt +84 -0
  16. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VButtonFactory.kt +73 -0
  17. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VCheckboxFactory.kt +93 -0
  18. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VDropdownFactory.kt +125 -0
  19. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VImageFactory.kt +75 -0
  20. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VInputFactory.kt +210 -0
  21. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VKeyboardAvoidingFactory.kt +31 -0
  22. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VListFactory.kt +183 -0
  23. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VModalFactory.kt +105 -0
  24. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VPickerFactory.kt +57 -0
  25. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VPressableFactory.kt +109 -0
  26. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VProgressBarFactory.kt +43 -0
  27. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VRadioFactory.kt +103 -0
  28. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VRefreshControlFactory.kt +73 -0
  29. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VRootFactory.kt +39 -0
  30. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VSafeAreaFactory.kt +48 -0
  31. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VScrollViewFactory.kt +105 -0
  32. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VSectionListFactory.kt +144 -0
  33. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VSegmentedControlFactory.kt +77 -0
  34. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VSliderFactory.kt +74 -0
  35. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VStatusBarFactory.kt +52 -0
  36. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VSwitchFactory.kt +62 -0
  37. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VTextFactory.kt +53 -0
  38. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VVideoFactory.kt +191 -0
  39. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VViewFactory.kt +48 -0
  40. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/Factories/VWebViewFactory.kt +90 -0
  41. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/NativeComponentFactory.kt +40 -0
  42. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Components/VTextNodeView.kt +23 -0
  43. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Helpers/GestureHelper.kt +16 -0
  44. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Helpers/TouchableView.kt +105 -0
  45. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/AnimationModule.kt +292 -0
  46. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/AppStateModule.kt +41 -0
  47. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/AsyncStorageModule.kt +59 -0
  48. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/AudioModule.kt +331 -0
  49. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/BackgroundTaskModule.kt +166 -0
  50. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/BiometryModule.kt +56 -0
  51. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/BluetoothModule.kt +302 -0
  52. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/CalendarModule.kt +198 -0
  53. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/CameraModule.kt +64 -0
  54. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/ClipboardModule.kt +36 -0
  55. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/ContactsModule.kt +288 -0
  56. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/DatabaseModule.kt +229 -0
  57. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/DeviceInfoModule.kt +39 -0
  58. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/FileSystemModule.kt +193 -0
  59. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/GeolocationModule.kt +68 -0
  60. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/HapticsModule.kt +61 -0
  61. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/HttpModule.kt +111 -0
  62. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/IAPModule.kt +302 -0
  63. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/KeyboardModule.kt +26 -0
  64. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/LinkingModule.kt +43 -0
  65. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/NativeModule.kt +27 -0
  66. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/NativeModuleRegistry.kt +92 -0
  67. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/NetworkModule.kt +75 -0
  68. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/NotificationsModule.kt +181 -0
  69. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/OTAModule.kt +255 -0
  70. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/PerformanceModule.kt +147 -0
  71. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/PermissionsModule.kt +126 -0
  72. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/SecureStorageModule.kt +51 -0
  73. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/SensorsModule.kt +134 -0
  74. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/ShareModule.kt +36 -0
  75. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/SocialAuthModule.kt +160 -0
  76. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Modules/WebSocketModule.kt +155 -0
  77. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Styling/StyleEngine.kt +802 -0
  78. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/Tags.kt +43 -0
  79. package/native/android/VueNativeCore/src/main/kotlin/com/vuenative/core/VueNativeActivity.kt +169 -0
  80. package/native/android/VueNativeCore/src/main/res/values/ids.xml +8 -0
  81. package/native/android/app/build.gradle.kts +45 -0
  82. package/native/android/app/proguard-rules.pro +5 -0
  83. package/native/android/app/src/main/AndroidManifest.xml +25 -0
  84. package/native/android/app/src/main/assets/.gitkeep +0 -0
  85. package/native/android/app/src/main/kotlin/com/vuenative/example/counter/MainActivity.kt +14 -0
  86. package/native/android/app/src/main/res/layout/activity_main.xml +6 -0
  87. package/native/android/app/src/main/res/values/strings.xml +3 -0
  88. package/native/android/app/src/main/res/values/themes.xml +9 -0
  89. package/native/android/app/src/main/res/xml/network_security_config.xml +8 -0
  90. package/native/android/build.gradle.kts +6 -0
  91. package/native/android/gradle/wrapper/gradle-wrapper.jar +0 -0
  92. package/native/android/gradle/wrapper/gradle-wrapper.properties +7 -0
  93. package/native/android/gradle.properties +4 -0
  94. package/native/android/gradlew +87 -0
  95. package/native/android/gradlew.bat +48 -0
  96. package/native/android/settings.gradle.kts +20 -0
  97. package/native/ios/VueNativeCore/Package.resolved +23 -0
  98. package/native/ios/VueNativeCore/Package.swift +32 -0
  99. package/native/ios/VueNativeCore/Sources/VueNativeCore/Bridge/CertificatePinning.swift +132 -0
  100. package/native/ios/VueNativeCore/Sources/VueNativeCore/Bridge/ErrorOverlayView.swift +92 -0
  101. package/native/ios/VueNativeCore/Sources/VueNativeCore/Bridge/HotReloadManager.swift +147 -0
  102. package/native/ios/VueNativeCore/Sources/VueNativeCore/Bridge/JSPolyfills.swift +711 -0
  103. package/native/ios/VueNativeCore/Sources/VueNativeCore/Bridge/JSRuntime.swift +421 -0
  104. package/native/ios/VueNativeCore/Sources/VueNativeCore/Bridge/NativeBridge.swift +891 -0
  105. package/native/ios/VueNativeCore/Sources/VueNativeCore/Bridge/VueNativeViewController.swift +88 -0
  106. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/ComponentRegistry.swift +193 -0
  107. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VActionSheetFactory.swift +91 -0
  108. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VActivityIndicatorFactory.swift +74 -0
  109. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VAlertDialogFactory.swift +150 -0
  110. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VButtonFactory.swift +93 -0
  111. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VCheckboxFactory.swift +114 -0
  112. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VDropdownFactory.swift +112 -0
  113. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VImageFactory.swift +172 -0
  114. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VInputFactory.swift +357 -0
  115. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VKeyboardAvoidingFactory.swift +99 -0
  116. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VListFactory.swift +250 -0
  117. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VModalFactory.swift +112 -0
  118. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VPickerFactory.swift +96 -0
  119. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VPressableFactory.swift +168 -0
  120. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VProgressBarFactory.swift +39 -0
  121. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VRadioFactory.swift +167 -0
  122. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VRefreshControlFactory.swift +153 -0
  123. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VSafeAreaFactory.swift +56 -0
  124. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VScrollViewFactory.swift +240 -0
  125. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VSectionListFactory.swift +248 -0
  126. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VSegmentedControlFactory.swift +73 -0
  127. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VSliderFactory.swift +63 -0
  128. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VStatusBarFactory.swift +50 -0
  129. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VSwitchFactory.swift +108 -0
  130. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VTextFactory.swift +290 -0
  131. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VVideoFactory.swift +246 -0
  132. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VViewFactory.swift +157 -0
  133. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/Factories/VWebViewFactory.swift +172 -0
  134. package/native/ios/VueNativeCore/Sources/VueNativeCore/Components/NativeComponentFactory.swift +53 -0
  135. package/native/ios/VueNativeCore/Sources/VueNativeCore/Helpers/GestureWrapper.swift +107 -0
  136. package/native/ios/VueNativeCore/Sources/VueNativeCore/Helpers/TouchableView.swift +136 -0
  137. package/native/ios/VueNativeCore/Sources/VueNativeCore/Helpers/UIColor+Hex.swift +80 -0
  138. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/AnimationModule.swift +291 -0
  139. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/AppStateModule.swift +65 -0
  140. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/AsyncStorageModule.swift +68 -0
  141. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/AudioModule.swift +366 -0
  142. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/BackgroundTaskModule.swift +135 -0
  143. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/BiometryModule.swift +61 -0
  144. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/BluetoothModule.swift +387 -0
  145. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/CalendarModule.swift +161 -0
  146. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/CameraModule.swift +318 -0
  147. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/ClipboardModule.swift +33 -0
  148. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/ContactsModule.swift +173 -0
  149. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/DatabaseModule.swift +259 -0
  150. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/DeviceInfoModule.swift +34 -0
  151. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/FileSystemModule.swift +233 -0
  152. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/GeolocationModule.swift +147 -0
  153. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/HapticsModule.swift +50 -0
  154. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/IAPModule.swift +194 -0
  155. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/KeyboardModule.swift +31 -0
  156. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/LinkingModule.swift +42 -0
  157. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/NativeModule.swift +28 -0
  158. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/NativeModuleRegistry.swift +78 -0
  159. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/NetworkModule.swift +62 -0
  160. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/NotificationsModule.swift +215 -0
  161. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/OTAModule.swift +281 -0
  162. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/PerformanceModule.swift +138 -0
  163. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/PermissionsModule.swift +190 -0
  164. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/SecureStorageModule.swift +118 -0
  165. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/SensorsModule.swift +103 -0
  166. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/ShareModule.swift +49 -0
  167. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/SocialAuthModule.swift +240 -0
  168. package/native/ios/VueNativeCore/Sources/VueNativeCore/Modules/WebSocketModule.swift +213 -0
  169. package/native/ios/VueNativeCore/Sources/VueNativeCore/Resources/vue-native-placeholder.js +8 -0
  170. package/native/ios/VueNativeCore/Sources/VueNativeCore/Styling/StyleEngine.swift +885 -0
  171. package/native/ios/VueNativeCore/Tests/VueNativeCoreTests/JSRuntimeTests.swift +362 -0
  172. package/package.json +3 -2
@@ -0,0 +1,109 @@
1
+ package com.vuenative.core
2
+
3
+ import android.content.Context
4
+ import android.view.MotionEvent
5
+ import android.view.View
6
+ import android.view.ViewGroup
7
+ import com.google.android.flexbox.FlexboxLayout
8
+
9
+ /**
10
+ * Factory for VPressable — a generic pressable container component.
11
+ *
12
+ * Like VButton but without built-in text/label support. Uses PressableView,
13
+ * a subclass of TouchableView that adds pressIn/pressOut callbacks.
14
+ */
15
+ class VPressableFactory : NativeComponentFactory {
16
+
17
+ override fun createView(context: Context): View {
18
+ return PressableView(context)
19
+ }
20
+
21
+ override fun updateProp(view: View, key: String, value: Any?) {
22
+ val pressable = view as? PressableView
23
+ if (pressable == null) {
24
+ StyleEngine.apply(key, value, view)
25
+ return
26
+ }
27
+
28
+ when (key) {
29
+ "disabled" -> {
30
+ pressable.isDisabled = value == true || value == "true" ||
31
+ (value is Number && value.toInt() != 0)
32
+ }
33
+ "activeOpacity" -> {
34
+ pressable.activeOpacity = when (value) {
35
+ is Double -> value.toFloat()
36
+ is Float -> value
37
+ is Int -> value.toFloat()
38
+ is String -> value.toFloatOrNull() ?: 0.7f
39
+ else -> 0.7f
40
+ }
41
+ }
42
+ else -> StyleEngine.apply(key, value, view)
43
+ }
44
+ }
45
+
46
+ override fun addEventListener(view: View, event: String, handler: (Any?) -> Unit) {
47
+ val pressable = view as? PressableView ?: return
48
+
49
+ when (event) {
50
+ "press" -> pressable.onPress = { handler(null) }
51
+ "longPress", "longpress" -> pressable.onLongPress = { handler(null) }
52
+ "pressIn", "pressin" -> pressable.onPressIn = { handler(null) }
53
+ "pressOut", "pressout" -> pressable.onPressOut = { handler(null) }
54
+ }
55
+ }
56
+
57
+ override fun removeEventListener(view: View, event: String) {
58
+ val pressable = view as? PressableView ?: return
59
+
60
+ when (event) {
61
+ "press" -> pressable.onPress = null
62
+ "longPress", "longpress" -> pressable.onLongPress = null
63
+ "pressIn", "pressin" -> pressable.onPressIn = null
64
+ "pressOut", "pressout" -> pressable.onPressOut = null
65
+ }
66
+ }
67
+
68
+ override fun insertChild(parent: View, child: View, index: Int) {
69
+ val flex = parent as? FlexboxLayout ?: return
70
+ val lp = StyleEngine.buildFlexLayoutParams(child)
71
+ if (index >= flex.childCount) flex.addView(child, lp)
72
+ else flex.addView(child, index, lp)
73
+ }
74
+
75
+ override fun removeChild(parent: View, child: View) {
76
+ (parent as? FlexboxLayout)?.removeView(child)
77
+ }
78
+ }
79
+
80
+ /**
81
+ * Extension of TouchableView that adds pressIn and pressOut callbacks.
82
+ * Fires pressIn when a touch begins and pressOut when the touch ends or is cancelled.
83
+ */
84
+ class PressableView(context: android.content.Context) : TouchableView(context) {
85
+
86
+ /** Called when a touch begins inside the view bounds. */
87
+ var onPressIn: (() -> Unit)? = null
88
+
89
+ /** Called when a touch ends or is cancelled. */
90
+ var onPressOut: (() -> Unit)? = null
91
+
92
+ override fun onTouchEvent(event: MotionEvent): Boolean {
93
+ if (isDisabled) return false
94
+
95
+ when (event.action) {
96
+ MotionEvent.ACTION_DOWN -> {
97
+ onPressIn?.invoke()
98
+ }
99
+ MotionEvent.ACTION_UP -> {
100
+ onPressOut?.invoke()
101
+ }
102
+ MotionEvent.ACTION_CANCEL -> {
103
+ onPressOut?.invoke()
104
+ }
105
+ }
106
+
107
+ return super.onTouchEvent(event)
108
+ }
109
+ }
@@ -0,0 +1,43 @@
1
+ package com.vuenative.core
2
+
3
+ import android.content.Context
4
+ import android.view.View
5
+ import android.view.ViewGroup
6
+ import android.widget.ProgressBar
7
+
8
+ class VProgressBarFactory : NativeComponentFactory {
9
+ override fun createView(context: Context): View {
10
+ return ProgressBar(context, null, android.R.attr.progressBarStyleHorizontal).apply {
11
+ isIndeterminate = false
12
+ max = 1000
13
+ progress = 0
14
+ layoutParams = ViewGroup.LayoutParams(
15
+ ViewGroup.LayoutParams.MATCH_PARENT,
16
+ ViewGroup.LayoutParams.WRAP_CONTENT
17
+ )
18
+ }
19
+ }
20
+
21
+ override fun updateProp(view: View, key: String, value: Any?) {
22
+ val pb = view as? ProgressBar ?: return
23
+ when (key) {
24
+ "progress" -> {
25
+ val f = StyleEngine.toFloat(value, 0f).coerceIn(0f, 1f)
26
+ pb.progress = (f * pb.max).toInt()
27
+ }
28
+ "progressTintColor" -> {
29
+ val color = StyleEngine.parseColor(value) ?: return
30
+ pb.progressTintList = android.content.res.ColorStateList.valueOf(color)
31
+ }
32
+ "trackTintColor" -> {
33
+ val color = StyleEngine.parseColor(value) ?: return
34
+ pb.progressBackgroundTintList = android.content.res.ColorStateList.valueOf(color)
35
+ }
36
+ "animated" -> {} // Android ProgressBar animates by default
37
+ else -> StyleEngine.apply(key, value, view)
38
+ }
39
+ }
40
+
41
+ override fun addEventListener(view: View, event: String, handler: (Any?) -> Unit) {}
42
+ override fun removeEventListener(view: View, event: String) {}
43
+ }
@@ -0,0 +1,103 @@
1
+ package com.vuenative.core
2
+
3
+ import android.content.Context
4
+ import android.view.View
5
+ import android.view.ViewGroup
6
+ import android.widget.RadioButton
7
+ import android.widget.RadioGroup
8
+ import org.json.JSONArray
9
+
10
+ class VRadioFactory : NativeComponentFactory {
11
+ private val changeHandlers = mutableMapOf<RadioGroup, (Any?) -> Unit>()
12
+ private val optionValues = mutableMapOf<RadioGroup, List<String>>()
13
+
14
+ override fun createView(context: Context): View {
15
+ return RadioGroup(context).apply {
16
+ orientation = RadioGroup.VERTICAL
17
+ layoutParams = ViewGroup.LayoutParams(
18
+ ViewGroup.LayoutParams.WRAP_CONTENT,
19
+ ViewGroup.LayoutParams.WRAP_CONTENT
20
+ )
21
+ }
22
+ }
23
+
24
+ override fun updateProp(view: View, key: String, value: Any?) {
25
+ val rg = view as? RadioGroup ?: return
26
+ when (key) {
27
+ "options" -> {
28
+ val items = when (value) {
29
+ is JSONArray -> (0 until value.length()).map { i ->
30
+ val obj = value.getJSONObject(i)
31
+ Pair(obj.optString("label", ""), obj.optString("value", ""))
32
+ }
33
+ is List<*> -> value.filterIsInstance<Map<*, *>>().map { m ->
34
+ Pair(m["label"]?.toString() ?: "", m["value"]?.toString() ?: "")
35
+ }
36
+ else -> emptyList()
37
+ }
38
+ optionValues[rg] = items.map { it.second }
39
+ rg.removeAllViews()
40
+ items.forEachIndexed { i, (label, _) ->
41
+ val btn = RadioButton(rg.context).apply {
42
+ text = label
43
+ id = View.generateViewId()
44
+ setPadding(0, 16, 24, 16)
45
+ }
46
+ rg.addView(btn)
47
+ }
48
+ // Re-apply selection
49
+ applySelection(rg)
50
+ }
51
+ "selectedValue" -> {
52
+ rg.tag = value?.toString()
53
+ applySelection(rg)
54
+ }
55
+ "disabled" -> {
56
+ val disabled = value == true || value == "true"
57
+ rg.isEnabled = !disabled
58
+ rg.alpha = if (disabled) 0.4f else 1.0f
59
+ (0 until rg.childCount).forEach {
60
+ rg.getChildAt(it).isEnabled = !disabled
61
+ }
62
+ }
63
+ "tintColor" -> {
64
+ val color = StyleEngine.parseColor(value) ?: return
65
+ (0 until rg.childCount).forEach { i ->
66
+ (rg.getChildAt(i) as? RadioButton)?.buttonTintList =
67
+ android.content.res.ColorStateList.valueOf(color)
68
+ }
69
+ }
70
+ else -> StyleEngine.apply(key, value, view)
71
+ }
72
+ }
73
+
74
+ override fun addEventListener(view: View, event: String, handler: (Any?) -> Unit) {
75
+ val rg = view as? RadioGroup ?: return
76
+ if (event == "change") {
77
+ changeHandlers[rg] = handler
78
+ rg.setOnCheckedChangeListener { group, checkedId ->
79
+ val idx = (0 until group.childCount).indexOfFirst { group.getChildAt(it).id == checkedId }
80
+ val value = optionValues[group]?.getOrNull(idx) ?: ""
81
+ changeHandlers[group]?.invoke(mapOf("value" to value))
82
+ }
83
+ }
84
+ }
85
+
86
+ override fun removeEventListener(view: View, event: String) {
87
+ val rg = view as? RadioGroup ?: return
88
+ if (event == "change") {
89
+ changeHandlers.remove(rg)
90
+ rg.setOnCheckedChangeListener(null)
91
+ }
92
+ }
93
+
94
+ private fun applySelection(rg: RadioGroup) {
95
+ val selected = rg.tag as? String ?: return
96
+ val values = optionValues[rg] ?: return
97
+ val idx = values.indexOf(selected)
98
+ if (idx >= 0 && idx < rg.childCount) {
99
+ val child = rg.getChildAt(idx) as? RadioButton
100
+ child?.id?.let { rg.check(it) }
101
+ }
102
+ }
103
+ }
@@ -0,0 +1,73 @@
1
+ package com.vuenative.core
2
+
3
+ import android.content.Context
4
+ import android.graphics.Color
5
+ import android.view.View
6
+ import android.view.ViewGroup
7
+ import androidx.swiperefreshlayout.widget.SwipeRefreshLayout
8
+
9
+ /**
10
+ * Factory for VRefreshControl — pull-to-refresh indicator.
11
+ *
12
+ * Creates a SwipeRefreshLayout that wraps its children. When used as a child
13
+ * of VScrollView, the bridge should attach this to the parent's refresh mechanism.
14
+ * For standalone usage, this provides its own SwipeRefreshLayout.
15
+ */
16
+ class VRefreshControlFactory : NativeComponentFactory {
17
+
18
+ override fun createView(context: Context): View {
19
+ // Create a zero-sized invisible view as a marker.
20
+ // The actual refresh behavior is wired by the parent VScrollView.
21
+ val marker = View(context).apply {
22
+ visibility = View.GONE
23
+ layoutParams = ViewGroup.LayoutParams(0, 0)
24
+ }
25
+ return marker
26
+ }
27
+
28
+ override fun updateProp(view: View, key: String, value: Any?) {
29
+ // VRefreshControl props are handled by the parent VScrollView.
30
+ // The bridge forwards refreshing/tintColor to the parent's SwipeRefreshLayout.
31
+ val parent = view.parent as? SwipeRefreshLayout
32
+ when (key) {
33
+ "refreshing" -> {
34
+ parent?.isRefreshing = value == true || value == "true"
35
+ }
36
+ "tintColor" -> {
37
+ val colorStr = value as? String ?: return
38
+ try {
39
+ val color = Color.parseColor(colorStr)
40
+ parent?.setColorSchemeColors(color)
41
+ } catch (_: IllegalArgumentException) {
42
+ // Ignore invalid color strings
43
+ }
44
+ }
45
+ // "title" is iOS-only (UIRefreshControl attributedTitle)
46
+ }
47
+ }
48
+
49
+ override fun addEventListener(view: View, event: String, handler: (Any?) -> Unit) {
50
+ if (event == "refresh") {
51
+ // Store handler on the view for the parent factory to wire up
52
+ view.setTag(TAG_EVENT_HANDLER, handler)
53
+
54
+ // If already inside a SwipeRefreshLayout, wire it up directly
55
+ val parent = view.parent as? SwipeRefreshLayout
56
+ if (parent != null) {
57
+ parent.isEnabled = true
58
+ parent.setOnRefreshListener { handler(null) }
59
+ }
60
+ }
61
+ }
62
+
63
+ override fun removeEventListener(view: View, event: String) {
64
+ if (event == "refresh") {
65
+ view.setTag(TAG_EVENT_HANDLER, null)
66
+ val parent = view.parent as? SwipeRefreshLayout
67
+ if (parent != null) {
68
+ parent.setOnRefreshListener(null)
69
+ parent.isEnabled = false
70
+ }
71
+ }
72
+ }
73
+ }
@@ -0,0 +1,39 @@
1
+ package com.vuenative.core
2
+
3
+ import android.content.Context
4
+ import android.view.View
5
+ import com.google.android.flexbox.FlexDirection
6
+ import com.google.android.flexbox.FlexboxLayout
7
+
8
+ class VRootFactory : NativeComponentFactory {
9
+ override fun createView(context: Context): View {
10
+ return FlexboxLayout(context).apply {
11
+ flexDirection = FlexDirection.COLUMN
12
+ layoutParams = android.view.ViewGroup.LayoutParams(
13
+ android.view.ViewGroup.LayoutParams.MATCH_PARENT,
14
+ android.view.ViewGroup.LayoutParams.MATCH_PARENT
15
+ )
16
+ }
17
+ }
18
+
19
+ override fun updateProp(view: View, key: String, value: Any?) {
20
+ StyleEngine.apply(key, value, view)
21
+ }
22
+
23
+ override fun addEventListener(view: View, event: String, handler: (Any?) -> Unit) {
24
+ if (event == "press") {
25
+ view.setOnClickListener { handler(null) }
26
+ }
27
+ }
28
+
29
+ override fun removeEventListener(view: View, event: String) {
30
+ if (event == "press") view.setOnClickListener(null)
31
+ }
32
+
33
+ override fun insertChild(parent: View, child: View, index: Int) {
34
+ val flex = parent as? FlexboxLayout ?: return
35
+ val lp = StyleEngine.buildFlexLayoutParams(child)
36
+ if (index >= flex.childCount) flex.addView(child, lp)
37
+ else flex.addView(child, index, lp)
38
+ }
39
+ }
@@ -0,0 +1,48 @@
1
+ package com.vuenative.core
2
+
3
+ import android.content.Context
4
+ import android.os.Build
5
+ import android.view.View
6
+ import android.view.ViewGroup
7
+ import android.view.WindowInsets
8
+ import com.google.android.flexbox.FlexDirection
9
+ import com.google.android.flexbox.FlexboxLayout
10
+
11
+ class VSafeAreaFactory : NativeComponentFactory {
12
+ override fun createView(context: Context): View {
13
+ val flex = FlexboxLayout(context).apply {
14
+ flexDirection = FlexDirection.COLUMN
15
+ layoutParams = ViewGroup.LayoutParams(
16
+ ViewGroup.LayoutParams.MATCH_PARENT,
17
+ ViewGroup.LayoutParams.MATCH_PARENT
18
+ )
19
+ }
20
+ // Apply safe area insets
21
+ flex.setOnApplyWindowInsetsListener { v, insets ->
22
+ val top = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
23
+ insets.getInsets(WindowInsets.Type.systemBars()).top
24
+ } else {
25
+ @Suppress("DEPRECATION")
26
+ insets.systemWindowInsetTop
27
+ }
28
+ val bottom = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
29
+ insets.getInsets(WindowInsets.Type.systemBars()).bottom
30
+ } else {
31
+ @Suppress("DEPRECATION")
32
+ insets.systemWindowInsetBottom
33
+ }
34
+ v.setPadding(v.paddingLeft, top, v.paddingRight, bottom)
35
+ insets
36
+ }
37
+ return flex
38
+ }
39
+
40
+ override fun updateProp(view: View, key: String, value: Any?) = StyleEngine.apply(key, value, view)
41
+ override fun addEventListener(view: View, event: String, handler: (Any?) -> Unit) {}
42
+ override fun removeEventListener(view: View, event: String) {}
43
+ override fun insertChild(parent: View, child: View, index: Int) {
44
+ val flex = parent as? FlexboxLayout ?: return
45
+ val lp = StyleEngine.buildFlexLayoutParams(child)
46
+ if (index >= flex.childCount) flex.addView(child, lp) else flex.addView(child, index, lp)
47
+ }
48
+ }
@@ -0,0 +1,105 @@
1
+ package com.vuenative.core
2
+
3
+ import android.content.Context
4
+ import android.view.View
5
+ import android.view.ViewGroup
6
+ import android.widget.ScrollView
7
+ import androidx.swiperefreshlayout.widget.SwipeRefreshLayout
8
+ import com.google.android.flexbox.FlexDirection
9
+ import com.google.android.flexbox.FlexboxLayout
10
+
11
+ class VScrollViewFactory : NativeComponentFactory {
12
+
13
+ // Tracks the inner ScrollView and content FlexboxLayout per SwipeRefreshLayout root
14
+ private data class ScrollState(val scrollView: ScrollView, val content: FlexboxLayout)
15
+ private val states = mutableMapOf<SwipeRefreshLayout, ScrollState>()
16
+
17
+ override fun createView(context: Context): View {
18
+ val content = FlexboxLayout(context).apply {
19
+ flexDirection = FlexDirection.COLUMN
20
+ layoutParams = ViewGroup.LayoutParams(
21
+ ViewGroup.LayoutParams.MATCH_PARENT,
22
+ ViewGroup.LayoutParams.WRAP_CONTENT
23
+ )
24
+ }
25
+ val scroll = ScrollView(context).apply {
26
+ isFillViewport = true
27
+ layoutParams = ViewGroup.LayoutParams(
28
+ ViewGroup.LayoutParams.MATCH_PARENT,
29
+ ViewGroup.LayoutParams.MATCH_PARENT
30
+ )
31
+ }
32
+ scroll.addView(content)
33
+
34
+ val srf = SwipeRefreshLayout(context).apply {
35
+ layoutParams = ViewGroup.LayoutParams(
36
+ ViewGroup.LayoutParams.MATCH_PARENT,
37
+ ViewGroup.LayoutParams.MATCH_PARENT
38
+ )
39
+ // Disabled by default; enabled when @refresh listener is added
40
+ isEnabled = false
41
+ }
42
+ srf.addView(scroll)
43
+ states[srf] = ScrollState(scroll, content)
44
+ return srf
45
+ }
46
+
47
+ override fun updateProp(view: View, key: String, value: Any?) {
48
+ val srf = view as? SwipeRefreshLayout ?: return
49
+ val scroll = states[srf]?.scrollView
50
+ when (key) {
51
+ "refreshing" -> {
52
+ srf.isRefreshing = value == true || value == "true"
53
+ }
54
+ "showsVerticalScrollIndicator" -> {
55
+ scroll?.isVerticalScrollBarEnabled = value != false && value != "false"
56
+ }
57
+ "showsHorizontalScrollIndicator" -> {
58
+ scroll?.isHorizontalScrollBarEnabled = value != false && value != "false"
59
+ }
60
+ "scrollEnabled" -> {
61
+ // ScrollView doesn't expose a direct enable toggle; no-op
62
+ }
63
+ else -> scroll?.let { StyleEngine.apply(key, value, it) }
64
+ }
65
+ }
66
+
67
+ override fun addEventListener(view: View, event: String, handler: (Any?) -> Unit) {
68
+ val srf = view as? SwipeRefreshLayout ?: return
69
+ val scroll = states[srf]?.scrollView
70
+ when (event) {
71
+ "refresh" -> {
72
+ srf.isEnabled = true
73
+ srf.setOnRefreshListener { handler(null) }
74
+ }
75
+ "scroll" -> {
76
+ scroll?.viewTreeObserver?.addOnScrollChangedListener {
77
+ handler(mapOf(
78
+ "contentOffset" to mapOf("x" to scroll.scrollX, "y" to scroll.scrollY)
79
+ ))
80
+ }
81
+ }
82
+ }
83
+ }
84
+
85
+ override fun removeEventListener(view: View, event: String) {
86
+ val srf = view as? SwipeRefreshLayout ?: return
87
+ if (event == "refresh") {
88
+ srf.setOnRefreshListener(null)
89
+ srf.isEnabled = false
90
+ }
91
+ }
92
+
93
+ override fun insertChild(parent: View, child: View, index: Int) {
94
+ val srf = parent as? SwipeRefreshLayout ?: return
95
+ val content = states[srf]?.content ?: return
96
+ val lp = StyleEngine.buildFlexLayoutParams(child)
97
+ if (index >= content.childCount) content.addView(child, lp)
98
+ else content.addView(child, index, lp)
99
+ }
100
+
101
+ override fun removeChild(parent: View, child: View) {
102
+ val srf = parent as? SwipeRefreshLayout ?: return
103
+ states[srf]?.content?.removeView(child)
104
+ }
105
+ }
@@ -0,0 +1,144 @@
1
+ package com.vuenative.core
2
+
3
+ import android.content.Context
4
+ import android.view.View
5
+ import android.view.ViewGroup
6
+ import androidx.recyclerview.widget.LinearLayoutManager
7
+ import androidx.recyclerview.widget.RecyclerView
8
+
9
+ /**
10
+ * Factory for VSectionList — a sectioned list backed by RecyclerView.
11
+ * Children marked with the `__sectionHeader` internal prop are treated as section headers.
12
+ * All other children are regular items grouped under the preceding header.
13
+ */
14
+ class VSectionListFactory : NativeComponentFactory {
15
+ private val childViews = mutableMapOf<RecyclerView, MutableList<View>>()
16
+ private val scrollHandlers = mutableMapOf<RecyclerView, (Any?) -> Unit>()
17
+ private val endReachedHandlers = mutableMapOf<RecyclerView, (Any?) -> Unit>()
18
+ private val scrollListeners = mutableMapOf<RecyclerView, RecyclerView.OnScrollListener>()
19
+ private val firedEndReached = mutableMapOf<RecyclerView, Boolean>()
20
+
21
+ override fun createView(context: Context): View {
22
+ val rv = RecyclerView(context).apply {
23
+ layoutManager = LinearLayoutManager(context)
24
+ layoutParams = ViewGroup.LayoutParams(
25
+ ViewGroup.LayoutParams.MATCH_PARENT,
26
+ ViewGroup.LayoutParams.MATCH_PARENT
27
+ )
28
+ }
29
+ childViews[rv] = mutableListOf()
30
+ firedEndReached[rv] = false
31
+ rv.adapter = VSectionListAdapter(childViews[rv]!!)
32
+ return rv
33
+ }
34
+
35
+ override fun updateProp(view: View, key: String, value: Any?) {
36
+ val rv = view as? RecyclerView ?: return
37
+ when (key) {
38
+ "bounces" -> {
39
+ rv.overScrollMode = if (value == false || value == "false")
40
+ View.OVER_SCROLL_NEVER else View.OVER_SCROLL_ALWAYS
41
+ }
42
+ "showsScrollIndicator" -> {
43
+ val show = value != false && value != "false"
44
+ rv.isVerticalScrollBarEnabled = show
45
+ }
46
+ "stickySectionHeaders" -> {
47
+ // RecyclerView sticky headers would require an ItemDecoration;
48
+ // for now we store the preference but don't implement sticky behavior
49
+ }
50
+ "estimatedItemHeight" -> { /* Used for initial sizing hints */ }
51
+ else -> StyleEngine.apply(key, value, view)
52
+ }
53
+ }
54
+
55
+ override fun addEventListener(view: View, event: String, handler: (Any?) -> Unit) {
56
+ val rv = view as? RecyclerView ?: return
57
+ when (event) {
58
+ "scroll" -> {
59
+ scrollHandlers[rv] = handler
60
+ ensureScrollListener(rv)
61
+ }
62
+ "endReached" -> {
63
+ endReachedHandlers[rv] = handler
64
+ ensureScrollListener(rv)
65
+ }
66
+ }
67
+ }
68
+
69
+ override fun removeEventListener(view: View, event: String) {
70
+ val rv = view as? RecyclerView ?: return
71
+ when (event) {
72
+ "scroll" -> scrollHandlers.remove(rv)
73
+ "endReached" -> endReachedHandlers.remove(rv)
74
+ }
75
+ if (!scrollHandlers.containsKey(rv) && !endReachedHandlers.containsKey(rv)) {
76
+ scrollListeners.remove(rv)?.let { rv.removeOnScrollListener(it) }
77
+ }
78
+ }
79
+
80
+ private fun ensureScrollListener(rv: RecyclerView) {
81
+ if (scrollListeners.containsKey(rv)) return
82
+ var cumulativeX = 0
83
+ var cumulativeY = 0
84
+ val listener = object : RecyclerView.OnScrollListener() {
85
+ override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
86
+ cumulativeX += dx
87
+ cumulativeY += dy
88
+ scrollHandlers[recyclerView]?.invoke(mapOf("x" to cumulativeX, "y" to cumulativeY))
89
+
90
+ val lm = recyclerView.layoutManager as? LinearLayoutManager ?: return
91
+ val totalItems = lm.itemCount
92
+ if (totalItems == 0) return
93
+ val lastVisible = lm.findLastVisibleItemPosition()
94
+ val threshold = (totalItems * 0.2).toInt().coerceAtLeast(1)
95
+
96
+ if (lastVisible >= totalItems - threshold) {
97
+ if (firedEndReached[recyclerView] != true) {
98
+ firedEndReached[recyclerView] = true
99
+ endReachedHandlers[recyclerView]?.invoke(null)
100
+ }
101
+ } else {
102
+ firedEndReached[recyclerView] = false
103
+ }
104
+ }
105
+ }
106
+ scrollListeners[rv] = listener
107
+ rv.addOnScrollListener(listener)
108
+ }
109
+
110
+ override fun insertChild(parent: View, child: View, index: Int) {
111
+ val rv = parent as? RecyclerView ?: return
112
+ val list = childViews[rv] ?: return
113
+ if (index >= list.size) list.add(child) else list.add(index, child)
114
+ rv.adapter?.notifyItemInserted(if (index >= list.size - 1) list.size - 1 else index)
115
+ }
116
+
117
+ override fun removeChild(parent: View, child: View) {
118
+ val rv = parent as? RecyclerView ?: return
119
+ val list = childViews[rv] ?: return
120
+ val idx = list.indexOf(child)
121
+ if (idx >= 0) {
122
+ list.removeAt(idx)
123
+ rv.adapter?.notifyItemRemoved(idx)
124
+ }
125
+ }
126
+ }
127
+
128
+ private class VSectionListAdapter(private val items: List<View>) : RecyclerView.Adapter<VSectionListAdapter.VH>() {
129
+ class VH(val view: View) : RecyclerView.ViewHolder(view)
130
+
131
+ override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): VH {
132
+ val v = items.getOrNull(viewType) ?: android.widget.FrameLayout(parent.context)
133
+ (v.parent as? ViewGroup)?.removeView(v)
134
+ v.layoutParams = RecyclerView.LayoutParams(
135
+ RecyclerView.LayoutParams.MATCH_PARENT,
136
+ RecyclerView.LayoutParams.WRAP_CONTENT
137
+ )
138
+ return VH(v)
139
+ }
140
+
141
+ override fun onBindViewHolder(holder: VH, position: Int) {}
142
+ override fun getItemCount(): Int = items.size
143
+ override fun getItemViewType(position: Int): Int = position
144
+ }