Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Prevent action on react native buttons while context menu is presented and support adding a title to Android context menu #120

Open
jefflewis opened this issue May 26, 2024 · 5 comments

Comments

@jefflewis
Copy link

Hi! 👋

Firstly, thanks for your work on this project! 🙂

Today I used patch-package to patch [email protected] for the project I'm working on.

Here is the diff that solved my problem:

diff --git a/node_modules/react-native-context-menu-view/android/src/main/java/com/mpiannucci/reactnativecontextmenu/ContextMenuManager.java b/node_modules/react-native-context-menu-view/android/src/main/java/com/mpiannucci/reactnativecontextmenu/ContextMenuManager.java
index 403dac6..52a0c2f 100644
--- a/node_modules/react-native-context-menu-view/android/src/main/java/com/mpiannucci/reactnativecontextmenu/ContextMenuManager.java
+++ b/node_modules/react-native-context-menu-view/android/src/main/java/com/mpiannucci/reactnativecontextmenu/ContextMenuManager.java
@@ -31,9 +31,7 @@ public class ContextMenuManager extends ViewGroupManager<ContextMenuView> {
     }
 
     @ReactProp(name = "title")
-    public void setTitle(ContextMenuView view, @Nullable String title) {
-        // TODO: Maybe support this? IDK if its necessary though
-    }
+    public void setTitle(ContextMenuView view, @Nullable String title) { view.setTitle(title); }
 
     @ReactProp(name = "actions")
     public void setActions(ContextMenuView view, @Nullable ReadableArray actions) {
diff --git a/node_modules/react-native-context-menu-view/android/src/main/java/com/mpiannucci/reactnativecontextmenu/ContextMenuView.java b/node_modules/react-native-context-menu-view/android/src/main/java/com/mpiannucci/reactnativecontextmenu/ContextMenuView.java
index 9fc8eeb..69bb41e 100644
--- a/node_modules/react-native-context-menu-view/android/src/main/java/com/mpiannucci/reactnativecontextmenu/ContextMenuView.java
+++ b/node_modules/react-native-context-menu-view/android/src/main/java/com/mpiannucci/reactnativecontextmenu/ContextMenuView.java
@@ -34,6 +34,7 @@ import javax.annotation.Nullable;
 
 public class ContextMenuView extends ReactViewGroup implements View.OnCreateContextMenuListener {
     @Nullable ReadableArray actions;
+    @Nullable String title;
 
     boolean cancelled = true;
 
@@ -92,6 +93,7 @@ public class ContextMenuView extends ReactViewGroup implements View.OnCreateCont
     public void onCreateContextMenu(ContextMenu contextMenu, View view, ContextMenu.ContextMenuInfo contextMenuInfo) {
         contextMenu.clear();
         setMenuIconDisplay(contextMenu, true);
+        contextMenu.setHeaderTitle(title);
 
         for (int i = 0; i < actions.size(); i++) {
             ReadableMap action = actions.getMap(i);
@@ -111,6 +113,10 @@ public class ContextMenuView extends ReactViewGroup implements View.OnCreateCont
         this.actions = actions;
     }
 
+    public void setTitle(@Nullable String title) {
+        this.title = title;
+    }
+
     public void setDropdownMenuMode(@Nullable boolean enabled) {
         this.dropdownMenuMode = enabled;
     }
diff --git a/node_modules/react-native-context-menu-view/ios/ContextMenuView.m b/node_modules/react-native-context-menu-view/ios/ContextMenuView.m
index 7f8ee75..5531995 100644
--- a/node_modules/react-native-context-menu-view/ios/ContextMenuView.m
+++ b/node_modules/react-native-context-menu-view/ios/ContextMenuView.m
@@ -18,6 +18,7 @@
 @implementation ContextMenuView {
   BOOL _cancelled;
   UIView *_customView;
+  UIView *_bgView;
 }
 
 - (id) init {
@@ -90,6 +91,15 @@
 }
 
 - (void)contextMenuInteraction:(UIContextMenuInteraction *)interaction willDisplayMenuForConfiguration:(UIContextMenuConfiguration *)configuration animator:(id<UIContextMenuInteractionAnimating>)animator API_AVAILABLE(ios(13.0)) {
+  // Add a transparent view to the root view that will intercept touch events.
+  // This will prevent buttons in React views from being actionable while the
+  // context menu is displayed.
+  _bgView = [[UIView alloc] init];
+  _bgView.backgroundColor = UIColor.clearColor;
+  _bgView.userInteractionEnabled = YES;
+  _bgView.frame = self.reactViewController.view.bounds;
+  [self.reactViewController.view addSubview: _bgView];
+  
   _cancelled = true;
 }
 
@@ -103,6 +113,7 @@
   if (_cancelled && self.onCancel) {
     self.onCancel(@{});
   }
+  [self.reactViewController.view removeReactSubview:_bgView];
 }
 
 - (UITargetedPreview *)contextMenuInteraction:(UIContextMenuInteraction *)interaction previewForHighlightingMenuWithConfiguration:(UIContextMenuConfiguration *)configuration API_AVAILABLE(ios(13.0)) {

This issue body was partially generated by patch-package.

@mpiannucci
Copy link
Owner

mpiannucci commented May 27, 2024

This is really cool! Would you be up for opening a PR to add this in? Thanks in advance

@jefflewis
Copy link
Author

I'm adding this to our own app, which will go through a thorough set of regression tests. Once that is all done and the patch is proven, I'll add a PR here with whatever we end up with.

I think everything is OK with this. I'm not doin null checking on the view, but my assumption is that the willEndForConfiguration will always be called if willDisplayMenuForConfiguration is called. If that isn't true, this would leave that garbage view in place forever.

For the android title, I'll split into a separate PR... mostly because the view doesn't expand to fit the title... I just put a bunch of spaces in the one spot where this affected my app, but it'd be better to get an actual fix in place.

@mabdurrafey-afl
Copy link

@jefflewis The patch for prevention of action while context menu is appearing is not working on our side.

@jefflewis
Copy link
Author

@jefflewis The patch for prevention of action while context menu is appearing is not working on our side.

I'll ensure I add to the sample app to test this behavior. This so far has been working for us the past month in production.

@marcelcamporelli
Copy link

We had a similar problem on Android not with a <Button> but with a <TouchableOpacity>; in our case, simply adding

onLongPress={() => {}}

to the enclosed <TouchableOpacity> would do the trick. Doing so, the onPress action stemming from the context menu is naturally ignored on the touchable opacity. I guess this could also work for a button.

I was wondering though why there is no Android code in your patch with regards to the "prevent action on buttons" part?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants