├── app
├── .gitignore
├── debug.keystore
├── src
│ └── main
│ │ ├── res
│ │ ├── values
│ │ │ ├── dimens.xml
│ │ │ ├── colors.xml
│ │ │ ├── styles.xml
│ │ │ ├── arrays.xml
│ │ │ └── strings.xml
│ │ ├── mipmap-hdpi
│ │ │ └── ic_launcher.png
│ │ ├── mipmap-mdpi
│ │ │ └── ic_launcher.png
│ │ ├── mipmap-xhdpi
│ │ │ └── ic_launcher.png
│ │ ├── mipmap-xxhdpi
│ │ │ └── ic_launcher.png
│ │ ├── mipmap-xxxhdpi
│ │ │ └── ic_launcher.png
│ │ └── layout
│ │ │ └── activity_main.xml
│ │ ├── java
│ │ ├── com
│ │ │ └── tencent
│ │ │ │ └── mm
│ │ │ │ └── ui
│ │ │ │ └── transmit
│ │ │ │ └── MsgRetransmitUI.java
│ │ └── ezy
│ │ │ └── demo
│ │ │ └── sdk3rd
│ │ │ └── MainActivity.java
│ │ └── AndroidManifest.xml
├── proguard-rules.pro
└── build.gradle
├── ezy.sdk3rd.3rd-alipay
├── .gitignore
├── libs
│ └── alipaySdk-20180601.jar
├── proguard-rules.pro
├── build.gradle
└── src
│ └── main
│ └── AndroidManifest.xml
├── ezy.sdk3rd.3rd-qq
├── .gitignore
├── libs
│ └── open_sdk_r6008_lite.jar
├── README.md
├── proguard-rules.pro
├── build.gradle
└── src
│ └── main
│ └── AndroidManifest.xml
├── ezy.sdk3rd.social
├── .gitignore
├── src
│ └── main
│ │ ├── java
│ │ └── ezy
│ │ │ └── sdk3rd
│ │ │ └── social
│ │ │ ├── payment
│ │ │ ├── PaymentVia.java
│ │ │ └── IPayable.java
│ │ │ ├── sdk
│ │ │ ├── OnSucceed.java
│ │ │ ├── IDisposable.java
│ │ │ ├── IResult.java
│ │ │ ├── IFactory.java
│ │ │ ├── ResultCode.java
│ │ │ ├── OnCallback.java
│ │ │ ├── Platform.java
│ │ │ ├── DefaultFactory.java
│ │ │ ├── DefaultCallback.java
│ │ │ └── Sdk.java
│ │ │ ├── authorize
│ │ │ ├── AuthorizeVia.java
│ │ │ └── IAuthorize.java
│ │ │ ├── share
│ │ │ ├── image
│ │ │ │ ├── resource
│ │ │ │ │ ├── ImageResource.java
│ │ │ │ │ ├── BytesResource.java
│ │ │ │ │ ├── UrlResource.java
│ │ │ │ │ ├── BitmapResource.java
│ │ │ │ │ ├── FileResource.java
│ │ │ │ │ ├── DrawableResource.java
│ │ │ │ │ └── ResIdResource.java
│ │ │ │ └── ImageTool.java
│ │ │ ├── IShareable.java
│ │ │ ├── media
│ │ │ │ ├── MoWeb.java
│ │ │ │ ├── IMediaObject.java
│ │ │ │ ├── MoEmoji.java
│ │ │ │ ├── MoVideo.java
│ │ │ │ ├── MoMusic.java
│ │ │ │ └── MoImage.java
│ │ │ ├── ShareTo.java
│ │ │ └── ShareData.java
│ │ │ ├── platforms
│ │ │ ├── weixin
│ │ │ │ ├── WXCallbackActivity.java
│ │ │ │ ├── WXAuth.java
│ │ │ │ ├── WXPayment.java
│ │ │ │ ├── WXBase.java
│ │ │ │ └── WXShare.java
│ │ │ ├── alipay
│ │ │ │ ├── Alipay.java
│ │ │ │ └── Result.java
│ │ │ ├── weibo
│ │ │ │ ├── WBAuth.java
│ │ │ │ └── WBShare.java
│ │ │ ├── qq
│ │ │ │ ├── QQAuth.java
│ │ │ │ └── TXShare.java
│ │ │ └── send
│ │ │ │ └── SendShare.java
│ │ │ ├── PaymentSDK.java
│ │ │ ├── AuthorizeSDK.java
│ │ │ ├── PlatformConfig.java
│ │ │ └── ShareSDK.java
│ │ └── AndroidManifest.xml
├── proguard-rules.pro
└── build.gradle
├── screenshot.png
├── settings.gradle
├── gradle
└── wrapper
│ ├── gradle-wrapper.jar
│ └── gradle-wrapper.properties
├── .idea
├── caches
│ └── build_file_checksums.ser
├── vcs.xml
├── runConfigurations.xml
├── modules.xml
├── gradle.xml
├── misc.xml
└── codeStyles
│ └── Project.xml
├── .gitignore
├── gradle.properties
├── gradlew.bat
├── gradlew
├── README.md
└── LICENSE
/app/.gitignore:
--------------------------------------------------------------------------------
1 | /build
2 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.3rd-alipay/.gitignore:
--------------------------------------------------------------------------------
1 | /build
2 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.3rd-qq/.gitignore:
--------------------------------------------------------------------------------
1 | /build
2 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/.gitignore:
--------------------------------------------------------------------------------
1 | /build
2 |
--------------------------------------------------------------------------------
/screenshot.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/czy1121/sdk3rd/HEAD/screenshot.png
--------------------------------------------------------------------------------
/app/debug.keystore:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/czy1121/sdk3rd/HEAD/app/debug.keystore
--------------------------------------------------------------------------------
/settings.gradle:
--------------------------------------------------------------------------------
1 | include ':app', ':ezy.sdk3rd.social', ':ezy.sdk3rd.3rd-qq', ':ezy.sdk3rd.3rd-alipay'
2 |
--------------------------------------------------------------------------------
/app/src/main/res/values/dimens.xml:
--------------------------------------------------------------------------------
1 |
2 | 16dp
3 |
4 |
--------------------------------------------------------------------------------
/gradle/wrapper/gradle-wrapper.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/czy1121/sdk3rd/HEAD/gradle/wrapper/gradle-wrapper.jar
--------------------------------------------------------------------------------
/.idea/caches/build_file_checksums.ser:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/czy1121/sdk3rd/HEAD/.idea/caches/build_file_checksums.ser
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-hdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/czy1121/sdk3rd/HEAD/app/src/main/res/mipmap-hdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-mdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/czy1121/sdk3rd/HEAD/app/src/main/res/mipmap-mdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/czy1121/sdk3rd/HEAD/app/src/main/res/mipmap-xhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xxhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/czy1121/sdk3rd/HEAD/app/src/main/res/mipmap-xxhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/ezy.sdk3rd.3rd-qq/libs/open_sdk_r6008_lite.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/czy1121/sdk3rd/HEAD/ezy.sdk3rd.3rd-qq/libs/open_sdk_r6008_lite.jar
--------------------------------------------------------------------------------
/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/czy1121/sdk3rd/HEAD/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/ezy.sdk3rd.3rd-alipay/libs/alipaySdk-20180601.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/czy1121/sdk3rd/HEAD/ezy.sdk3rd.3rd-alipay/libs/alipaySdk-20180601.jar
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | *.iml
2 | .gradle
3 | local.properties
4 | app/gradle.properties
5 | .idea/workspace.xml
6 | .idea/libraries/
7 | .idea/caches/
8 | build/
9 | .DS_Store
10 | */.DS_Store
11 |
--------------------------------------------------------------------------------
/.idea/vcs.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/payment/PaymentVia.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.payment;
2 |
3 | public class PaymentVia {
4 | public static final String Alipay = "alipay";
5 | public static final String Wxpay = "wxpay";
6 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/sdk/OnSucceed.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.sdk;
2 |
3 | /**
4 | * Created by ezy on 17/3/18.
5 | */
6 |
7 | public interface OnSucceed {
8 | void onSucceed(T result);
9 | }
10 |
--------------------------------------------------------------------------------
/app/src/main/res/values/colors.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | #3F51B5
4 | #303F9F
5 | #FF4081
6 |
7 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/sdk/IDisposable.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.sdk;
2 |
3 | import android.content.Intent;
4 |
5 | /**
6 | * Created by ezy on 17/3/18.
7 | */
8 |
9 | public interface IDisposable {
10 | void onDispose();
11 | }
12 |
--------------------------------------------------------------------------------
/gradle/wrapper/gradle-wrapper.properties:
--------------------------------------------------------------------------------
1 | #Wed Jan 31 14:03:23 CST 2018
2 | distributionBase=GRADLE_USER_HOME
3 | distributionPath=wrapper/dists
4 | zipStoreBase=GRADLE_USER_HOME
5 | zipStorePath=wrapper/dists
6 | distributionUrl=https\://services.gradle.org/distributions/gradle-4.6-all.zip
7 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/authorize/AuthorizeVia.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.authorize;
2 |
3 | public class AuthorizeVia {
4 | public static final String QQ = "qq";
5 | public static final String Weibo = "weibo";
6 | public static final String Weixin = "weixin";
7 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/sdk/IResult.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.sdk;
2 |
3 | import android.content.Intent;
4 |
5 | /**
6 | * Created by ezy on 17/3/18.
7 | */
8 |
9 | public interface IResult {
10 | void onResult(int requestCode, int resultCode, Intent data);
11 | }
12 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/image/resource/ImageResource.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.image.resource;
2 |
3 | import android.graphics.Bitmap;
4 |
5 | public interface ImageResource {
6 |
7 | String toUri();
8 |
9 | Bitmap toBitmap();
10 |
11 | byte[] toBytes();
12 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/sdk/IFactory.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.sdk;
2 |
3 | import android.app.Activity;
4 |
5 | /**
6 | * Created by ezy on 17/3/18.
7 | */
8 |
9 | public interface IFactory {
10 |
11 | Platform getPlatform();
12 |
13 | T create(Activity activity);
14 | }
15 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/authorize/IAuthorize.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.authorize;
2 |
3 | import ezy.sdk3rd.social.sdk.IResult;
4 | import ezy.sdk3rd.social.sdk.OnCallback;
5 |
6 | /**
7 | * Created by ezy on 17/3/18.
8 | */
9 |
10 | public interface IAuthorize extends IResult {
11 | void authorize(OnCallback callback);
12 | }
13 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/payment/IPayable.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.payment;
2 |
3 | import ezy.sdk3rd.social.sdk.IResult;
4 | import ezy.sdk3rd.social.sdk.OnCallback;
5 |
6 | /**
7 | * Created by ezy on 17/3/18.
8 | */
9 |
10 | public interface IPayable extends IResult {
11 | void pay(String data, OnCallback callback);
12 | }
13 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/IShareable.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share;
2 |
3 | import ezy.sdk3rd.social.sdk.IResult;
4 | import ezy.sdk3rd.social.sdk.OnCallback;
5 |
6 | /**
7 | * Created by ezy on 17/3/18.
8 | */
9 |
10 | public interface IShareable extends IResult {
11 | void share(ShareData data, OnCallback callback);
12 | }
13 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/sdk/ResultCode.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.sdk;
2 |
3 | /**
4 | * Created by ezy on 17/3/18.
5 | */
6 |
7 | public class ResultCode {
8 | public static final int RESULT_OK = 0;
9 | public static final int RESULT_PENDING = 1;
10 | public static final int RESULT_CANCELLED = 2;
11 | public static final int RESULT_FAILED = 3;
12 |
13 | }
14 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/media/MoWeb.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.media;
2 |
3 | import android.support.annotation.NonNull;
4 |
5 | public class MoWeb implements IMediaObject {
6 |
7 | public String url;
8 |
9 | public MoWeb(@NonNull String url) {
10 | this.url = url;
11 | }
12 |
13 | @Override
14 | public int type() {
15 | return TYPE_WEB;
16 | }
17 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/media/IMediaObject.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.media;
2 |
3 | public interface IMediaObject {
4 | int TYPE_INVALID = 0;
5 | int TYPE_TEXT = 1;
6 | int TYPE_IMAGE = 2;
7 | int TYPE_TEXT_IMAGE = 3;
8 | int TYPE_EMOJI = 4;
9 | int TYPE_MUSIC = 5;
10 | int TYPE_VIDEO = 6;
11 | int TYPE_WEB = 7;
12 | int TYPE_FILE = 8;
13 |
14 | int type();
15 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/sdk/OnCallback.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.sdk;
2 |
3 | import android.app.Activity;
4 |
5 | /**
6 | * Created by ezy on 17/3/18.
7 | */
8 |
9 | public interface OnCallback {
10 | void onStarted(Activity activity);
11 | void onCompleted(Activity activity);
12 | void onSucceed(Activity activity, T result);
13 | void onFailed(Activity activity, int code, String message);
14 | }
15 |
--------------------------------------------------------------------------------
/app/src/main/java/com/tencent/mm/ui/transmit/MsgRetransmitUI.java:
--------------------------------------------------------------------------------
1 | package com.tencent.mm.ui.transmit;
2 |
3 | import android.os.Bundle;
4 | import android.support.v7.app.AppCompatActivity;
5 | import android.util.Log;
6 |
7 | public class MsgRetransmitUI extends AppCompatActivity {
8 |
9 |
10 | @Override
11 | protected void onCreate(Bundle savedInstanceState) {
12 | super.onCreate(savedInstanceState);
13 |
14 | Log.e("ezy", "" + getIntent());
15 | }
16 |
17 | }
18 |
--------------------------------------------------------------------------------
/.idea/runConfigurations.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
11 |
12 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/ShareTo.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share;
2 |
3 | public class ShareTo {
4 | public static final String Weibo = "weibo";
5 |
6 | public static final String QQ = "qq";
7 | public static final String QZone = "qzone";
8 |
9 | public static final String WXSession = "wxsession";
10 | public static final String WXTimeline = "wxtimeline";
11 | public static final String WXFavorite = "wxfavorite";
12 |
13 |
14 | public static final String ToWXSession = "towxsession";
15 | public static final String ToWXTimeline = "towxtimeline";
16 | public static final String ToQQ = "toqq";
17 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.3rd-qq/README.md:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | ## manifest
5 |
6 | ``` xml
7 |
8 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 | ```
24 |
25 |
26 | ## proguard
27 |
28 | ```
29 | ```
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/image/resource/BytesResource.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.image.resource;
2 |
3 | import android.graphics.Bitmap;
4 |
5 | import ezy.sdk3rd.social.share.image.ImageTool;
6 |
7 | public class BytesResource implements ImageResource {
8 | public final byte[] bytes;
9 |
10 | public BytesResource(byte[] bytes) {
11 | this.bytes = bytes;
12 | }
13 |
14 | @Override
15 | public String toUri() {
16 | return null;
17 | }
18 |
19 | @Override
20 | public Bitmap toBitmap() {
21 | return ImageTool.toBitmap(bytes);
22 | }
23 |
24 | @Override
25 | public byte[] toBytes() {
26 | return bytes;
27 | }
28 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/media/MoEmoji.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.media;
2 |
3 | import android.graphics.Bitmap;
4 |
5 | import java.io.File;
6 |
7 | import ezy.sdk3rd.social.share.image.resource.ImageResource;
8 |
9 | public class MoEmoji extends MoImage {
10 |
11 | public MoEmoji(ImageResource source) {
12 | super(source);
13 | }
14 |
15 | public MoEmoji(File file) {
16 | super(file);
17 | }
18 |
19 | public MoEmoji(byte[] bytes) {
20 | super(bytes);
21 | }
22 |
23 | public MoEmoji(Bitmap bitmap) {
24 | super(bitmap);
25 | }
26 |
27 | @Override
28 | public int type() {
29 | return TYPE_EMOJI;
30 | }
31 | }
--------------------------------------------------------------------------------
/app/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # By default, the flags in this file are appended to flags specified
3 | # in /Volumes/data/cellar/android/sdk/tools/proguard/proguard-android.txt
4 | # You can edit the include path and order by changing the proguardFiles
5 | # directive in build.gradle.
6 | #
7 | # For more details, see
8 | # http://developer.android.com/guide/developing/tools/proguard.html
9 |
10 | # Add any project specific keep options here:
11 |
12 | # If your project uses WebView with JS, uncomment the following
13 | # and specify the fully qualified class name to the JavaScript interface
14 | # class:
15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16 | # public *;
17 | #}
18 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.3rd-qq/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # By default, the flags in this file are appended to flags specified
3 | # in /Volumes/data/cellar/android/sdk/tools/proguard/proguard-android.txt
4 | # You can edit the include path and order by changing the proguardFiles
5 | # directive in build.gradle.
6 | #
7 | # For more details, see
8 | # http://developer.android.com/guide/developing/tools/proguard.html
9 |
10 | # Add any project specific keep options here:
11 |
12 | # If your project uses WebView with JS, uncomment the following
13 | # and specify the fully qualified class name to the JavaScript interface
14 | # class:
15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16 | # public *;
17 | #}
18 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # By default, the flags in this file are appended to flags specified
3 | # in /Volumes/data/cellar/android/sdk/tools/proguard/proguard-android.txt
4 | # You can edit the include path and order by changing the proguardFiles
5 | # directive in build.gradle.
6 | #
7 | # For more details, see
8 | # http://developer.android.com/guide/developing/tools/proguard.html
9 |
10 | # Add any project specific keep options here:
11 |
12 | # If your project uses WebView with JS, uncomment the following
13 | # and specify the fully qualified class name to the JavaScript interface
14 | # class:
15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16 | # public *;
17 | #}
18 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/image/resource/UrlResource.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.image.resource;
2 |
3 | import android.graphics.Bitmap;
4 |
5 | import ezy.sdk3rd.social.share.image.ImageTool;
6 |
7 | public class UrlResource implements ImageResource {
8 | public final String url;
9 |
10 | public UrlResource(String url) {
11 | this.url = url;
12 | }
13 |
14 | @Override
15 | public String toUri() {
16 | return url;
17 | }
18 |
19 | @Override
20 | public Bitmap toBitmap() {
21 | return ImageTool.toBitmap(ImageTool.loadNetImage(url));
22 | }
23 |
24 | @Override
25 | public byte[] toBytes() {
26 | return ImageTool.loadNetImage(url);
27 | }
28 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.3rd-alipay/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # By default, the flags in this file are appended to flags specified
3 | # in /Volumes/data/cellar/android/sdk/tools/proguard/proguard-android.txt
4 | # You can edit the include path and order by changing the proguardFiles
5 | # directive in build.gradle.
6 | #
7 | # For more details, see
8 | # http://developer.android.com/guide/developing/tools/proguard.html
9 |
10 | # Add any project specific keep options here:
11 |
12 | # If your project uses WebView with JS, uncomment the following
13 | # and specify the fully qualified class name to the JavaScript interface
14 | # class:
15 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16 | # public *;
17 | #}
18 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/image/resource/BitmapResource.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.image.resource;
2 |
3 | import android.graphics.Bitmap;
4 |
5 | import ezy.sdk3rd.social.share.image.ImageTool;
6 |
7 | public class BitmapResource implements ImageResource {
8 | public final Bitmap bitmap;
9 |
10 | public BitmapResource(Bitmap bitmap) {
11 | this.bitmap = bitmap;
12 | }
13 |
14 | @Override
15 | public String toUri() {
16 | return null;
17 | }
18 |
19 | @Override
20 | public Bitmap toBitmap() {
21 | return bitmap;
22 | }
23 |
24 | @Override
25 | public byte[] toBytes() {
26 | return ImageTool.toBytes(bitmap, Bitmap.CompressFormat.JPEG);
27 | }
28 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.3rd-qq/build.gradle:
--------------------------------------------------------------------------------
1 | plugins {
2 | id "com.github.dcendents.android-maven" version "2.0"
3 | }
4 | apply plugin: 'com.android.library'
5 |
6 | group=SDK3RD_GROUP
7 | version=SDK3RD_VERSION
8 | archivesBaseName='sdk3rd-qq'
9 |
10 |
11 |
12 |
13 | android {
14 | compileSdkVersion compile_sdk_version
15 |
16 | defaultConfig {
17 | minSdkVersion min_sdk_version
18 | targetSdkVersion target_sdk_version
19 | }
20 | buildTypes {
21 | release {
22 | minifyEnabled false
23 | }
24 | }
25 | }
26 |
27 | afterEvaluate {
28 | tasks.each {
29 | if (it.name.contains("Test")) {
30 | it.enabled = false
31 | }
32 | }
33 | }
34 |
35 | dependencies {
36 | api fileTree(dir: 'libs', include: ['*.jar'])
37 | }
38 |
--------------------------------------------------------------------------------
/app/src/main/res/values/styles.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
10 |
11 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/image/resource/FileResource.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.image.resource;
2 |
3 | import android.graphics.Bitmap;
4 |
5 | import java.io.File;
6 |
7 | import ezy.sdk3rd.social.share.image.ImageTool;
8 |
9 | public class FileResource implements ImageResource {
10 | public final File file;
11 |
12 | public FileResource(File file) {
13 | this.file = file;
14 | }
15 |
16 | @Override
17 | public String toUri() {
18 | return file.toString();
19 | }
20 |
21 | @Override
22 | public Bitmap toBitmap() {
23 | return ImageTool.toBitmap(file);
24 | }
25 |
26 | @Override
27 | public byte[] toBytes() {
28 | return ImageTool.toBytes(ImageTool.toBitmap(file), Bitmap.CompressFormat.JPEG);
29 | }
30 |
31 | }
--------------------------------------------------------------------------------
/app/src/main/res/values/arrays.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | - Weixin
5 | - QQ
6 | - Weibo
7 |
8 |
9 | - Weibo
10 | - QQ
11 | - QZone
12 | - WXSession
13 | - WXTimeline
14 | - WXFavorite
15 | - ToWXSession
16 | - ToWXTimeline
17 | - ToQQ
18 |
19 |
20 | - 链接
21 | - 纯文本
22 | - 纯图片
23 | - 图文
24 | - 音乐
25 | - 视频
26 |
27 |
28 |
--------------------------------------------------------------------------------
/app/src/main/res/values/strings.xml:
--------------------------------------------------------------------------------
1 |
2 | sdk3rd
3 | sdk3rd
4 |
5 |
6 |
7 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/image/resource/DrawableResource.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.image.resource;
2 |
3 | import android.graphics.Bitmap;
4 | import android.graphics.drawable.Drawable;
5 |
6 | import ezy.sdk3rd.social.share.image.ImageTool;
7 |
8 | public class DrawableResource implements ImageResource {
9 | public final Drawable drawable;
10 |
11 | public DrawableResource(Drawable drawable) {
12 | this.drawable = drawable;
13 | }
14 |
15 | @Override
16 | public String toUri() {
17 | return null;
18 | }
19 |
20 | @Override
21 | public Bitmap toBitmap() {
22 | return ImageTool.toBitmap(drawable);
23 | }
24 |
25 | @Override
26 | public byte[] toBytes() {
27 | return ImageTool.toBytes(ImageTool.toBitmap(drawable), Bitmap.CompressFormat.JPEG);
28 | }
29 | }
--------------------------------------------------------------------------------
/.idea/modules.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/image/resource/ResIdResource.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.image.resource;
2 |
3 | import android.content.Context;
4 | import android.graphics.Bitmap;
5 |
6 | import ezy.sdk3rd.social.share.image.ImageTool;
7 |
8 | public class ResIdResource implements ImageResource {
9 | Context mContext;
10 | int mResId;
11 | boolean mIsRaw;
12 |
13 | public ResIdResource(Context context, int resId, boolean isRaw) {
14 | mContext = context;
15 | mResId = resId;
16 | mIsRaw = isRaw;
17 | }
18 |
19 | @Override
20 | public String toUri() {
21 | return null;
22 | }
23 |
24 | @Override
25 | public Bitmap toBitmap() {
26 | return ImageTool.toBitmap(mContext, mResId, mIsRaw);
27 | }
28 |
29 | @Override
30 | public byte[] toBytes() {
31 | return ImageTool.toBytes(mContext, mResId, mIsRaw, Bitmap.CompressFormat.JPEG);
32 | }
33 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/sdk/Platform.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.sdk;
2 |
3 | import android.support.annotation.NonNull;
4 |
5 | import java.util.HashMap;
6 | import java.util.Map;
7 |
8 | /**
9 | * Created by ezy on 17/3/18.
10 | */
11 |
12 | public class Platform {
13 | final String name;
14 | final String appId;
15 |
16 | Map extra;
17 |
18 | public Platform(@NonNull String name, @NonNull String appId) {
19 | this.name = name;
20 | this.appId = appId;
21 | }
22 |
23 | public String getName() {
24 | return name;
25 | }
26 |
27 | public String getAppId() {
28 | return appId;
29 | }
30 |
31 | public String extra(String key) {
32 | return extra == null ? "" : extra.get(key);
33 | }
34 |
35 | public Platform extra(String key, String value) {
36 | if (extra == null) {
37 | extra = new HashMap<>();
38 | }
39 | extra.put(key, value);
40 | return this;
41 | }
42 | }
43 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/weixin/WXCallbackActivity.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.weixin;
2 |
3 |
4 | import android.app.Activity;
5 | import android.content.Intent;
6 | import android.os.Bundle;
7 | import android.util.Log;
8 |
9 | import ezy.sdk3rd.social.sdk.IResult;
10 |
11 | public class WXCallbackActivity extends Activity {
12 |
13 | @Override
14 | protected void onCreate(Bundle savedInstanceState) {
15 | super.onCreate(savedInstanceState);
16 | onNewIntent(getIntent());
17 | }
18 |
19 | @Override
20 | protected void onNewIntent(Intent intent) {
21 | super.onNewIntent(intent);
22 | setIntent(intent);
23 | Log.e(WXBase.TAG, "==> " + ((getIntent() == null) ? "" : getIntent().getExtras()));
24 |
25 | for (IResult service: WXBase.services.keySet()) {
26 | if (service != null) {
27 | service.onResult(WXBase.REQUEST_CODE, Activity.RESULT_OK, intent);
28 | }
29 | }
30 | finish();
31 | }
32 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.3rd-qq/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
3 |
4 |
5 |
6 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
24 |
25 |
26 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.3rd-alipay/build.gradle:
--------------------------------------------------------------------------------
1 | plugins {
2 | id "com.github.dcendents.android-maven" version "2.0"
3 | }
4 | apply plugin: 'com.android.library'
5 |
6 | group=SDK3RD_GROUP
7 | version=SDK3RD_VERSION
8 | archivesBaseName='sdk3rd-alipay'
9 |
10 | android {
11 | compileSdkVersion compile_sdk_version
12 |
13 | defaultConfig {
14 | minSdkVersion min_sdk_version
15 | targetSdkVersion target_sdk_version
16 | }
17 | buildTypes {
18 | release {
19 | minifyEnabled false
20 | }
21 | }
22 | }
23 |
24 | dependencies {
25 | api fileTree(dir: 'libs', include: ['*.jar'])
26 | }
27 |
28 | task sourcesJar(type: Jar) {
29 | classifier = 'sources'
30 | from android.sourceSets.main.java.srcDirs
31 | }
32 | task javadoc(type: Javadoc) {
33 | failOnError false
34 | source = android.sourceSets.main.java.srcDirs
35 | }
36 | task javadocJar(type: Jar, dependsOn: javadoc) {
37 | classifier = 'javadoc'
38 | from javadoc.destinationDir
39 | }
40 | artifacts {
41 | archives javadocJar
42 | archives sourcesJar
43 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/media/MoVideo.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.media;
2 |
3 | public class MoVideo implements IMediaObject {
4 |
5 |
6 | public String mediaUrl;
7 | public String mediaDataUrl;
8 | public String lowBandUrl;
9 | public String lowBandDataUrl;
10 | public int duration;
11 |
12 | public MoVideo(String url) {
13 | this.mediaUrl = url;
14 | }
15 |
16 | public MoVideo(String url, String dataUrl) {
17 | this.mediaUrl = url;
18 | this.mediaDataUrl = dataUrl;
19 | }
20 | public MoVideo withDuration(int value) {
21 | this.duration = value;
22 | return this;
23 | }
24 | public MoVideo withLowBand(String url) {
25 | this.lowBandUrl = url;
26 | return this;
27 | }
28 | public MoVideo withLowBand(String url, String dataUrl) {
29 | this.lowBandUrl = url;
30 | this.lowBandDataUrl = dataUrl;
31 | return this;
32 | }
33 | @Override
34 | public int type() {
35 | return TYPE_VIDEO;
36 | }
37 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/media/MoMusic.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.media;
2 |
3 | public class MoMusic implements IMediaObject {
4 |
5 | public String mediaUrl;
6 | public String mediaDataUrl;
7 | public String lowBandUrl;
8 | public String lowBandDataUrl;
9 | public int duration;
10 |
11 | public MoMusic(String url) {
12 | this.mediaUrl = url;
13 | }
14 |
15 | public MoMusic(String url, String dataUrl) {
16 | this.mediaUrl = url;
17 | this.mediaDataUrl = dataUrl;
18 | }
19 | public MoMusic withDuration(int value) {
20 | this.duration = value;
21 | return this;
22 | }
23 | public MoMusic withLowBand(String url) {
24 | this.lowBandUrl = url;
25 | return this;
26 | }
27 | public MoMusic withLowBand(String url, String dataUrl) {
28 | this.lowBandUrl = url;
29 | this.lowBandDataUrl = dataUrl;
30 | return this;
31 | }
32 |
33 | @Override
34 | public int type() {
35 | return TYPE_MUSIC;
36 | }
37 |
38 | }
--------------------------------------------------------------------------------
/.idea/gradle.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
3 |
4 |
5 |
6 |
7 |
14 |
15 |
19 |
20 |
24 |
25 |
26 |
27 |
28 |
29 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/build.gradle:
--------------------------------------------------------------------------------
1 | plugins {
2 | id "com.github.dcendents.android-maven" version "2.0"
3 | }
4 | apply plugin: 'com.android.library'
5 |
6 | group=SDK3RD_GROUP
7 | version=SDK3RD_VERSION
8 | archivesBaseName='sdk3rd-social'
9 |
10 | android {
11 | compileSdkVersion compile_sdk_version
12 |
13 | defaultConfig {
14 | minSdkVersion min_sdk_version
15 | targetSdkVersion target_sdk_version
16 | }
17 | buildTypes {
18 | release {
19 | minifyEnabled false
20 | }
21 | }
22 | }
23 |
24 | repositories {
25 | jcenter()
26 | mavenCentral()
27 | maven { url "https://dl.bintray.com/thelasterstar/maven/" }
28 | }
29 |
30 | dependencies {
31 | api fileTree(dir: 'libs', include: ['*.jar'])
32 |
33 | api "com.android.support:support-fragment:$supportVersion"
34 | api "com.android.support:support-annotations:$supportVersion"
35 |
36 | compileOnly project(":ezy.sdk3rd.3rd-alipay")
37 | compileOnly project(":ezy.sdk3rd.3rd-qq")
38 |
39 | compileOnly 'com.sina.weibo.sdk:core:2.0.3:openDefaultRelease@aar'
40 | compileOnly 'com.tencent.mm.opensdk:wechat-sdk-android-without-mta:5.5.4'
41 | }
42 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/sdk/DefaultFactory.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.sdk;
2 |
3 | import android.app.Activity;
4 | import android.support.annotation.NonNull;
5 |
6 | import java.lang.reflect.Constructor;
7 |
8 | /**
9 | * Created by ezy on 17/3/18.
10 | */
11 |
12 | public class DefaultFactory implements IFactory {
13 | final Platform platform;
14 |
15 | final Class clazz;
16 |
17 | public DefaultFactory(@NonNull String name, String appId, Class clazz) {
18 | this.platform = new Platform(name, appId);
19 | this.clazz = clazz;
20 | }
21 |
22 | public DefaultFactory(@NonNull Platform platform, Class clazz) {
23 | this.platform = platform;
24 | this.clazz = clazz;
25 | }
26 |
27 | @Override
28 | public Platform getPlatform() {
29 | return platform;
30 | }
31 |
32 | @Override
33 | public T create(Activity activity) {
34 | try {
35 | Constructor constructor = clazz.getDeclaredConstructor(Activity.class, Platform.class);
36 | constructor.setAccessible(true);
37 | return constructor.newInstance(activity, platform);
38 | } catch (Exception e) {
39 | e.printStackTrace();
40 | }
41 | return null;
42 | }
43 | }
44 |
--------------------------------------------------------------------------------
/app/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
5 |
11 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.3rd-alipay/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
19 |
20 |
26 |
27 |
28 |
29 |
30 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/sdk/DefaultCallback.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.sdk;
2 |
3 | import android.app.Activity;
4 |
5 | /**
6 | * Created by ezy on 17/3/18.
7 | */
8 |
9 | public class DefaultCallback implements OnCallback {
10 | OnCallback onCallback;
11 | OnSucceed onSuccess;
12 |
13 | public DefaultCallback(OnCallback callback, OnSucceed success) {
14 | onCallback = callback;
15 | onSuccess = success;
16 | }
17 |
18 | @Override
19 | public void onStarted(Activity activity) {
20 | if (onCallback != null) {
21 | onCallback.onStarted(activity);
22 | }
23 | }
24 |
25 | @Override
26 | public void onCompleted(Activity activity) {
27 | if (onCallback != null) {
28 | onCallback.onCompleted(activity);
29 | }
30 | }
31 |
32 | @Override
33 | public void onFailed(Activity activity, int code, String message) {
34 | if (onCallback != null) {
35 | onCallback.onFailed(activity, code, message);
36 | }
37 | }
38 |
39 | @Override
40 | public void onSucceed(Activity activity, R result) {
41 | if (onCallback != null) {
42 | onCallback.onSucceed(activity, result);
43 | }
44 | if (onSuccess != null) {
45 | onSuccess.onSucceed(result);
46 | }
47 | }
48 | }
49 |
--------------------------------------------------------------------------------
/gradle.properties:
--------------------------------------------------------------------------------
1 | # Project-wide Gradle settings.
2 |
3 | # IDE (e.g. Android Studio) users:
4 | # Gradle settings configured through the IDE *will override*
5 | # any settings specified in this file.
6 |
7 | # For more details on how to configure your build environment visit
8 | # http://www.gradle.org/docs/current/userguide/build_environment.html
9 |
10 | # Specifies the JVM arguments used for the daemon process.
11 | # The setting is particularly useful for tweaking memory settings.
12 | # Default value: -Xmx10248m -XX:MaxPermSize=256m
13 | # org.gradle.jvmargs=-Xmx2048m -XX:MaxPermSize=512m -XX:+HeapDumpOnOutOfMemoryError -Dfile.encoding=UTF-8
14 |
15 | # When configured, Gradle will run in incubating parallel mode.
16 | # This option should only be used with decoupled projects. More details, visit
17 | # http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
18 | # org.gradle.parallel=true
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 | APPLICATION_ID=ezy.demo.sdk3rd
30 |
31 | APPID_QQ=YOUR_APPID
32 | APPID_WEIXIN=YOUR_APPID
33 | APPID_WEIBO=YOUR_APPID
34 |
35 | SINGING_ALIAS=androiddebugkey
36 | SINGING_PASSWORD=android
37 | SINGING_FILE=debug.keystore
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 | SDK3RD_GROUP=com.github.czy1121
47 | SDK3RD_VERSION=0.1.11
48 |
49 |
50 |
51 | supportVersion=27.1.1
52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |
60 |
61 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/media/MoImage.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.media;
2 |
3 | import android.graphics.Bitmap;
4 | import android.support.annotation.NonNull;
5 |
6 | import java.io.File;
7 |
8 | import ezy.sdk3rd.social.share.image.resource.BitmapResource;
9 | import ezy.sdk3rd.social.share.image.resource.BytesResource;
10 | import ezy.sdk3rd.social.share.image.resource.FileResource;
11 | import ezy.sdk3rd.social.share.image.resource.ImageResource;
12 | import ezy.sdk3rd.social.share.image.resource.UrlResource;
13 |
14 | public class MoImage implements IMediaObject {
15 |
16 | public ImageResource resource;
17 |
18 | public MoImage(@NonNull ImageResource resource) {
19 | this.resource = resource;
20 | }
21 |
22 | public MoImage(String url) {
23 | resource = new UrlResource(url);
24 | }
25 |
26 | public MoImage(File file) {
27 | resource = new FileResource(file);
28 | }
29 |
30 | public MoImage(byte[] bytes) {
31 | resource = new BytesResource(bytes);
32 | }
33 |
34 | public MoImage(Bitmap bitmap) {
35 | resource = new BitmapResource(bitmap);
36 | }
37 |
38 |
39 | @Override
40 | public int type() {
41 | return TYPE_IMAGE;
42 | }
43 |
44 | public String toUri() {
45 | return resource.toUri();
46 | }
47 |
48 | public byte[] toBytes() {
49 | return resource.toBytes();
50 | }
51 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/weixin/WXAuth.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.weixin;
2 |
3 | import android.app.Activity;
4 | import android.support.annotation.NonNull;
5 | import android.util.Log;
6 |
7 | import com.tencent.mm.opensdk.modelmsg.SendAuth;
8 |
9 | import java.io.Closeable;
10 | import java.io.IOException;
11 |
12 | import ezy.sdk3rd.social.authorize.IAuthorize;
13 | import ezy.sdk3rd.social.sdk.IDisposable;
14 | import ezy.sdk3rd.social.sdk.OnCallback;
15 | import ezy.sdk3rd.social.sdk.Platform;
16 | import ezy.sdk3rd.social.sdk.ResultCode;
17 |
18 | /**
19 | * Created by ezy on 17/3/18.
20 | */
21 |
22 | public class WXAuth extends WXBase implements IAuthorize, IDisposable {
23 |
24 | WXAuth(Activity activity, Platform platform) {
25 | super(activity, platform);
26 | }
27 |
28 |
29 | @Override
30 | public void authorize(@NonNull OnCallback callback) {
31 | mCallback = callback;
32 | if (!mApi.isWXAppInstalled()) {
33 | mCallback.onFailed(mActivity, ResultCode.RESULT_FAILED, "您未安装微信!");
34 | return;
35 | }
36 |
37 | SendAuth.Req req = new SendAuth.Req();
38 | req.scope = "snsapi_userinfo";
39 | req.state = "wechat";
40 |
41 | Log.e(TAG, "send start");
42 | mCallback.onStarted(mActivity);
43 | boolean ret = mApi.sendReq(req);
44 | Log.e(TAG, "send end " + ret);
45 | }
46 |
47 | @Override
48 | protected void onResultOk(SendAuth.Resp resp) {
49 | Log.e(TAG, "code = " + resp.code);
50 | mCallback.onSucceed(mActivity, "code|" + resp.code);
51 | }
52 |
53 | @Override
54 | public void onDispose() {
55 | services.remove(this);
56 | }
57 | }
58 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/ShareData.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share;
2 |
3 | import android.text.TextUtils;
4 |
5 | import ezy.sdk3rd.social.share.image.resource.ImageResource;
6 | import ezy.sdk3rd.social.share.media.IMediaObject;
7 |
8 | public class ShareData {
9 | public static final int THUMB_LIMIT = 24576;
10 | public static final int THUMB_LIMIT_WX = 32*1024;
11 | public static final int IMAGE_LIMIT = 491520;
12 | public static final String DEFAULT_TITLE = "这里是标题";
13 | public static final String DEFAULT_DESCRIPTION = "这里是描述";
14 |
15 |
16 | public String url = "";
17 | public String text = "";
18 | public String title = "";
19 | public String description = "";
20 | public ImageResource thumb;
21 | public IMediaObject media;
22 |
23 | public boolean hasUrl() {
24 | return !TextUtils.isEmpty(url);
25 | }
26 |
27 | public boolean hasText() {
28 | return !TextUtils.isEmpty(text);
29 | }
30 |
31 | public boolean hasTitle() {
32 | return !TextUtils.isEmpty(title);
33 | }
34 |
35 | public boolean hasDescription() {
36 | return !TextUtils.isEmpty(description);
37 | }
38 |
39 | public boolean hasThumb() {
40 | return thumb != null;
41 | }
42 |
43 | public boolean hasMedia() {
44 | return media != null;
45 | }
46 |
47 | public int type() {
48 | if (media != null) {
49 | return media.type();
50 | }
51 | if (hasText()) {
52 | return IMediaObject.TYPE_TEXT;
53 | }
54 | return IMediaObject.TYPE_INVALID;
55 | }
56 |
57 | @Override
58 | public String toString() {
59 | return "ShareData [type=" + type() + ", title=" + title + ", desc=" + description + ", thumb=" + thumb + "]";
60 | }
61 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/PaymentSDK.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social;
2 |
3 | import android.app.Activity;
4 | import android.content.Intent;
5 |
6 | import ezy.sdk3rd.social.payment.IPayable;
7 | import ezy.sdk3rd.social.sdk.DefaultCallback;
8 | import ezy.sdk3rd.social.sdk.IFactory;
9 | import ezy.sdk3rd.social.sdk.OnCallback;
10 | import ezy.sdk3rd.social.sdk.OnSucceed;
11 | import ezy.sdk3rd.social.sdk.ResultCode;
12 | import ezy.sdk3rd.social.sdk.Sdk;
13 |
14 | public class PaymentSDK {
15 | static Sdk sdk = new Sdk<>();
16 |
17 | public static void setDefaultCallback(OnCallback callback) {
18 | sdk.setDefaultCallback(callback);
19 | }
20 |
21 | public static void register(String name, Class clazz) {
22 | sdk.register(name, "", clazz);
23 | }
24 |
25 | public static void register(IFactory factory) {
26 | sdk.register(factory);
27 | }
28 |
29 | public static void pay(Activity activity, String platform, String data, OnSucceed listener) {
30 | pay(activity, platform, data, new DefaultCallback(sdk.getDefaultCallback(), listener));
31 | }
32 |
33 | public static void pay(Activity activity, String platform, String data, OnCallback callback) {
34 | if (!sdk.isSupport(platform)) {
35 | callback.onFailed(activity, ResultCode.RESULT_FAILED, "不支持的平台[" + platform + "]");
36 | return;
37 | }
38 | IPayable api = sdk.get(activity, platform);
39 | if (api == null) {
40 | return;
41 | }
42 | api.pay(data, callback);
43 | }
44 |
45 | public static void onHandleResult(Activity activity, int requestCode, int resultCode, Intent data) {
46 | sdk.onHandleResult(activity, requestCode, resultCode, data);
47 | }
48 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/AuthorizeSDK.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social;
2 |
3 | import android.app.Activity;
4 | import android.content.Intent;
5 |
6 | import ezy.sdk3rd.social.authorize.IAuthorize;
7 | import ezy.sdk3rd.social.sdk.DefaultCallback;
8 | import ezy.sdk3rd.social.sdk.IFactory;
9 | import ezy.sdk3rd.social.sdk.OnCallback;
10 | import ezy.sdk3rd.social.sdk.OnSucceed;
11 | import ezy.sdk3rd.social.sdk.ResultCode;
12 | import ezy.sdk3rd.social.sdk.Sdk;
13 |
14 | public class AuthorizeSDK {
15 | static Sdk sdk = new Sdk<>();
16 |
17 | public static void setDefaultCallback(OnCallback callback) {
18 | sdk.setDefaultCallback(callback);
19 | }
20 |
21 | public static void register(String name, String appId, Class clazz) {
22 | sdk.register(name, appId, clazz);
23 | }
24 |
25 | public static void register(IFactory factory) {
26 | sdk.register(factory);
27 | }
28 |
29 | public static void authorize(final Activity activity, String platform, OnSucceed listener) {
30 | authorize(activity, platform, new DefaultCallback(sdk.getDefaultCallback(), listener));
31 | }
32 |
33 | public static void authorize(Activity activity, String platform, OnCallback callback) {
34 | if (!sdk.isSupport(platform)) {
35 | callback.onFailed(activity, ResultCode.RESULT_FAILED, "不支持的平台[" + platform + "]");
36 | return;
37 | }
38 | IAuthorize api = sdk.get(activity, platform);
39 | if (api == null) {
40 | return;
41 | }
42 | api.authorize(callback);
43 | }
44 |
45 |
46 | public static void onHandleResult(Activity activity, int requestCode, int resultCode, Intent data) {
47 | sdk.onHandleResult(activity, requestCode, resultCode, data);
48 | }
49 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/alipay/Alipay.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.alipay;
2 |
3 |
4 | import android.app.Activity;
5 | import android.content.Intent;
6 | import android.os.AsyncTask;
7 |
8 | import com.alipay.sdk.app.PayTask;
9 |
10 | import ezy.sdk3rd.social.payment.IPayable;
11 | import ezy.sdk3rd.social.sdk.OnCallback;
12 | import ezy.sdk3rd.social.sdk.Platform;
13 | import ezy.sdk3rd.social.sdk.ResultCode;
14 |
15 | public class Alipay implements IPayable {
16 | public static final String TAG = "ezy.sdk3rd.alipay";
17 |
18 | Activity mActivity;
19 |
20 | Alipay(Activity activity, Platform platform) {
21 | mActivity = activity;
22 | }
23 |
24 | @Override
25 | public void pay(final String data, final OnCallback callback) {
26 |
27 | new AsyncTask() {
28 | @Override
29 | protected void onPreExecute() {
30 | callback.onStarted(mActivity);
31 | }
32 |
33 | @Override
34 | protected Result doInBackground(String... params) {
35 | final PayTask task = new PayTask(mActivity);
36 | return new Result(task.payV2(data, true));
37 | }
38 |
39 | @Override
40 | protected void onPostExecute(Result result) {
41 | String message = "[" + result.resultStatus + "]" + result.resultText;
42 | if (result.isSuccess()) {
43 | callback.onSucceed(mActivity, "");
44 | } else if (result.isPending()) {
45 | callback.onFailed(mActivity, ResultCode.RESULT_PENDING, message);
46 | } else if (result.isCancelled()){
47 | callback.onFailed(mActivity, ResultCode.RESULT_CANCELLED, message);
48 | } else {
49 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, message);
50 | }
51 | callback.onCompleted(mActivity);
52 | }
53 | }.execute(data);
54 |
55 | }
56 |
57 | @Override
58 | public void onResult(int requestCode, int resultCode, Intent data) {
59 |
60 | }
61 | }
--------------------------------------------------------------------------------
/app/build.gradle:
--------------------------------------------------------------------------------
1 | apply plugin: 'com.android.application'
2 |
3 | def addFieldsAndPlaceholders = { flavor, items ->
4 | for (def item : items) {
5 | flavor.buildConfigField "String", item.key, '"' + item.value + '"'
6 | }
7 | flavor.addManifestPlaceholders(items)
8 | }
9 | android {
10 | compileSdkVersion compile_sdk_version
11 |
12 | defaultConfig {
13 | applicationId APPLICATION_ID
14 | minSdkVersion min_sdk_version
15 | targetSdkVersion target_sdk_version
16 | versionCode 1000
17 | versionName "1.0.0"
18 |
19 | println("===> " + APPID_QQ)
20 | println("===> " + APPID_WEIXIN)
21 | println("===> " + APPID_WEIBO)
22 |
23 | addFieldsAndPlaceholders(it, [
24 | APPID_QQ : APPID_QQ,
25 | APPID_WEIXIN : APPID_WEIXIN,
26 | APPID_WEIBO : APPID_WEIBO,
27 |
28 | ])
29 |
30 | }
31 |
32 | dataBinding {
33 | enabled = true
34 | }
35 | signingConfigs {
36 | release {
37 | keyAlias SINGING_ALIAS
38 | keyPassword SINGING_PASSWORD
39 | storeFile file(SINGING_FILE)
40 | storePassword SINGING_PASSWORD
41 | v2SigningEnabled false
42 | }
43 | }
44 | buildTypes {
45 | release {
46 | signingConfig = signingConfigs.release
47 | minifyEnabled false
48 | shrinkResources false
49 | zipAlignEnabled true
50 | proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
51 | }
52 | }
53 | }
54 |
55 | repositories {
56 | jcenter()
57 | mavenCentral()
58 | maven { url "https://dl.bintray.com/thelasterstar/maven/" }
59 | }
60 |
61 | dependencies {
62 | implementation fileTree(dir: 'libs', include: ['*.jar'])
63 | implementation "com.android.support:appcompat-v7:$supportVersion"
64 |
65 |
66 | implementation project(':ezy.sdk3rd.social')
67 |
68 | implementation project(':ezy.sdk3rd.3rd-alipay')
69 | implementation project(':ezy.sdk3rd.3rd-qq')
70 |
71 | implementation 'com.sina.weibo.sdk:core:2.0.3:openDefaultRelease@aar'
72 | implementation 'com.tencent.mm.opensdk:wechat-sdk-android-without-mta:5.1.6'
73 | }
74 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/PlatformConfig.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social;
2 |
3 | import android.support.annotation.NonNull;
4 |
5 | import ezy.sdk3rd.social.authorize.AuthorizeVia;
6 | import ezy.sdk3rd.social.payment.PaymentVia;
7 | import ezy.sdk3rd.social.platforms.alipay.Alipay;
8 | import ezy.sdk3rd.social.platforms.qq.QQAuth;
9 | import ezy.sdk3rd.social.platforms.qq.TXShare;
10 | import ezy.sdk3rd.social.platforms.send.SendShare;
11 | import ezy.sdk3rd.social.platforms.weibo.WBAuth;
12 | import ezy.sdk3rd.social.platforms.weibo.WBShare;
13 | import ezy.sdk3rd.social.platforms.weixin.WXAuth;
14 | import ezy.sdk3rd.social.platforms.weixin.WXPayment;
15 | import ezy.sdk3rd.social.platforms.weixin.WXShare;
16 | import ezy.sdk3rd.social.sdk.DefaultFactory;
17 | import ezy.sdk3rd.social.sdk.Platform;
18 | import ezy.sdk3rd.social.share.ShareTo;
19 |
20 | /**
21 | * Created by ezy on 17/3/18.
22 | */
23 |
24 | public class PlatformConfig {
25 |
26 | public static void useWeibo(@NonNull String appId, @NonNull String redirectUrl) {
27 | Platform platform = new Platform(AuthorizeVia.Weibo, appId).extra("redirectUrl", redirectUrl);
28 | AuthorizeSDK.register(new DefaultFactory(platform, WBAuth.class));
29 | ShareSDK.register(new DefaultFactory(platform, WBShare.class));
30 | }
31 |
32 | public static void useQQ(@NonNull String appId) {
33 | AuthorizeSDK.register(AuthorizeVia.QQ, appId, QQAuth.class);
34 |
35 | ShareSDK.register(ShareTo.QQ, appId, TXShare.class);
36 | ShareSDK.register(ShareTo.QZone, appId, TXShare.class);
37 | ShareSDK.register(ShareTo.ToQQ, "", SendShare.class);
38 | }
39 |
40 | public static void useWeixin(@NonNull String appId) {
41 | AuthorizeSDK.register(AuthorizeVia.Weixin, appId, WXAuth.class);
42 |
43 | ShareSDK.register(ShareTo.WXSession, appId, WXShare.class);
44 | ShareSDK.register(ShareTo.WXTimeline, appId, WXShare.class);
45 | ShareSDK.register(ShareTo.WXFavorite, appId, WXShare.class);
46 | ShareSDK.register(ShareTo.ToWXSession, "", SendShare.class);
47 | ShareSDK.register(ShareTo.ToWXTimeline, "", SendShare.class);
48 | }
49 | public static void usePayments() {
50 | PaymentSDK.register(PaymentVia.Wxpay, WXPayment.class);
51 | PaymentSDK.register(PaymentVia.Alipay, Alipay.class);
52 | }
53 | }
54 |
--------------------------------------------------------------------------------
/.idea/misc.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/alipay/Result.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.alipay;
2 |
3 | import android.text.TextUtils;
4 |
5 | import java.util.HashMap;
6 | import java.util.Map;
7 |
8 | public class Result {
9 |
10 |
11 | private static final Map sResultStatus;
12 | static {
13 | sResultStatus = new HashMap();
14 | sResultStatus.put("9000", "支付成功");
15 | sResultStatus.put("8000", "支付结果确认中");
16 | sResultStatus.put("4000", "系统异常");
17 | sResultStatus.put("4001", "数据格式不正确");
18 | sResultStatus.put("4003", "该用户绑定的支付宝账户被冻结或不允许支付");
19 | sResultStatus.put("4004", "该用户已解除绑定");
20 | sResultStatus.put("4005", "绑定失败或没有绑定");
21 | sResultStatus.put("4006", "订单支付失败");
22 | sResultStatus.put("4010", "重新绑定账户");
23 | sResultStatus.put("6000", "支付服务正在进行升级操作");
24 | sResultStatus.put("6001", "用户中途取消支付操作");
25 | sResultStatus.put("7001", "网页支付失败");
26 | }
27 |
28 | public String result;
29 | public String resultStatus;
30 | public String memo;
31 | public String resultText;
32 |
33 | public Result(Map raw) {
34 |
35 | if (raw == null || raw.isEmpty()) {
36 | return;
37 | }
38 | for (String key : raw.keySet()) {
39 | if (TextUtils.equals(key, "resultStatus")) {
40 | resultStatus = raw.get(key);
41 | } else if (TextUtils.equals(key, "result")) {
42 | result = raw.get(key);
43 | } else if (TextUtils.equals(key, "memo")) {
44 | memo = raw.get(key);
45 | }
46 | }
47 | if (sResultStatus.containsKey(resultStatus)) {
48 | resultText = sResultStatus.get(resultStatus);
49 | } else {
50 | resultText = "支付失败";
51 | }
52 | }
53 |
54 | // 判断resultStatus 为“9000”则代表支付成功,具体状态码代表含义可参考接口文档
55 | public boolean isSuccess() {
56 | return "9000".equals(resultStatus);
57 | }
58 | // "8000"代表支付结果因为支付渠道原因或者系统原因还在等待支付结果确认,最终交易是否成功以服务端异步通知为准(小概率状态)
59 | public boolean isPending() {
60 | return "8000".equals(resultStatus);
61 | }
62 | public boolean isCancelled() {
63 | return "6001".equals(resultStatus);
64 | }
65 |
66 | @Override
67 | public String toString() {
68 | return "resultStatus={" + resultStatus + "};memo={" + memo + "};result={" + result + "}";
69 | }
70 |
71 | }
72 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/weixin/WXPayment.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.weixin;
2 |
3 | import android.app.Activity;
4 | import android.support.annotation.NonNull;
5 | import android.text.TextUtils;
6 | import android.util.Log;
7 |
8 | import com.tencent.mm.opensdk.modelpay.PayReq;
9 | import com.tencent.mm.opensdk.modelpay.PayResp;
10 | import com.tencent.mm.opensdk.openapi.WXAPIFactory;
11 |
12 | import org.json.JSONObject;
13 |
14 | import ezy.sdk3rd.social.payment.IPayable;
15 | import ezy.sdk3rd.social.sdk.OnCallback;
16 | import ezy.sdk3rd.social.sdk.Platform;
17 | import ezy.sdk3rd.social.sdk.ResultCode;
18 |
19 | /**
20 | * Created by ezy on 17/3/18.
21 | */
22 |
23 | public class WXPayment extends WXBase implements IPayable {
24 |
25 |
26 | WXPayment(Activity activity, Platform platform) {
27 | super(activity, platform);
28 | }
29 |
30 | @Override
31 | public void pay(String data, final @NonNull OnCallback callback) {
32 | PayReq req = new PayReq();
33 | Log.e(TAG, "data ==> " + data);
34 | try {
35 | JSONObject o = new JSONObject(data);
36 | req.appId = o.getString("appid");
37 | req.partnerId = o.getString("partnerid");
38 | req.prepayId = o.getString("prepayid");
39 | req.packageValue = o.getString("package");
40 | req.nonceStr = o.getString("noncestr");
41 | req.timeStamp = o.getString("timestamp");
42 | req.sign = o.getString("sign");
43 | req.transaction = req.nonceStr;
44 | } catch (Exception e) {
45 | Log.e(TAG, "parse error ==> " + e.toString());
46 | }
47 | if (!TextUtils.isEmpty(req.appId)) {
48 | mApi = WXAPIFactory.createWXAPI(mActivity.getApplicationContext(), req.appId, true);
49 | mApi.registerApp(req.appId);
50 | }
51 | mCallback = callback;
52 | if (!mApi.isWXAppInstalled()) {
53 | mCallback.onFailed(mActivity, ResultCode.RESULT_FAILED, "您未安装微信!");
54 | return;
55 | }
56 | mCallback.onStarted(mActivity);
57 | boolean ret = mApi.sendReq(req);
58 | Log.e(TAG, "send end, pay request ==> " + ret);
59 |
60 | if (ret) {
61 | }
62 | }
63 |
64 | @Override
65 | protected void onResultOk(PayResp resp) {
66 | Log.e(TAG, "prepayId = " + resp.prepayId);
67 | mCallback.onSucceed(mActivity, resp.prepayId);
68 | }
69 | }
70 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/weibo/WBAuth.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.weibo;
2 |
3 | import android.app.Activity;
4 | import android.content.Intent;
5 | import android.support.annotation.NonNull;
6 | import android.util.Log;
7 |
8 | import com.sina.weibo.sdk.WbSdk;
9 | import com.sina.weibo.sdk.auth.AuthInfo;
10 | import com.sina.weibo.sdk.auth.Oauth2AccessToken;
11 | import com.sina.weibo.sdk.auth.WbAuthListener;
12 | import com.sina.weibo.sdk.auth.WbConnectErrorMessage;
13 | import com.sina.weibo.sdk.auth.sso.SsoHandler;
14 |
15 | import ezy.sdk3rd.social.authorize.IAuthorize;
16 | import ezy.sdk3rd.social.sdk.OnCallback;
17 | import ezy.sdk3rd.social.sdk.Platform;
18 | import ezy.sdk3rd.social.sdk.ResultCode;
19 |
20 | /**
21 | * Created by ezy on 17/3/18.
22 | */
23 |
24 | public class WBAuth implements IAuthorize {
25 | public static final String TAG = "ezy.sdk3rd.weibo.auth";
26 |
27 | Activity mActivity;
28 | Platform mPlatform;
29 |
30 | SsoHandler mApi;
31 |
32 | WBAuth(Activity activity, Platform platform) {
33 | WbSdk.install(activity, new AuthInfo(activity, platform.getAppId(), platform.extra("redirectUrl"), "all"));
34 | mActivity = activity;
35 | mPlatform = platform;
36 | mApi = new SsoHandler(mActivity);
37 |
38 | }
39 |
40 | @Override
41 | public void authorize(@NonNull final OnCallback callback) {
42 | callback.onStarted(mActivity);
43 | mApi.authorize(new WbAuthListener() {
44 | @Override
45 | public void onSuccess(Oauth2AccessToken token) {
46 | Log.e(TAG, token.toString());
47 | if (token.isSessionValid()) {
48 | callback.onSucceed(mActivity, "token|" + token.getUid() + "|" + token.getToken());
49 | }
50 | callback.onCompleted(mActivity);
51 | }
52 |
53 | @Override
54 | public void cancel() {
55 | Log.e(TAG, "用户取消了登录");
56 | callback.onFailed(mActivity, ResultCode.RESULT_CANCELLED, "用户取消了登录");
57 | }
58 |
59 | @Override
60 | public void onFailure(WbConnectErrorMessage e) {
61 | Log.e(TAG, e.getErrorMessage());
62 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, e.getErrorMessage());
63 | }
64 | });
65 | }
66 |
67 | @Override
68 | public void onResult(int requestCode, int resultCode, Intent data) {
69 | if (mApi != null) {
70 | mApi.authorizeCallBack(requestCode, resultCode, data);
71 | }
72 | }
73 | }
74 |
--------------------------------------------------------------------------------
/gradlew.bat:
--------------------------------------------------------------------------------
1 | @if "%DEBUG%" == "" @echo off
2 | @rem ##########################################################################
3 | @rem
4 | @rem Gradle startup script for Windows
5 | @rem
6 | @rem ##########################################################################
7 |
8 | @rem Set local scope for the variables with windows NT shell
9 | if "%OS%"=="Windows_NT" setlocal
10 |
11 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
12 | set DEFAULT_JVM_OPTS=
13 |
14 | set DIRNAME=%~dp0
15 | if "%DIRNAME%" == "" set DIRNAME=.
16 | set APP_BASE_NAME=%~n0
17 | set APP_HOME=%DIRNAME%
18 |
19 | @rem Find java.exe
20 | if defined JAVA_HOME goto findJavaFromJavaHome
21 |
22 | set JAVA_EXE=java.exe
23 | %JAVA_EXE% -version >NUL 2>&1
24 | if "%ERRORLEVEL%" == "0" goto init
25 |
26 | echo.
27 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
28 | echo.
29 | echo Please set the JAVA_HOME variable in your environment to match the
30 | echo location of your Java installation.
31 |
32 | goto fail
33 |
34 | :findJavaFromJavaHome
35 | set JAVA_HOME=%JAVA_HOME:"=%
36 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe
37 |
38 | if exist "%JAVA_EXE%" goto init
39 |
40 | echo.
41 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
42 | echo.
43 | echo Please set the JAVA_HOME variable in your environment to match the
44 | echo location of your Java installation.
45 |
46 | goto fail
47 |
48 | :init
49 | @rem Get command-line arguments, handling Windowz variants
50 |
51 | if not "%OS%" == "Windows_NT" goto win9xME_args
52 | if "%@eval[2+2]" == "4" goto 4NT_args
53 |
54 | :win9xME_args
55 | @rem Slurp the command line arguments.
56 | set CMD_LINE_ARGS=
57 | set _SKIP=2
58 |
59 | :win9xME_args_slurp
60 | if "x%~1" == "x" goto execute
61 |
62 | set CMD_LINE_ARGS=%*
63 | goto execute
64 |
65 | :4NT_args
66 | @rem Get arguments from the 4NT Shell from JP Software
67 | set CMD_LINE_ARGS=%$
68 |
69 | :execute
70 | @rem Setup the command line
71 |
72 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
73 |
74 | @rem Execute Gradle
75 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
76 |
77 | :end
78 | @rem End local scope for the variables with windows NT shell
79 | if "%ERRORLEVEL%"=="0" goto mainEnd
80 |
81 | :fail
82 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
83 | rem the _cmd.exe /c_ return code!
84 | if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
85 | exit /b 1
86 |
87 | :mainEnd
88 | if "%OS%"=="Windows_NT" endlocal
89 |
90 | :omega
91 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/qq/QQAuth.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.qq;
2 |
3 | import android.app.Activity;
4 | import android.content.Intent;
5 | import android.support.annotation.NonNull;
6 | import android.text.TextUtils;
7 | import android.util.Log;
8 |
9 | import com.tencent.connect.common.Constants;
10 | import com.tencent.tauth.IUiListener;
11 | import com.tencent.tauth.Tencent;
12 | import com.tencent.tauth.UiError;
13 |
14 | import org.json.JSONObject;
15 |
16 | import ezy.sdk3rd.social.authorize.IAuthorize;
17 | import ezy.sdk3rd.social.sdk.OnCallback;
18 | import ezy.sdk3rd.social.sdk.Platform;
19 | import ezy.sdk3rd.social.sdk.ResultCode;
20 |
21 | /**
22 | * Created by ezy on 17/3/18.
23 | */
24 |
25 | public class QQAuth implements IAuthorize {
26 | public static final String TAG = "ezy.sdk3rd.qq.auth";
27 |
28 | Activity mActivity;
29 | Platform mPlatform;
30 | Tencent mApi;
31 |
32 | IUiListener mListener;
33 |
34 | QQAuth(Activity activity, Platform platform) {
35 | mActivity = activity;
36 | mPlatform = platform;
37 | mApi = Tencent.createInstance(platform.getAppId(), mActivity);
38 | }
39 |
40 | String toMessage(UiError error) {
41 | return "[" + error.errorCode + "]" + error.errorMessage;
42 | }
43 |
44 | @Override
45 | public void authorize(@NonNull final OnCallback callback) {
46 | mListener = new IUiListener() {
47 | @Override
48 | public void onComplete(Object response) {
49 | Log.e(TAG, "complete ==> " + response);
50 | if (response instanceof JSONObject && ((JSONObject) response).length() > 0) {
51 | JSONObject jo = (JSONObject) response;
52 | String token = jo.optString(Constants.PARAM_ACCESS_TOKEN);
53 | String expires = jo.optString(Constants.PARAM_EXPIRES_IN);
54 | String openId = jo.optString(Constants.PARAM_OPEN_ID);
55 | if (!TextUtils.isEmpty(token) && !TextUtils.isEmpty(expires) && !TextUtils.isEmpty(openId)) {
56 | mApi.setAccessToken(token, expires);
57 | mApi.setOpenId(openId);
58 | }
59 | callback.onSucceed(mActivity, "token|" + mApi.getOpenId() + "|" + mApi.getAccessToken());
60 | } else {
61 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, "登录失败: 返回为空");
62 | }
63 | callback.onCompleted(mActivity);
64 | }
65 |
66 |
67 | @Override
68 | public void onError(UiError e) {
69 | Log.e(TAG, "error ==> " + e.errorDetail);
70 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, toMessage(e));
71 | }
72 |
73 | @Override
74 | public void onCancel() {
75 | callback.onFailed(mActivity, ResultCode.RESULT_CANCELLED, "用户取消了登录");
76 | }
77 | };
78 | callback.onStarted(mActivity);
79 | mApi.login(mActivity, "get_simple_userinfo", mListener);
80 | }
81 |
82 | @Override
83 | public void onResult(int requestCode, int resultCode, Intent data) {
84 | if (requestCode == Constants.REQUEST_LOGIN) {
85 | Tencent.onActivityResultData(requestCode, resultCode, data, mListener);
86 | }
87 | }
88 |
89 | }
90 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/ShareSDK.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social;
2 |
3 | import android.app.Activity;
4 | import android.content.Intent;
5 |
6 | import ezy.sdk3rd.social.sdk.DefaultCallback;
7 | import ezy.sdk3rd.social.sdk.IFactory;
8 | import ezy.sdk3rd.social.sdk.OnCallback;
9 | import ezy.sdk3rd.social.sdk.OnSucceed;
10 | import ezy.sdk3rd.social.sdk.ResultCode;
11 | import ezy.sdk3rd.social.sdk.Sdk;
12 | import ezy.sdk3rd.social.share.IShareable;
13 | import ezy.sdk3rd.social.share.ShareData;
14 | import ezy.sdk3rd.social.share.image.resource.ImageResource;
15 | import ezy.sdk3rd.social.share.media.IMediaObject;
16 | import ezy.sdk3rd.social.share.media.MoImage;
17 |
18 | public class ShareSDK {
19 | static Sdk sdk = new Sdk<>();
20 |
21 | public static void setDefaultCallback(OnCallback callback) {
22 | sdk.setDefaultCallback(callback);
23 | }
24 |
25 | public static void register(String name, String appId, Class clazz) {
26 | sdk.register(name, appId, clazz);
27 | }
28 |
29 | public static void register(IFactory factory) {
30 | sdk.register(factory);
31 | }
32 |
33 |
34 | private ShareData mData = new ShareData();
35 |
36 | private Activity mActivity;
37 |
38 | private ShareSDK(Activity activity, String text, IMediaObject media) {
39 | mActivity = activity;
40 | mData.text = text;
41 | mData.media = media;
42 | }
43 |
44 | // 文本
45 | public static ShareSDK make(Activity activity, String text) {
46 | return new ShareSDK(activity, text, null);
47 | }
48 |
49 | // 图片
50 | public static ShareSDK make(Activity activity, ImageResource image) {
51 | return new ShareSDK(activity, null, new MoImage(image));
52 | }
53 |
54 | // 图片、音乐、视频、文件
55 | public static ShareSDK make(Activity activity, IMediaObject media) {
56 | return new ShareSDK(activity, null, media);
57 | }
58 |
59 | public static ShareSDK make(Activity activity, String text, IMediaObject media) {
60 | return new ShareSDK(activity, text, media);
61 | }
62 |
63 | public ShareSDK withUrl(String value) {
64 | mData.url = value;
65 | return this;
66 | }
67 |
68 | public ShareSDK withTitle(String value) {
69 | mData.title = value;
70 | return this;
71 | }
72 |
73 | public ShareSDK withDescription(String value) {
74 | mData.description = value;
75 | return this;
76 | }
77 |
78 | public ShareSDK withThumb(ImageResource thumb) {
79 | mData.thumb = thumb;
80 | return this;
81 | }
82 |
83 | public void share(String platform) {
84 | share(platform, new DefaultCallback(sdk.getDefaultCallback(), null));
85 | }
86 |
87 | public void share(String platform, OnSucceed listener) {
88 | share(platform, new DefaultCallback(sdk.getDefaultCallback(), listener));
89 | }
90 | public void share(String platform, OnCallback callback) {
91 | if (!sdk.isSupport(platform)) {
92 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, "不支持的平台[" + platform + "]");
93 | return;
94 | }
95 | IShareable api = sdk.get(mActivity, platform);
96 | if (api == null) {
97 | return;
98 | }
99 | api.share(mData, callback);
100 | }
101 |
102 | public static void onHandleResult(Activity activity, int requestCode, int resultCode, Intent data) {
103 | sdk.onHandleResult(activity, requestCode, resultCode, data);
104 | }
105 | }
--------------------------------------------------------------------------------
/.idea/codeStyles/Project.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 | xmlns:android
11 |
12 | ^$
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 | xmlns:.*
22 |
23 | ^$
24 |
25 |
26 | BY_NAME
27 |
28 |
29 |
30 |
31 |
32 |
33 | .*:id
34 |
35 | http://schemas.android.com/apk/res/android
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 | .*:name
45 |
46 | http://schemas.android.com/apk/res/android
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 | name
56 |
57 | ^$
58 |
59 |
60 |
61 |
62 |
63 |
64 |
65 |
66 | style
67 |
68 | ^$
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 | .*
78 |
79 | ^$
80 |
81 |
82 | BY_NAME
83 |
84 |
85 |
86 |
87 |
88 |
89 | .*
90 |
91 | http://schemas.android.com/apk/res/android
92 |
93 |
94 | ANDROID_ATTRIBUTE_ORDER
95 |
96 |
97 |
98 |
99 |
100 |
101 | .*
102 |
103 | .*
104 |
105 |
106 | BY_NAME
107 |
108 |
109 |
110 |
111 |
112 |
113 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/weixin/WXBase.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.weixin;
2 |
3 | import android.app.Activity;
4 | import android.content.Intent;
5 | import android.text.TextUtils;
6 | import android.util.Log;
7 |
8 | import com.tencent.mm.opensdk.constants.ConstantsAPI;
9 | import com.tencent.mm.opensdk.modelbase.BaseReq;
10 | import com.tencent.mm.opensdk.modelbase.BaseResp;
11 | import com.tencent.mm.opensdk.modelmsg.SendAuth;
12 | import com.tencent.mm.opensdk.modelmsg.SendMessageToWX;
13 | import com.tencent.mm.opensdk.modelpay.PayResp;
14 | import com.tencent.mm.opensdk.openapi.IWXAPI;
15 | import com.tencent.mm.opensdk.openapi.IWXAPIEventHandler;
16 | import com.tencent.mm.opensdk.openapi.WXAPIFactory;
17 |
18 | import java.util.WeakHashMap;
19 |
20 | import ezy.sdk3rd.social.sdk.IResult;
21 | import ezy.sdk3rd.social.sdk.OnCallback;
22 | import ezy.sdk3rd.social.sdk.Platform;
23 | import ezy.sdk3rd.social.sdk.ResultCode;
24 |
25 | /**
26 | * Created by ezy on 17/3/18.
27 | */
28 |
29 | abstract class WXBase implements IResult, IWXAPIEventHandler {
30 | public static final String TAG = "ezy.sdk3rd.wx";
31 |
32 | public static int REQUEST_CODE = 1999;
33 |
34 | static WeakHashMap services = new WeakHashMap<>();
35 |
36 | final protected Activity mActivity;
37 | final protected Platform mPlatform;
38 |
39 | protected OnCallback mCallback;
40 |
41 | IWXAPI mApi;
42 |
43 | protected WXBase(Activity activity, Platform platform) {
44 | mActivity = activity;
45 | mPlatform = platform;
46 | if (!TextUtils.isEmpty(platform.getAppId())) {
47 | mApi = WXAPIFactory.createWXAPI(activity.getApplicationContext(), platform.getAppId(), true);
48 | mApi.registerApp(platform.getAppId());
49 | }
50 | services.put(this, true);
51 | }
52 |
53 |
54 | @Override
55 | public void onResult(int requestCode, int resultCode, Intent data) {
56 | if (mApi != null && requestCode == REQUEST_CODE) {
57 | mApi.handleIntent(data, this);
58 | }
59 | }
60 |
61 | @Override
62 | public void onReq(BaseReq req) {
63 | Log.e(TAG, "transaction = " + req.transaction + ", type = " + req.getType() + ", openId = " + req.openId);
64 | }
65 |
66 | @Override
67 | public void onResp(BaseResp resp) {
68 | Log.e(TAG, "transaction = " + resp.transaction + ", type = " + resp.getType() + ", errCode = " + resp.errCode + ", err = " + resp.errStr);
69 |
70 | if (resp.errCode == BaseResp.ErrCode.ERR_OK) {
71 | switch (resp.getType()) {
72 | case ConstantsAPI.COMMAND_SENDAUTH:
73 | onResultOk((SendAuth.Resp) resp);
74 | break;
75 | case ConstantsAPI.COMMAND_PAY_BY_WX:
76 | onResultOk((PayResp) resp);
77 | break;
78 | case ConstantsAPI.COMMAND_SENDMESSAGE_TO_WX:
79 | onResultOk((SendMessageToWX.Resp) resp);
80 | break;
81 | }
82 | } else if (resp.errCode == BaseResp.ErrCode.ERR_USER_CANCEL) {
83 | mCallback.onFailed(mActivity, ResultCode.RESULT_CANCELLED, toMessage(resp));
84 | } else {
85 | mCallback.onFailed(mActivity, ResultCode.RESULT_FAILED, toMessage(resp));
86 | }
87 | mCallback.onCompleted(mActivity);
88 | }
89 |
90 | String toMessage(BaseResp resp) {
91 | return "[" + resp.errCode + "]" + (resp.errStr == null ? "" : resp.errStr);
92 | }
93 |
94 | protected void onResultOk(PayResp resp) {
95 |
96 | }
97 |
98 | protected void onResultOk(SendAuth.Resp resp) {
99 | }
100 |
101 | protected void onResultOk(SendMessageToWX.Resp resp) {
102 | }
103 | }
104 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/sdk/Sdk.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.sdk;
2 |
3 | import android.app.Activity;
4 | import android.app.Application;
5 | import android.content.Intent;
6 | import android.os.Bundle;
7 |
8 | import java.io.Closeable;
9 | import java.util.HashMap;
10 | import java.util.Map;
11 | import java.util.WeakHashMap;
12 |
13 | /**
14 | *
15 | * Created by ezy on 17/3/18.
16 | */
17 |
18 | public class Sdk {
19 |
20 | private Map mPlatforms = new HashMap<>();
21 | private Map> mMap = new WeakHashMap<>();
22 | private Map> mFactories = new HashMap<>();
23 |
24 | private OnCallback mDefaultCallback;
25 |
26 | public OnCallback getDefaultCallback() {
27 | return mDefaultCallback;
28 | }
29 | public void setDefaultCallback(OnCallback callback) {
30 | mDefaultCallback = callback;
31 | }
32 |
33 | public void register(String name, String appId, Class clazz) {
34 | mFactories.put(name, new DefaultFactory(name, appId, clazz));
35 | }
36 |
37 | public void register(IFactory factory) {
38 | mFactories.put(factory.getPlatform().getName(), factory);
39 | }
40 |
41 | public boolean isSupport(String platform) {
42 | return mFactories.get(platform) != null;
43 | }
44 |
45 | public T get(final Activity activity, final String platform) {
46 | Map sub = mMap.get(activity);
47 | if (sub == null) {
48 | sub = new HashMap<>();
49 | mMap.put(activity, sub);
50 | }
51 | T api = sub.get(platform);
52 | if (api == null) {
53 | IFactory factory = mFactories.get(platform);
54 | if (factory != null) {
55 | api = factory.create(activity);
56 | if (api != null) {
57 | sub.put(platform, api);
58 | activity.getApplication().registerActivityLifecycleCallbacks(new LifecycleCallback(activity, api));
59 | }
60 | }
61 | }
62 | return api;
63 | }
64 |
65 | public void onHandleResult(Activity activity, int requestCode, int resultCode, Intent data) {
66 | if (mMap.containsKey(activity)) {
67 | for (T api: mMap.get(activity).values()) {
68 | if (api != null) {
69 | api.onResult(requestCode, resultCode, data);
70 | }
71 | }
72 | }
73 | }
74 |
75 | private class LifecycleCallback implements Application.ActivityLifecycleCallbacks {
76 |
77 | final private Activity _activity;
78 | final private IResult _api;
79 | public LifecycleCallback(Activity activity, IResult api) {
80 | _activity = activity;
81 | _api = api;
82 | }
83 |
84 | @Override
85 | public void onActivityCreated(Activity activity, Bundle savedInstanceState) {
86 |
87 | }
88 |
89 | @Override
90 | public void onActivityStarted(Activity activity) {
91 |
92 | }
93 |
94 | @Override
95 | public void onActivityResumed(Activity activity) {
96 |
97 | }
98 |
99 | @Override
100 | public void onActivityPaused(Activity activity) {
101 |
102 | }
103 |
104 | @Override
105 | public void onActivityStopped(Activity activity) {
106 |
107 | }
108 |
109 | @Override
110 | public void onActivitySaveInstanceState(Activity activity, Bundle outState) {
111 |
112 | }
113 |
114 | @Override
115 | public void onActivityDestroyed(Activity activity) {
116 | if (activity == _activity) {
117 | activity.getApplication().unregisterActivityLifecycleCallbacks(this);
118 | if (_api instanceof IDisposable) {
119 | ((IDisposable) _api).onDispose();
120 | }
121 | }
122 |
123 | }
124 | }
125 |
126 | }
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/weibo/WBShare.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.weibo;
2 |
3 | import android.app.Activity;
4 | import android.content.Intent;
5 | import android.support.annotation.NonNull;
6 | import android.text.TextUtils;
7 | import android.util.Log;
8 |
9 | import com.sina.weibo.sdk.WbSdk;
10 | import com.sina.weibo.sdk.api.ImageObject;
11 | import com.sina.weibo.sdk.api.TextObject;
12 | import com.sina.weibo.sdk.api.WebpageObject;
13 | import com.sina.weibo.sdk.api.WeiboMultiMessage;
14 | import com.sina.weibo.sdk.auth.AuthInfo;
15 | import com.sina.weibo.sdk.share.WbShareCallback;
16 | import com.sina.weibo.sdk.share.WbShareHandler;
17 | import com.sina.weibo.sdk.utils.Utility;
18 |
19 | import java.util.Map;
20 | import java.util.WeakHashMap;
21 |
22 | import ezy.sdk3rd.social.sdk.IResult;
23 | import ezy.sdk3rd.social.sdk.OnCallback;
24 | import ezy.sdk3rd.social.sdk.Platform;
25 | import ezy.sdk3rd.social.sdk.ResultCode;
26 | import ezy.sdk3rd.social.share.IShareable;
27 | import ezy.sdk3rd.social.share.ShareData;
28 | import ezy.sdk3rd.social.share.image.resource.ImageResource;
29 | import ezy.sdk3rd.social.share.media.MoImage;
30 |
31 | /**
32 | * Created by ezy on 17/3/18.
33 | */
34 |
35 | public class WBShare implements IShareable, WbShareCallback {
36 | public static final String TAG = "ezy.sdk3rd.weibo.share";
37 |
38 | public static int REQUEST_CODE = 1998;
39 |
40 | static Map services = new WeakHashMap<>();
41 |
42 |
43 | Activity mActivity;
44 | Platform mPlatform;
45 |
46 | WbShareHandler mApi;
47 | OnCallback mCallback;
48 |
49 | WBShare(Activity activity, Platform platform) {
50 | WbSdk.install(activity, new AuthInfo(activity, platform.getAppId(), platform.extra("redirectUrl"), "all"));
51 | mActivity = activity;
52 | mPlatform = platform;
53 | mApi = new WbShareHandler(mActivity);
54 | mApi.registerApp();
55 | services.put(this, true);
56 | }
57 |
58 | TextObject toText(String text) {
59 | TextObject object = new TextObject();
60 | object.text = text;
61 | return object;
62 | }
63 |
64 | ImageObject toImage(ImageResource resource) {
65 | ImageObject object = new ImageObject();
66 | object.imagePath = resource.toUri();
67 | if (TextUtils.isEmpty(object.imagePath)) {
68 | object.imageData = resource.toBytes();
69 | }
70 | return object;
71 | }
72 |
73 | WebpageObject toWeb(ShareData data) {
74 | WebpageObject mo = new WebpageObject();
75 | mo.identify = Utility.generateGUID();
76 | mo.title = data.title;
77 | mo.description = data.description;
78 | // Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.ic_logo);
79 | // 设置 Bitmap 类型的图片到视频对象里 设置缩略图。 注意:最终压缩过的缩略图大小不得超过 32kb。
80 | mo.setThumbImage(data.thumb.toBitmap());
81 | mo.actionUrl = data.url;
82 | mo.defaultText = "Webpage 默认文案";
83 | return mo;
84 | }
85 |
86 | @Override
87 | public void share(@NonNull final ShareData data, @NonNull final OnCallback callback) {
88 |
89 | // if (!mApi.isWeiboAppInstalled()) {
90 | // callback.onFailed(mActivity, ResultCode.RESULT_FAILED, "您未安装微博!");
91 | // return;
92 | // }
93 |
94 | WeiboMultiMessage message = new WeiboMultiMessage();
95 |
96 | if (data.hasText()) {
97 | message.textObject = toText(data.hasUrl() ? (data.text + " " + data.url) : data.text);
98 | }
99 |
100 | if (data.media instanceof MoImage) {
101 | message.imageObject = toImage(((MoImage) data.media).resource);
102 | }
103 |
104 | if (message.textObject == null && message.imageObject == null) {
105 | // unsupported
106 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, "不支持的分享类型");
107 | return;
108 | }
109 |
110 | mCallback = callback;
111 | mCallback.onStarted(mActivity);
112 |
113 | mApi.shareMessage(message, true);
114 | }
115 |
116 | @Override
117 | public void onResult(int requestCode, int resultCode, Intent data) {
118 | Log.e(TAG, "==> requestCode = " + requestCode + ", " + data);
119 | if (mApi != null && requestCode == REQUEST_CODE) {
120 | mApi.doResultIntent(data, this);
121 | }
122 | }
123 |
124 | @Override
125 | public void onWbShareCancel() {
126 | mCallback.onFailed(mActivity, ResultCode.RESULT_CANCELLED, "");
127 | mCallback.onCompleted(mActivity);
128 | }
129 |
130 | @Override
131 | public void onWbShareFail() {
132 | mCallback.onFailed(mActivity, ResultCode.RESULT_FAILED, "");
133 | mCallback.onCompleted(mActivity);
134 | }
135 |
136 | @Override
137 | public void onWbShareSuccess() {
138 | mCallback.onSucceed(mActivity, "");
139 | mCallback.onCompleted(mActivity);
140 | }
141 |
142 | }
143 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/weixin/WXShare.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.weixin;
2 |
3 | import android.app.Activity;
4 | import android.os.AsyncTask;
5 | import android.support.annotation.NonNull;
6 | import android.text.TextUtils;
7 |
8 | import com.tencent.mm.opensdk.modelbase.BaseReq;
9 | import com.tencent.mm.opensdk.modelmsg.SendMessageToWX;
10 | import com.tencent.mm.opensdk.modelmsg.WXImageObject;
11 | import com.tencent.mm.opensdk.modelmsg.WXMediaMessage;
12 | import com.tencent.mm.opensdk.modelmsg.WXMusicObject;
13 | import com.tencent.mm.opensdk.modelmsg.WXTextObject;
14 | import com.tencent.mm.opensdk.modelmsg.WXVideoObject;
15 | import com.tencent.mm.opensdk.modelmsg.WXWebpageObject;
16 |
17 | import ezy.sdk3rd.social.sdk.OnCallback;
18 | import ezy.sdk3rd.social.sdk.Platform;
19 | import ezy.sdk3rd.social.sdk.ResultCode;
20 | import ezy.sdk3rd.social.share.IShareable;
21 | import ezy.sdk3rd.social.share.ShareData;
22 | import ezy.sdk3rd.social.share.ShareTo;
23 | import ezy.sdk3rd.social.share.media.IMediaObject;
24 | import ezy.sdk3rd.social.share.media.MoImage;
25 | import ezy.sdk3rd.social.share.media.MoMusic;
26 | import ezy.sdk3rd.social.share.media.MoVideo;
27 | import ezy.sdk3rd.social.share.media.MoWeb;
28 |
29 | /**
30 | * Created by ezy on 17/3/18.
31 | */
32 |
33 | public class WXShare extends WXBase implements IShareable {
34 |
35 | WXShare(Activity activity, Platform platform) {
36 | super(activity, platform);
37 | }
38 |
39 | @Override
40 | public void share(@NonNull final ShareData data, @NonNull final OnCallback callback) {
41 |
42 | if (!mApi.isWXAppInstalled()) {
43 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, "您未安装微信!");
44 | return;
45 | }
46 | mCallback = callback;
47 | new AsyncTask() {
48 | @Override
49 | protected BaseReq doInBackground(ShareData... params) {
50 | return makeReq(params[0]);
51 | }
52 |
53 | @Override
54 | protected void onPostExecute(BaseReq req) {
55 | mCallback.onStarted(mActivity);
56 | mApi.sendReq(req);
57 | }
58 | }.execute(data);
59 | }
60 |
61 | BaseReq makeReq(ShareData data) {
62 |
63 | WXMediaMessage message = new WXMediaMessage();
64 | if (data.hasTitle()) {
65 | message.title = data.title;
66 | }
67 | if (data.hasDescription()) {
68 | message.description = data.description;
69 | }
70 | if (data.hasThumb()) {
71 | message.thumbData = data.thumb.toBytes();
72 | }
73 |
74 | switch (data.type()) {
75 | case IMediaObject.TYPE_TEXT:
76 | message.mediaObject = new WXTextObject(data.text);
77 | message.description = data.text;
78 | break;
79 | case IMediaObject.TYPE_WEB:
80 | message.mediaObject = new WXWebpageObject(((MoWeb) data.media).url);
81 | break;
82 | case IMediaObject.TYPE_EMOJI:
83 | case IMediaObject.TYPE_IMAGE: {
84 |
85 | MoImage mo = (MoImage) data.media;
86 | WXImageObject wxo = new WXImageObject();
87 | wxo.imagePath = mo.toUri();
88 | if (TextUtils.isEmpty(wxo.imagePath)) {
89 | wxo.imageData = mo.toBytes();
90 | }
91 | // wxo.imageData = data.thumb.toBytes();
92 | message.mediaObject = wxo;
93 | }
94 | break;
95 | case IMediaObject.TYPE_VIDEO: {
96 | MoVideo mo = (MoVideo) data.media;
97 | WXVideoObject wxo = new WXVideoObject();
98 | wxo.videoUrl = mo.mediaUrl;
99 | wxo.videoLowBandUrl = mo.lowBandUrl;
100 | message.mediaObject = wxo;
101 | }
102 | break;
103 | case IMediaObject.TYPE_MUSIC: {
104 | MoMusic mo = (MoMusic) data.media;
105 | WXMusicObject wxo = new WXMusicObject();
106 | wxo.musicUrl = mo.mediaUrl;
107 | wxo.musicDataUrl = mo.mediaDataUrl;
108 | wxo.musicLowBandUrl = mo.lowBandUrl;
109 | wxo.musicLowBandDataUrl = mo.lowBandDataUrl;
110 | message.mediaObject = wxo;
111 | }
112 | break;
113 |
114 | }
115 |
116 | SendMessageToWX.Req req = new SendMessageToWX.Req();
117 | req.transaction = String.valueOf(System.currentTimeMillis());
118 | req.message = message;
119 | req.scene = toScene(mPlatform.getName());
120 |
121 | return req;
122 | }
123 |
124 | @Override
125 | protected void onResultOk(SendMessageToWX.Resp resp) {
126 | mCallback.onSucceed(mActivity, "");
127 | }
128 |
129 | int toScene(String platform) {
130 | switch (platform) {
131 | case ShareTo.WXSession:
132 | return 0;
133 | case ShareTo.WXTimeline:
134 | return 1;
135 | case ShareTo.WXFavorite:
136 | return 2;
137 | }
138 | return 0;
139 | }
140 |
141 |
142 | }
143 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/send/SendShare.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.send;
2 |
3 | import android.app.Activity;
4 | import android.content.Context;
5 | import android.content.Intent;
6 | import android.content.pm.PackageInfo;
7 | import android.content.pm.PackageManager;
8 | import android.net.Uri;
9 | import android.provider.MediaStore;
10 | import android.support.annotation.NonNull;
11 | import android.util.Log;
12 |
13 | import java.util.List;
14 |
15 | import ezy.sdk3rd.social.sdk.OnCallback;
16 | import ezy.sdk3rd.social.sdk.Platform;
17 | import ezy.sdk3rd.social.sdk.ResultCode;
18 | import ezy.sdk3rd.social.share.IShareable;
19 | import ezy.sdk3rd.social.share.ShareData;
20 | import ezy.sdk3rd.social.share.ShareTo;
21 | import ezy.sdk3rd.social.share.image.resource.BitmapResource;
22 | import ezy.sdk3rd.social.share.image.resource.FileResource;
23 | import ezy.sdk3rd.social.share.image.resource.ImageResource;
24 | import ezy.sdk3rd.social.share.media.IMediaObject;
25 | import ezy.sdk3rd.social.share.media.MoImage;
26 |
27 | /**
28 | * Created by ezy on 17/3/18.
29 | */
30 |
31 | public class SendShare implements IShareable {
32 | public static final String TAG = "ezy.sdk3rd.qq.share";
33 |
34 | static final String PACKAGE_QQ = "com.tencent.mobileqq";
35 | static final String PACKAGE_WX = "com.tencent.mm";
36 |
37 | Activity mActivity;
38 | Platform mPlatform;
39 |
40 |
41 | SendShare(Activity activity, Platform platform) {
42 | mActivity = activity;
43 | mPlatform = platform;
44 | }
45 |
46 | @Override
47 | public void share(@NonNull final ShareData data, @NonNull final OnCallback callback) {
48 |
49 | if (mPlatform.getName().equals(ShareTo.ToQQ)) {
50 | if (!isApplicationInstalled(mActivity, PACKAGE_QQ)) {
51 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, "无法分享,请先安装QQ");
52 | return;
53 | }
54 | } else {
55 | if (!isApplicationInstalled(mActivity, PACKAGE_WX)) {
56 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, "无法分享,请先安装微信");
57 | return;
58 | }
59 | }
60 | Intent intent = new Intent(Intent.ACTION_SEND);
61 |
62 | if (mPlatform.getName().equals(ShareTo.ToQQ)) {
63 | intent.setClassName(PACKAGE_QQ, "com.tencent.mobileqq.activity.JumpActivity");
64 | } else if (mPlatform.getName().equals(ShareTo.ToWXSession)) {
65 | intent.setClassName(PACKAGE_WX, "com.tencent.mm.ui.tools.ShareImgUI");
66 | } else {
67 | intent.setClassName(PACKAGE_WX, "com.tencent.mm.ui.tools.ShareToTimeLineUI");
68 | }
69 |
70 | switch (data.type()) {
71 | case IMediaObject.TYPE_IMAGE:
72 | intent.setType("image/*");
73 | intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK | Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_GRANT_READ_URI_PERMISSION);
74 |
75 |
76 |
77 | ImageResource resource = ((MoImage) data.media).resource;
78 | if (resource instanceof BitmapResource) {
79 | final Uri uri = Uri.parse(MediaStore.Images.Media.insertImage(mActivity.getContentResolver(), resource.toBitmap(), null, null));
80 | intent.putExtra(Intent.EXTRA_STREAM, uri);
81 | } else if (resource instanceof FileResource) {
82 | intent.putExtra(Intent.EXTRA_STREAM, Uri.fromFile(((FileResource) resource).file));
83 | } else {
84 | Log.e("ezy", "" + Uri.parse(resource.toUri()));
85 | intent.setData(Uri.parse(resource.toUri()));
86 | // final Uri uri = Uri.parse(MediaStore.Images.Media.insertImage(mActivity.getContentResolver(), data.thumb.toBitmap(), null, null));
87 | // intent.putExtra(Intent.EXTRA_STREAM, uri);
88 | }
89 | break;
90 | case IMediaObject.TYPE_TEXT:
91 | intent.setType("text/plain");
92 | intent.putExtra("Kdescription", data.text);
93 | intent.putExtra(Intent.EXTRA_TEXT, data.text);
94 | intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
95 | break;
96 | default:
97 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, "不支持的分享类型");
98 | return;
99 | }
100 | if (isIntentAvailable(mActivity, intent)) {
101 | mActivity.startActivity(intent);
102 | } else {
103 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, "分享失败");
104 | return;
105 | }
106 | }
107 |
108 | boolean isIntentAvailable(Context context, Intent intent) {
109 | PackageManager pm = context.getPackageManager();
110 | List list = pm.queryIntentActivities(intent, PackageManager.MATCH_DEFAULT_ONLY);
111 | return list.size() > 0;
112 | }
113 |
114 | boolean isApplicationInstalled(Context context, String packageName) {
115 | PackageManager pm = context.getPackageManager();
116 | List list = pm.getInstalledPackages(0);
117 | for (int i = 0; i < list.size(); i++) {
118 | if (list.get(i).packageName.equalsIgnoreCase(packageName)) {
119 | return true;
120 | }
121 | }
122 | return false;
123 | }
124 |
125 |
126 | @Override
127 | public void onResult(int requestCode, int resultCode, Intent data) {
128 | }
129 | }
130 |
--------------------------------------------------------------------------------
/gradlew:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env bash
2 |
3 | ##############################################################################
4 | ##
5 | ## Gradle start up script for UN*X
6 | ##
7 | ##############################################################################
8 |
9 | # Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
10 | DEFAULT_JVM_OPTS=""
11 |
12 | APP_NAME="Gradle"
13 | APP_BASE_NAME=`basename "$0"`
14 |
15 | # Use the maximum available, or set MAX_FD != -1 to use that value.
16 | MAX_FD="maximum"
17 |
18 | warn ( ) {
19 | echo "$*"
20 | }
21 |
22 | die ( ) {
23 | echo
24 | echo "$*"
25 | echo
26 | exit 1
27 | }
28 |
29 | # OS specific support (must be 'true' or 'false').
30 | cygwin=false
31 | msys=false
32 | darwin=false
33 | case "`uname`" in
34 | CYGWIN* )
35 | cygwin=true
36 | ;;
37 | Darwin* )
38 | darwin=true
39 | ;;
40 | MINGW* )
41 | msys=true
42 | ;;
43 | esac
44 |
45 | # Attempt to set APP_HOME
46 | # Resolve links: $0 may be a link
47 | PRG="$0"
48 | # Need this for relative symlinks.
49 | while [ -h "$PRG" ] ; do
50 | ls=`ls -ld "$PRG"`
51 | link=`expr "$ls" : '.*-> \(.*\)$'`
52 | if expr "$link" : '/.*' > /dev/null; then
53 | PRG="$link"
54 | else
55 | PRG=`dirname "$PRG"`"/$link"
56 | fi
57 | done
58 | SAVED="`pwd`"
59 | cd "`dirname \"$PRG\"`/" >/dev/null
60 | APP_HOME="`pwd -P`"
61 | cd "$SAVED" >/dev/null
62 |
63 | CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
64 |
65 | # Determine the Java command to use to start the JVM.
66 | if [ -n "$JAVA_HOME" ] ; then
67 | if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
68 | # IBM's JDK on AIX uses strange locations for the executables
69 | JAVACMD="$JAVA_HOME/jre/sh/java"
70 | else
71 | JAVACMD="$JAVA_HOME/bin/java"
72 | fi
73 | if [ ! -x "$JAVACMD" ] ; then
74 | die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
75 |
76 | Please set the JAVA_HOME variable in your environment to match the
77 | location of your Java installation."
78 | fi
79 | else
80 | JAVACMD="java"
81 | which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
82 |
83 | Please set the JAVA_HOME variable in your environment to match the
84 | location of your Java installation."
85 | fi
86 |
87 | # Increase the maximum file descriptors if we can.
88 | if [ "$cygwin" = "false" -a "$darwin" = "false" ] ; then
89 | MAX_FD_LIMIT=`ulimit -H -n`
90 | if [ $? -eq 0 ] ; then
91 | if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
92 | MAX_FD="$MAX_FD_LIMIT"
93 | fi
94 | ulimit -n $MAX_FD
95 | if [ $? -ne 0 ] ; then
96 | warn "Could not set maximum file descriptor limit: $MAX_FD"
97 | fi
98 | else
99 | warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
100 | fi
101 | fi
102 |
103 | # For Darwin, add options to specify how the application appears in the dock
104 | if $darwin; then
105 | GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
106 | fi
107 |
108 | # For Cygwin, switch paths to Windows format before running java
109 | if $cygwin ; then
110 | APP_HOME=`cygpath --path --mixed "$APP_HOME"`
111 | CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
112 | JAVACMD=`cygpath --unix "$JAVACMD"`
113 |
114 | # We build the pattern for arguments to be converted via cygpath
115 | ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
116 | SEP=""
117 | for dir in $ROOTDIRSRAW ; do
118 | ROOTDIRS="$ROOTDIRS$SEP$dir"
119 | SEP="|"
120 | done
121 | OURCYGPATTERN="(^($ROOTDIRS))"
122 | # Add a user-defined pattern to the cygpath arguments
123 | if [ "$GRADLE_CYGPATTERN" != "" ] ; then
124 | OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
125 | fi
126 | # Now convert the arguments - kludge to limit ourselves to /bin/sh
127 | i=0
128 | for arg in "$@" ; do
129 | CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
130 | CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option
131 |
132 | if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition
133 | eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
134 | else
135 | eval `echo args$i`="\"$arg\""
136 | fi
137 | i=$((i+1))
138 | done
139 | case $i in
140 | (0) set -- ;;
141 | (1) set -- "$args0" ;;
142 | (2) set -- "$args0" "$args1" ;;
143 | (3) set -- "$args0" "$args1" "$args2" ;;
144 | (4) set -- "$args0" "$args1" "$args2" "$args3" ;;
145 | (5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
146 | (6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
147 | (7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
148 | (8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
149 | (9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
150 | esac
151 | fi
152 |
153 | # Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules
154 | function splitJvmOpts() {
155 | JVM_OPTS=("$@")
156 | }
157 | eval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS
158 | JVM_OPTS[${#JVM_OPTS[*]}]="-Dorg.gradle.appname=$APP_BASE_NAME"
159 |
160 | exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@"
161 |
--------------------------------------------------------------------------------
/app/src/main/res/layout/activity_main.xml:
--------------------------------------------------------------------------------
1 |
2 |
6 |
7 |
8 |
11 |
14 |
17 |
18 |
22 |
23 |
24 |
29 |
30 |
41 |
42 |
52 |
53 |
54 |
55 |
60 |
61 |
72 |
73 |
83 |
84 |
85 |
86 |
92 |
99 |
100 |
108 |
109 |
110 |
117 |
124 |
131 |
132 |
140 |
141 |
142 |
143 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # sdk3rd [](https://jitpack.io/#czy1121/sdk3rd)
2 |
3 | 第三方SDK集成库,支持 授权/分享/支付 等功能
4 |
5 | - 授权 目前支持 微信/QQ/新浪微博,客户端只需要配置APPID(新浪微博)
6 | - 分享 目前支持 微信(会话/朋友圈/收藏),QQ/QZone,新浪微博
7 | - 支付 目前支持 支付宝/微信支付
8 | - 对于授权与分享,客户端不用配置APPSECRET,只需要要APPID(新浪微博授权需要redirectUrl)
9 | - 对于支付,APPID包含在由后端动态返回的paydata里
10 | - 可注册自定义平台实现,满足特殊需求
11 | - 分享并未实现ui,需要自己提供ui
12 |
13 | 
14 |
15 | 目前这个库还不稳定,有些细节并未仔细考虑,有些功能也并未进行测试,支持的平台也不多,欢迎大家 star/issue/pr,共同完善这个库
16 |
17 |
18 | ### 关于授权
19 |
20 | 成功后的结果为 "code|{code}", "token|{openId}|{token}" 两种形式
21 |
22 | - 微信授权是OAuth2.0返回的授权码(code)
23 | - QQ授权是SSO返回的是token
24 | - 微博授权其文档说是支持SSO与OAuth2.0,根据情况可能返回code与token
25 |
26 | 但客户端其实不需要关心是code还是token,直接把result发结服务端就好了
27 |
28 |
29 | ### 关于支付
30 |
31 | 很多支付类库会在客户端处理商品支付信息,其实这是不必要的,直接由服务端返回数据并交给支付SDK,然后处理支付结果就好了
32 |
33 |
34 | ### 关于分享
35 |
36 | 支持 纯文本/纯图片/图文/网页/音乐/视频 等分享类型
37 |
38 | - 网页/音乐/视频 是卡片形式,可添加 标题(title)/描述(description)/缩略图(thumb)
39 | - 微信朋友圈的网页链接不显示 description
40 | - 新浪微博文本包含的网址会转成链接
41 | - QZone 的 纯文本/纯图片/图文/视频 以“说说”的形式发布
42 |
43 | |平台|纯文本|纯图片|图文|网页|音乐|视频|
44 | |---|---|---|---|---|---|---|
45 | |QQ|x|o|x|o|o|x|
46 | |QZone|o|o|o|o|x|o|
47 | |WXSession|o|o|x|o|o|o|
48 | |WXTimeline|o|o|x|o|o|o|
49 | |Weibo|o|o|o|x|x|x|
50 | |SendToQQ|o|o|x|x|x|x|
51 | |SendToWXS|o|o|x|x|x|x|
52 | |SendToWXT|o|o|x|x|x|x|
53 |
54 | ## Demo
55 |
56 | 运行demo需要在`gradle.properties`中修改app的**包名,签名和为app申请的APPID**
57 |
58 | ```
59 |
60 | APPLICATION_ID=ezy.demo.sdk3rd
61 |
62 | APPID_QQ=YOUR_APPID
63 | APPID_WEIXIN=YOUR_APPID
64 | APPID_WEIBO=YOUR_APPID
65 |
66 | SINGING_ALIAS=androiddebugkey
67 | SINGING_PASSWORD=android
68 | SINGING_FILE=debug.keystore
69 | ```
70 |
71 | ## 使用方法
72 |
73 |
74 | ### 添加依赖
75 |
76 |
77 | ``` groovy
78 | repositories {
79 | maven { url "https://jitpack.io" }
80 | }
81 | dependencies {
82 | compile 'com.github.czy1121.sdk3rd:sdk3rd:0.1.2'
83 | compile 'com.github.czy1121.sdk3rd:sdk3rd-alipay:0.1.1'
84 | compile 'com.github.czy1121.sdk3rd:sdk3rd-qq:0.1.0'
85 |
86 | compile 'com.sina.weibo.sdk:core:1.0.0:openDefaultRelease@aar'
87 | compile 'com.tencent.mm.opensdk:wechat-sdk-android-without-mta:1.0.2'
88 |
89 | }
90 | ```
91 |
92 | ### 使用配置
93 |
94 | 配置APPID
95 |
96 | ``` java
97 |
98 | PlatformConfig.useQQ(BuildConfig.APPID_QQ);
99 | PlatformConfig.useWeixin(BuildConfig.APPID_WEIXIN);
100 | PlatformConfig.useWeibo(BuildConfig.APPID_WEIBO, "http://www.sina.com/");
101 | PlatformConfig.usePayments();
102 |
103 | ```
104 |
105 |
106 | ### 使用授权SDK
107 |
108 | 设置全局事件回调(非必要)
109 |
110 |
111 | ``` java
112 | AuthorizeSDK.setDefaultCallback(new OnCallback() {
113 | @Override
114 | public void onStarted(Activity activity) {
115 | Log.e("ezy", "authorize started");
116 | }
117 |
118 | @Override
119 | public void onCompleted(Activity activity) {
120 | Log.e("ezy", "authorize completed");
121 | }
122 |
123 | @Override
124 | public void onSucceed(Activity activity, Object result) {
125 | Log.e("ezy", "authorize succeed");
126 | }
127 |
128 | @Override
129 | public void onFailed(Activity activity, int code, String message) {
130 | Log.e("ezy", "authorize failed [" + code + "]" + message);
131 | }
132 | });
133 |
134 | ```
135 |
136 | 接收授权结果(新浪微博/QQ)
137 |
138 | ``` java
139 | @Override
140 | protected void onActivityResult(int requestCode, int resultCode, Intent data) {
141 | super.onActivityResult(requestCode, resultCode, data);
142 | AuthorizeSDK.onHandleResult(this, requestCode, resultCode, data);
143 | }
144 | ```
145 |
146 | 调用授权
147 |
148 | ``` java
149 | AuthorizeSDK.authorize(MainActivity.this, platform, new OnSucceed() {
150 | @Override
151 | public void onSucceed(String result) {
152 | Toast.makeText(MainActivity.this, "登陆成功 - " + result, Toast.LENGTH_LONG).show();
153 |
154 | }
155 | });
156 | ```
157 |
158 | 注册自定义平台,需要实现 IAuthorize 与相应的 IFactory
159 |
160 | ``` java
161 | AuthorizeSDK.register(IFactory factory);
162 | AuthorizeSDK.register(String platformName, String appId, Class clazz);
163 | ```
164 |
165 |
166 | ### 使用支付SDK
167 |
168 | 全局事件回调的设置与授权SDK类似
169 |
170 |
171 | 调用支付
172 |
173 | ``` java
174 | PaymentSDK.pay(MainActivity.this, platform, paydata, new OnSucceed() {
175 | @Override
176 | public void onSucceed(String result) {
177 | // todo
178 | }
179 | });
180 | ```
181 |
182 | 注册自定义平台,需要实现 IPayable 与相应的 IFactory
183 |
184 | ``` java
185 | PaymentSDK.register(IFactory factory);
186 | PaymentSDK.register(String platformName, Class clazz);
187 | ```
188 |
189 |
190 | ### 使用分享SDK
191 |
192 | 全局事件回调的设置与授权SDK类似
193 |
194 | ...
195 |
196 | 分享结果的接收也与授权SDK类似(QQ)
197 |
198 | ...
199 |
200 | 注册自定义平台,需要实现 IShareable 与相应的 IFactory
201 |
202 | ``` java
203 | ShareSDK.register(IFactory factory);
204 | ShareSDK.register(String platformName, Class clazz);
205 | ```
206 |
207 | 分享
208 |
209 |
210 | ``` java
211 | // 分享纯文本
212 | ShareSDK.make(this, text).share(platform);
213 | // 分享纯图片
214 | ShareSDK.make(this, new MoImage(image)).share(platform);
215 | // 分享图文
216 | ShareSDK.make(this, text, new MoImage(image)).share(platform);
217 |
218 | // 分享网页链接
219 | ShareSDK.make(this, new MoWeb(url))
220 | .withTitle("这是标题")
221 | .withDescription("这是摘要")
222 | .withThumb(thumb)
223 | .share(platform, new OnSucceed() {
224 | @Override
225 | public void onSucceed(String result) {
226 | Toast.makeText(MainActivity.this, "分享成功", Toast.LENGTH_LONG).show();
227 | }
228 | });
229 |
230 | // 分享音乐
231 | ShareSDK.make(this, new MoMusic(url))
232 | .withTitle("这是标题")
233 | .withDescription("这是摘要")
234 | .withThumb(thumb)
235 | .share(platform);
236 | ```
237 |
238 |
239 |
240 | ## 参考
241 |
242 | 友盟+分享组件90%常见问题汇总
243 | http://bbs.umeng.com/thread-17764-1-1.html
244 |
245 | 友盟各平台可分享内容预览
246 | http://dev.umeng.com/social/android/share-detail#5
247 |
248 | Android 不同平台分享内容的详细说明
249 | http://wiki.mob.com/不同平台分享内容的详细说明
250 |
251 | 新浪微博SDK
252 | https://github.com/sinaweibosdk/weibo_android_sdk
253 |
254 |
255 | ## License
256 |
257 | ```
258 | Copyright 2017 czy1121
259 |
260 | Licensed under the Apache License, Version 2.0 (the "License");
261 | you may not use this file except in compliance with the License.
262 | You may obtain a copy of the License at
263 |
264 | http://www.apache.org/licenses/LICENSE-2.0
265 |
266 | Unless required by applicable law or agreed to in writing, software
267 | distributed under the License is distributed on an "AS IS" BASIS,
268 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
269 | See the License for the specific language governing permissions and
270 | limitations under the License.
271 | ```
272 |
--------------------------------------------------------------------------------
/app/src/main/java/ezy/demo/sdk3rd/MainActivity.java:
--------------------------------------------------------------------------------
1 | package ezy.demo.sdk3rd;
2 |
3 | import android.app.Activity;
4 | import android.content.Intent;
5 | import android.databinding.DataBindingUtil;
6 | import android.os.Bundle;
7 | import android.support.v7.app.AppCompatActivity;
8 | import android.util.Log;
9 | import android.view.View;
10 | import android.widget.Toast;
11 |
12 | import java.io.File;
13 |
14 | import ezy.demo.sdk3rd.databinding.ActivityMainBinding;
15 | import ezy.sdk3rd.social.AuthorizeSDK;
16 | import ezy.sdk3rd.social.PaymentSDK;
17 | import ezy.sdk3rd.social.PlatformConfig;
18 | import ezy.sdk3rd.social.ShareSDK;
19 | import ezy.sdk3rd.social.payment.PaymentVia;
20 | import ezy.sdk3rd.social.sdk.OnCallback;
21 | import ezy.sdk3rd.social.sdk.OnSucceed;
22 | import ezy.sdk3rd.social.share.image.resource.FileResource;
23 | import ezy.sdk3rd.social.share.image.resource.ResIdResource;
24 | import ezy.sdk3rd.social.share.image.resource.UrlResource;
25 | import ezy.sdk3rd.social.share.media.MoImage;
26 | import ezy.sdk3rd.social.share.media.MoMusic;
27 | import ezy.sdk3rd.social.share.media.MoVideo;
28 | import ezy.sdk3rd.social.share.media.MoWeb;
29 |
30 | public class MainActivity extends AppCompatActivity implements View.OnClickListener {
31 |
32 | ActivityMainBinding binding;
33 |
34 | @Override
35 | protected void onCreate(Bundle savedInstanceState) {
36 | super.onCreate(savedInstanceState);
37 | binding = DataBindingUtil.setContentView(this, R.layout.activity_main);
38 |
39 | PlatformConfig.useQQ(BuildConfig.APPID_QQ);
40 | PlatformConfig.useWeixin(BuildConfig.APPID_WEIXIN);
41 | PlatformConfig.useWeibo(BuildConfig.APPID_WEIBO, "http://www.sina.com/");
42 | PlatformConfig.usePayments();
43 |
44 | ShareSDK.setDefaultCallback(new DefaultCallback("share"));
45 | PaymentSDK.setDefaultCallback(new DefaultCallback("payment"));
46 | AuthorizeSDK.setDefaultCallback(new DefaultCallback("auth"));
47 |
48 |
49 | binding.setOnShare(this);
50 | binding.setOnAuth(new View.OnClickListener() {
51 | @Override
52 | public void onClick(View v) {
53 | String platform = binding.spAuth.getSelectedItem().toString().toLowerCase();
54 | AuthorizeSDK.authorize(MainActivity.this, platform, new OnSucceed() {
55 | @Override
56 | public void onSucceed(String result) {
57 | Toast.makeText(MainActivity.this, "登陆成功 - " + result, Toast.LENGTH_SHORT).show();
58 |
59 | }
60 | });
61 | }
62 |
63 | });
64 | binding.setOnPay(new View.OnClickListener() {
65 | @Override
66 | public void onClick(View v) {
67 | String platform = "";
68 | String data = "";
69 | switch (v.getId()) {
70 | case R.id.btn_wxpay:
71 | platform = PaymentVia.Wxpay;
72 | data = binding.txtWxpaydata.getText().toString();
73 | break;
74 | case R.id.btn_alipay:
75 | default:
76 | platform = PaymentVia.Alipay;
77 | data = binding.txtAlipaydata.getText().toString();
78 | break;
79 | }
80 | PaymentSDK.pay(MainActivity.this, platform, data, new OnSucceed() {
81 | @Override
82 | public void onSucceed(String result) {
83 | Toast.makeText(MainActivity.this, "支付成功 - " + result, Toast.LENGTH_SHORT).show();
84 | }
85 | });
86 | }
87 | });
88 |
89 | }
90 |
91 | @Override
92 | public void onClick(View v) {
93 |
94 |
95 | FileResource thumb = new FileResource(new File("/storage/emulated/0/thumb.jpg"));
96 |
97 | FileResource file = new FileResource(new File("/storage/emulated/0/DCIM/Camera/IMG_20171014_224236.jpg"));
98 | UrlResource imageUrl = new UrlResource("http://435a362e.ngrok.io/images/cat.jpg");
99 | ResIdResource resId = new ResIdResource(this, R.mipmap.ic_launcher, true);
100 |
101 |
102 | String platform = binding.spShare.getSelectedItem().toString().toLowerCase();
103 | OnSucceed onSucceed = new OnSucceed() {
104 | @Override
105 | public void onSucceed(String result) {
106 | Toast.makeText(MainActivity.this, "分享成功", Toast.LENGTH_SHORT).show();
107 | }
108 | };
109 | switch (binding.spType.getSelectedItemPosition()) {
110 | case 0: // web
111 | ShareSDK.make(this, new MoWeb("https://baidu.com")).withTitle("这是标题").withDescription("这是摘要").withThumb(resId).share(platform, onSucceed);
112 | break;
113 | case 1: // text
114 | ShareSDK.make(this, "这是文本~~~").share(platform, onSucceed);
115 | break;
116 | case 2: // image
117 | ShareSDK.make(this, new MoImage(file)).withThumb(thumb).share(platform, onSucceed);
118 | break;
119 | case 3: // text+image
120 | ShareSDK.make(this, "这是文本~~~", new MoImage(file)).share(platform, onSucceed);
121 | break;
122 | case 4: // music
123 | String music = "https://archive.org/download/testmp3testfile/mpthreetest.mp3";
124 | ShareSDK.make(this, new MoMusic(music)).withTitle("这是标题").withDescription("这是摘要").withThumb(resId).share(platform, onSucceed);
125 | break;
126 | case 5: // video
127 | ShareSDK.make(this, new MoVideo("https://archive.org/download/Dokku_obrash/wmv.mp4"))
128 | .withTitle("这是标题")
129 | .withDescription("这是摘要")
130 | .withThumb(resId)
131 | .share(platform, onSucceed);
132 | break;
133 | }
134 | }
135 |
136 | @Override
137 | protected void onActivityResult(int requestCode, int resultCode, Intent data) {
138 | super.onActivityResult(requestCode, resultCode, data);
139 | AuthorizeSDK.onHandleResult(this, requestCode, resultCode, data);
140 | ShareSDK.onHandleResult(this, requestCode, resultCode, data);
141 | }
142 |
143 | public static class DefaultCallback implements OnCallback {
144 |
145 | final String name;
146 |
147 | public DefaultCallback(String name) {
148 | this.name = name;
149 | }
150 |
151 | @Override
152 | public void onStarted(Activity activity) {
153 | Log.e("ezy", name + " started");
154 | Toast.makeText(activity, name + " started", Toast.LENGTH_LONG).show();
155 | }
156 |
157 | @Override
158 | public void onCompleted(Activity activity) {
159 | Log.e("ezy", name + " completed");
160 | Toast.makeText(activity, name + " completed", Toast.LENGTH_LONG).show();
161 | }
162 |
163 | @Override
164 | public void onSucceed(Activity activity, Object result) {
165 | Log.e("ezy", name + " succeed");
166 | Toast.makeText(activity, name + " succeed", Toast.LENGTH_LONG).show();
167 | }
168 |
169 | @Override
170 | public void onFailed(Activity activity, int code, String message) {
171 | Log.e("ezy", name + " failed [" + code + "]" + message);
172 | Toast.makeText(activity, name + " failed [" + code + "]" + message, Toast.LENGTH_SHORT).show();
173 | }
174 |
175 | }
176 | }
177 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/platforms/qq/TXShare.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.platforms.qq;
2 |
3 | import android.app.Activity;
4 | import android.content.Intent;
5 | import android.os.Bundle;
6 | import android.support.annotation.NonNull;
7 | import android.util.Log;
8 |
9 | import com.tencent.connect.common.Constants;
10 | import com.tencent.connect.share.QQShare;
11 | import com.tencent.connect.share.QzonePublish;
12 | import com.tencent.tauth.IUiListener;
13 | import com.tencent.tauth.Tencent;
14 | import com.tencent.tauth.UiError;
15 |
16 | import org.json.JSONObject;
17 |
18 | import java.util.ArrayList;
19 |
20 | import ezy.sdk3rd.social.sdk.OnCallback;
21 | import ezy.sdk3rd.social.sdk.Platform;
22 | import ezy.sdk3rd.social.sdk.ResultCode;
23 | import ezy.sdk3rd.social.share.IShareable;
24 | import ezy.sdk3rd.social.share.ShareData;
25 | import ezy.sdk3rd.social.share.ShareTo;
26 | import ezy.sdk3rd.social.share.media.IMediaObject;
27 | import ezy.sdk3rd.social.share.media.MoImage;
28 | import ezy.sdk3rd.social.share.media.MoMusic;
29 | import ezy.sdk3rd.social.share.media.MoVideo;
30 | import ezy.sdk3rd.social.share.media.MoWeb;
31 |
32 | /**
33 | * Created by ezy on 17/3/18.
34 | */
35 |
36 | public class TXShare implements IShareable {
37 | public static final String TAG = "ezy.sdk3rd.qq.share";
38 |
39 | private static final String KEY_REQ_TYPE = QQShare.SHARE_TO_QQ_KEY_TYPE;
40 | private static final String KEY_TARGET_URL = QQShare.SHARE_TO_QQ_TARGET_URL;
41 | private static final String KEY_IMAGE_URL = QQShare.SHARE_TO_QQ_IMAGE_URL;
42 | private static final String KEY_IMAGE_LOCAL_URL = QQShare.SHARE_TO_QQ_IMAGE_LOCAL_URL;
43 | private static final String KEY_AUDIO_URL = QQShare.SHARE_TO_QQ_AUDIO_URL;
44 | private static final String KEY_AUDIO_VIDEO_PATH = QzonePublish.PUBLISH_TO_QZONE_VIDEO_PATH;
45 |
46 | private static final int REQ_TYPE_DEFAULT = 1;
47 | private static final int REQ_TYPE_AUDIO = 2;
48 | private static final int REQ_TYPE_MOOD = 3;
49 | private static final int REQ_TYPE_VIDEO = 4;
50 | private static final int REQ_TYPE_IMAGE = 5;
51 |
52 | Activity mActivity;
53 | Platform mPlatform;
54 | Tencent mApi;
55 |
56 | IUiListener mListener;
57 |
58 | TXShare(Activity activity, Platform platform) {
59 | mActivity = activity;
60 | mPlatform = platform;
61 | mApi = Tencent.createInstance(platform.getAppId(), mActivity);
62 | }
63 |
64 | String toMessage(UiError error) {
65 | return "[" + error.errorCode + "]" + error.errorMessage;
66 | }
67 |
68 | @Override
69 | public void share(@NonNull final ShareData data, @NonNull final OnCallback callback) {
70 |
71 | final boolean isShareToQQ = mPlatform.getName().equals(ShareTo.QQ);
72 | mListener = new IUiListener() {
73 | @Override
74 | public void onComplete(Object response) {
75 | Log.e(TAG, "response ==> " + response);
76 | if (response instanceof JSONObject && ((JSONObject) response).length() > 0) {
77 | callback.onSucceed(mActivity, "");
78 | } else {
79 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, "分享失败: 返回为空");
80 | }
81 | callback.onCompleted(mActivity);
82 | }
83 |
84 | @Override
85 | public void onError(UiError e) {
86 | Log.e(TAG, "错误信息: " + e.errorDetail);
87 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, toMessage(e));
88 | }
89 |
90 | @Override
91 | public void onCancel() {
92 | callback.onFailed(mActivity, ResultCode.RESULT_CANCELLED, "用户取消了分享");
93 | }
94 | };
95 | Bundle bundle = new Bundle();
96 |
97 | if (data.hasText()) {
98 | bundle.putString(QQShare.SHARE_TO_QQ_TITLE, data.text);
99 | } else if (data.hasTitle()) {
100 | bundle.putString(QQShare.SHARE_TO_QQ_TITLE, data.title);
101 | }
102 | if (data.hasDescription()) {
103 | bundle.putString(QQShare.SHARE_TO_QQ_SUMMARY, data.description);
104 | }
105 | if (data.hasUrl()) {
106 | bundle.putString(QQShare.SHARE_TO_QQ_TARGET_URL, data.url);
107 | }
108 | bundle.putString(QQShare.SHARE_TO_QQ_APP_NAME, mActivity.getPackageManager().getApplicationLabel(mActivity.getApplicationInfo()).toString());
109 | putImageUrl(data, bundle, isShareToQQ);
110 |
111 | boolean unsupported = false;
112 | switch (data.type()) {
113 | case IMediaObject.TYPE_WEB:
114 | bundle.putInt(KEY_REQ_TYPE, REQ_TYPE_DEFAULT);
115 | bundle.putString(QQShare.SHARE_TO_QQ_TARGET_URL, ((MoWeb) data.media).url);
116 | shareTo(bundle, isShareToQQ, false, callback);
117 | break;
118 | case IMediaObject.TYPE_EMOJI:
119 | case IMediaObject.TYPE_IMAGE:
120 | if (isShareToQQ) {
121 | bundle.putInt(KEY_REQ_TYPE, REQ_TYPE_IMAGE);
122 | bundle.putString(KEY_IMAGE_LOCAL_URL, ((MoImage) data.media).toUri());
123 | } else {
124 | bundle.putInt(KEY_REQ_TYPE, REQ_TYPE_MOOD);
125 | }
126 | shareTo(bundle, isShareToQQ, true, callback);
127 | break;
128 | case IMediaObject.TYPE_MUSIC:
129 | unsupported = !isShareToQQ;
130 | bundle.putInt(KEY_REQ_TYPE, REQ_TYPE_AUDIO);
131 | bundle.putString(KEY_AUDIO_URL, ((MoMusic) data.media).mediaUrl);
132 | shareTo(bundle, true, false, callback);
133 | break;
134 | case IMediaObject.TYPE_TEXT:
135 | bundle.putInt(KEY_REQ_TYPE, REQ_TYPE_MOOD);
136 | shareTo(bundle, isShareToQQ, true, callback);
137 | unsupported = isShareToQQ;
138 | break;
139 | case IMediaObject.TYPE_VIDEO:
140 | bundle.putInt(KEY_REQ_TYPE, REQ_TYPE_AUDIO);
141 | bundle.putString(KEY_AUDIO_VIDEO_PATH, ((MoVideo) data.media).mediaUrl);
142 | shareTo(bundle, false, true, callback);
143 | unsupported = isShareToQQ;
144 | break;
145 | default:
146 | unsupported = true;
147 | // unsupported
148 | break;
149 | }
150 | if (unsupported) {
151 | callback.onFailed(mActivity, ResultCode.RESULT_FAILED, "不支持的分享类型");
152 | }
153 | }
154 |
155 | void putImageUrl(ShareData data, Bundle bundle, boolean isShareToQQ) {
156 |
157 | if (data.media instanceof MoImage) {
158 | if (isShareToQQ) {
159 | bundle.putString(KEY_IMAGE_URL, ((MoImage) data.media).toUri());
160 | } else {
161 | bundle.putStringArrayList(KEY_IMAGE_URL, imageList(((MoImage) data.media).toUri()));
162 | }
163 | } else if (data.hasThumb()) {
164 | if (isShareToQQ) {
165 | bundle.putString(KEY_IMAGE_URL, data.thumb.toUri());
166 | } else {
167 | bundle.putStringArrayList(KEY_IMAGE_URL, imageList(data.thumb.toUri()));
168 | }
169 | }
170 | }
171 |
172 | void shareTo(Bundle bundle, boolean isShareToQQ, boolean isPublishToQZone, OnCallback callback) {
173 |
174 | if (isShareToQQ) {
175 | callback.onStarted(mActivity);
176 | mApi.shareToQQ(mActivity, bundle, mListener);
177 | } else if (isPublishToQZone) {
178 | callback.onStarted(mActivity);
179 | mApi.publishToQzone(mActivity, bundle, mListener);
180 | } else {
181 | callback.onStarted(mActivity);
182 | mApi.shareToQzone(mActivity, bundle, mListener);
183 | }
184 | Log.e(TAG, bundle.toString());
185 | }
186 |
187 | ArrayList imageList(String image) {
188 | ArrayList images = new ArrayList();
189 | images.add(image);
190 | return images;
191 | }
192 |
193 |
194 | @Override
195 | public void onResult(int requestCode, int resultCode, Intent data) {
196 | if (requestCode == Constants.REQUEST_QQ_SHARE || requestCode == Constants.REQUEST_QZONE_SHARE) {
197 | Tencent.onActivityResultData(requestCode, resultCode, data, mListener);
198 | }
199 | }
200 | }
201 |
--------------------------------------------------------------------------------
/ezy.sdk3rd.social/src/main/java/ezy/sdk3rd/social/share/image/ImageTool.java:
--------------------------------------------------------------------------------
1 | package ezy.sdk3rd.social.share.image;
2 |
3 | import android.content.Context;
4 | import android.graphics.Bitmap;
5 | import android.graphics.BitmapFactory;
6 | import android.graphics.Canvas;
7 | import android.graphics.PixelFormat;
8 | import android.graphics.drawable.Drawable;
9 | import android.text.TextUtils;
10 | import android.util.Log;
11 |
12 | import java.io.BufferedOutputStream;
13 | import java.io.ByteArrayOutputStream;
14 | import java.io.Closeable;
15 | import java.io.File;
16 | import java.io.FileOutputStream;
17 | import java.io.InputStream;
18 | import java.net.HttpURLConnection;
19 | import java.net.URL;
20 |
21 | public class ImageTool {
22 | public static final int SIZE_3M = 3072;
23 | public static int MAX_WIDTH = 768;
24 | public static int MAX_HEIGHT = 1024;
25 |
26 |
27 | public static byte[] compress(Bitmap bitmap, int maxSize, Bitmap.CompressFormat format) {
28 | ByteArrayOutputStream os = null;
29 | try {
30 | int size = bitmap.getRowBytes() * bitmap.getHeight();
31 | int quality = 100;
32 | if (size > maxSize) {
33 | quality = (int) (1f * quality * maxSize / size);
34 | }
35 | Log.d("compress", "compress quality:" + quality);
36 |
37 | os = new ByteArrayOutputStream();
38 | bitmap.compress(format, quality, os);
39 | return os.toByteArray();
40 | } catch (Exception e) {
41 | e.printStackTrace();
42 | } finally {
43 | close(os);
44 | }
45 | return null;
46 | }
47 |
48 | public static byte[] compress(byte[] bytes, int maxSize, Bitmap.CompressFormat format) {
49 | Bitmap bitmap = BitmapFactory.decodeByteArray(bytes, 0, bytes.length);
50 | byte[] out = compress(bitmap, maxSize, format);
51 | bitmap.recycle();
52 | return out;
53 | }
54 |
55 | public static byte[] compress(File file, int maxSize, Bitmap.CompressFormat format) {
56 | if ((file == null) || (!file.getAbsoluteFile().exists())) {
57 | return null;
58 | }
59 | Bitmap bitmap = BitmapFactory.decodeFile(file.toString());
60 | byte[] out = compress(bitmap, maxSize, format);
61 | bitmap.recycle();
62 | return out;
63 | }
64 |
65 | public static byte[] compressCircularly(Bitmap bitmap, int maxSize, Bitmap.CompressFormat format) {
66 | ByteArrayOutputStream os = new ByteArrayOutputStream();
67 | try {
68 | for (int i = 1; i <= 10; i++) {
69 | bitmap.compress(format, (int) (100 * Math.pow(0.8, i)), os);
70 | Log.e("compress", "size = " + os.size());
71 | if (os.size() > maxSize) {
72 | break;
73 | } else {
74 | os.reset();
75 | }
76 | }
77 | return os.toByteArray();
78 | } catch (Exception e) {
79 | e.printStackTrace();
80 | } finally {
81 | close(os);
82 | }
83 | return null;
84 | }
85 |
86 | public static byte[] compressCircularly(byte[] bytes, int maxSize, Bitmap.CompressFormat format) {
87 | if (bytes == null || bytes.length <= maxSize) {
88 | return bytes;
89 | }
90 | Bitmap bitmap = BitmapFactory.decodeByteArray(bytes, 0, bytes.length);
91 | byte[] out = compressCircularly(bitmap, maxSize, format);
92 | bitmap.recycle();
93 | return out;
94 | }
95 |
96 | public static BitmapFactory.Options decodeScaledOptions(byte[] bytes, int maxWidth, int maxHeight) {
97 | BitmapFactory.Options options = new BitmapFactory.Options();
98 |
99 | options.inJustDecodeBounds = true;
100 | BitmapFactory.decodeByteArray(bytes, 0, bytes.length, options);
101 |
102 | int sw = (int) Math.ceil(options.outWidth / maxWidth);
103 | int sh = (int) Math.ceil(options.outHeight / maxHeight);
104 |
105 | if ((sh > 1) && (sw > 1)) {
106 | options.inSampleSize = Math.max(sw, sh);
107 | } else if (sh > 1) {
108 | options.inSampleSize = sh;
109 | } else if (sw > 1) {
110 | options.inSampleSize = sw;
111 | }
112 |
113 | options.inJustDecodeBounds = false;
114 | return options;
115 | }
116 |
117 | public static byte[] loadNetImage(String url) {
118 | if (TextUtils.isEmpty(url)) {
119 | return null;
120 | }
121 | ByteArrayOutputStream os = null;
122 | InputStream is = null;
123 | try {
124 | HttpURLConnection connection = (HttpURLConnection) new URL(url).openConnection();
125 | connection.setInstanceFollowRedirects(true);
126 | connection.setConnectTimeout(30000);
127 | connection.setReadTimeout(30000);
128 |
129 | if (connection.getResponseCode() == 301) {
130 | String redirect = connection.getHeaderField("Location");
131 | if (redirect.equals(url)) {
132 | Log.e("image", "重定向问题:url和重定向url相同");
133 | return null;
134 | }
135 | return loadNetImage(redirect);
136 | }
137 | is = connection.getInputStream();
138 | Log.d("image", "load image from url ==> " + url);
139 |
140 | os = new ByteArrayOutputStream();
141 | byte[] buffer = new byte[4096];
142 | int i;
143 | while ((i = is.read(buffer)) != -1) {
144 | os.write(buffer, 0, i);
145 | }
146 | return os.toByteArray();
147 | } catch (Exception e) {
148 | Log.e("image", "图片下载失败:" + e.getMessage());
149 | return null;
150 | } finally {
151 | close(is);
152 | close(os);
153 | }
154 | }
155 |
156 |
157 |
158 | public static byte[] toBytes(Bitmap bitmap, Bitmap.CompressFormat format) {
159 | ByteArrayOutputStream os = new ByteArrayOutputStream();
160 | bitmap.compress(format, 100, os);
161 | return os.toByteArray();
162 | }
163 |
164 | public static byte[] toBytes(Context context, int resId, boolean raw, Bitmap.CompressFormat format) {
165 | return toBytes(toBitmap(context, resId, raw), format);
166 | }
167 |
168 | public static Bitmap toBitmap(Context context, int resId, boolean raw) {
169 | BitmapFactory.Options options = new BitmapFactory.Options();
170 | options.inPreferredConfig = Bitmap.Config.RGB_565;
171 | if (!raw) {
172 | options.inScaled = true;
173 | options.inTargetDensity = context.getResources().getDisplayMetrics().densityDpi;
174 | }
175 | return BitmapFactory.decodeResource(context.getResources(), resId, options);
176 | }
177 |
178 | public static Bitmap toBitmap(byte[] bytes) {
179 | return BitmapFactory.decodeByteArray(bytes, 0, bytes.length);
180 | }
181 |
182 | public static Bitmap toBitmap(File file) {
183 | return BitmapFactory.decodeFile(file.toString());
184 | }
185 |
186 | public static Bitmap toBitmap(Drawable drawable) {
187 | int w = drawable.getIntrinsicWidth();
188 | int h = drawable.getIntrinsicHeight();
189 | Bitmap.Config config = drawable.getOpacity() != PixelFormat.OPAQUE ? Bitmap.Config.ARGB_8888 : Bitmap.Config.RGB_565;
190 | Bitmap bitmap = Bitmap.createBitmap(w, h, config);
191 | Canvas canvas = new Canvas(bitmap);
192 | drawable.setBounds(0, 0, w, h);
193 | drawable.draw(canvas);
194 | return bitmap;
195 | }
196 |
197 |
198 | private static void close(Closeable closeable) {
199 | try {
200 | if (closeable != null) {
201 | closeable.close();
202 | }
203 | } catch (Exception e) {
204 | e.printStackTrace();
205 | }
206 | }
207 | private static void saveTo(byte[] bytes, File file) {
208 | BufferedOutputStream bos = null;
209 | try {
210 | bos = new BufferedOutputStream(new FileOutputStream(file));
211 | bos.write(bytes);
212 | } catch (Exception e) {
213 | e.printStackTrace();
214 | } finally {
215 | close(bos);
216 | }
217 | }
218 | }
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | Apache License
2 | Version 2.0, January 2004
3 | http://www.apache.org/licenses/
4 |
5 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
6 |
7 | 1. Definitions.
8 |
9 | "License" shall mean the terms and conditions for use, reproduction,
10 | and distribution as defined by Sections 1 through 9 of this document.
11 |
12 | "Licensor" shall mean the copyright owner or entity authorized by
13 | the copyright owner that is granting the License.
14 |
15 | "Legal Entity" shall mean the union of the acting entity and all
16 | other entities that control, are controlled by, or are under common
17 | control with that entity. For the purposes of this definition,
18 | "control" means (i) the power, direct or indirect, to cause the
19 | direction or management of such entity, whether by contract or
20 | otherwise, or (ii) ownership of fifty percent (50%) or more of the
21 | outstanding shares, or (iii) beneficial ownership of such entity.
22 |
23 | "You" (or "Your") shall mean an individual or Legal Entity
24 | exercising permissions granted by this License.
25 |
26 | "Source" form shall mean the preferred form for making modifications,
27 | including but not limited to software source code, documentation
28 | source, and configuration files.
29 |
30 | "Object" form shall mean any form resulting from mechanical
31 | transformation or translation of a Source form, including but
32 | not limited to compiled object code, generated documentation,
33 | and conversions to other media types.
34 |
35 | "Work" shall mean the work of authorship, whether in Source or
36 | Object form, made available under the License, as indicated by a
37 | copyright notice that is included in or attached to the work
38 | (an example is provided in the Appendix below).
39 |
40 | "Derivative Works" shall mean any work, whether in Source or Object
41 | form, that is based on (or derived from) the Work and for which the
42 | editorial revisions, annotations, elaborations, or other modifications
43 | represent, as a whole, an original work of authorship. For the purposes
44 | of this License, Derivative Works shall not include works that remain
45 | separable from, or merely link (or bind by name) to the interfaces of,
46 | the Work and Derivative Works thereof.
47 |
48 | "Contribution" shall mean any work of authorship, including
49 | the original version of the Work and any modifications or additions
50 | to that Work or Derivative Works thereof, that is intentionally
51 | submitted to Licensor for inclusion in the Work by the copyright owner
52 | or by an individual or Legal Entity authorized to submit on behalf of
53 | the copyright owner. For the purposes of this definition, "submitted"
54 | means any form of electronic, verbal, or written communication sent
55 | to the Licensor or its representatives, including but not limited to
56 | communication on electronic mailing lists, source code control systems,
57 | and issue tracking systems that are managed by, or on behalf of, the
58 | Licensor for the purpose of discussing and improving the Work, but
59 | excluding communication that is conspicuously marked or otherwise
60 | designated in writing by the copyright owner as "Not a Contribution."
61 |
62 | "Contributor" shall mean Licensor and any individual or Legal Entity
63 | on behalf of whom a Contribution has been received by Licensor and
64 | subsequently incorporated within the Work.
65 |
66 | 2. Grant of Copyright License. Subject to the terms and conditions of
67 | this License, each Contributor hereby grants to You a perpetual,
68 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable
69 | copyright license to reproduce, prepare Derivative Works of,
70 | publicly display, publicly perform, sublicense, and distribute the
71 | Work and such Derivative Works in Source or Object form.
72 |
73 | 3. Grant of Patent License. Subject to the terms and conditions of
74 | this License, each Contributor hereby grants to You a perpetual,
75 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable
76 | (except as stated in this section) patent license to make, have made,
77 | use, offer to sell, sell, import, and otherwise transfer the Work,
78 | where such license applies only to those patent claims licensable
79 | by such Contributor that are necessarily infringed by their
80 | Contribution(s) alone or by combination of their Contribution(s)
81 | with the Work to which such Contribution(s) was submitted. If You
82 | institute patent litigation against any entity (including a
83 | cross-claim or counterclaim in a lawsuit) alleging that the Work
84 | or a Contribution incorporated within the Work constitutes direct
85 | or contributory patent infringement, then any patent licenses
86 | granted to You under this License for that Work shall terminate
87 | as of the date such litigation is filed.
88 |
89 | 4. Redistribution. You may reproduce and distribute copies of the
90 | Work or Derivative Works thereof in any medium, with or without
91 | modifications, and in Source or Object form, provided that You
92 | meet the following conditions:
93 |
94 | (a) You must give any other recipients of the Work or
95 | Derivative Works a copy of this License; and
96 |
97 | (b) You must cause any modified files to carry prominent notices
98 | stating that You changed the files; and
99 |
100 | (c) You must retain, in the Source form of any Derivative Works
101 | that You distribute, all copyright, patent, trademark, and
102 | attribution notices from the Source form of the Work,
103 | excluding those notices that do not pertain to any part of
104 | the Derivative Works; and
105 |
106 | (d) If the Work includes a "NOTICE" text file as part of its
107 | distribution, then any Derivative Works that You distribute must
108 | include a readable copy of the attribution notices contained
109 | within such NOTICE file, excluding those notices that do not
110 | pertain to any part of the Derivative Works, in at least one
111 | of the following places: within a NOTICE text file distributed
112 | as part of the Derivative Works; within the Source form or
113 | documentation, if provided along with the Derivative Works; or,
114 | within a display generated by the Derivative Works, if and
115 | wherever such third-party notices normally appear. The contents
116 | of the NOTICE file are for informational purposes only and
117 | do not modify the License. You may add Your own attribution
118 | notices within Derivative Works that You distribute, alongside
119 | or as an addendum to the NOTICE text from the Work, provided
120 | that such additional attribution notices cannot be construed
121 | as modifying the License.
122 |
123 | You may add Your own copyright statement to Your modifications and
124 | may provide additional or different license terms and conditions
125 | for use, reproduction, or distribution of Your modifications, or
126 | for any such Derivative Works as a whole, provided Your use,
127 | reproduction, and distribution of the Work otherwise complies with
128 | the conditions stated in this License.
129 |
130 | 5. Submission of Contributions. Unless You explicitly state otherwise,
131 | any Contribution intentionally submitted for inclusion in the Work
132 | by You to the Licensor shall be under the terms and conditions of
133 | this License, without any additional terms or conditions.
134 | Notwithstanding the above, nothing herein shall supersede or modify
135 | the terms of any separate license agreement you may have executed
136 | with Licensor regarding such Contributions.
137 |
138 | 6. Trademarks. This License does not grant permission to use the trade
139 | names, trademarks, service marks, or product names of the Licensor,
140 | except as required for reasonable and customary use in describing the
141 | origin of the Work and reproducing the content of the NOTICE file.
142 |
143 | 7. Disclaimer of Warranty. Unless required by applicable law or
144 | agreed to in writing, Licensor provides the Work (and each
145 | Contributor provides its Contributions) on an "AS IS" BASIS,
146 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
147 | implied, including, without limitation, any warranties or conditions
148 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
149 | PARTICULAR PURPOSE. You are solely responsible for determining the
150 | appropriateness of using or redistributing the Work and assume any
151 | risks associated with Your exercise of permissions under this License.
152 |
153 | 8. Limitation of Liability. In no event and under no legal theory,
154 | whether in tort (including negligence), contract, or otherwise,
155 | unless required by applicable law (such as deliberate and grossly
156 | negligent acts) or agreed to in writing, shall any Contributor be
157 | liable to You for damages, including any direct, indirect, special,
158 | incidental, or consequential damages of any character arising as a
159 | result of this License or out of the use or inability to use the
160 | Work (including but not limited to damages for loss of goodwill,
161 | work stoppage, computer failure or malfunction, or any and all
162 | other commercial damages or losses), even if such Contributor
163 | has been advised of the possibility of such damages.
164 |
165 | 9. Accepting Warranty or Additional Liability. While redistributing
166 | the Work or Derivative Works thereof, You may choose to offer,
167 | and charge a fee for, acceptance of support, warranty, indemnity,
168 | or other liability obligations and/or rights consistent with this
169 | License. However, in accepting such obligations, You may act only
170 | on Your own behalf and on Your sole responsibility, not on behalf
171 | of any other Contributor, and only if You agree to indemnify,
172 | defend, and hold each Contributor harmless for any liability
173 | incurred by, or claims asserted against, such Contributor by reason
174 | of your accepting any such warranty or additional liability.
175 |
176 | END OF TERMS AND CONDITIONS
177 |
178 | APPENDIX: How to apply the Apache License to your work.
179 |
180 | To apply the Apache License to your work, attach the following
181 | boilerplate notice, with the fields enclosed by brackets "{}"
182 | replaced with your own identifying information. (Don't include
183 | the brackets!) The text should be enclosed in the appropriate
184 | comment syntax for the file format. We also recommend that a
185 | file or class name and description of purpose be included on the
186 | same "printed page" as the copyright notice for easier
187 | identification within third-party archives.
188 |
189 | Copyright {yyyy} {name of copyright owner}
190 |
191 | Licensed under the Apache License, Version 2.0 (the "License");
192 | you may not use this file except in compliance with the License.
193 | You may obtain a copy of the License at
194 |
195 | http://www.apache.org/licenses/LICENSE-2.0
196 |
197 | Unless required by applicable law or agreed to in writing, software
198 | distributed under the License is distributed on an "AS IS" BASIS,
199 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
200 | See the License for the specific language governing permissions and
201 | limitations under the License.
202 |
--------------------------------------------------------------------------------