Commit ebfa88e0 authored by Sinan Sahin's avatar Sinan Sahin Committed by Commit Bot

[Context menu] Extract native methods into a delegate

This CL extracts ChromeContextMenuPopulator's native methods into a
separate class, ChromeContextMenuNativeDelegate. This class implements
an interface, ContextMenuNativeDelegate, that is referenced from other
classes without depending on the populator.

Bug: 1137469
Change-Id: If111e8e40af011566271040ca1ad3a18fc81c915
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2462047Reviewed-by: default avatarJinsuk Kim <jinsukkim@chromium.org>
Reviewed-by: default avatarTheresa  <twellington@chromium.org>
Commit-Queue: Sinan Sahin <sinansahin@google.com>
Cr-Commit-Position: refs/heads/master@{#816327}
parent dd589196
......@@ -1500,7 +1500,8 @@ if (is_android) {
}
java_cpp_enum("context_menu_image_format_enum_javagen") {
sources = [ "browser/android/context_menu/chrome_context_menu_populator.h" ]
sources =
[ "browser/android/context_menu/context_menu_native_delegate_impl.h" ]
}
source_set("chrome_android_core") {
......
......@@ -667,6 +667,7 @@ group("jni_headers") {
":chrome_jni_headers",
"//chrome/android/features/autofill_assistant:jni_headers",
"//chrome/android/features/keyboard_accessory:jni_headers",
"//chrome/browser/contextmenu:jni_headers",
"//chrome/browser/download/android:jni_headers",
"//chrome/browser/enterprise/util:jni_headers",
"//chrome/browser/flags:jni_headers",
......@@ -802,6 +803,7 @@ junit_binary("chrome_junit_tests") {
"//chrome/browser/android/lifecycle:java",
"//chrome/browser/browser_controls/android:java",
"//chrome/browser/browser_controls/android:junit",
"//chrome/browser/contextmenu:java",
"//chrome/browser/device:java",
"//chrome/browser/device:junit",
"//chrome/browser/download/android:java",
......@@ -3137,7 +3139,6 @@ generate_jni("chrome_jni_headers") {
"java/src/org/chromium/chrome/browser/compositor/scene_layer/TabStripSceneLayer.java",
"java/src/org/chromium/chrome/browser/consent_auditor/ConsentAuditorBridge.java",
"java/src/org/chromium/chrome/browser/content/ContentUtils.java",
"java/src/org/chromium/chrome/browser/contextmenu/ChromeContextMenuPopulator.java",
"java/src/org/chromium/chrome/browser/contextmenu/ContextMenuHelper.java",
"java/src/org/chromium/chrome/browser/contextualsearch/ContextualSearchContext.java",
"java/src/org/chromium/chrome/browser/contextualsearch/ContextualSearchManager.java",
......
......@@ -13,7 +13,6 @@ import org.chromium.chrome.browser.contextmenu.ChromeContextMenuPopulator.Contex
import org.chromium.chrome.browser.externalauth.ExternalAuthUtils;
import org.chromium.chrome.browser.share.ShareDelegate;
import org.chromium.components.embedder_support.contextmenu.ContextMenuParams;
import org.chromium.content_public.browser.RenderFrameHost;
/**
* Factory for creating {@link ContextMenuPopulator}s.
......@@ -40,8 +39,8 @@ public class ChromeContextMenuPopulatorFactory implements ContextMenuPopulatorFa
@Override
public ContextMenuPopulator createContextMenuPopulator(
Context context, ContextMenuParams params, RenderFrameHost renderFrameHost) {
Context context, ContextMenuParams params, ContextMenuNativeDelegate nativeDelegate) {
return new ChromeContextMenuPopulator(mItemDelegate, mShareDelegateSupplier,
mContextMenuMode, mExternalAuthUtils, context, params, renderFrameHost);
mContextMenuMode, mExternalAuthUtils, context, params, nativeDelegate);
}
}
......@@ -36,6 +36,7 @@ public class ContextMenuHelper {
private final WebContents mWebContents;
private long mNativeContextMenuHelper;
private ContextMenuNativeDelegate mCurrentNativeDelegate;
private ContextMenuPopulator mCurrentPopulator;
private ContextMenuPopulatorFactory mPopulatorFactory;
private ContextMenuParams mCurrentContextMenuParams;
......@@ -64,7 +65,7 @@ public class ContextMenuHelper {
mCurrentContextMenu.dismiss();
mCurrentContextMenu = null;
}
if (mCurrentPopulator != null) mCurrentPopulator.onDestroy();
if (mCurrentNativeDelegate != null) mCurrentNativeDelegate.destroy();
if (mPopulatorFactory != null) mPopulatorFactory.onDestroy();
mNativeContextMenuHelper = 0;
}
......@@ -75,7 +76,7 @@ public class ContextMenuHelper {
mCurrentContextMenu.dismiss();
mCurrentContextMenu = null;
}
if (mCurrentPopulator != null) mCurrentPopulator.onDestroy();
if (mCurrentNativeDelegate != null) mCurrentNativeDelegate.destroy();
mCurrentPopulator = null;
if (mPopulatorFactory != null) mPopulatorFactory.onDestroy();
mPopulatorFactory = populatorFactory;
......@@ -100,8 +101,10 @@ public class ContextMenuHelper {
return;
}
mCurrentNativeDelegate =
new ContextMenuNativeDelegateImpl(mWebContents, renderFrameHost, params);
mCurrentPopulator = mPopulatorFactory.createContextMenuPopulator(
windowAndroid.getActivity().get(), params, renderFrameHost);
windowAndroid.getActivity().get(), params, mCurrentNativeDelegate);
mIsIncognito = mCurrentPopulator.isIncognito();
mCurrentContextMenuParams = params;
mWindow = windowAndroid;
......@@ -122,9 +125,12 @@ public class ContextMenuHelper {
mOnMenuClosed = () -> {
recordTimeToTakeActionHistogram(mSelectedItemBeforeDismiss);
mCurrentContextMenu = null;
if (mCurrentNativeDelegate != null) {
mCurrentNativeDelegate.destroy();
mCurrentNativeDelegate = null;
}
if (mCurrentPopulator != null) {
mCurrentPopulator.onMenuClosed();
mCurrentPopulator.onDestroy();
mCurrentPopulator = null;
}
if (LensUtils.enableShoppyImageMenuItem() || LensUtils.enableImageChip(mIsIncognito)) {
......@@ -141,11 +147,12 @@ public class ContextMenuHelper {
// not be enabled under any circumstances on Stable Chrome builds due to potential
// latency impact.
if (LensUtils.enableShoppyImageMenuItem()) {
mCurrentPopulator.retrieveImage(ContextMenuImageFormat.ORIGINAL, (Uri uri) -> {
LensController.getInstance().classifyImage(uri, (Boolean isShoppyImage) -> {
displayRevampedContextMenu(topContentOffsetPx, isShoppyImage);
});
});
Callback<Uri> callback = (Uri uri) -> {
LensController.getInstance().classifyImage(uri,
(Boolean isShoppyImage)
-> displayRevampedContextMenu(topContentOffsetPx, isShoppyImage));
};
mCurrentNativeDelegate.retrieveImageForShare(ContextMenuImageFormat.ORIGINAL, callback);
} else {
displayRevampedContextMenu(topContentOffsetPx, /* addShoppyMenuItem */ false);
}
......@@ -160,12 +167,12 @@ public class ContextMenuHelper {
}
final RevampedContextMenuCoordinator menuCoordinator =
new RevampedContextMenuCoordinator(topContentOffsetPx);
new RevampedContextMenuCoordinator(topContentOffsetPx, mCurrentNativeDelegate);
mCurrentContextMenu = menuCoordinator;
if (LensUtils.enableImageChip(mIsIncognito)) {
LensAsyncManager lensAsyncManager =
new LensAsyncManager(mCurrentContextMenuParams, mCurrentPopulator);
new LensAsyncManager(mCurrentContextMenuParams, mCurrentNativeDelegate);
menuCoordinator.displayMenuWithLensChip(mWindow, mWebContents,
mCurrentContextMenuParams, items, mCallback, mOnMenuShown, mOnMenuClosed,
lensAsyncManager);
......@@ -177,10 +184,6 @@ public class ContextMenuHelper {
if (sRevampedContextMenuShownCallback != null) {
sRevampedContextMenuShownCallback.onResult(menuCoordinator);
}
// TODO(sinansahin): This could be pushed in to the header mediator.
if (mCurrentContextMenuParams.isImage()) {
mCurrentPopulator.getThumbnail(menuCoordinator.getOnImageThumbnailRetrievedReference());
}
}
private void recordTimeToTakeActionHistogram(boolean selectedItem) {
......
......@@ -4,6 +4,8 @@
package org.chromium.chrome.browser.contextmenu;
import android.net.Uri;
import org.chromium.base.Callback;
import org.chromium.chrome.browser.lens.LensController;
import org.chromium.components.embedder_support.contextmenu.ContextMenuParams;
......@@ -15,16 +17,16 @@ class LensAsyncManager {
private static final String TAG = "LensAsyncManager";
private ContextMenuParams mParams;
private ContextMenuPopulator mPopulator;
private ContextMenuNativeDelegate mNativeDelegate;
/**
* Construct a lens async manager.
* @param params Context menu params used to retrieve additional metadata.
* @param populator A populator reference used to retrieve image bytes.
* @param nativeDelegate {@link ContextMenuNativeDelegate} used to retrieve image bytes.
*/
public LensAsyncManager(ContextMenuParams params, ContextMenuPopulator populator) {
public LensAsyncManager(ContextMenuParams params, ContextMenuNativeDelegate nativeDelegate) {
mParams = params;
mPopulator = populator;
mNativeDelegate = nativeDelegate;
}
/**
......@@ -32,14 +34,12 @@ class LensAsyncManager {
* @param replyCallback The function to callback with the classification.
*/
public void classifyImageAsync(Callback<Boolean> replyCallback) {
Callback<Uri> callback = (uri)
-> LensController.getInstance().classifyImage(uri, mParams.getPageUrl(),
mParams.getTitleText(), (isClassificationSuccessful) -> {
replyCallback.onResult(isClassificationSuccessful);
});
// Must occur on UI thread.
mPopulator.retrieveImage(ContextMenuImageFormat.ORIGINAL, (uri) -> {
LensController.getInstance().classifyImage(uri,
mParams.getPageUrl(),
mParams.getTitleText(),
(isClassificationSuccessful) -> {
replyCallback.onResult(isClassificationSuccessful);
});
});
mNativeDelegate.retrieveImageForShare(ContextMenuImageFormat.ORIGINAL, callback);
}
}
\ No newline at end of file
......@@ -9,7 +9,6 @@ import static org.chromium.chrome.browser.contextmenu.RevampedContextMenuItemWit
import static org.chromium.chrome.browser.contextmenu.RevampedContextMenuItemWithIconButtonProperties.BUTTON_MENU_ID;
import android.app.Activity;
import android.graphics.Bitmap;
import android.util.Pair;
import android.view.LayoutInflater;
import android.view.View;
......@@ -66,14 +65,19 @@ public class RevampedContextMenuCoordinator implements ContextMenuUi {
private float mTopContentOffsetPx;
private ContextMenuDialog mDialog;
private Runnable mOnMenuClosed;
private ContextMenuNativeDelegate mNativeDelegate;
/**
* Constructor that also sets the content offset.
*
* @param topContentOffsetPx content offset from the top.
* @param nativeDelegate The {@link ContextMenuNativeDelegate} to retrieve the thumbnail from
* native.
*/
RevampedContextMenuCoordinator(float topContentOffsetPx) {
RevampedContextMenuCoordinator(
float topContentOffsetPx, ContextMenuNativeDelegate nativeDelegate) {
mTopContentOffsetPx = topContentOffsetPx;
mNativeDelegate = nativeDelegate;
}
@Override
......@@ -135,8 +139,8 @@ public class RevampedContextMenuCoordinator implements ContextMenuUi {
? PerformanceHintsObserver.getPerformanceClassForURL(
webContents, params.getLinkUrl())
: PerformanceClass.PERFORMANCE_UNKNOWN;
mHeaderCoordinator = new RevampedContextMenuHeaderCoordinator(
activity, performanceClass, params, Profile.fromWebContents(mWebContents));
mHeaderCoordinator = new RevampedContextMenuHeaderCoordinator(activity, performanceClass,
params, Profile.fromWebContents(mWebContents), mNativeDelegate);
// The Integer here specifies the {@link ListItemType}.
ModelList listItems = getItemList(activity, items, onItemClicked);
......@@ -271,15 +275,11 @@ public class RevampedContextMenuCoordinator implements ContextMenuUi {
mDialog.dismiss();
}
Callback<Bitmap> getOnImageThumbnailRetrievedReference() {
return mHeaderCoordinator.getOnImageThumbnailRetrievedReference();
}
@VisibleForTesting
void initializeHeaderCoordinatorForTesting(
Activity activity, ContextMenuParams params, Profile profile) {
void initializeHeaderCoordinatorForTesting(Activity activity, ContextMenuParams params,
Profile profile, ContextMenuNativeDelegate nativeDelegate) {
mHeaderCoordinator = new RevampedContextMenuHeaderCoordinator(
activity, PerformanceClass.PERFORMANCE_UNKNOWN, params, profile);
activity, PerformanceClass.PERFORMANCE_UNKNOWN, params, profile, nativeDelegate);
}
@VisibleForTesting
......
......@@ -5,11 +5,9 @@
package org.chromium.chrome.browser.contextmenu;
import android.app.Activity;
import android.graphics.Bitmap;
import android.text.SpannableString;
import android.text.TextUtils;
import org.chromium.base.Callback;
import org.chromium.chrome.browser.ChromeBaseAppCompatActivity;
import org.chromium.chrome.browser.night_mode.GlobalNightModeStateProviderHolder;
import org.chromium.chrome.browser.omnibox.ChromeAutocompleteSchemeClassifier;
......@@ -25,10 +23,10 @@ class RevampedContextMenuHeaderCoordinator {
private RevampedContextMenuHeaderMediator mMediator;
RevampedContextMenuHeaderCoordinator(Activity activity, @PerformanceClass int performanceClass,
ContextMenuParams params, Profile profile) {
ContextMenuParams params, Profile profile, ContextMenuNativeDelegate nativeDelegate) {
mModel = buildModel(ContextMenuUtils.getTitle(params), getUrl(activity, params, profile));
mMediator = new RevampedContextMenuHeaderMediator(
activity, mModel, performanceClass, params, profile);
activity, mModel, performanceClass, params, profile, nativeDelegate);
}
private PropertyModel buildModel(String title, CharSequence url) {
......@@ -70,10 +68,6 @@ class RevampedContextMenuHeaderCoordinator {
return url;
}
Callback<Bitmap> getOnImageThumbnailRetrievedReference() {
return mMediator::onImageThumbnailRetrieved;
}
PropertyModel getModel() {
return mModel;
}
......
......@@ -41,13 +41,20 @@ class RevampedContextMenuHeaderMediator implements View.OnClickListener {
private String mPlainUrl;
RevampedContextMenuHeaderMediator(Context context, PropertyModel model,
@PerformanceClass int performanceClass, ContextMenuParams params, Profile profile) {
@PerformanceClass int performanceClass, ContextMenuParams params, Profile profile,
ContextMenuNativeDelegate nativeDelegate) {
mContext = context;
mPlainUrl = params.getUrl();
mModel = model;
mModel.set(RevampedContextMenuHeaderProperties.TITLE_AND_URL_CLICK_LISTENER, this);
if (!params.isImage() && !params.isVideo()) {
if (params.isImage()) {
final Resources res = mContext.getResources();
final int imageMaxSize =
res.getDimensionPixelSize(R.dimen.revamped_context_menu_header_image_max_size);
nativeDelegate.retrieveImageForContextMenu(
imageMaxSize, imageMaxSize, this::onImageThumbnailRetrieved);
} else if (!params.isImage() && !params.isVideo()) {
LargeIconBridge iconBridge = new LargeIconBridge(profile);
iconBridge.getLargeIconForStringUrl(mPlainUrl,
context.getResources().getDimensionPixelSize(R.dimen.default_favicon_min_size),
......
......@@ -15,6 +15,7 @@ include_rules = [
"+chrome/android/java/src/org/chromium/chrome/browser/ssl/SecurityStateModel.java",
"+chrome/android/java/src/org/chromium/chrome/browser/tab",
"+chrome/browser/tab/java/src/org/chromium/chrome/browser/tab/Tab.java",
"+chrome/browser/contextmenu/java/src/org/chromium/chrome/browser/contextmenu/ContextMenuNativeDelegate.java",
"+chrome/browser/contextmenu/java/src/org/chromium/chrome/browser/contextmenu/ContextMenuPopulator.java",
"+chrome/browser/contextmenu/java/src/org/chromium/chrome/browser/contextmenu/ContextMenuPopulatorFactory.java",
"+chrome/android/java/src/org/chromium/chrome/browser/ui/TabObscuringHandler.java",
......
......@@ -4,15 +4,11 @@
package org.chromium.chrome.browser.tab;
import android.graphics.Bitmap;
import android.net.Uri;
import android.util.Pair;
import androidx.annotation.Nullable;
import org.chromium.base.Callback;
import org.chromium.base.ObserverList.RewindableIterator;
import org.chromium.chrome.browser.contextmenu.ContextMenuImageFormat;
import org.chromium.chrome.browser.contextmenu.ContextMenuPopulator;
import org.chromium.ui.modelutil.MVCListAdapter.ModelList;
......@@ -37,13 +33,6 @@ public class TabContextMenuPopulator implements ContextMenuPopulator {
mTab = (TabImpl) tab;
}
@Override
public void onDestroy() {
// |mPopulator| can be null for activities that do not use context menu. Following
// methods are not called, but |onDestroy| is.
if (mPopulator != null) mPopulator.onDestroy();
}
@Override
public List<Pair<Integer, ModelList>> buildContextMenu(boolean isShoppyImage) {
List<Pair<Integer, ModelList>> itemGroups = mPopulator.buildContextMenu(isShoppyImage);
......@@ -59,16 +48,6 @@ public class TabContextMenuPopulator implements ContextMenuPopulator {
return mPopulator.onItemSelected(itemId);
}
@Override
public void getThumbnail(final Callback<Bitmap> callback) {
mPopulator.getThumbnail(callback);
}
@Override
public void retrieveImage(@ContextMenuImageFormat int imageFormat, Callback<Uri> callback) {
mPopulator.retrieveImage(imageFormat, callback);
}
@Override
public void onMenuClosed() {
mPopulator.onMenuClosed();
......
......@@ -6,10 +6,10 @@ package org.chromium.chrome.browser.tab;
import android.content.Context;
import org.chromium.chrome.browser.contextmenu.ContextMenuNativeDelegate;
import org.chromium.chrome.browser.contextmenu.ContextMenuPopulator;
import org.chromium.chrome.browser.contextmenu.ContextMenuPopulatorFactory;
import org.chromium.components.embedder_support.contextmenu.ContextMenuParams;
import org.chromium.content_public.browser.RenderFrameHost;
/**
* A simple wrapper around a {@link ContextMenuPopulatorFactory} for creating
......@@ -37,9 +37,9 @@ class TabContextMenuPopulatorFactory implements ContextMenuPopulatorFactory {
@Override
public ContextMenuPopulator createContextMenuPopulator(
Context context, ContextMenuParams params, RenderFrameHost renderFrameHost) {
Context context, ContextMenuParams params, ContextMenuNativeDelegate nativeDelegate) {
return new TabContextMenuPopulator(
mPopulatorFactory.createContextMenuPopulator(context, params, renderFrameHost),
mPopulatorFactory.createContextMenuPopulator(context, params, nativeDelegate),
mTab);
}
}
......@@ -37,7 +37,6 @@ import org.chromium.chrome.browser.flags.ChromeFeatureList;
import org.chromium.chrome.browser.share.ShareDelegate;
import org.chromium.components.embedder_support.contextmenu.ContextMenuParams;
import org.chromium.components.search_engines.TemplateUrlService;
import org.chromium.content_public.browser.RenderFrameHost;
import org.chromium.content_public.browser.test.NativeLibraryTestUtils;
import org.chromium.ui.base.MenuSourceType;
import org.chromium.ui.modelutil.MVCListAdapter.ModelList;
......@@ -67,7 +66,7 @@ public class ChromeContextMenuPopulatorTest {
@Mock
private ExternalAuthUtils mExternalAuthUtils;
@Mock
private RenderFrameHost mRenderFrameHost;
private ContextMenuNativeDelegate mNativeDelegate;
// Despite this being a spy, we add the @Mock annotation so that proguard doesn't strip the
// spied class.
......@@ -100,7 +99,7 @@ public class ChromeContextMenuPopulatorTest {
()
-> mShareDelegate,
mode, mExternalAuthUtils, ContextUtils.getApplicationContext(), params,
mRenderFrameHost));
mNativeDelegate));
doReturn(mTemplateUrlService).when(mPopulator).getTemplateUrlService();
doReturn(false).when(mPopulator).shouldTriggerEphemeralTabHelpUi();
doReturn(true).when(mExternalAuthUtils).isGoogleSigned(IntentHandler.PACKAGE_GSA);
......
......@@ -1098,7 +1098,8 @@ public class RevampedContextMenuTest implements DownloadTestRule.CustomMainActiv
String mockImageData = "randomdata";
byte[] mockImageByteArray = mockImageData.getBytes();
// See function javadoc for more context.
ChromeContextMenuPopulator.setHardcodedImageBytesForTesting(mockImageByteArray, extension);
ContextMenuNativeDelegateImpl.setHardcodedImageBytesForTesting(
mockImageByteArray, extension);
}
private void assertStringContains(String subString, String superString) {
......
......@@ -54,6 +54,8 @@ public class RevampedContextMenuCoordinatorTest {
@Mock
PerformanceHintsObserver.Natives mNativeMock;
@Mock
ContextMenuNativeDelegate mNativeDelegate;
private RevampedContextMenuCoordinator mCoordinator;
private Activity mActivity;
......@@ -62,7 +64,7 @@ public class RevampedContextMenuCoordinatorTest {
@Before
public void setUpTest() {
mActivity = Robolectric.setupActivity(Activity.class);
mCoordinator = new RevampedContextMenuCoordinator(0);
mCoordinator = new RevampedContextMenuCoordinator(0, mNativeDelegate);
MockitoAnnotations.initMocks(this);
mocker.mock(PerformanceHintsObserverJni.TEST_HOOKS, mNativeMock);
when(mNativeMock.isContextMenuPerformanceInfoEnabled()).thenReturn(false);
......@@ -87,7 +89,8 @@ public class RevampedContextMenuCoordinatorTest {
groupTwo.add(createShareListItem(Item.SHARE_IMAGE));
rawItems.add(new Pair<>(ContextMenuGroup.IMAGE, groupTwo));
mCoordinator.initializeHeaderCoordinatorForTesting(mActivity, params, mProfile);
mCoordinator.initializeHeaderCoordinatorForTesting(
mActivity, params, mProfile, mNativeDelegate);
ModelList itemList = mCoordinator.getItemList(mActivity, rawItems, (i) -> {});
assertThat(itemList.get(0).type, equalTo(ListItemType.HEADER));
......@@ -119,7 +122,8 @@ public class RevampedContextMenuCoordinatorTest {
groupOne.add(createShareListItem(Item.SHARE_LINK));
rawItems.add(new Pair<>(ContextMenuGroup.LINK, groupOne));
mCoordinator.initializeHeaderCoordinatorForTesting(mActivity, params, mProfile);
mCoordinator.initializeHeaderCoordinatorForTesting(
mActivity, params, mProfile, mNativeDelegate);
ModelList itemList = mCoordinator.getItemList(mActivity, rawItems, (i) -> {});
assertThat(itemList.get(0).type, equalTo(ListItemType.HEADER));
......@@ -140,7 +144,8 @@ public class RevampedContextMenuCoordinatorTest {
groupOne.add(createListItem(Item.SAVE_VIDEO));
rawItems.add(new Pair<>(ContextMenuGroup.LINK, groupOne));
mCoordinator.initializeHeaderCoordinatorForTesting(mActivity, params, mProfile);
mCoordinator.initializeHeaderCoordinatorForTesting(
mActivity, params, mProfile, mNativeDelegate);
ModelList itemList = mCoordinator.getItemList(mActivity, rawItems, (i) -> {});
assertThat(itemList.get(0).type, equalTo(ListItemType.HEADER));
......
......@@ -43,6 +43,8 @@ public class RevampedContextMenuHeaderMediatorTest {
@Mock
PerformanceHintsObserver.Natives mNativeMock;
@Mock
ContextMenuNativeDelegate mNativeDelegate;
private Activity mActivity;
private final Profile mProfile = Mockito.mock(Profile.class);
......@@ -65,8 +67,9 @@ public class RevampedContextMenuHeaderMediatorTest {
final ContextMenuParams params =
new ContextMenuParams(0, ContextMenuDataMediaType.IMAGE, "https://example.org",
"https://example.org/sitemap", "", "", "", "", null, false, 0, 0, 0);
final RevampedContextMenuHeaderMediator mediator = new RevampedContextMenuHeaderMediator(
mActivity, model, PerformanceClass.PERFORMANCE_FAST, params, mProfile);
final RevampedContextMenuHeaderMediator mediator =
new RevampedContextMenuHeaderMediator(mActivity, model,
PerformanceClass.PERFORMANCE_FAST, params, mProfile, mNativeDelegate);
assertThat(model.get(RevampedContextMenuHeaderProperties.URL_PERFORMANCE_CLASS),
equalTo(PerformanceClass.PERFORMANCE_FAST));
}
......@@ -82,8 +85,9 @@ public class RevampedContextMenuHeaderMediatorTest {
final ContextMenuParams params =
new ContextMenuParams(0, ContextMenuDataMediaType.IMAGE, "https://example.org",
"https://example.org/sitemap", "", "", "", "", null, false, 0, 0, 0);
final RevampedContextMenuHeaderMediator mediator = new RevampedContextMenuHeaderMediator(
mActivity, model, PerformanceClass.PERFORMANCE_FAST, params, mProfile);
final RevampedContextMenuHeaderMediator mediator =
new RevampedContextMenuHeaderMediator(mActivity, model,
PerformanceClass.PERFORMANCE_FAST, params, mProfile, mNativeDelegate);
assertThat(model.get(RevampedContextMenuHeaderProperties.URL_PERFORMANCE_CLASS),
equalTo(PerformanceClass.PERFORMANCE_UNKNOWN));
}
......@@ -98,8 +102,9 @@ public class RevampedContextMenuHeaderMediatorTest {
.build();
final ContextMenuParams params = new ContextMenuParams(0, ContextMenuDataMediaType.IMAGE,
"https://example.org", "", "", "", "", "", null, false, 0, 0, 0);
final RevampedContextMenuHeaderMediator mediator = new RevampedContextMenuHeaderMediator(
mActivity, model, PerformanceClass.PERFORMANCE_FAST, params, mProfile);
final RevampedContextMenuHeaderMediator mediator =
new RevampedContextMenuHeaderMediator(mActivity, model,
PerformanceClass.PERFORMANCE_FAST, params, mProfile, mNativeDelegate);
assertThat(model.get(RevampedContextMenuHeaderProperties.URL_PERFORMANCE_CLASS),
equalTo(PerformanceClass.PERFORMANCE_UNKNOWN));
}
......
......@@ -2486,8 +2486,8 @@ static_library("browser") {
"android/compositor/tab_content_manager.h",
"android/consent_auditor/consent_auditor_bridge.cc",
"android/content/content_utils.cc",
"android/context_menu/chrome_context_menu_populator.cc",
"android/context_menu/chrome_context_menu_populator.h",
"android/context_menu/context_menu_native_delegate_impl.cc",
"android/context_menu/context_menu_native_delegate_impl.h",
"android/contextualsearch/contextual_search_context.cc",
"android/contextualsearch/contextual_search_context.h",
"android/contextualsearch/contextual_search_delegate.cc",
......
......@@ -2,37 +2,30 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/android/context_menu/chrome_context_menu_populator.h"
#include "chrome/browser/android/context_menu/context_menu_native_delegate_impl.h"
#include "base/android/callback_android.h"
#include "base/android/jni_android.h"
#include "base/android/jni_array.h"
#include "base/android/jni_string.h"
#include "base/bind.h"
#include "base/bind_helpers.h"
#include "base/strings/string_util.h"
#include "chrome/android/chrome_jni_headers/ChromeContextMenuPopulator_jni.h"
#include "chrome/browser/contextmenu/jni_headers/ContextMenuNativeDelegateImpl_jni.h"
#include "chrome/browser/download/android/download_controller_base.h"
#include "chrome/browser/image_decoder/image_decoder.h"
#include "chrome/browser/ui/tab_contents/core_tab_helper.h"
#include "components/embedder_support/android/contextmenu/context_menu_builder.h"
#include "content/public/browser/context_menu_params.h"
#include "content/public/browser/render_frame_host.h"
#include "content/public/browser/web_contents.h"
#include "third_party/blink/public/common/associated_interfaces/associated_interface_provider.h"
#include "ui/gfx/android/java_bitmap.h"
#include "ui/gfx/geometry/size.h"
using base::android::JavaParamRef;
using base::android::JavaRef;
namespace {
class ContextMenuPopulatorImageRequest : public ImageDecoder::ImageRequest {
class ContextMenuImageRequest : public ImageDecoder::ImageRequest {
public:
static void Start(const JavaRef<jobject>& jcallback,
const std::vector<uint8_t>& thumbnail_data) {
auto* request = new ContextMenuPopulatorImageRequest(jcallback);
auto* request = new ContextMenuImageRequest(jcallback);
ImageDecoder::Start(request, thumbnail_data);
}
......@@ -50,12 +43,12 @@ class ContextMenuPopulatorImageRequest : public ImageDecoder::ImageRequest {
}
private:
explicit ContextMenuPopulatorImageRequest(const JavaRef<jobject>& jcallback)
explicit ContextMenuImageRequest(const JavaRef<jobject>& jcallback)
: jcallback_(jcallback) {}
const base::android::ScopedJavaGlobalRef<jobject> jcallback_;
DISALLOW_IMPLICIT_CONSTRUCTORS(ContextMenuPopulatorImageRequest);
DISALLOW_IMPLICIT_CONSTRUCTORS(ContextMenuImageRequest);
};
chrome::mojom::ImageFormat ToChromeMojomImageFormat(int image_format) {
......@@ -85,7 +78,7 @@ void OnRetrieveImageForShare(
auto j_extension =
base::android::ConvertUTF8ToJavaString(env, image_extension);
base::android::RunObjectCallbackAndroid(
jcallback, Java_ChromeContextMenuPopulator_createImageCallbackResult(
jcallback, Java_ContextMenuNativeDelegateImpl_createImageCallbackResult(
env, j_data, j_extension));
}
......@@ -96,20 +89,20 @@ void OnRetrieveImageForContextMenu(
const std::vector<uint8_t>& thumbnail_data,
const gfx::Size& original_size,
const std::string& filename_extension) {
ContextMenuPopulatorImageRequest::Start(jcallback, thumbnail_data);
ContextMenuImageRequest::Start(jcallback, thumbnail_data);
}
} // namespace
ChromeContextMenuPopulator::ChromeContextMenuPopulator(
content::WebContents* web_contents,
content::ContextMenuParams* context_menu_params,
content::RenderFrameHost* render_frame_host)
ContextMenuNativeDelegateImpl::ContextMenuNativeDelegateImpl(
content::WebContents* const web_contents,
content::ContextMenuParams* const context_menu_params,
content::RenderFrameHost* const render_frame_host)
: web_contents_(web_contents),
context_menu_params_(context_menu_params),
render_frame_host_(render_frame_host) {}
void ChromeContextMenuPopulator::OnStartDownload(
void ContextMenuNativeDelegateImpl::StartDownload(
JNIEnv* env,
const JavaParamRef<jobject>& obj,
jboolean jis_link) {
......@@ -118,7 +111,7 @@ void ChromeContextMenuPopulator::OnStartDownload(
*context_menu_params_, web_contents_, jis_link, headers);
}
void ChromeContextMenuPopulator::SearchForImage(
void ContextMenuNativeDelegateImpl::SearchForImage(
JNIEnv* env,
const JavaParamRef<jobject>& obj) {
if (!render_frame_host_)
......@@ -129,19 +122,19 @@ void ChromeContextMenuPopulator::SearchForImage(
context_menu_params_->src_url);
}
void ChromeContextMenuPopulator::RetrieveImageForShare(
void ContextMenuNativeDelegateImpl::RetrieveImageForShare(
JNIEnv* env,
const JavaParamRef<jobject>& obj,
const JavaParamRef<jobject>& jcallback,
jint max_width_px,
jint max_height_px,
jint j_image_format) {
jint jimage_format) {
RetrieveImageInternal(env, base::BindOnce(&OnRetrieveImageForShare),
jcallback, max_width_px, max_height_px,
ToChromeMojomImageFormat(j_image_format));
ToChromeMojomImageFormat(jimage_format));
}
void ChromeContextMenuPopulator::RetrieveImageForContextMenu(
void ContextMenuNativeDelegateImpl::RetrieveImageForContextMenu(
JNIEnv* env,
const JavaParamRef<jobject>& obj,
const JavaParamRef<jobject>& jcallback,
......@@ -153,7 +146,7 @@ void ChromeContextMenuPopulator::RetrieveImageForContextMenu(
chrome::mojom::ImageFormat::PNG);
}
void ChromeContextMenuPopulator::RetrieveImageInternal(
void ContextMenuNativeDelegateImpl::RetrieveImageInternal(
JNIEnv* env,
ImageRetrieveCallback retrieve_callback,
const JavaParamRef<jobject>& jcallback,
......@@ -177,7 +170,7 @@ void ChromeContextMenuPopulator::RetrieveImageInternal(
base::android::ScopedJavaGlobalRef<jobject>(env, jcallback)));
}
static jlong JNI_ChromeContextMenuPopulator_Init(
static jlong JNI_ContextMenuNativeDelegateImpl_Init(
JNIEnv* env,
const JavaParamRef<jobject>& jweb_contents,
const JavaParamRef<jobject>& jcontext_menu_params,
......@@ -190,6 +183,6 @@ static jlong JNI_ChromeContextMenuPopulator_Init(
context_menu::ContextMenuParamsFromJavaObject(jcontext_menu_params);
auto* render_frame_host =
content::RenderFrameHost::FromJavaRenderFrameHost(jrender_frame_host);
return reinterpret_cast<intptr_t>(
new ChromeContextMenuPopulator(web_contents, params, render_frame_host));
return reinterpret_cast<intptr_t>(new ContextMenuNativeDelegateImpl(
web_contents, params, render_frame_host));
}
......@@ -2,11 +2,9 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CHROME_BROWSER_ANDROID_CONTEXT_MENU_CHROME_CONTEXT_MENU_POPULATOR_H_
#define CHROME_BROWSER_ANDROID_CONTEXT_MENU_CHROME_CONTEXT_MENU_POPULATOR_H_
#ifndef CHROME_BROWSER_ANDROID_CONTEXT_MENU_CONTEXT_MENU_NATIVE_DELEGATE_IMPL_H_
#define CHROME_BROWSER_ANDROID_CONTEXT_MENU_CONTEXT_MENU_NATIVE_DELEGATE_IMPL_H_
#include "base/android/jni_android.h"
#include "base/android/scoped_java_ref.h"
#include "chrome/common/chrome_render_frame.mojom.h"
#include "content/public/browser/context_menu_params.h"
#include "content/public/browser/render_frame_host.h"
......@@ -16,8 +14,6 @@ namespace content {
class WebContents;
}
class ImageRetrieveCallback;
// GENERATED_JAVA_ENUM_PACKAGE: org.chromium.chrome.browser.contextmenu
enum ContextMenuImageFormat {
JPEG = 0,
......@@ -25,29 +21,19 @@ enum ContextMenuImageFormat {
ORIGINAL = 2,
};
// Performs context menu-related actions.
class ChromeContextMenuPopulator {
protected:
using ImageRetrieveCallback = base::OnceCallback<void(
mojo::AssociatedRemote<chrome::mojom::ChromeRenderFrame>
chrome_render_frame_ptr,
const base::android::JavaRef<jobject>& jcallback,
const std::vector<uint8_t>& thumbnail_data,
const gfx::Size& max_dimen_px,
const std::string& image_extension)>;
class ContextMenuNativeDelegateImpl {
public:
explicit ChromeContextMenuPopulator(
explicit ContextMenuNativeDelegateImpl(
content::WebContents* const web_contents,
content::ContextMenuParams* context_menu_params,
content::ContextMenuParams* const context_menu_params,
content::RenderFrameHost* const render_frame_host);
void OnStartDownload(
void RetrieveImageForContextMenu(
JNIEnv* env,
const base::android::JavaParamRef<jobject>& obj,
jboolean jis_link);
void SearchForImage(JNIEnv* env,
const base::android::JavaParamRef<jobject>& obj);
const base::android::JavaParamRef<jobject>& jcallback,
jint max_width_px,
jint max_height_px);
void RetrieveImageForShare(
JNIEnv* env,
const base::android::JavaParamRef<jobject>& obj,
......@@ -55,12 +41,20 @@ class ChromeContextMenuPopulator {
jint max_width_px,
jint max_height_px,
jint j_image_type);
void RetrieveImageForContextMenu(
JNIEnv* env,
const base::android::JavaParamRef<jobject>& obj,
const base::android::JavaParamRef<jobject>& jcallback,
jint max_width_px,
jint max_height_px);
void StartDownload(JNIEnv* env,
const base::android::JavaParamRef<jobject>& obj,
jboolean jis_link);
void SearchForImage(JNIEnv* env,
const base::android::JavaParamRef<jobject>& obj);
protected:
using ImageRetrieveCallback = base::OnceCallback<void(
mojo::AssociatedRemote<chrome::mojom::ChromeRenderFrame>
chrome_render_frame_ptr,
const base::android::JavaRef<jobject>& jcallback,
const std::vector<uint8_t>& thumbnail_data,
const gfx::Size& max_dimen_px,
const std::string& image_extension)>;
private:
void RetrieveImageInternal(
......@@ -76,4 +70,4 @@ class ChromeContextMenuPopulator {
content::RenderFrameHost* const render_frame_host_;
};
#endif // CHROME_BROWSER_ANDROID_CONTEXT_MENU_CHROME_CONTEXT_MENU_POPULATOR_H_
#endif // CHROME_BROWSER_ANDROID_CONTEXT_MENU_CONTEXT_MENU_NATIVE_DELEGATE_IMPL_H_
......@@ -9,17 +9,26 @@ import("//chrome/browser/buildflags.gni")
android_library("java") {
sources = [
"java/src/org/chromium/chrome/browser/contextmenu/ContextMenuItemDelegate.java",
"java/src/org/chromium/chrome/browser/contextmenu/ContextMenuNativeDelegate.java",
"java/src/org/chromium/chrome/browser/contextmenu/ContextMenuNativeDelegateImpl.java",
"java/src/org/chromium/chrome/browser/contextmenu/ContextMenuPopulator.java",
"java/src/org/chromium/chrome/browser/contextmenu/ContextMenuPopulatorFactory.java",
]
annotation_processor_deps = [ "//base/android/jni_generator:jni_processor" ]
srcjar_deps = [ "//chrome:context_menu_image_format_enum_javagen" ]
deps = [
"//base:base_java",
"//base:jni_java",
"//components/browser_ui/share/android:java",
"//components/embedder_support/android:context_menu_java",
"//content/public/android:content_java",
"//third_party/android_deps:androidx_annotation_annotation_java",
"//ui/android:ui_no_recycler_view_java",
]
}
generate_jni("jni_headers") {
sources = [ "java/src/org/chromium/chrome/browser/contextmenu/ContextMenuNativeDelegateImpl.java" ]
}
// Copyright 2020 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
package org.chromium.chrome.browser.contextmenu;
import android.graphics.Bitmap;
import android.net.Uri;
import org.chromium.base.Callback;
/**
* Interface to handle context menu actions in native.
*/
public interface ContextMenuNativeDelegate {
/**
* Called when this {@link ContextMenuNativeDelegate} is being destroyed.
*/
void destroy();
/**
* Retrieves the image bitmap from the current {@link RenderFrameHost} that the context menu
* was triggered on to use in the context menu.
* @param maxWidthPx The maximum width for the retrieved bitmap in pixels.
* @param maxHeightPx The maximum height for the retrieved bitmap in pixels.
* @param callback The callback to be called with the retrieved bitmap.
*/
void retrieveImageForContextMenu(int maxWidthPx, int maxHeightPx, Callback<Bitmap> callback);
/**
* Retrieves the image from the current {@link RenderFrameHost} that the context menu was
* triggered on, to be shared.
* @param imageFormat The image format that will be requested.
* @param callback The callback to be called with the retrieved image's {@link Uri}.
*/
void retrieveImageForShare(@ContextMenuImageFormat int imageFormat, Callback<Uri> callback);
/**
* Starts a download based on the params.
* @param isLink Whether the download target is a link.
*/
void startDownload(boolean isLink);
/**
* Does a reverse image search for the current image that the context menu was triggered on.
*/
void searchForImage();
}
// Copyright 2020 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
package org.chromium.chrome.browser.contextmenu;
import android.graphics.Bitmap;
import android.net.Uri;
import androidx.annotation.VisibleForTesting;
import org.chromium.base.Callback;
import org.chromium.base.annotations.CalledByNative;
import org.chromium.base.annotations.NativeMethods;
import org.chromium.components.browser_ui.share.ShareImageFileUtils;
import org.chromium.components.embedder_support.contextmenu.ContextMenuParams;
import org.chromium.content_public.browser.RenderFrameHost;
import org.chromium.content_public.browser.WebContents;
class ContextMenuNativeDelegateImpl implements ContextMenuNativeDelegate {
private static final int MAX_SHARE_DIMEN_PX = 2048;
private long mNativePtr;
/**
* See function for details.
*/
private static byte[] sHardcodedImageBytesForTesting;
private static String sHardcodedImageExtensionForTesting;
/**
* The tests trigger the context menu via JS rather than via a true native call which means
* the native code does not have a reference to the image's render frame host. Instead allow
* test cases to hardcode the test image bytes that will be shared.
* @param hardcodedImageBytes The hard coded image bytes to fake or null if image should not be
* faked.
* @param hardcodedImageExtension The hard coded image extension.
*/
@VisibleForTesting
public static void setHardcodedImageBytesForTesting(
byte[] hardcodedImageBytes, String hardcodedImageExtension) {
sHardcodedImageBytesForTesting = hardcodedImageBytes;
sHardcodedImageExtensionForTesting = hardcodedImageExtension;
}
public ContextMenuNativeDelegateImpl(WebContents webContents, RenderFrameHost renderFrameHost,
ContextMenuParams contextMenuParams) {
mNativePtr = ContextMenuNativeDelegateImplJni.get().init(
webContents, contextMenuParams, renderFrameHost);
}
@Override
public void destroy() {
mNativePtr = 0;
}
@Override
public void retrieveImageForShare(int imageFormat, Callback<Uri> callback) {
if (mNativePtr == 0) return;
Callback<ImageCallbackResult> imageRetrieveCallback = (result) -> {
ShareImageFileUtils.generateTemporaryUriFromData(
result.imageData, result.extension, callback);
};
if (sHardcodedImageBytesForTesting != null) {
imageRetrieveCallback.onResult(createImageCallbackResultForTesting());
} else {
ContextMenuNativeDelegateImplJni.get().retrieveImageForShare(mNativePtr,
ContextMenuNativeDelegateImpl.this, imageRetrieveCallback, MAX_SHARE_DIMEN_PX,
MAX_SHARE_DIMEN_PX, imageFormat);
}
}
@Override
public void retrieveImageForContextMenu(
int maxWidthPx, int maxHeightPx, Callback<Bitmap> callback) {
if (mNativePtr == 0) return;
ContextMenuNativeDelegateImplJni.get().retrieveImageForContextMenu(
mNativePtr, ContextMenuNativeDelegateImpl.this, callback, maxWidthPx, maxHeightPx);
}
@Override
public void startDownload(boolean isLink) {
if (mNativePtr == 0) return;
ContextMenuNativeDelegateImplJni.get().startDownload(
mNativePtr, ContextMenuNativeDelegateImpl.this, isLink);
}
@Override
public void searchForImage() {
if (mNativePtr == 0) return;
ContextMenuNativeDelegateImplJni.get().searchForImage(
mNativePtr, ContextMenuNativeDelegateImpl.this);
}
/**
* The class hold the |retrieveImageForShare| callback result.
*/
@VisibleForTesting
static class ImageCallbackResult {
public byte[] imageData;
public String extension;
public ImageCallbackResult(byte[] imageData, String extension) {
this.imageData = imageData;
this.extension = extension;
}
}
private static ImageCallbackResult createImageCallbackResultForTesting() {
return new ImageCallbackResult(
sHardcodedImageBytesForTesting, sHardcodedImageExtensionForTesting);
}
@CalledByNative
private static ImageCallbackResult createImageCallbackResult(
byte[] imageData, String extension) {
return new ImageCallbackResult(imageData, extension);
}
@NativeMethods
interface Natives {
long init(WebContents webContents, ContextMenuParams contextMenuParams,
RenderFrameHost renderFrameHost);
void retrieveImageForShare(long nativeContextMenuNativeDelegateImpl,
ContextMenuNativeDelegateImpl caller, Callback<ImageCallbackResult> callback,
int maxWidthPx, int maxHeightPx, @ContextMenuImageFormat int imageFormat);
void retrieveImageForContextMenu(long nativeContextMenuNativeDelegateImpl,
ContextMenuNativeDelegateImpl caller, Callback<Bitmap> callback, int maxWidthPx,
int maxHeightPx);
void startDownload(long nativeContextMenuNativeDelegateImpl,
ContextMenuNativeDelegateImpl caller, boolean isLink);
void searchForImage(
long nativeContextMenuNativeDelegateImpl, ContextMenuNativeDelegateImpl caller);
}
}
......@@ -4,11 +4,8 @@
package org.chromium.chrome.browser.contextmenu;
import android.graphics.Bitmap;
import android.net.Uri;
import android.util.Pair;
import org.chromium.base.Callback;
import org.chromium.ui.modelutil.MVCListAdapter.ModelList;
import java.util.List;
......@@ -18,11 +15,6 @@ import java.util.List;
* ContextMenuHelper.
*/
public interface ContextMenuPopulator {
/**
* Called when this ContextMenuPopulator is about to be destroyed.
*/
void onDestroy();
/**
* Should be used to populate {@code menu} with the correct context menu items.
* @param isShoppyImage Whether the selected item was a shoppy image.
......@@ -41,20 +33,6 @@ public interface ContextMenuPopulator {
*/
boolean onItemSelected(int itemId);
/**
* Gets the thumbnail of the current image that triggered the context menu.
* @param callback Called once the the thumbnail is received.
*/
void getThumbnail(final Callback<Bitmap> callback);
/**
* Retrieves a URI for the selected image for sharing with external apps. If the function fails
* to retrieve the image bytes or generate a URI the callback will *not* be called.
* @param imageFormat The image format will be requested.
* @param callback Called once the image is generated and ready to be shared.
*/
void retrieveImage(@ContextMenuImageFormat int imageFormat, Callback<Uri> callback);
/**
* Called when the context menu is closed.
*/
......
......@@ -7,7 +7,6 @@ package org.chromium.chrome.browser.contextmenu;
import android.content.Context;
import org.chromium.components.embedder_support.contextmenu.ContextMenuParams;
import org.chromium.content_public.browser.RenderFrameHost;
/**
* Factory interface for creating {@link ContextMenuPopulator}s.
......@@ -17,11 +16,11 @@ public interface ContextMenuPopulatorFactory {
* Creates a {@ContextMenuPopulator}.
* @param context The {@link Context} used to retrieve the strings.
* @param params The {@link ContextMenuParams} used to build the context menu.
* @param renderFrameHost The {@link RenderFrameHost} for the context menu.
* @param nativeDelegate The {@link ContextMenuNativeDelegate} for the context menu.
* @return The new {@ContextMenuPopulator}.
*/
ContextMenuPopulator createContextMenuPopulator(
Context context, ContextMenuParams params, RenderFrameHost renderFrameHost);
Context context, ContextMenuParams params, ContextMenuNativeDelegate nativeDelegate);
void onDestroy();
}
......@@ -2,4 +2,5 @@ include_rules = [
"-chrome",
"+base/android/java/src/org/chromium/base",
"+content/public/android/java/src/org/chromium/content_public",
"+components/browser_ui/share/android/java/src/org/chromium/components/browser_ui/share",
]
......@@ -6,7 +6,6 @@ package org.chromium.chrome.browser.share.clipboard;
import static org.chromium.chrome.browser.preferences.ChromePreferenceKeys.CLIPBOARD_SHARED_URI;
import android.content.Context;
import android.net.Uri;
import android.text.TextUtils;
......@@ -24,9 +23,8 @@ import org.chromium.ui.base.Clipboard;
public class ClipboardImageFileProvider implements Clipboard.ImageFileProvider {
@Override
public void storeImageAndGenerateUri(
Context context, byte[] imageData, String fileExtension, Callback<Uri> callback) {
ShareImageFileUtils.generateTemporaryUriFromData(
context, imageData, fileExtension, callback);
byte[] imageData, String fileExtension, Callback<Uri> callback) {
ShareImageFileUtils.generateTemporaryUriFromData(imageData, fileExtension, callback);
}
@Override
......
......@@ -111,12 +111,12 @@ class ScreenshotShareSheetMediator {
params, new ChromeShareExtras.Builder().build(), System.currentTimeMillis());
};
generateTemporaryUriFromBitmap(mContext, title, bitmap, callback);
generateTemporaryUriFromBitmap(title, bitmap, callback);
mCloseDialogRunnable.run();
}
protected void generateTemporaryUriFromBitmap(
Context context, String fileName, Bitmap bitmap, Callback<Uri> callback) {
ShareImageFileUtils.generateTemporaryUriFromBitmap(context, fileName, bitmap, callback);
String fileName, Bitmap bitmap, Callback<Uri> callback) {
ShareImageFileUtils.generateTemporaryUriFromBitmap(fileName, bitmap, callback);
}
}
......@@ -78,7 +78,7 @@ public class ScreenshotShareSheetMediatorUnitTest {
}
@Override
protected void generateTemporaryUriFromBitmap(
Context context, String fileName, Bitmap bitmap, Callback<Uri> callback) {
String fileName, Bitmap bitmap, Callback<Uri> callback) {
mGenerateTemporaryUriFromBitmapCalled = true;
}
......
......@@ -121,13 +121,12 @@ public class ShareImageFileUtils {
* Temporarily saves the given set of image bytes and provides that URI to a callback for
* sharing.
*
* @param context The context used to trigger the share action.
* @param imageData The image data to be shared in |fileExtension| format.
* @param fileExtension File extension which |imageData| encoded to.
* @param callback A provided callback function which will act on the generated URI.
*/
public static void generateTemporaryUriFromData(final Context context, final byte[] imageData,
String fileExtension, Callback<Uri> callback) {
public static void generateTemporaryUriFromData(
final byte[] imageData, String fileExtension, Callback<Uri> callback) {
if (imageData.length == 0) {
Log.w(TAG, "Share failed -- Received image contains no data.");
return;
......@@ -153,13 +152,12 @@ public class ShareImageFileUtils {
/**
* Temporarily saves the bitmap and provides that URI to a callback for sharing.
*
* @param context The Context to use for determining download location.
* @param filename The filename without extension.
* @param bitmap The Bitmap to download.
* @param callback A provided callback function which will act on the generated URI.
*/
public static void generateTemporaryUriFromBitmap(
final Context context, String fileName, Bitmap bitmap, Callback<Uri> callback) {
String fileName, Bitmap bitmap, Callback<Uri> callback) {
OnImageSaveListener listener = new OnImageSaveListener() {
@Override
public void onImageSaved(Uri uri, String displayName) {
......
......@@ -121,7 +121,7 @@ public class ShareImageFileUtilsTest extends DummyUiActivityTestCase {
private Uri generateAnImageToClipboard(String fileExtension) throws TimeoutException {
GenerateUriCallback imageCallback = new GenerateUriCallback();
ShareImageFileUtils.generateTemporaryUriFromData(
getActivity(), TEST_IMAGE_DATA, fileExtension, imageCallback);
TEST_IMAGE_DATA, fileExtension, imageCallback);
imageCallback.waitForCallback(0, 1, WAIT_TIMEOUT_SECONDS, TimeUnit.SECONDS);
Clipboard.getInstance().setImageUri(imageCallback.getImageUri());
CriteriaHelper.pollInstrumentationThread(() -> {
......
......@@ -70,13 +70,12 @@ public class Clipboard implements ClipboardManager.OnPrimaryClipChangedListener
* Saves the given set of image bytes and provides that URI to a callback for
* sharing the image.
*
* @param context The context used to trigger the action.
* @param imageData The image data to be shared in |fileExtension| format.
* @param fileExtension File extension which |imageData| encoded to.
* @param callback A provided callback function which will act on the generated URI.
*/
void storeImageAndGenerateUri(final Context context, final byte[] imageData,
String fileExtension, Callback<Uri> callback);
void storeImageAndGenerateUri(
final byte[] imageData, String fileExtension, Callback<Uri> callback);
/**
* Store the last image uri we put in the sytstem clipboard, this is special case for
......@@ -317,7 +316,7 @@ public class Clipboard implements ClipboardManager.OnPrimaryClipChangedListener
}
mImageFileProvider.storeImageAndGenerateUri(
mContext, imageData, extension, (Uri uri) -> { setImageUri(uri); });
imageData, extension, (Uri uri) -> { setImageUri(uri); });
}
/**
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment