@tarojs/plugin-platform-harmony-ets 4.0.0-beta.113 → 4.0.0-beta.115
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/dist/apis/media/image/index.ts +124 -135
- package/dist/runtime-ets/dom/element/movableView.ts +12 -8
- package/dist/runtime-framework/react/native-page.ts +40 -10
- package/dist/runtime-utils.js +117 -148
- package/dist/runtime-utils.js.map +1 -1
- package/dist/runtime.js +117 -148
- package/dist/runtime.js.map +1 -1
- package/package.json +9 -9
|
@@ -16,8 +16,7 @@ import { Current } from '@tarojs/runtime'
|
|
|
16
16
|
import { isNull } from '@tarojs/shared'
|
|
17
17
|
|
|
18
18
|
import { getSystemInfoSync } from '../../base'
|
|
19
|
-
import { callAsyncFail, callAsyncSuccess,
|
|
20
|
-
import { IMAGE_PERMISSION } from '../../utils/permissions'
|
|
19
|
+
import { callAsyncFail, callAsyncSuccess, temporarilyNotSupport, validateParams } from '../../utils'
|
|
21
20
|
|
|
22
21
|
import type Taro from '@tarojs/taro/types'
|
|
23
22
|
|
|
@@ -113,117 +112,143 @@ async function saveImage(compressedImageData, compressedImageUri) {
|
|
|
113
112
|
|
|
114
113
|
export const compressImage: typeof Taro.compressImage = function (options) {
|
|
115
114
|
return new Promise((resolve, reject) => {
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
const file = fs.openSync(src, fs.OpenMode.READ_ONLY)
|
|
126
|
-
|
|
127
|
-
// const stat = fs.statSync(file.fd)
|
|
128
|
-
// console.log('[Taro] 压缩前图片的大小为:', stat.size)
|
|
129
|
-
|
|
130
|
-
const source = image.createImageSource(file.fd)
|
|
131
|
-
if (isNull(source)) {
|
|
132
|
-
const createImageSourceError = { errMsg: 'compressImage fail: createImageSource has failed.' }
|
|
133
|
-
callAsyncFail(reject, createImageSourceError, options)
|
|
134
|
-
return
|
|
135
|
-
}
|
|
115
|
+
try {
|
|
116
|
+
validateParams('compressImage', options, compressImageSchema)
|
|
117
|
+
} catch (error) {
|
|
118
|
+
const res = { errMsg: error.message }
|
|
119
|
+
return callAsyncFail(reject, res, options)
|
|
120
|
+
}
|
|
121
|
+
const { src, quality = 80, compressedWidth, compressedHeight } = options
|
|
122
|
+
const srcAfterCompress = src.includes('_after_compress') ? src : src.split('.').join('_after_compress.')
|
|
123
|
+
const file = fs.openSync(src, fs.OpenMode.READ_ONLY)
|
|
136
124
|
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
let wantWidth = compressedWidth || compressedHeight || 0
|
|
140
|
-
let wantHeight = compressedHeight || compressedWidth || 0
|
|
125
|
+
// const stat = fs.statSync(file.fd)
|
|
126
|
+
// console.log('[Taro] 压缩前图片的大小为:', stat.size)
|
|
141
127
|
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
128
|
+
const source = image.createImageSource(file.fd)
|
|
129
|
+
if (isNull(source)) {
|
|
130
|
+
const createImageSourceError = { errMsg: 'compressImage fail: createImageSource has failed.' }
|
|
131
|
+
callAsyncFail(reject, createImageSourceError, options)
|
|
132
|
+
return
|
|
133
|
+
}
|
|
146
134
|
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
135
|
+
const width = source.getImageInfoSync().size.width
|
|
136
|
+
const height = source.getImageInfoSync().size.height
|
|
137
|
+
let wantWidth = compressedWidth || compressedHeight || 0
|
|
138
|
+
let wantHeight = compressedHeight || compressedWidth || 0
|
|
150
139
|
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
140
|
+
if (width > wantWidth || height > wantHeight) {
|
|
141
|
+
const heightRatio = height / wantHeight
|
|
142
|
+
const widthRatio = width / wantWidth
|
|
143
|
+
const finalRatio = heightRatio < widthRatio ? heightRatio : widthRatio
|
|
144
|
+
|
|
145
|
+
wantWidth = Math.round(width / finalRatio)
|
|
146
|
+
wantHeight = Math.round(height / finalRatio)
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
const decodingOptions = {
|
|
150
|
+
editable: true,
|
|
151
|
+
desiredPixelFormat: image.PixelMapFormat.RGBA_8888,
|
|
152
|
+
desiredSize: { width: wantWidth, height: wantHeight }
|
|
153
|
+
}
|
|
154
|
+
source.createPixelMap(decodingOptions, (error, pixelMap) => {
|
|
155
|
+
if (error !== undefined) {
|
|
156
|
+
fs.closeSync(file)
|
|
157
|
+
const res = { errMsg: error }
|
|
158
|
+
callAsyncFail(reject, res, options)
|
|
159
|
+
} else {
|
|
160
|
+
const packer = image.createImagePacker(file.fd)
|
|
161
|
+
if (isNull(packer)) {
|
|
158
162
|
fs.closeSync(file)
|
|
159
|
-
const
|
|
160
|
-
callAsyncFail(reject,
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
if (isNull(packer)) {
|
|
164
|
-
fs.closeSync(file)
|
|
165
|
-
const createImagePackerError = { errMsg: 'compressImage fail: createImagePacker has failed.' }
|
|
166
|
-
callAsyncFail(reject, createImagePackerError, options)
|
|
167
|
-
return
|
|
168
|
-
}
|
|
163
|
+
const createImagePackerError = { errMsg: 'compressImage fail: createImagePacker has failed.' }
|
|
164
|
+
callAsyncFail(reject, createImagePackerError, options)
|
|
165
|
+
return
|
|
166
|
+
}
|
|
169
167
|
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
}
|
|
175
|
-
packer.packing(pixelMap, packingOptionsOHOS).then((value) => {
|
|
176
|
-
fs.closeSync(file)
|
|
177
|
-
saveImage(value, srcAfterCompress).then(result => {
|
|
178
|
-
callAsyncSuccess(resolve, { tempFilePath: result.imageUri }, options)
|
|
179
|
-
})
|
|
180
|
-
}).catch((error) => {
|
|
181
|
-
fs.closeSync(file)
|
|
182
|
-
callAsyncFail(reject, error, options)
|
|
183
|
-
})
|
|
168
|
+
const isPNG = src.endsWith('.png')
|
|
169
|
+
const packingOptionsOHOS: IPackingOptionOHOS = {
|
|
170
|
+
format: isPNG ? 'image/png' : 'image/jpeg',
|
|
171
|
+
quality: quality
|
|
184
172
|
}
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
173
|
+
packer.packing(pixelMap, packingOptionsOHOS).then((value) => {
|
|
174
|
+
fs.closeSync(file)
|
|
175
|
+
saveImage(value, srcAfterCompress).then(result => {
|
|
176
|
+
callAsyncSuccess(resolve, { tempFilePath: result.imageUri }, options)
|
|
177
|
+
})
|
|
178
|
+
}).catch((error) => {
|
|
179
|
+
fs.closeSync(file)
|
|
180
|
+
callAsyncFail(reject, error, options)
|
|
181
|
+
})
|
|
182
|
+
}
|
|
189
183
|
})
|
|
190
184
|
})
|
|
191
185
|
}
|
|
192
186
|
|
|
193
187
|
export const chooseImage: typeof Taro.chooseImage = function (options) {
|
|
194
188
|
return new Promise((resolve, reject) => {
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
}
|
|
189
|
+
try {
|
|
190
|
+
validateParams('chooseImage', options, chooseImageSchema)
|
|
191
|
+
} catch (error) {
|
|
192
|
+
const res = { errMsg: error.message }
|
|
193
|
+
return callAsyncFail(reject, res, options)
|
|
194
|
+
}
|
|
202
195
|
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
196
|
+
const { count = 9 } = options
|
|
197
|
+
const photoViewPicker = new picker.PhotoViewPicker()
|
|
198
|
+
let sizeType = options.sizeType
|
|
206
199
|
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
200
|
+
if (!sizeType || !sizeType.length) {
|
|
201
|
+
sizeType = ['compressed', 'original']
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
photoSelectOptions.maxSelectNumber = count // 选择媒体文件的最大数目
|
|
205
|
+
photoSelectOptions.MIMEType = picker.PhotoViewMIMETypes.IMAGE_TYPE // 过滤选择媒体文件类型为IMAGE
|
|
206
|
+
|
|
207
|
+
photoViewPicker.select(photoSelectOptions).then((photoSelectResult) => {
|
|
208
|
+
const result: IChooseImageData = {}
|
|
209
|
+
const isOrigin = photoSelectResult.isOriginalPhoto
|
|
210
210
|
|
|
211
|
-
|
|
212
|
-
|
|
211
|
+
if (isOrigin) {
|
|
212
|
+
const tempFilePaths: string[] = []
|
|
213
|
+
const tempFiles = photoSelectResult.photoUris.map(uri => {
|
|
214
|
+
const file = fs.openSync(uri, fs.OpenMode.READ_ONLY)
|
|
215
|
+
const stat = fs.statSync(file.fd)
|
|
216
|
+
const size = stat.size
|
|
213
217
|
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
218
|
+
fs.closeSync(file)
|
|
219
|
+
tempFilePaths.push(uri)
|
|
220
|
+
|
|
221
|
+
return {
|
|
222
|
+
size,
|
|
223
|
+
path: uri,
|
|
224
|
+
}
|
|
225
|
+
})
|
|
226
|
+
|
|
227
|
+
result.tempFiles = tempFiles
|
|
228
|
+
result.tempFilePaths = tempFilePaths
|
|
229
|
+
|
|
230
|
+
callAsyncSuccess(resolve, result, options)
|
|
231
|
+
} else {
|
|
232
|
+
const actions: Promise<string>[] = photoSelectResult.photoUris.map(uri => {
|
|
233
|
+
return new Promise<string>(resolve => {
|
|
234
|
+
compressImage({
|
|
235
|
+
src: uri,
|
|
236
|
+
compressedWidth: getSystemInfoSync().screenWidth / 2,
|
|
237
|
+
compressedHeight: getSystemInfoSync().screenHeight / 2,
|
|
238
|
+
success: (compressResult) => {
|
|
239
|
+
resolve(compressResult.tempFilePath)
|
|
240
|
+
}
|
|
241
|
+
})
|
|
242
|
+
})
|
|
243
|
+
})
|
|
217
244
|
|
|
218
|
-
|
|
219
|
-
const tempFilePaths
|
|
220
|
-
const tempFiles = photoSelectResult.photoUris.map(uri => {
|
|
245
|
+
Promise.all(actions).then(tempFilePaths => {
|
|
246
|
+
const tempFiles = tempFilePaths.map(uri => {
|
|
221
247
|
const file = fs.openSync(uri, fs.OpenMode.READ_ONLY)
|
|
222
248
|
const stat = fs.statSync(file.fd)
|
|
223
|
-
const size = stat.size
|
|
249
|
+
const size: number = stat.size
|
|
224
250
|
|
|
225
251
|
fs.closeSync(file)
|
|
226
|
-
tempFilePaths.push(uri)
|
|
227
252
|
|
|
228
253
|
return {
|
|
229
254
|
size,
|
|
@@ -231,53 +256,17 @@ export const chooseImage: typeof Taro.chooseImage = function (options) {
|
|
|
231
256
|
}
|
|
232
257
|
})
|
|
233
258
|
|
|
234
|
-
result.tempFiles = tempFiles
|
|
235
259
|
result.tempFilePaths = tempFilePaths
|
|
260
|
+
result.tempFiles = tempFiles
|
|
236
261
|
|
|
237
262
|
callAsyncSuccess(resolve, result, options)
|
|
238
|
-
}
|
|
239
|
-
const
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
success: (compressResult) => {
|
|
246
|
-
resolve(compressResult.tempFilePath)
|
|
247
|
-
}
|
|
248
|
-
})
|
|
249
|
-
})
|
|
250
|
-
})
|
|
251
|
-
|
|
252
|
-
Promise.all(actions).then(tempFilePaths => {
|
|
253
|
-
const tempFiles = tempFilePaths.map(uri => {
|
|
254
|
-
const file = fs.openSync(uri, fs.OpenMode.READ_ONLY)
|
|
255
|
-
const stat = fs.statSync(file.fd)
|
|
256
|
-
const size: number = stat.size
|
|
257
|
-
|
|
258
|
-
fs.closeSync(file)
|
|
259
|
-
|
|
260
|
-
return {
|
|
261
|
-
size,
|
|
262
|
-
path: uri,
|
|
263
|
-
}
|
|
264
|
-
})
|
|
265
|
-
|
|
266
|
-
result.tempFilePaths = tempFilePaths
|
|
267
|
-
result.tempFiles = tempFiles
|
|
268
|
-
|
|
269
|
-
callAsyncSuccess(resolve, result, options)
|
|
270
|
-
}).catch(error => {
|
|
271
|
-
const res = { errMsg: error }
|
|
272
|
-
return callAsyncFail(reject, res, options)
|
|
273
|
-
})
|
|
274
|
-
}
|
|
275
|
-
}).catch((error) => {
|
|
276
|
-
callAsyncFail(reject, error, options)
|
|
277
|
-
})
|
|
278
|
-
}, (error: string) => {
|
|
279
|
-
const res = { errMsg: error }
|
|
280
|
-
return callAsyncFail(reject, res, options)
|
|
263
|
+
}).catch(error => {
|
|
264
|
+
const res = { errMsg: error }
|
|
265
|
+
return callAsyncFail(reject, res, options)
|
|
266
|
+
})
|
|
267
|
+
}
|
|
268
|
+
}).catch((error) => {
|
|
269
|
+
callAsyncFail(reject, error, options)
|
|
281
270
|
})
|
|
282
271
|
})
|
|
283
272
|
}
|
|
@@ -231,14 +231,18 @@ export class TaroMovableViewElement extends TaroElement<MovableViewProps & { ani
|
|
|
231
231
|
public callTouchEventFnFromGesture(eventName: string, gestureEvent: GestureEvent) {
|
|
232
232
|
const touchFns = (this?.__listeners?.[eventName] || []) as Function[]
|
|
233
233
|
touchFns.forEach(fn => {
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
234
|
+
try {
|
|
235
|
+
fn({
|
|
236
|
+
_hmEvent: gestureEvent,
|
|
237
|
+
target: this,
|
|
238
|
+
changedTouches: gestureEvent.fingerList.map(finger => ({
|
|
239
|
+
clientX: finger.globalX,
|
|
240
|
+
clientY: finger.globalY
|
|
241
|
+
}))
|
|
242
|
+
})
|
|
243
|
+
} catch (error) {
|
|
244
|
+
console.error(error)
|
|
245
|
+
}
|
|
242
246
|
})
|
|
243
247
|
}
|
|
244
248
|
}
|
|
@@ -29,10 +29,11 @@ interface InitNativeComponentEntryParams {
|
|
|
29
29
|
cb?: TFunc
|
|
30
30
|
// 是否使用默认的 DOM 入口 - app;默认为true,false的时候,会创建一个新的dom并且把它挂载在 app 下面
|
|
31
31
|
isDefaultEntryDom?: boolean
|
|
32
|
+
isUseReact18?: boolean
|
|
32
33
|
}
|
|
33
34
|
|
|
34
35
|
function initNativeComponentEntry (params: InitNativeComponentEntryParams) {
|
|
35
|
-
const { R, ReactDOM, cb, isDefaultEntryDom = true } = params
|
|
36
|
+
const { R, ReactDOM, cb, isDefaultEntryDom = true, isUseReact18 = false } = params
|
|
36
37
|
interface IEntryState {
|
|
37
38
|
components: {
|
|
38
39
|
compId: string
|
|
@@ -134,14 +135,23 @@ function initNativeComponentEntry (params: InitNativeComponentEntryParams) {
|
|
|
134
135
|
}),
|
|
135
136
|
}
|
|
136
137
|
|
|
137
|
-
|
|
138
|
+
if (isUseReact18) {
|
|
139
|
+
ReactDOM.flushSync(() => {
|
|
140
|
+
this.setState(
|
|
141
|
+
{
|
|
142
|
+
components: [...this.state.components, item],
|
|
143
|
+
},
|
|
144
|
+
() => cb && cb()
|
|
145
|
+
)
|
|
146
|
+
})
|
|
147
|
+
} else {
|
|
138
148
|
this.setState(
|
|
139
149
|
{
|
|
140
150
|
components: [...this.state.components, item],
|
|
141
151
|
},
|
|
142
152
|
() => cb && cb()
|
|
143
153
|
)
|
|
144
|
-
}
|
|
154
|
+
}
|
|
145
155
|
}
|
|
146
156
|
|
|
147
157
|
unmount (compId, cb?) {
|
|
@@ -149,7 +159,20 @@ function initNativeComponentEntry (params: InitNativeComponentEntryParams) {
|
|
|
149
159
|
const index = components.findIndex((item) => item.compId === compId)
|
|
150
160
|
const next = [...components.slice(0, index), ...components.slice(index + 1)]
|
|
151
161
|
|
|
152
|
-
|
|
162
|
+
|
|
163
|
+
if (isUseReact18) {
|
|
164
|
+
ReactDOM.flushSync(() => {
|
|
165
|
+
this.setState(
|
|
166
|
+
{
|
|
167
|
+
components: next,
|
|
168
|
+
},
|
|
169
|
+
() => {
|
|
170
|
+
removePageInstance(compId)
|
|
171
|
+
cb && cb()
|
|
172
|
+
}
|
|
173
|
+
)
|
|
174
|
+
})
|
|
175
|
+
} else {
|
|
153
176
|
this.setState(
|
|
154
177
|
{
|
|
155
178
|
components: next,
|
|
@@ -159,7 +182,7 @@ function initNativeComponentEntry (params: InitNativeComponentEntryParams) {
|
|
|
159
182
|
cb && cb()
|
|
160
183
|
}
|
|
161
184
|
)
|
|
162
|
-
}
|
|
185
|
+
}
|
|
163
186
|
}
|
|
164
187
|
|
|
165
188
|
render () {
|
|
@@ -180,11 +203,16 @@ function initNativeComponentEntry (params: InitNativeComponentEntryParams) {
|
|
|
180
203
|
app = nativeApp
|
|
181
204
|
}
|
|
182
205
|
|
|
183
|
-
|
|
206
|
+
if (isUseReact18) {
|
|
207
|
+
const root = ReactDOM.createRoot(app)
|
|
184
208
|
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
209
|
+
ReactDOM.flushSync(() => {
|
|
210
|
+
root.render?.(h(Entry))
|
|
211
|
+
})
|
|
212
|
+
} else {
|
|
213
|
+
// eslint-disable-next-line react/no-deprecated
|
|
214
|
+
ReactDOM.render(h(Entry, {}), app)
|
|
215
|
+
}
|
|
188
216
|
}
|
|
189
217
|
|
|
190
218
|
|
|
@@ -273,6 +301,7 @@ export function createNativePageConfig (
|
|
|
273
301
|
initNativeComponentEntry({
|
|
274
302
|
R: react,
|
|
275
303
|
ReactDOM,
|
|
304
|
+
isUseReact18: pageConfig?.isUseReact18,
|
|
276
305
|
cb: () => {
|
|
277
306
|
Current.app!.mount!(Component, $taroPath, () => this, mountCallback)
|
|
278
307
|
},
|
|
@@ -397,7 +426,7 @@ export function createNativeComponentConfig (
|
|
|
397
426
|
h = react.createElement
|
|
398
427
|
ReactDOM = reactdom
|
|
399
428
|
setReconciler(ReactDOM)
|
|
400
|
-
const { isNewBlended } = componentConfig
|
|
429
|
+
const { isNewBlended, isUseReact18 } = componentConfig
|
|
401
430
|
|
|
402
431
|
const componentObj: Record<string, any> = {
|
|
403
432
|
options: componentConfig,
|
|
@@ -434,6 +463,7 @@ export function createNativeComponentConfig (
|
|
|
434
463
|
R: react,
|
|
435
464
|
ReactDOM,
|
|
436
465
|
isDefaultEntryDom: !isNewBlended,
|
|
466
|
+
isUseReact18,
|
|
437
467
|
cb: mountComponent,
|
|
438
468
|
})
|
|
439
469
|
} else {
|