如何从Firebase加载WhatsApp Sticker?

时间:2019-03-20 03:18:05

标签: java

问题描述 如何从Firebase加载贴纸包?

链接 我已经经历过- https://github.com/idoideas/StickerMaker-for-Whatsapp https://github.com/viztushar/stickers-internet

1 个答案:

答案 0 :(得分:1)

好吧,在从firebase加载贴纸之前,您必须先创建一个带有sticker属性的类,一个提供程序以及更多其他内容(您可以轻松地知道如何从firebase检索数据,对于任何数据都是一样的,所以im将跳过该步骤。.

动态WAStickers应用程序应具有以下特征:

  • 内容提供者以获取必要的详细信息
  • 它应该向Whatsapp发送意图,以共享有关Sticker Pack All的必要详细信息
  • 图像必须为(或转换为)webp格式

为什么应该有内容提供商?

内容提供者是位于应用程序及其数据源之间的一类,其作用是提供对基础数据源的轻松访问。设备上的其他应用程序也可以访问此数据。

要向WhatsApp提供有关StickerPack的必要信息,您需要创建一个名为StickerPack的类,该类将包含以下参数。

class StickerPack implements Parcelable {
    String identifier;
    String name;
    String publisher;
    String trayImageFile;
    final String publisherEmail;
    final String publisherWebsite;
    final String privacyPolicyWebsite;
    final String licenseAgreementWebsite;

    String iosAppStoreLink;
    private List<Sticker> stickers;
    private long totalSize;
    String androidPlayStoreLink;
    private boolean isWhitelisted;

    StickerPack(String identifier, String name, String publisher, String trayImageFile, String publisherEmail, String publisherWebsite, String privacyPolicyWebsite, String licenseAgreementWebsite) {
        this.identifier = identifier;
        this.name = name;
        this.publisher = publisher;
        this.trayImageFile = trayImageFile;
        this.publisherEmail = publisherEmail;
        this.publisherWebsite = publisherWebsite;
        this.privacyPolicyWebsite = privacyPolicyWebsite;
        this.licenseAgreementWebsite = licenseAgreementWebsite;
       }
    }

有关此类的其他信息,请遵循Link

此类还包含Stickers的ArrayList,其中Sticker由以下类定义。

package com.example.samplestickerapp;

import android.os.Parcel;
import android.os.Parcelable;

import java.util.List;

class Sticker implements Parcelable {
    String imageFileName;
    List<String> emojis;
    long size;

    Sticker(String imageFileName, List<String> emojis) {
        this.imageFileName = imageFileName;
        this.emojis = emojis;
    }

    protected Sticker(Parcel in) {
        imageFileName = in.readString();
        emojis = in.createStringArrayList();
        size = in.readLong();
    }

    public static final Creator<Sticker> CREATOR = new Creator<Sticker>() {
        @Override
        public Sticker createFromParcel(Parcel in) {
            return new Sticker(in);
        }

        @Override
        public Sticker[] newArray(int size) {
            return new Sticker[size];
        }
    };

    public void setSize(long size) {
        this.size = size;
    }

    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(Parcel dest, int flags) {
        dest.writeString(imageFileName);
        dest.writeStringList(emojis);
        dest.writeLong(size);
    }
}

创建内容提供商 要创建内容提供商,第一步是:

获得使用ContentProvider的权限: 在Android清单中,我们应该请求读取/写入权限才能使用内容提供程序。这是一项安全功能,可告知用户该应用程序的实际功能。

<provider
        android:name=".StickerContentProvider"
        android:authorities="${contentProviderAuthority}"
        android:enabled="true"
        android:exported="true"
        android:readPermission="com.whatsapp.sticker.READ" />

${contentProviderAuthority}将替换为内容提供商的授权名称。

创建一个扩展ContentProvider的类 URI-统一资源标识符: URI用于专门识别或提供电话中某些数据的位置。

此位置可让您确切知道我们要查询的数据类型。该位置由3部分组成:

  • (1)content:// —内容提供者前缀
  • (2)内容授权-ifies指定要使用的内容提供商
  • (3)特定的 数据-一个字符串,用于准确标识内容中的哪些数据 提供商,我们很有趣。

在我们的内容提供商中,我们需要提及此处提到的4个URI。

首先,在ContentProvider类的onCreate方法中,创建一个URI Matcher对象,并将URI添加到该对象中。 在阅读下面的代码片段之前,请先从here阅读有关Uri Matcher的内容。

现在,由于您熟悉URI匹配器,因此您必须熟悉如何使用它

  • 首先,我们构建Uri Matcher对象树。
  • 然后我们将Url传递给getType函数,该函数将其与我们的URI相匹配 让我们在这里执行第一步。

    私有静态最终UriMatcher MATCHER =新的UriMatcher(UriMatcher.NO_MATCH);     静态最终字符串METADATA =“元数据”;     私有静态最终int METADATA_CODE = 1;     私有静态最终int METADATA_CODE_FOR_SINGLE_PACK = 2;     私有静态最终int STICKERS_CODE = 3;     静态最终字符串STICKERS_ASSET =“ stickers_asset”;     私有静态最终int STICKERS_ASSET_CODE = 4;     私有静态最终int STICKER_PACK_TRAY_ICON_CODE = 5;

    @Override
    public boolean onCreate() {
        final String authority = BuildConfig.CONTENT_PROVIDER_AUTHORITY;
        if (!authority.startsWith(Objects.requireNonNull(getContext()).getPackageName())) {
            throw new IllegalStateException("your authority (" + authority + ") for the content provider should start with your package name: " + getContext().getPackageName());
        }
        MATCHER.addURI(authority, METADATA, METADATA_CODE);
        MATCHER.addURI(authority, METADATA + "/*", METADATA_CODE_FOR_SINGLE_PACK);
        MATCHER.addURI(authority, STICKERS + "/*", STICKERS_CODE);
    
        for (StickerPack stickerPack : getStickerPackList()) {
            MATCHER.addURI(authority, STICKERS_ASSET + "/" + stickerPack.identifier + "/" + stickerPack.trayImageFile, STICKER_PACK_TRAY_ICON_CODE);
            for (Sticker sticker : stickerPack.getStickers()) {
                MATCHER.addURI(authority, STICKERS_ASSET + "/" + stickerPack.identifier + "/" + sticker.imageFileName, STICKERS_ASSET_CODE);
            }
        }
    
        return true;
    }
    

在上述方法中,我们向MATCHER对象添加了一个Uri模式,现在我们需要匹配此模式并返回确切的UrI,它将在设备上粘贴标签数据。接下来,WhatsApp命中的Url传递到getType函数,以使其与我们的Uri匹配,并返回设备上数据的特定位置。

@Override
    public String getType(@NonNull Uri uri) {
        final int matchCode = MATCHER.match(uri);
        switch (matchCode) {
            case METADATA_CODE:
                return "vnd.android.cursor.dir/vnd." + BuildConfig.CONTENT_PROVIDER_AUTHORITY + "." + METADATA;
            case METADATA_CODE_FOR_SINGLE_PACK:
                return "vnd.android.cursor.item/vnd." + BuildConfig.CONTENT_PROVIDER_AUTHORITY + "." + METADATA;
            case STICKERS_CODE:
                return "vnd.android.cursor.dir/vnd." + BuildConfig.CONTENT_PROVIDER_AUTHORITY + "." + STICKERS;
            case STICKERS_ASSET_CODE:
                return "image/webp";
            case STICKER_PACK_TRAY_ICON_CODE:
                return "image/png";
            default:
                throw new IllegalArgumentException("Unknown URI: " + uri);
        }
    }

接下来,根据Url,我们将调用查询方法,该方法将匹配Uri并返回特定Uri的游标对象。

@Override
    public Cursor query(@NonNull Uri uri, @Nullable String[] projection, String selection,
                        String[] selectionArgs, String sortOrder) {
        final int code = MATCHER.match(uri);
        if (code == METADATA_CODE) {
            return getPackForAllStickerPacks(uri);
        } else if (code == METADATA_CODE_FOR_SINGLE_PACK) {
            return getCursorForSingleStickerPack(uri);
        } else if (code == STICKERS_CODE) {
            return getStickersForAStickerPack(uri);
        } else {
            throw new IllegalArgumentException("Unknown URI: " + uri);
        }
    }

游标是提供对内容提供者数据的读/写访问权限的迭代器。

请参阅here中的getPackForAllStickerPacks(),getCursorForSingleStickerPack()和getStickerPackInfo()函数。知道游标对象将提供的数据类型。

恭喜!到目前为止,您已经达到了第一个里程碑。到目前为止,我们已经了解到:

  • 什么是内容提供商?
  • 我们通过ContentProviders发送什么类型的数据?
  • 我们如何处理Uri赋予特定的Cursor对象?

如果您能回答这些问题,那么恭喜!你做了出色的工作。如果不是这样,我建议您阅读有关ContentProviders和UriMatcher的文章,以获得适当的了解。

之后,您只需要从firebase加载内容,该内容在您的类中应该具有相同的结构。

来源:Link