react-native-pdf-jsi 1.0.1
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.
- package/DoubleTapView.js +125 -0
- package/INTEGRATION_GUIDE.md +419 -0
- package/LICENSE +21 -0
- package/PdfManager.js +26 -0
- package/PdfPageView.js +53 -0
- package/PdfView.js +421 -0
- package/PdfViewFlatList.js +30 -0
- package/PinchZoomView.js +125 -0
- package/README.md +693 -0
- package/README_JSI.md +348 -0
- package/android/.gradle/5.6.1/fileChanges/last-build.bin +0 -0
- package/android/.gradle/5.6.1/fileHashes/fileHashes.lock +0 -0
- package/android/.gradle/5.6.1/gc.properties +0 -0
- package/android/.gradle/8.5/checksums/checksums.lock +0 -0
- package/android/.gradle/8.5/checksums/md5-checksums.bin +0 -0
- package/android/.gradle/8.5/checksums/sha1-checksums.bin +0 -0
- package/android/.gradle/8.5/dependencies-accessors/dependencies-accessors.lock +0 -0
- package/android/.gradle/8.5/dependencies-accessors/gc.properties +0 -0
- package/android/.gradle/8.5/executionHistory/executionHistory.lock +0 -0
- package/android/.gradle/8.5/fileChanges/last-build.bin +0 -0
- package/android/.gradle/8.5/fileHashes/fileHashes.lock +0 -0
- package/android/.gradle/8.5/gc.properties +0 -0
- package/android/.gradle/buildOutputCleanup/buildOutputCleanup.lock +0 -0
- package/android/.gradle/buildOutputCleanup/cache.properties +2 -0
- package/android/.gradle/vcs-1/gc.properties +0 -0
- package/android/build.gradle +198 -0
- package/android/gradle/wrapper/gradle-wrapper.jar +0 -0
- package/android/gradle/wrapper/gradle-wrapper.properties +7 -0
- package/android/gradle.properties +2 -0
- package/android/gradlew +249 -0
- package/android/gradlew.bat +92 -0
- package/android/project.properties +12 -0
- package/android/src/main/AndroidManifest.xml +4 -0
- package/android/src/main/cpp/Android.mk +50 -0
- package/android/src/main/cpp/CMakeLists.txt +76 -0
- package/android/src/main/cpp/PDFJSI.cpp +190 -0
- package/android/src/main/cpp/PDFJSI.h +95 -0
- package/android/src/main/cpp/PDFJSIBridge.cpp +32 -0
- package/android/src/main/cpp/PDFJSIModule.cpp +31 -0
- package/android/src/main/java/org/wonday/pdf/EnhancedPdfJSIBridge.java +281 -0
- package/android/src/main/java/org/wonday/pdf/PDFJSIManager.java +317 -0
- package/android/src/main/java/org/wonday/pdf/PDFJSIModule.java +189 -0
- package/android/src/main/java/org/wonday/pdf/PdfManager.java +180 -0
- package/android/src/main/java/org/wonday/pdf/PdfView.java +505 -0
- package/android/src/main/java/org/wonday/pdf/RNPDFPackage.java +43 -0
- package/android/src/main/java/org/wonday/pdf/events/TopChangeEvent.java +26 -0
- package/android/src/main/jniLibs/arm64-v8a/libpdfjsi.so +0 -0
- package/android/src/main/jniLibs/armeabi-v7a/libpdfjsi.so +0 -0
- package/android/src/main/jniLibs/x86/libpdfjsi.so +0 -0
- package/android/src/main/jniLibs/x86_64/libpdfjsi.so +0 -0
- package/android/src/paper/java/com/facebook/react/viewmanagers/RNPDFPdfViewManagerDelegate.java +92 -0
- package/android/src/paper/java/com/facebook/react/viewmanagers/RNPDFPdfViewManagerInterface.java +35 -0
- package/fabric/RNPDFPdfNativeComponent.js +48 -0
- package/index.d.ts +72 -0
- package/index.js +603 -0
- package/index.js.flow +67 -0
- package/ios/RNPDFPdf/PdfManager.h +23 -0
- package/ios/RNPDFPdf/PdfManager.mm +152 -0
- package/ios/RNPDFPdf/RNPDFPdfPageView.h +21 -0
- package/ios/RNPDFPdf/RNPDFPdfPageView.mm +185 -0
- package/ios/RNPDFPdf/RNPDFPdfPageViewManager.h +18 -0
- package/ios/RNPDFPdf/RNPDFPdfPageViewManager.mm +30 -0
- package/ios/RNPDFPdf/RNPDFPdfView.h +63 -0
- package/ios/RNPDFPdf/RNPDFPdfView.mm +1092 -0
- package/ios/RNPDFPdf/RNPDFPdfViewManager.h +18 -0
- package/ios/RNPDFPdf/RNPDFPdfViewManager.mm +68 -0
- package/ios/RNPDFPdf.xcodeproj/project.pbxproj +321 -0
- package/package.json +78 -0
- package/react-native-pdf.podspec +31 -0
- package/src/EnhancedPdfView.js +362 -0
- package/src/PDFJSI.js +519 -0
- package/src/examples/PDFJSIExample.js +296 -0
- package/src/hooks/usePDFJSI.js +346 -0
- package/src/index.js +32 -0
- package/windows/RCTPdf/PropertySheet.props +16 -0
- package/windows/RCTPdf/RCTPdf.def +3 -0
- package/windows/RCTPdf/RCTPdf.vcxproj +180 -0
- package/windows/RCTPdf/RCTPdf.vcxproj.filters +38 -0
- package/windows/RCTPdf/RCTPdfControl.cpp +667 -0
- package/windows/RCTPdf/RCTPdfControl.h +119 -0
- package/windows/RCTPdf/RCTPdfControl.idl +10 -0
- package/windows/RCTPdf/RCTPdfControl.xaml +33 -0
- package/windows/RCTPdf/RCTPdfViewManager.cpp +69 -0
- package/windows/RCTPdf/RCTPdfViewManager.h +51 -0
- package/windows/RCTPdf/ReactPackageProvider.cpp +15 -0
- package/windows/RCTPdf/ReactPackageProvider.h +16 -0
- package/windows/RCTPdf/ReactPackageProvider.idl +9 -0
- package/windows/RCTPdf/packages.config +4 -0
- package/windows/RCTPdf/pch.cpp +1 -0
- package/windows/RCTPdf/pch.h +31 -0
- package/windows/README.md +21 -0
|
@@ -0,0 +1,362 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2025-present, Punith M (punithm300@gmail.com)
|
|
3
|
+
* Enhanced PDF View with JSI integration
|
|
4
|
+
* All rights reserved.
|
|
5
|
+
*
|
|
6
|
+
* Enhanced PDF View component that automatically uses JSI when available
|
|
7
|
+
* Falls back to traditional bridge-based operations when JSI is not available
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
import React, { Component } from 'react';
|
|
11
|
+
import { Platform, Alert } from 'react-native';
|
|
12
|
+
import Pdf from '../index';
|
|
13
|
+
import PDFJSI from './PDFJSI';
|
|
14
|
+
|
|
15
|
+
export default class EnhancedPdfView extends Component {
|
|
16
|
+
constructor(props) {
|
|
17
|
+
super(props);
|
|
18
|
+
|
|
19
|
+
this.state = {
|
|
20
|
+
isJSIAvailable: false,
|
|
21
|
+
jsiInitialized: false,
|
|
22
|
+
pdfData: null,
|
|
23
|
+
renderMode: 'bridge' // 'bridge' or 'jsi'
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
this.initializeJSI();
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
/**
|
|
30
|
+
* Initialize JSI availability check
|
|
31
|
+
*/
|
|
32
|
+
async initializeJSI() {
|
|
33
|
+
try {
|
|
34
|
+
if (Platform.OS === 'android') {
|
|
35
|
+
const isAvailable = await PDFJSI.checkJSIAvailability();
|
|
36
|
+
this.setState({
|
|
37
|
+
isJSIAvailable: isAvailable,
|
|
38
|
+
jsiInitialized: true,
|
|
39
|
+
renderMode: isAvailable ? 'jsi' : 'bridge'
|
|
40
|
+
});
|
|
41
|
+
|
|
42
|
+
if (isAvailable) {
|
|
43
|
+
console.log('📱 EnhancedPdfView: JSI mode enabled - High performance mode active');
|
|
44
|
+
} else {
|
|
45
|
+
console.log('📱 EnhancedPdfView: Bridge mode - Standard performance mode');
|
|
46
|
+
}
|
|
47
|
+
} else {
|
|
48
|
+
this.setState({
|
|
49
|
+
isJSIAvailable: false,
|
|
50
|
+
jsiInitialized: true,
|
|
51
|
+
renderMode: 'bridge'
|
|
52
|
+
});
|
|
53
|
+
console.log('📱 EnhancedPdfView: iOS detected - Using bridge mode');
|
|
54
|
+
}
|
|
55
|
+
} catch (error) {
|
|
56
|
+
console.error('📱 EnhancedPdfView: Error initializing JSI:', error);
|
|
57
|
+
this.setState({
|
|
58
|
+
isJSIAvailable: false,
|
|
59
|
+
jsiInitialized: true,
|
|
60
|
+
renderMode: 'bridge'
|
|
61
|
+
});
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
/**
|
|
66
|
+
* Render PDF page using JSI (high-performance)
|
|
67
|
+
*/
|
|
68
|
+
async renderPageWithJSI(pageNumber, scale = 1.0) {
|
|
69
|
+
if (!this.state.isJSIAvailable) {
|
|
70
|
+
throw new Error('JSI not available');
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
try {
|
|
74
|
+
const { source } = this.props;
|
|
75
|
+
let base64Data = '';
|
|
76
|
+
|
|
77
|
+
// Handle different source types
|
|
78
|
+
if (typeof source === 'string') {
|
|
79
|
+
// Assume it's a URL or file path
|
|
80
|
+
base64Data = source;
|
|
81
|
+
} else if (source && source.uri) {
|
|
82
|
+
base64Data = source.uri;
|
|
83
|
+
} else {
|
|
84
|
+
throw new Error('Invalid PDF source');
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
const pdfId = `pdf_${Date.now()}`;
|
|
88
|
+
const result = await PDFJSI.renderPageDirect(pdfId, pageNumber, scale, base64Data);
|
|
89
|
+
|
|
90
|
+
if (result.success) {
|
|
91
|
+
return result.data;
|
|
92
|
+
} else {
|
|
93
|
+
throw new Error(result.error || 'Failed to render page');
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
} catch (error) {
|
|
97
|
+
console.error('📱 EnhancedPdfView: JSI render error:', error);
|
|
98
|
+
throw error;
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
/**
|
|
103
|
+
* Get page metrics using JSI
|
|
104
|
+
*/
|
|
105
|
+
async getPageMetricsWithJSI(pageNumber) {
|
|
106
|
+
if (!this.state.isJSIAvailable) {
|
|
107
|
+
throw new Error('JSI not available');
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
try {
|
|
111
|
+
const pdfId = `pdf_${Date.now()}`;
|
|
112
|
+
const result = await PDFJSI.getPageMetrics(pdfId, pageNumber);
|
|
113
|
+
|
|
114
|
+
if (result.success) {
|
|
115
|
+
return result.data;
|
|
116
|
+
} else {
|
|
117
|
+
throw new Error(result.error || 'Failed to get page metrics');
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
} catch (error) {
|
|
121
|
+
console.error('📱 EnhancedPdfView: JSI metrics error:', error);
|
|
122
|
+
throw error;
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
/**
|
|
127
|
+
* Preload pages using JSI
|
|
128
|
+
*/
|
|
129
|
+
async preloadPagesWithJSI(startPage, endPage) {
|
|
130
|
+
if (!this.state.isJSIAvailable) {
|
|
131
|
+
throw new Error('JSI not available');
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
try {
|
|
135
|
+
const pdfId = `pdf_${Date.now()}`;
|
|
136
|
+
const success = await PDFJSI.preloadPagesDirect(pdfId, startPage, endPage);
|
|
137
|
+
|
|
138
|
+
if (success) {
|
|
139
|
+
console.log(`📱 EnhancedPdfView: Preloaded pages ${startPage}-${endPage} via JSI`);
|
|
140
|
+
} else {
|
|
141
|
+
throw new Error('Failed to preload pages');
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
return success;
|
|
145
|
+
|
|
146
|
+
} catch (error) {
|
|
147
|
+
console.error('📱 EnhancedPdfView: JSI preload error:', error);
|
|
148
|
+
throw error;
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
/**
|
|
153
|
+
* Search text using JSI
|
|
154
|
+
*/
|
|
155
|
+
async searchTextWithJSI(searchTerm, startPage = 1, endPage = 10) {
|
|
156
|
+
if (!this.state.isJSIAvailable) {
|
|
157
|
+
throw new Error('JSI not available');
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
try {
|
|
161
|
+
const pdfId = `pdf_${Date.now()}`;
|
|
162
|
+
const results = await PDFJSI.searchTextDirect(pdfId, searchTerm, startPage, endPage);
|
|
163
|
+
|
|
164
|
+
console.log(`📱 EnhancedPdfView: Found ${results.length} matches for '${searchTerm}' via JSI`);
|
|
165
|
+
return results;
|
|
166
|
+
|
|
167
|
+
} catch (error) {
|
|
168
|
+
console.error('📱 EnhancedPdfView: JSI search error:', error);
|
|
169
|
+
throw error;
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
/**
|
|
174
|
+
* Get performance metrics
|
|
175
|
+
*/
|
|
176
|
+
async getPerformanceMetrics() {
|
|
177
|
+
try {
|
|
178
|
+
const pdfId = `pdf_${Date.now()}`;
|
|
179
|
+
const metrics = await PDFJSI.getPerformanceMetrics(pdfId);
|
|
180
|
+
return metrics;
|
|
181
|
+
} catch (error) {
|
|
182
|
+
console.error('📱 EnhancedPdfView: Error getting performance metrics:', error);
|
|
183
|
+
return null;
|
|
184
|
+
}
|
|
185
|
+
}
|
|
186
|
+
|
|
187
|
+
/**
|
|
188
|
+
* Get JSI statistics
|
|
189
|
+
*/
|
|
190
|
+
async getJSIStats() {
|
|
191
|
+
try {
|
|
192
|
+
const stats = await PDFJSI.getJSIStats();
|
|
193
|
+
return stats;
|
|
194
|
+
} catch (error) {
|
|
195
|
+
console.error('📱 EnhancedPdfView: Error getting JSI stats:', error);
|
|
196
|
+
return null;
|
|
197
|
+
}
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
/**
|
|
201
|
+
* Clear cache
|
|
202
|
+
*/
|
|
203
|
+
async clearCache(cacheType = 'all') {
|
|
204
|
+
try {
|
|
205
|
+
const pdfId = `pdf_${Date.now()}`;
|
|
206
|
+
const success = await PDFJSI.clearCacheDirect(pdfId, cacheType);
|
|
207
|
+
|
|
208
|
+
if (success) {
|
|
209
|
+
console.log(`📱 EnhancedPdfView: Cache cleared successfully (${cacheType})`);
|
|
210
|
+
}
|
|
211
|
+
|
|
212
|
+
return success;
|
|
213
|
+
} catch (error) {
|
|
214
|
+
console.error('📱 EnhancedPdfView: Error clearing cache:', error);
|
|
215
|
+
return false;
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
|
|
219
|
+
/**
|
|
220
|
+
* Optimize memory
|
|
221
|
+
*/
|
|
222
|
+
async optimizeMemory() {
|
|
223
|
+
try {
|
|
224
|
+
const pdfId = `pdf_${Date.now()}`;
|
|
225
|
+
const success = await PDFJSI.optimizeMemory(pdfId);
|
|
226
|
+
|
|
227
|
+
if (success) {
|
|
228
|
+
console.log('📱 EnhancedPdfView: Memory optimized successfully');
|
|
229
|
+
}
|
|
230
|
+
|
|
231
|
+
return success;
|
|
232
|
+
} catch (error) {
|
|
233
|
+
console.error('📱 EnhancedPdfView: Error optimizing memory:', error);
|
|
234
|
+
return false;
|
|
235
|
+
}
|
|
236
|
+
}
|
|
237
|
+
|
|
238
|
+
/**
|
|
239
|
+
* Set render quality
|
|
240
|
+
*/
|
|
241
|
+
async setRenderQuality(quality) {
|
|
242
|
+
try {
|
|
243
|
+
const pdfId = `pdf_${Date.now()}`;
|
|
244
|
+
const success = await PDFJSI.setRenderQuality(pdfId, quality);
|
|
245
|
+
|
|
246
|
+
if (success) {
|
|
247
|
+
console.log(`📱 EnhancedPdfView: Render quality set to ${quality}`);
|
|
248
|
+
}
|
|
249
|
+
|
|
250
|
+
return success;
|
|
251
|
+
} catch (error) {
|
|
252
|
+
console.error('📱 EnhancedPdfView: Error setting render quality:', error);
|
|
253
|
+
return false;
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
/**
|
|
258
|
+
* Show performance information
|
|
259
|
+
*/
|
|
260
|
+
showPerformanceInfo = async () => {
|
|
261
|
+
try {
|
|
262
|
+
const stats = await this.getJSIStats();
|
|
263
|
+
const metrics = await this.getPerformanceMetrics();
|
|
264
|
+
|
|
265
|
+
const message = `Render Mode: ${this.state.renderMode.toUpperCase()}\n` +
|
|
266
|
+
`JSI Available: ${this.state.isJSIAvailable ? 'Yes' : 'No'}\n` +
|
|
267
|
+
`Performance Level: ${stats?.performanceLevel || 'Standard'}\n` +
|
|
268
|
+
`Direct Memory Access: ${stats?.directMemoryAccess ? 'Yes' : 'No'}`;
|
|
269
|
+
|
|
270
|
+
Alert.alert('Enhanced PDF Performance', message);
|
|
271
|
+
} catch (error) {
|
|
272
|
+
Alert.alert('Performance Info', `Render Mode: ${this.state.renderMode.toUpperCase()}\nJSI Available: ${this.state.isJSIAvailable ? 'Yes' : 'No'}`);
|
|
273
|
+
}
|
|
274
|
+
};
|
|
275
|
+
|
|
276
|
+
render() {
|
|
277
|
+
const { isJSIAvailable, jsiInitialized, renderMode } = this.state;
|
|
278
|
+
|
|
279
|
+
// Add JSI-specific props to the PDF component
|
|
280
|
+
const enhancedProps = {
|
|
281
|
+
...this.props,
|
|
282
|
+
// Add JSI-specific props that can be used by the native component
|
|
283
|
+
jsiEnabled: isJSIAvailable,
|
|
284
|
+
renderMode: renderMode,
|
|
285
|
+
// Add performance tracking props
|
|
286
|
+
enablePerformanceTracking: true,
|
|
287
|
+
// Add cache optimization props
|
|
288
|
+
enableSmartCaching: isJSIAvailable,
|
|
289
|
+
};
|
|
290
|
+
|
|
291
|
+
return (
|
|
292
|
+
<Pdf
|
|
293
|
+
{...enhancedProps}
|
|
294
|
+
ref={this.props.pdfRef}
|
|
295
|
+
/>
|
|
296
|
+
);
|
|
297
|
+
}
|
|
298
|
+
}
|
|
299
|
+
|
|
300
|
+
// Export additional utilities
|
|
301
|
+
export const EnhancedPdfUtils = {
|
|
302
|
+
/**
|
|
303
|
+
* Check if JSI is available
|
|
304
|
+
*/
|
|
305
|
+
async isJSIAvailable() {
|
|
306
|
+
try {
|
|
307
|
+
return await PDFJSI.checkJSIAvailability();
|
|
308
|
+
} catch (error) {
|
|
309
|
+
return false;
|
|
310
|
+
}
|
|
311
|
+
},
|
|
312
|
+
|
|
313
|
+
/**
|
|
314
|
+
* Get performance benchmark
|
|
315
|
+
*/
|
|
316
|
+
async getPerformanceBenchmark() {
|
|
317
|
+
try {
|
|
318
|
+
const stats = await PDFJSI.getJSIStats();
|
|
319
|
+
const history = PDFJSI.getPerformanceHistory();
|
|
320
|
+
|
|
321
|
+
return {
|
|
322
|
+
jsiAvailable: stats?.jsiEnabled || false,
|
|
323
|
+
performanceLevel: stats?.performanceLevel || 'Standard',
|
|
324
|
+
directMemoryAccess: stats?.directMemoryAccess || false,
|
|
325
|
+
bridgeOptimized: stats?.bridgeOptimized || false,
|
|
326
|
+
operationHistory: history
|
|
327
|
+
};
|
|
328
|
+
} catch (error) {
|
|
329
|
+
return {
|
|
330
|
+
jsiAvailable: false,
|
|
331
|
+
performanceLevel: 'Standard',
|
|
332
|
+
directMemoryAccess: false,
|
|
333
|
+
bridgeOptimized: false,
|
|
334
|
+
operationHistory: []
|
|
335
|
+
};
|
|
336
|
+
}
|
|
337
|
+
},
|
|
338
|
+
|
|
339
|
+
/**
|
|
340
|
+
* Clear all caches
|
|
341
|
+
*/
|
|
342
|
+
async clearAllCaches() {
|
|
343
|
+
try {
|
|
344
|
+
const pdfId = `pdf_${Date.now()}`;
|
|
345
|
+
return await PDFJSI.clearCacheDirect(pdfId, 'all');
|
|
346
|
+
} catch (error) {
|
|
347
|
+
return false;
|
|
348
|
+
}
|
|
349
|
+
},
|
|
350
|
+
|
|
351
|
+
/**
|
|
352
|
+
* Optimize all memory
|
|
353
|
+
*/
|
|
354
|
+
async optimizeAllMemory() {
|
|
355
|
+
try {
|
|
356
|
+
const pdfId = `pdf_${Date.now()}`;
|
|
357
|
+
return await PDFJSI.optimizeMemory(pdfId);
|
|
358
|
+
} catch (error) {
|
|
359
|
+
return false;
|
|
360
|
+
}
|
|
361
|
+
}
|
|
362
|
+
};
|