私はAndroidアプリを開発していますが、Androidの共有インテントを使用してアプリ内からアプリのユーザーのステータスを更新する方法を知りたいと思っています。
FacebookのSDKを調べたところ、これは簡単に実行できるように見えますが、ユーザーが通常のShare Intentポップアップウィンドウを使用して実行できるようにしたいのですが。ここに見られる:
私は通常の共有インテントコードを試しましたが、これはもはやFacebookでは機能しないようです。
public void invokeShare(Activity activity, String quote, String credit) {
Intent shareIntent = new Intent(Android.content.Intent.ACTION_SEND);
shareIntent.setType("text/plain");
shareIntent.putExtra(Android.content.Intent.EXTRA_SUBJECT, activity.getString(R.string.share_subject));
shareIntent.putExtra(Android.content.Intent.EXTRA_TEXT, "Example text");
activity.startActivity(Intent.createChooser(shareIntent, activity.getString(R.string.share_title)));
}
更新:さらに掘り下げたところ、まだ解決されていないFacebookのアプリのバグのように見えます! ( facebookのバグ )当面は、「共有が機能しない!!!」という否定的なことを我慢しなければならないようです。レビュー。乾杯Facebook:*(
Facebookアプリケーションは、
EXTRA_SUBJECT
またはEXTRA_TEXT
フィールドを処理しません。
バグリンクは次のとおりです。 https://developers.facebook.com/bugs/33261962681642
ありがとう@billynomates:
問題は、
EXTRA_TEXT
フィールドにURLを入力すると、does動作することです。意図的にテキストを削除しているようです。
どうやら(2014年現在)Facebookで sharer.php URL を開いているか、Androidインテントをより特殊な方法で使用している場合でも、共有画面をカスタマイズすることはできません。たとえば、これらの回答を参照してください。
とにかく、プレーンインテントを使用すると、あなたはcanはまだURLを共有できますが、デフォルトテキストは共有しません 、 billynomatesのコメント 。 (また、共有するURLがない場合は、空の[投稿の書き込み](つまり、ステータスの更新)ダイアログでFacebookアプリを起動するのも同様に簡単です。以下のコードを使用しますが、EXTRA_TEXT
は省略します。)
Facebook SDKを使用しないnotであることがわかった最良のソリューションを次に示します。
このコードは、公式のFacebookアプリがインストールされている場合は直接開き、それ以外の場合はブラウザーでsharer.phpを開くことにフォールバックします。 (この質問の他の解決策のほとんどは、 巨大な「…を使用してアクションを完了する」ダイアログ を表示しますが、これは最適ではありませんまったく!)
String urlToShare = "https://stackoverflow.com/questions/7545254";
Intent intent = new Intent(Intent.ACTION_SEND);
intent.setType("text/plain");
// intent.putExtra(Intent.EXTRA_SUBJECT, "Foo bar"); // NB: has no effect!
intent.putExtra(Intent.EXTRA_TEXT, urlToShare);
// See if official Facebook app is found
boolean facebookAppFound = false;
List<ResolveInfo> matches = getPackageManager().queryIntentActivities(intent, 0);
for (ResolveInfo info : matches) {
if (info.activityInfo.packageName.toLowerCase().startsWith("com.facebook.katana")) {
intent.setPackage(info.activityInfo.packageName);
facebookAppFound = true;
break;
}
}
// As fallback, launch sharer.php in a browser
if (!facebookAppFound) {
String sharerUrl = "https://www.facebook.com/sharer/sharer.php?u=" + urlToShare;
intent = new Intent(Intent.ACTION_VIEW, Uri.parse(sharerUrl));
}
startActivity(intent);
( com.facebook.katana
パッケージ名については、 MatheusJardimBのコメント を参照してください。)
FacebookアプリがインストールされているNexus 7(Android 4.4)では、結果は次のようになります。
通常の方法
求めているものを作成する通常の方法は、次のことを行うことです。
Intent intent = new Intent(Intent.ACTION_SEND);
intent.setType("text/plain");
intent.putExtra(Intent.EXTRA_TEXT, "The status update text");
startActivity(Intent.createChooser(intent, "Dialog title text"));
これは問題なく機能します。
代替方法(たぶん)
これを行うことの潜在的な問題は、電子メール、SMSなどを介してメッセージを送信することも許可していることです。次のコードは、ユーザーが電子メールを送信できるようにするアプリケーションで使用しているものです-Gmailを使用したメール。 Facebookでのみ動作するように変更できると思います。
エラーや例外にどのように応答するのかわかりません(Facebookがインストールされていない場合に発生するのではないかと推測しています)ので、少しテストする必要があるかもしれません。
try {
Intent emailIntent = new Intent(Android.content.Intent.ACTION_SEND);
String[] recipients = new String[]{"e-mail address"};
emailIntent.putExtra(Android.content.Intent.EXTRA_EMAIL, recipients);
emailIntent.putExtra(Android.content.Intent.EXTRA_SUBJECT, "E-mail subject");
emailIntent.putExtra(Android.content.Intent.EXTRA_TEXT, "E-mail text");
emailIntent.setType("plain/text"); // This is incorrect MIME, but Gmail is one of the only apps that responds to it - this might need to be replaced with text/plain for Facebook
final PackageManager pm = getPackageManager();
final List<ResolveInfo> matches = pm.queryIntentActivities(emailIntent, 0);
ResolveInfo best = null;
for (final ResolveInfo info : matches)
if (info.activityInfo.packageName.endsWith(".gm") ||
info.activityInfo.name.toLowerCase().contains("gmail")) best = info;
if (best != null)
emailIntent.setClassName(best.activityInfo.packageName, best.activityInfo.name);
startActivity(emailIntent);
} catch (Exception e) {
Toast.makeText(this, "Application not found", Toast.LENGTH_SHORT).show();
}
これが私がしたことです(テキスト用)。コードでは、クリップボードに必要なテキストをコピーします。個人が初めて共有インテントボタンを使用しようとすると、Facebookで共有するかどうかを説明する通知がポップアップ表示されます。「Facebook」をクリックしてから長押しして貼り付ける必要がありますAndroidインテントシステムが破損しています)。次に、関連情報がフィールドにあります。ユーザーが苦情を申し立てることができるように、この投稿へのリンクを含めることもできます...
private void setClipboardText(String text) { // TODO
int sdk = Android.os.Build.VERSION.SDK_INT;
if(sdk < Android.os.Build.VERSION_CODES.HONEYCOMB) {
Android.text.ClipboardManager clipboard = (Android.text.ClipboardManager) getSystemService(Context.CLIPBOARD_SERVICE);
clipboard.setText(text);
} else {
Android.content.ClipboardManager clipboard = (Android.content.ClipboardManager) getSystemService(Context.CLIPBOARD_SERVICE);
Android.content.ClipData clip = Android.content.ClipData.newPlainText("text label",text);
clipboard.setPrimaryClip(clip);
}
}
以下は、w/priorバージョンを扱う方法です
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case R.id.menu_item_share:
Intent shareIntent = new Intent(Intent.ACTION_SEND);
shareIntent.setType("text/plain");
shareIntent.putExtra(Intent.EXTRA_TEXT, "text here");
ClipboardManager clipboard = (ClipboardManager) getSystemService(CLIPBOARD_SERVICE); //TODO
ClipData clip = ClipData.newPlainText("label", "text here");
clipboard.setPrimaryClip(clip);
setShareIntent(shareIntent);
break;
}
return super.onOptionsItemSelected(item);
}
Lollipop(21)では、Intent.EXTRA_REPLACEMENT_EXTRAS
を使用して、Facebookの意図を具体的にオーバーライドできます(およびリンクのみを指定します)
https://developer.Android.com/reference/Android/content/Intent.html#EXTRA_REPLACEMENT_EXTRAS
private void doShareLink(String text, String link) {
Intent shareIntent = new Intent(Intent.ACTION_SEND);
shareIntent.setType("text/plain");
Intent chooserIntent = Intent.createChooser(shareIntent, getString(R.string.share_via));
// for 21+, we can use EXTRA_REPLACEMENT_EXTRAS to support the specific case of Facebook
// (only supports a link)
// >=21: facebook=link, other=text+link
// <=20: all=link
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Lollipop) {
shareIntent.putExtra(Intent.EXTRA_TEXT, text + " " + link);
Bundle facebookBundle = new Bundle();
facebookBundle.putString(Intent.EXTRA_TEXT, link);
Bundle replacement = new Bundle();
replacement.putBundle("com.facebook.katana", facebookBundle);
chooserIntent.putExtra(Intent.EXTRA_REPLACEMENT_EXTRAS, replacement);
} else {
shareIntent.putExtra(Intent.EXTRA_TEXT, link);
}
chooserIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(chooserIntent);
}
共有できるのはTextorImage、両方ともIntents
を使用しません。以下のコードは、存在する場合はImageのみを共有し、Imageが存在する場合はTextのみを共有します終了しません。両方を共有したい場合は、ここから Facebook SDKを使用する必要があります。
以下のコードの代わりに他のソリューションを使用する場合、パッケージ名com.facebook.liteも指定することを忘れないでください。これはFacebook Lite。テストしていませんが、com.facebook.orcaは、必要に応じてFacebook Messengerのパッケージ名ですそれもターゲットにします。
WhatsApp 、 Twitter と共有するためのメソッドを追加できます...
public class IntentShareHelper {
/**
* <b>Beware,</b> this shares only image if exists, or only text if image does not exits. Can't share both
*/
public static void shareOnFacebook(AppCompatActivity appCompatActivity, String textBody, Uri fileUri) {
Intent intent = new Intent(Intent.ACTION_SEND);
intent.setType("text/plain");
intent.putExtra(Intent.EXTRA_TEXT,!TextUtils.isEmpty(textBody) ? textBody : "");
if (fileUri != null) {
intent.putExtra(Intent.EXTRA_STREAM, fileUri);
intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
intent.setType("image/*");
}
boolean facebookAppFound = false;
List<ResolveInfo> matches = appCompatActivity.getPackageManager().queryIntentActivities(intent, PackageManager.MATCH_DEFAULT_ONLY);
for (ResolveInfo info : matches) {
if (info.activityInfo.packageName.toLowerCase().startsWith("com.facebook.katana") ||
info.activityInfo.packageName.toLowerCase().startsWith("com.facebook.lite")) {
intent.setPackage(info.activityInfo.packageName);
facebookAppFound = true;
break;
}
}
if (facebookAppFound) {
appCompatActivity.startActivity(intent);
} else {
showWarningDialog(appCompatActivity, appCompatActivity.getString(R.string.error_activity_not_found));
}
}
public static void shareOnWhatsapp(AppCompatActivity appCompatActivity, String textBody, Uri fileUri){...}
private static void showWarningDialog(Context context, String message) {
new AlertDialog.Builder(context)
.setMessage(message)
.setNegativeButton(context.getString(R.string.close), new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
}
})
.setCancelable(true)
.create().show();
}
}
FileからUriを取得するには、以下のクラスを使用します。
public class UtilityFile {
public static @Nullable Uri getUriFromFile(Context context, @Nullable File file) {
if (file == null)
return null;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
try {
return FileProvider.getUriForFile(context, "com.my.package.fileprovider", file);
} catch (Exception e) {
e.printStackTrace();
return null;
}
} else {
return Uri.fromFile(file);
}
}
// Returns the URI path to the Bitmap displayed in specified ImageView
public static Uri getLocalBitmapUri(Context context, ImageView imageView) {
Drawable drawable = imageView.getDrawable();
Bitmap bmp = null;
if (drawable instanceof BitmapDrawable) {
bmp = ((BitmapDrawable) imageView.getDrawable()).getBitmap();
} else {
return null;
}
// Store image to default external storage directory
Uri bmpUri = null;
try {
// Use methods on Context to access package-specific directories on external storage.
// This way, you don't need to request external read/write permission.
File file = new File(context.getExternalFilesDir(Environment.DIRECTORY_PICTURES), "share_image_" + System.currentTimeMillis() + ".png");
FileOutputStream out = new FileOutputStream(file);
bmp.compress(Bitmap.CompressFormat.PNG, 90, out);
out.close();
bmpUri = getUriFromFile(context, file);
} catch (IOException e) {
e.printStackTrace();
}
return bmpUri;
}
}
書き込みFileProviderには、次のリンクを使用します: https://github.com/codepath/Android_guides/wiki/Sharing-Content-with -インテント
このソリューションも機能します。 Facebookがインストールされていない場合、通常の共有ダイアログを実行するだけです。ログインしていない場合は、ログイン画面に移動します。ログインしている場合は、共有ダイアログが開き、Intent Extraから「共有URL」が入力されます。
Intent intent = new Intent(Intent.ACTION_SEND);
intent.putExtra(Intent.EXTRA_TEXT, "Share url");
intent.setType("text/plain");
List<ResolveInfo> matches = getMainFragmentActivity().getPackageManager().queryIntentActivities(intent, 0);
for (ResolveInfo info : matches) {
if (info.activityInfo.packageName.toLowerCase().contains("facebook")) {
intent.setPackage(info.activityInfo.packageName);
}
}
startActivity(intent);
Facebookのバージョン4.0.0では、多くのことが変更されたようです。これは私のコードで正常に動作しています。お役に立てば幸いです。
/**
* Facebook does not support sharing content without using their SDK however
* it is possible to share URL
*
* @param content
* @param url
*/
private void shareOnFacebook(String content, String url)
{
try
{
// TODO: This part does not work properly based on my test
Intent fbIntent = new Intent(Intent.ACTION_SEND);
fbIntent.setType("text/plain");
fbIntent.putExtra(Intent.EXTRA_TEXT, content);
fbIntent.putExtra(Intent.EXTRA_STREAM, url);
fbIntent.addCategory(Intent.CATEGORY_LAUNCHER);
fbIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK
| Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);
fbIntent.setComponent(new ComponentName("com.facebook.katana",
"com.facebook.composer.shareintent.ImplicitShareIntentHandler"));
startActivity(fbIntent);
return;
}
catch (Exception e)
{
// User doesn't have Facebook app installed. Try sharing through browser.
}
// If we failed (not native FB app installed), try share through SEND
String sharerUrl = "https://www.facebook.com/sharer/sharer.php?u=" + url;
SupportUtils.doShowUri(this.getActivity(), sharerUrl);
}
Facebookアプリをリンクで開くために行ったこと
shareIntent = new Intent(Intent.ACTION_SEND);
shareIntent.setComponent(new ComponentName("com.facebook.katana",
"com.facebook.katana.activity.composer.ImplicitShareIntentHandler"));
shareIntent.setType("text/plain");
shareIntent.putExtra(Intent.EXTRA_TEXT, videoUrl);
FacebookはIntent.EXTRA_TEXT
とプレーンテキストデータを共有することはできませんが、これを使用してFacebookのメッセンジャーとテキスト+リンクを共有できます。
Intent sendIntent = new Intent();
sendIntent.setAction(Intent.ACTION_SEND);
sendIntent.putExtra(Intent.EXTRA_TEXT, text+url link);
sendIntent.setType("text/plain");
sendIntent.setPackage("com.facebook.orca");
startActivity(sendIntent);
public void invokeShare(Activity activity, String quote, String credit) {
Intent shareIntent = new Intent(Android.content.Intent.ACTION_SEND);
shareIntent.setType("text/plain");
shareIntent.putExtra(Android.content.Intent.EXTRA_SUBJECT, activity.getString(R.string.share_subject));
shareIntent.putExtra(Android.content.Intent.EXTRA_TEXT, "Example text");
shareIntent.putExtra("com.facebook.platform.extra.APPLICATION_ID", activity.getString(R.string.app_id));
activity.startActivity(Intent.createChooser(shareIntent, activity.getString(R.string.share_title)));
}
アプリからFacebookにメッセージを渡す最も簡単な方法は、プログラムでクリップボードにコピーし、貼り付けるオプションがあることをユーザーに警告することです。ユーザーが手動で行う必要がなくなります。私のアプリは貼り付けられませんが、ユーザーが貼り付ける可能性があります。
...
if (app.equals("facebook")) {
// overcome fb 'putExtra' constraint;
// copy message to clipboard for user to paste into fb.
ClipboardManager cb = (ClipboardManager)
getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText("post", msg);
cb.setPrimaryClip(clip);
// tell the to PASTE POST with option to stop showing this dialogue
showDialog(this, getString(R.string.facebook_post));
}
startActivity(appIntent);
...