@bluebillywig/react-native-bb-player 8.42.15 → 8.45.0

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 (55) hide show
  1. package/README.md +80 -59
  2. package/android/build.gradle +2 -1
  3. package/android/src/main/java/com/bluebillywig/bbplayer/BBPlayerModule.kt +146 -28
  4. package/android/src/main/java/com/bluebillywig/bbplayer/BBPlayerView.kt +74 -165
  5. package/android/src/main/java/com/bluebillywig/bbplayer/BBPlayerViewManager.kt +0 -6
  6. package/android/src/paper/java/com/bluebillywig/bbplayer/NativeBBPlayerModuleSpec.java +19 -8
  7. package/ios/BBPlayerModule.mm +17 -8
  8. package/ios/BBPlayerModule.swift +193 -31
  9. package/ios/BBPlayerView.swift +141 -132
  10. package/ios/BBPlayerViewManager.m +0 -2
  11. package/ios/BBPlayerViewManager.swift +8 -0
  12. package/lib/commonjs/BBModalPlayer.js +21 -0
  13. package/lib/commonjs/BBModalPlayer.js.map +1 -0
  14. package/lib/commonjs/BBOutstreamView.js +0 -1
  15. package/lib/commonjs/BBOutstreamView.js.map +1 -1
  16. package/lib/commonjs/BBPlayerView.js +0 -1
  17. package/lib/commonjs/BBPlayerView.js.map +1 -1
  18. package/lib/commonjs/NativeCommands.js +24 -24
  19. package/lib/commonjs/NativeCommands.js.map +1 -1
  20. package/lib/commonjs/index.js +9 -1
  21. package/lib/commonjs/index.js.map +1 -1
  22. package/lib/commonjs/specs/NativeBBPlayerModule.js.map +1 -1
  23. package/lib/module/BBModalPlayer.js +17 -0
  24. package/lib/module/BBModalPlayer.js.map +1 -0
  25. package/lib/module/BBOutstreamView.js +0 -1
  26. package/lib/module/BBOutstreamView.js.map +1 -1
  27. package/lib/module/BBPlayerView.js +0 -1
  28. package/lib/module/BBPlayerView.js.map +1 -1
  29. package/lib/module/NativeCommands.js +24 -24
  30. package/lib/module/NativeCommands.js.map +1 -1
  31. package/lib/module/index.js +1 -0
  32. package/lib/module/index.js.map +1 -1
  33. package/lib/module/specs/NativeBBPlayerModule.js.map +1 -1
  34. package/lib/typescript/src/BBModalPlayer.d.ts +13 -0
  35. package/lib/typescript/src/BBModalPlayer.d.ts.map +1 -0
  36. package/lib/typescript/src/BBOutstreamView.d.ts.map +1 -1
  37. package/lib/typescript/src/BBPlayer.types.d.ts +24 -20
  38. package/lib/typescript/src/BBPlayer.types.d.ts.map +1 -1
  39. package/lib/typescript/src/BBPlayerView.d.ts +0 -2
  40. package/lib/typescript/src/BBPlayerView.d.ts.map +1 -1
  41. package/lib/typescript/src/NativeCommands.d.ts +8 -9
  42. package/lib/typescript/src/NativeCommands.d.ts.map +1 -1
  43. package/lib/typescript/src/index.d.ts +2 -0
  44. package/lib/typescript/src/index.d.ts.map +1 -1
  45. package/lib/typescript/src/specs/NativeBBPlayerModule.d.ts +13 -8
  46. package/lib/typescript/src/specs/NativeBBPlayerModule.d.ts.map +1 -1
  47. package/package.json +8 -11
  48. package/src/BBModalPlayer.ts +32 -0
  49. package/src/BBOutstreamView.tsx +0 -1
  50. package/src/BBPlayer.types.ts +31 -17
  51. package/src/BBPlayerView.tsx +0 -12
  52. package/src/NativeCommands.ts +37 -26
  53. package/src/index.ts +2 -0
  54. package/src/specs/NativeBBPlayerModule.ts +25 -8
  55. package/android/proguard-rules.pro +0 -59
@@ -8,6 +8,21 @@ import type {
8
8
  State,
9
9
  } from "./types";
10
10
 
11
+ /**
12
+ * Context for playlist/collection navigation.
13
+ * Enables "next up" list and proper playlist navigation in the player.
14
+ */
15
+ export type LoadContext = {
16
+ /** Context entity type (always 'MediaClipList' for playlists) */
17
+ contextEntityType?: 'MediaClipList';
18
+ /** Playlist ID for "next up" list */
19
+ contextEntityId?: string;
20
+ /** Context collection type (always 'MediaClipList' for collections) */
21
+ contextCollectionType?: 'MediaClipList';
22
+ /** Collection ID if playing within a collection */
23
+ contextCollectionId?: string;
24
+ };
25
+
11
26
  /**
12
27
  * Options for loading a clip via loadClip()
13
28
  */
@@ -20,6 +35,8 @@ export type LoadClipOptions = {
20
35
  seekTo?: number;
21
36
  /** Initiator identifier for analytics */
22
37
  initiator?: string;
38
+ /** Playlist/collection context for navigation */
39
+ context?: LoadContext;
23
40
  };
24
41
 
25
42
  /**
@@ -74,43 +91,48 @@ export type BBPlayerViewMethods = {
74
91
  clipId: string,
75
92
  initiator?: string,
76
93
  autoPlay?: boolean,
77
- seekTo?: number
94
+ seekTo?: number,
95
+ context?: LoadContext
78
96
  ) => void;
79
97
  loadWithClipListId: (
80
98
  clipListId: string,
81
99
  initiator?: string,
82
100
  autoPlay?: boolean,
83
- seekTo?: number
101
+ seekTo?: number,
102
+ context?: LoadContext
84
103
  ) => void;
85
104
  loadWithProjectId: (
86
105
  projectId: string,
87
106
  initiator?: string,
88
107
  autoPlay?: boolean,
89
- seekTo?: number
108
+ seekTo?: number,
109
+ context?: LoadContext
90
110
  ) => void;
91
111
  loadWithClipJson: (
92
112
  clipJson: string,
93
113
  initiator?: string,
94
114
  autoPlay?: boolean,
95
- seekTo?: number
115
+ seekTo?: number,
116
+ context?: LoadContext
96
117
  ) => void;
97
118
  loadWithClipListJson: (
98
119
  clipListJson: string,
99
120
  initiator?: string,
100
121
  autoPlay?: boolean,
101
- seekTo?: number
122
+ seekTo?: number,
123
+ context?: LoadContext
102
124
  ) => void;
103
125
  loadWithProjectJson: (
104
126
  projectJson: string,
105
127
  initiator?: string,
106
128
  autoPlay?: boolean,
107
- seekTo?: number
129
+ seekTo?: number,
130
+ context?: LoadContext
108
131
  ) => void;
109
- loadWithJsonUrl: (jsonUrl: string, autoPlay?: boolean) => void;
132
+ loadWithJsonUrl: (jsonUrl: string, autoPlay?: boolean, context?: LoadContext) => void;
110
133
 
111
134
  // Getter methods (async)
112
135
  getDuration: () => Promise<number | null>;
113
- getCurrentTime: () => Promise<number | null>;
114
136
  getMuted: () => Promise<boolean | null>;
115
137
  getVolume: () => Promise<number | null>;
116
138
  getPhase: () => Promise<string | null>;
@@ -140,7 +162,7 @@ export type BBPlayerViewMethods = {
140
162
  * const state = await playerRef.current?.getPlayerState();
141
163
  * if (state) {
142
164
  * console.log(`Playing: ${state.state === 'PLAYING'}`);
143
- * console.log(`Progress: ${state.currentTime}/${state.duration}`);
165
+ * console.log(`Duration: ${state.duration}`);
144
166
  * }
145
167
  */
146
168
  getPlayerState: () => Promise<BBPlayerState | null>;
@@ -165,10 +187,6 @@ export type BBPlayerViewProps = {
165
187
  * JSON URL to load player configuration from.
166
188
  */
167
189
  jsonUrl?: string;
168
- /**
169
- * Enable periodic time update events (onDidTriggerTimeUpdate).
170
- */
171
- enableTimeUpdates?: boolean;
172
190
  onDidFailWithError?: (error: string) => void;
173
191
  onDidRequestCollapse?: () => void;
174
192
  onDidRequestExpand?: () => void;
@@ -205,7 +223,6 @@ export type BBPlayerViewProps = {
205
223
  onDidTriggerSeeking?: () => void;
206
224
  onDidTriggerStall?: () => void;
207
225
  onDidTriggerStateChange?: (state: State) => void;
208
- onDidTriggerTimeUpdate?: (currentTime: number, duration: number) => void;
209
226
  onDidTriggerViewFinished?: () => void;
210
227
  onDidTriggerViewStarted?: () => void;
211
228
  onDidTriggerVolumeChange?: (volume: number) => void;
@@ -226,8 +243,6 @@ export type BBPlayerState = {
226
243
  phase: Phase;
227
244
  /** Current playback mode */
228
245
  mode: string | null;
229
- /** Current playback position in seconds */
230
- currentTime: number;
231
246
  /** Total duration in seconds */
232
247
  duration: number;
233
248
  /** Whether audio is muted */
@@ -264,7 +279,6 @@ export type BBPlayerEventPayloads = {
264
279
  stateChange: { state: State };
265
280
  phaseChange: { phase: Phase };
266
281
  modeChange: { mode: string };
267
- timeUpdate: { currentTime: number; duration: number };
268
282
  durationChange: { duration: number };
269
283
  volumeChange: { volume: number; muted: boolean };
270
284
  seeked: { position: number };
@@ -82,9 +82,6 @@ type NativeBBPlayerViewProps = Override<
82
82
  onDidTriggerStateChange?: (
83
83
  event: NativeSyntheticEvent<{ state: State }>
84
84
  ) => void;
85
- onDidTriggerTimeUpdate?: (
86
- event: NativeSyntheticEvent<{ currentTime: number; duration: number }>
87
- ) => void;
88
85
  onDidTriggerViewFinished?: (event: NativeSyntheticEvent<{}>) => void;
89
86
  onDidTriggerViewStarted?: (event: NativeSyntheticEvent<{}>) => void;
90
87
  onDidTriggerVolumeChange?: (
@@ -310,15 +307,6 @@ const BBPlayerView = forwardRef<BBPlayerViewMethods, BBPlayerViewProps>(
310
307
  props.onDidTriggerStateChange?.(event.nativeEvent.state)
311
308
  : undefined
312
309
  }
313
- onDidTriggerTimeUpdate={
314
- props.onDidTriggerTimeUpdate
315
- ? (event) =>
316
- props.onDidTriggerTimeUpdate?.(
317
- event.nativeEvent.currentTime,
318
- event.nativeEvent.duration
319
- )
320
- : undefined
321
- }
322
310
  onDidTriggerViewFinished={
323
311
  props.onDidTriggerViewFinished
324
312
  ? () => props.onDidTriggerViewFinished?.()
@@ -1,6 +1,6 @@
1
1
  import { NativeModules, findNodeHandle } from "react-native";
2
2
 
3
- import type { LoadClipOptions, BBPlayerState } from "./BBPlayer.types";
3
+ import type { LoadClipOptions, LoadContext, BBPlayerState } from "./BBPlayer.types";
4
4
  import type { State, Phase } from "./types";
5
5
 
6
6
  // Try TurboModule first, fallback to legacy NativeModules
@@ -110,12 +110,14 @@ export function createCommands(viewRef: React.RefObject<any>) {
110
110
  const tag = getViewTag(viewRef);
111
111
  if (tag != null) {
112
112
  // Use loadWithClipId under the hood, passing playout as initiator if provided
113
+ const contextJson = options?.context ? JSON.stringify(options.context) : null;
113
114
  BBPlayerModule?.loadWithClipId(
114
115
  tag,
115
116
  clipId,
116
117
  options?.initiator ?? options?.playout ?? null,
117
118
  options?.autoPlay ?? false,
118
- options?.seekTo ?? 0
119
+ options?.seekTo ?? 0,
120
+ contextJson
119
121
  );
120
122
  }
121
123
  },
@@ -125,16 +127,19 @@ export function createCommands(viewRef: React.RefObject<any>) {
125
127
  clipId: string,
126
128
  initiator?: string,
127
129
  autoPlay?: boolean,
128
- seekTo?: number
130
+ seekTo?: number,
131
+ context?: LoadContext
129
132
  ) => {
130
133
  const tag = getViewTag(viewRef);
131
134
  if (tag != null) {
135
+ const contextJson = context ? JSON.stringify(context) : null;
132
136
  BBPlayerModule?.loadWithClipId(
133
137
  tag,
134
138
  clipId,
135
139
  initiator ?? null,
136
140
  autoPlay ?? false,
137
- seekTo ?? 0
141
+ seekTo ?? 0,
142
+ contextJson
138
143
  );
139
144
  }
140
145
  },
@@ -142,16 +147,19 @@ export function createCommands(viewRef: React.RefObject<any>) {
142
147
  clipListId: string,
143
148
  initiator?: string,
144
149
  autoPlay?: boolean,
145
- seekTo?: number
150
+ seekTo?: number,
151
+ context?: LoadContext
146
152
  ) => {
147
153
  const tag = getViewTag(viewRef);
148
154
  if (tag != null) {
155
+ const contextJson = context ? JSON.stringify(context) : null;
149
156
  BBPlayerModule?.loadWithClipListId(
150
157
  tag,
151
158
  clipListId,
152
159
  initiator ?? null,
153
160
  autoPlay ?? false,
154
- seekTo ?? 0
161
+ seekTo ?? 0,
162
+ contextJson
155
163
  );
156
164
  }
157
165
  },
@@ -159,16 +167,19 @@ export function createCommands(viewRef: React.RefObject<any>) {
159
167
  projectId: string,
160
168
  initiator?: string,
161
169
  autoPlay?: boolean,
162
- seekTo?: number
170
+ seekTo?: number,
171
+ context?: LoadContext
163
172
  ) => {
164
173
  const tag = getViewTag(viewRef);
165
174
  if (tag != null) {
175
+ const contextJson = context ? JSON.stringify(context) : null;
166
176
  BBPlayerModule?.loadWithProjectId(
167
177
  tag,
168
178
  projectId,
169
179
  initiator ?? null,
170
180
  autoPlay ?? false,
171
- seekTo ?? 0
181
+ seekTo ?? 0,
182
+ contextJson
172
183
  );
173
184
  }
174
185
  },
@@ -176,16 +187,19 @@ export function createCommands(viewRef: React.RefObject<any>) {
176
187
  clipJson: string,
177
188
  initiator?: string,
178
189
  autoPlay?: boolean,
179
- seekTo?: number
190
+ seekTo?: number,
191
+ context?: LoadContext
180
192
  ) => {
181
193
  const tag = getViewTag(viewRef);
182
194
  if (tag != null) {
195
+ const contextJson = context ? JSON.stringify(context) : null;
183
196
  BBPlayerModule?.loadWithClipJson(
184
197
  tag,
185
198
  clipJson,
186
199
  initiator ?? null,
187
200
  autoPlay ?? false,
188
- seekTo ?? 0
201
+ seekTo ?? 0,
202
+ contextJson
189
203
  );
190
204
  }
191
205
  },
@@ -193,16 +207,19 @@ export function createCommands(viewRef: React.RefObject<any>) {
193
207
  clipListJson: string,
194
208
  initiator?: string,
195
209
  autoPlay?: boolean,
196
- seekTo?: number
210
+ seekTo?: number,
211
+ context?: LoadContext
197
212
  ) => {
198
213
  const tag = getViewTag(viewRef);
199
214
  if (tag != null) {
215
+ const contextJson = context ? JSON.stringify(context) : null;
200
216
  BBPlayerModule?.loadWithClipListJson(
201
217
  tag,
202
218
  clipListJson,
203
219
  initiator ?? null,
204
220
  autoPlay ?? false,
205
- seekTo ?? 0
221
+ seekTo ?? 0,
222
+ contextJson
206
223
  );
207
224
  }
208
225
  },
@@ -210,23 +227,27 @@ export function createCommands(viewRef: React.RefObject<any>) {
210
227
  projectJson: string,
211
228
  initiator?: string,
212
229
  autoPlay?: boolean,
213
- seekTo?: number
230
+ seekTo?: number,
231
+ context?: LoadContext
214
232
  ) => {
215
233
  const tag = getViewTag(viewRef);
216
234
  if (tag != null) {
235
+ const contextJson = context ? JSON.stringify(context) : null;
217
236
  BBPlayerModule?.loadWithProjectJson(
218
237
  tag,
219
238
  projectJson,
220
239
  initiator ?? null,
221
240
  autoPlay ?? false,
222
- seekTo ?? 0
241
+ seekTo ?? 0,
242
+ contextJson
223
243
  );
224
244
  }
225
245
  },
226
- loadWithJsonUrl: (jsonUrl: string, autoPlay?: boolean) => {
246
+ loadWithJsonUrl: (jsonUrl: string, autoPlay?: boolean, context?: LoadContext) => {
227
247
  const tag = getViewTag(viewRef);
228
248
  if (tag != null) {
229
- BBPlayerModule?.loadWithJsonUrl(tag, jsonUrl, autoPlay ?? true);
249
+ const contextJson = context ? JSON.stringify(context) : null;
250
+ BBPlayerModule?.loadWithJsonUrl(tag, jsonUrl, autoPlay ?? true, contextJson);
230
251
  }
231
252
  },
232
253
 
@@ -240,13 +261,6 @@ export function createCommands(viewRef: React.RefObject<any>) {
240
261
  }
241
262
  return null;
242
263
  },
243
- getCurrentTime: async (): Promise<number | null> => {
244
- const tag = getViewTag(viewRef);
245
- if (tag != null && BBPlayerModule?.getCurrentTime) {
246
- return BBPlayerModule.getCurrentTime(tag);
247
- }
248
- return null;
249
- },
250
264
  getMuted: async (): Promise<boolean | null> => {
251
265
  const tag = getViewTag(viewRef);
252
266
  if (tag != null && BBPlayerModule?.getMuted) {
@@ -330,7 +344,6 @@ export function createCommands(viewRef: React.RefObject<any>) {
330
344
  state,
331
345
  phase,
332
346
  mode,
333
- currentTime,
334
347
  duration,
335
348
  muted,
336
349
  volume,
@@ -341,7 +354,6 @@ export function createCommands(viewRef: React.RefObject<any>) {
341
354
  BBPlayerModule.getState?.(tag) ?? null,
342
355
  BBPlayerModule.getPhase?.(tag) ?? null,
343
356
  BBPlayerModule.getMode?.(tag) ?? null,
344
- BBPlayerModule.getCurrentTime?.(tag) ?? 0,
345
357
  BBPlayerModule.getDuration?.(tag) ?? 0,
346
358
  BBPlayerModule.getMuted?.(tag) ?? false,
347
359
  BBPlayerModule.getVolume?.(tag) ?? 1,
@@ -354,7 +366,6 @@ export function createCommands(viewRef: React.RefObject<any>) {
354
366
  state: (state as State) ?? "IDLE",
355
367
  phase: (phase as Phase) ?? "INIT",
356
368
  mode: mode ?? null,
357
- currentTime: currentTime ?? 0,
358
369
  duration: duration ?? 0,
359
370
  muted: muted ?? false,
360
371
  volume: volume ?? 1,
package/src/index.ts CHANGED
@@ -2,6 +2,8 @@
2
2
  export { default as BBPlayerView } from "./BBPlayerView";
3
3
  export { default as BBShortsView } from "./BBShortsView";
4
4
  export { default as BBOutstreamView } from "./BBOutstreamView";
5
+ export { BBModalPlayer } from "./BBModalPlayer";
6
+ export type { ModalPlayerOptions } from "./BBModalPlayer";
5
7
  export * from "./BBPlayer.types";
6
8
  export * from "./BBShortsView"; // Export BBShortsView types
7
9
  export * from "./BBOutstreamView"; // Export BBOutstreamView types
@@ -19,6 +19,10 @@ export interface Spec extends TurboModule {
19
19
  collapse(viewTag: number): void;
20
20
  expand(viewTag: number): void;
21
21
 
22
+ // Void methods - modal control (per-view)
23
+ presentModal(viewTag: number): void;
24
+ closeModal(viewTag: number): void;
25
+
22
26
  // Void methods - other commands
23
27
  autoPlayNextCancel(viewTag: number): void;
24
28
  destroy(viewTag: number): void;
@@ -30,48 +34,53 @@ export interface Spec extends TurboModule {
30
34
  clipId: string,
31
35
  initiator: string | null,
32
36
  autoPlay: boolean,
33
- seekTo: number
37
+ seekTo: number,
38
+ contextJson: string | null
34
39
  ): void;
35
40
  loadWithClipListId(
36
41
  viewTag: number,
37
42
  clipListId: string,
38
43
  initiator: string | null,
39
44
  autoPlay: boolean,
40
- seekTo: number
45
+ seekTo: number,
46
+ contextJson: string | null
41
47
  ): void;
42
48
  loadWithProjectId(
43
49
  viewTag: number,
44
50
  projectId: string,
45
51
  initiator: string | null,
46
52
  autoPlay: boolean,
47
- seekTo: number
53
+ seekTo: number,
54
+ contextJson: string | null
48
55
  ): void;
49
56
  loadWithClipJson(
50
57
  viewTag: number,
51
58
  clipJson: string,
52
59
  initiator: string | null,
53
60
  autoPlay: boolean,
54
- seekTo: number
61
+ seekTo: number,
62
+ contextJson: string | null
55
63
  ): void;
56
64
  loadWithClipListJson(
57
65
  viewTag: number,
58
66
  clipListJson: string,
59
67
  initiator: string | null,
60
68
  autoPlay: boolean,
61
- seekTo: number
69
+ seekTo: number,
70
+ contextJson: string | null
62
71
  ): void;
63
72
  loadWithProjectJson(
64
73
  viewTag: number,
65
74
  projectJson: string,
66
75
  initiator: string | null,
67
76
  autoPlay: boolean,
68
- seekTo: number
77
+ seekTo: number,
78
+ contextJson: string | null
69
79
  ): void;
70
- loadWithJsonUrl(viewTag: number, jsonUrl: string, autoPlay: boolean): void;
80
+ loadWithJsonUrl(viewTag: number, jsonUrl: string, autoPlay: boolean, contextJson: string | null): void;
71
81
 
72
82
  // Promise getters
73
83
  getDuration(viewTag: number): Promise<number | null>;
74
- getCurrentTime(viewTag: number): Promise<number | null>;
75
84
  getMuted(viewTag: number): Promise<boolean | null>;
76
85
  getVolume(viewTag: number): Promise<number | null>;
77
86
  getPhase(viewTag: number): Promise<string | null>;
@@ -80,6 +89,14 @@ export interface Spec extends TurboModule {
80
89
  getClipData(viewTag: number): Promise<Object | null>;
81
90
  getProjectData(viewTag: number): Promise<Object | null>;
82
91
  getPlayoutData(viewTag: number): Promise<Object | null>;
92
+
93
+ // Modal player (module-level, no React view needed)
94
+ presentModalPlayer(jsonUrl: string, optionsJson: string | null): void;
95
+ dismissModalPlayer(): void;
96
+
97
+ // Event emitter support (required for NativeEventEmitter)
98
+ addListener(eventName: string): void;
99
+ removeListeners(count: number): void;
83
100
  }
84
101
 
85
102
  // Use get() instead of getEnforcing() to avoid crash when module not registered
@@ -1,59 +0,0 @@
1
- # Expo BB Player ProGuard Rules
2
- # Optimizations for release builds
3
-
4
- # Keep Blue Billywig Native Player SDK classes
5
- -keep class com.bluebillywig.** { *; }
6
- -keep interface com.bluebillywig.** { *; }
7
- -keepclassmembers class com.bluebillywig.** { *; }
8
-
9
- # Keep Blue Billywig Native Shared classes
10
- -keep class com.bluebillywig.bbnativeshared.** { *; }
11
- -keep interface com.bluebillywig.bbnativeshared.** { *; }
12
-
13
- # Keep Expo BB Player module classes
14
- -keep class expo.modules.bbplayer.** { *; }
15
- -keep interface expo.modules.bbplayer.** { *; }
16
-
17
- # Keep Expo Modules API classes that are accessed via reflection
18
- -keep class expo.modules.kotlin.** { *; }
19
- -keepclassmembers class expo.modules.kotlin.** { *; }
20
-
21
- # Keep delegate interfaces and their implementations
22
- -keep class * implements com.bluebillywig.bbnativeplayersdk.BBNativePlayerViewDelegate { *; }
23
-
24
- # Keep enum classes used by the SDK
25
- -keepclassmembers enum com.bluebillywig.bbnativeshared.enums.** { *; }
26
-
27
- # Keep model classes that are serialized/deserialized
28
- -keepclassmembers class com.bluebillywig.bbnativeshared.model.** { *; }
29
-
30
- # Remove debug logging in release builds (already guarded by BuildConfig.DEBUG)
31
- -assumenosideeffects class android.util.Log {
32
- public static *** d(...);
33
- public static *** v(...);
34
- public static *** i(...);
35
- }
36
-
37
- # Optimize - but not aggressively to avoid breaking functionality
38
- -optimizations !code/simplification/arithmetic,!code/simplification/cast,!field/*,!class/merging/*
39
- -optimizationpasses 5
40
- -allowaccessmodification
41
-
42
- # Keep line numbers for better crash reports
43
- -keepattributes SourceFile,LineNumberTable
44
-
45
- # Keep annotations
46
- -keepattributes *Annotation*
47
-
48
- # Keep native methods
49
- -keepclasseswithmembernames class * {
50
- native <methods>;
51
- }
52
-
53
- # Keep custom view constructors (required for Android layout inflation)
54
- -keepclasseswithmembers class * {
55
- public <init>(android.content.Context, android.util.AttributeSet);
56
- }
57
- -keepclasseswithmembers class * {
58
- public <init>(android.content.Context, android.util.AttributeSet, int);
59
- }