pixy meta upgrade/cleanup

This commit is contained in:
Thibault Deckers 2024-01-29 00:00:23 +01:00
parent 743f8f72f9
commit 73d99e9687
3 changed files with 49 additions and 37 deletions

View file

@ -236,7 +236,7 @@ dependencies {
implementation 'com.github.deckerst:Android-TiffBitmapFactory:90c06eebf4' implementation 'com.github.deckerst:Android-TiffBitmapFactory:90c06eebf4'
implementation 'com.github.deckerst.mp4parser:isoparser:4cc0c5d06c' implementation 'com.github.deckerst.mp4parser:isoparser:4cc0c5d06c'
implementation 'com.github.deckerst.mp4parser:muxer:4cc0c5d06c' implementation 'com.github.deckerst.mp4parser:muxer:4cc0c5d06c'
implementation 'com.github.deckerst:pixymeta-android:706bd73d6e' implementation 'com.github.deckerst:pixymeta-android:9ec7097f17'
// huawei flavor only // huawei flavor only
huaweiImplementation "com.huawei.agconnect:agconnect-core:$huawei_agconnect_version" huaweiImplementation "com.huawei.agconnect:agconnect-core:$huawei_agconnect_version"

View file

@ -1,5 +1,7 @@
package deckers.thibault.aves.metadata package deckers.thibault.aves.metadata
import android.content.Context
import android.net.Uri
import deckers.thibault.aves.metadata.Metadata.TYPE_COMMENT import deckers.thibault.aves.metadata.Metadata.TYPE_COMMENT
import deckers.thibault.aves.metadata.Metadata.TYPE_EXIF import deckers.thibault.aves.metadata.Metadata.TYPE_EXIF
import deckers.thibault.aves.metadata.Metadata.TYPE_ICC_PROFILE import deckers.thibault.aves.metadata.Metadata.TYPE_ICC_PROFILE
@ -10,6 +12,8 @@ import deckers.thibault.aves.metadata.Metadata.TYPE_JPEG_DUCKY
import deckers.thibault.aves.metadata.Metadata.TYPE_PHOTOSHOP_IRB import deckers.thibault.aves.metadata.Metadata.TYPE_PHOTOSHOP_IRB
import deckers.thibault.aves.metadata.Metadata.TYPE_XMP import deckers.thibault.aves.metadata.Metadata.TYPE_XMP
import deckers.thibault.aves.model.FieldMap import deckers.thibault.aves.model.FieldMap
import deckers.thibault.aves.utils.MimeTypes
import deckers.thibault.aves.utils.StorageUtils
import pixy.meta.meta.Metadata import pixy.meta.meta.Metadata
import pixy.meta.meta.MetadataEntry import pixy.meta.meta.MetadataEntry
import pixy.meta.meta.MetadataType import pixy.meta.meta.MetadataType
@ -19,6 +23,7 @@ import pixy.meta.meta.iptc.IPTCRecord
import pixy.meta.meta.jpeg.JPGMeta import pixy.meta.meta.jpeg.JPGMeta
import pixy.meta.meta.xmp.XMP import pixy.meta.meta.xmp.XMP
import pixy.meta.string.XMLUtils import pixy.meta.string.XMLUtils
import java.io.File
import java.io.InputStream import java.io.InputStream
import java.io.OutputStream import java.io.OutputStream
import java.util.* import java.util.*
@ -105,6 +110,48 @@ object PixyMetaHelper {
fun XMP.extendedXmpDocString(): String = XMLUtils.serializeToString(extendedXmpDocument) fun XMP.extendedXmpDocString(): String = XMLUtils.serializeToString(extendedXmpDocument)
fun copyIptcXmp(
context: Context,
sourceMimeType: String,
sourceUri: Uri,
targetMimeType: String,
targetUri: Uri,
editableFile: File,
) {
var pixyIptc: IPTC? = null
var pixyXmp: XMP? = null
if (MimeTypes.canReadWithPixyMeta(sourceMimeType)) {
StorageUtils.openInputStream(context, sourceUri)?.use { input ->
val metadata = Metadata.readMetadata(input)
if (MimeTypes.canEditIptc(targetMimeType)) {
pixyIptc = metadata[MetadataType.IPTC] as IPTC?
}
if (MimeTypes.canEditXmp(targetMimeType)) {
pixyXmp = metadata[MetadataType.XMP] as XMP?
}
}
}
if (pixyIptc != null || pixyXmp != null) {
editableFile.outputStream().use { output ->
if (pixyIptc != null) {
// reopen input to read from start
StorageUtils.openInputStream(context, targetUri)?.use { input ->
val iptcs = pixyIptc!!.dataSets.flatMap { it.value }
Metadata.insertIPTC(input, output, iptcs)
}
}
if (pixyXmp != null) {
// reopen input to read from start
StorageUtils.openInputStream(context, targetUri)?.use { input ->
val xmpString = pixyXmp!!.xmpDocString()
val extendedXmp = if (pixyXmp!!.hasExtendedXmp()) pixyXmp!!.extendedXmpDocString() else null
setXmp(input, output, xmpString, if (targetMimeType == MimeTypes.JPEG) extendedXmp else null)
}
}
}
}
}
fun removeMetadata(input: InputStream, output: OutputStream, metadataTypes: Set<String>) { fun removeMetadata(input: InputStream, output: OutputStream, metadataTypes: Set<String>) {
val types = metadataTypes.map(::toMetadataType).toTypedArray() val types = metadataTypes.map(::toMetadataType).toTypedArray()
Metadata.removeMetadata(input, output, *types) Metadata.removeMetadata(input, output, *types)

View file

@ -53,15 +53,12 @@ import deckers.thibault.aves.utils.MimeTypes.canEditExif
import deckers.thibault.aves.utils.MimeTypes.canEditIptc import deckers.thibault.aves.utils.MimeTypes.canEditIptc
import deckers.thibault.aves.utils.MimeTypes.canEditXmp import deckers.thibault.aves.utils.MimeTypes.canEditXmp
import deckers.thibault.aves.utils.MimeTypes.canReadWithExifInterface import deckers.thibault.aves.utils.MimeTypes.canReadWithExifInterface
import deckers.thibault.aves.utils.MimeTypes.canReadWithPixyMeta
import deckers.thibault.aves.utils.MimeTypes.canRemoveMetadata import deckers.thibault.aves.utils.MimeTypes.canRemoveMetadata
import deckers.thibault.aves.utils.MimeTypes.extensionFor import deckers.thibault.aves.utils.MimeTypes.extensionFor
import deckers.thibault.aves.utils.MimeTypes.isVideo import deckers.thibault.aves.utils.MimeTypes.isVideo
import deckers.thibault.aves.utils.StorageUtils import deckers.thibault.aves.utils.StorageUtils
import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.withContext import kotlinx.coroutines.withContext
import pixy.meta.meta.Metadata
import pixy.meta.meta.MetadataType
import java.io.ByteArrayInputStream import java.io.ByteArrayInputStream
import java.io.File import java.io.File
import java.io.FileOutputStream import java.io.FileOutputStream
@ -405,39 +402,7 @@ abstract class ImageProvider {
} }
// copy IPTC / XMP via PixyMeta // copy IPTC / XMP via PixyMeta
PixyMetaHelper.copyIptcXmp(context, sourceMimeType, sourceUri, targetMimeType, targetUri, editableFile)
var pixyIptc: pixy.meta.meta.iptc.IPTC? = null
var pixyXmp: pixy.meta.meta.xmp.XMP? = null
if (canReadWithPixyMeta(sourceMimeType)) {
StorageUtils.openInputStream(context, sourceUri)?.use { input ->
val metadata = Metadata.readMetadata(input)
if (canEditIptc(targetMimeType)) {
pixyIptc = metadata[MetadataType.IPTC] as pixy.meta.meta.iptc.IPTC?
}
if (canEditXmp(targetMimeType)) {
pixyXmp = metadata[MetadataType.XMP] as pixy.meta.meta.xmp.XMP?
}
}
}
if (pixyIptc != null || pixyXmp != null) {
editableFile.outputStream().use { output ->
if (pixyIptc != null) {
// reopen input to read from start
StorageUtils.openInputStream(context, targetUri)?.use { input ->
val iptcs = pixyIptc!!.dataSets.flatMap { it.value }
Metadata.insertIPTC(input, output, iptcs)
}
}
if (pixyXmp != null) {
// reopen input to read from start
StorageUtils.openInputStream(context, targetUri)?.use { input ->
val xmpString = pixyXmp!!.xmpDocString()
val extendedXmp = if (pixyXmp!!.hasExtendedXmp()) pixyXmp!!.extendedXmpDocString() else null
PixyMetaHelper.setXmp(input, output, xmpString, if (targetMimeType == MimeTypes.JPEG) extendedXmp else null)
}
}
}
}
// copy Exif via ExifInterface // copy Exif via ExifInterface