emacs-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

feature/android 198b8160cfe: Update Android port


From: Po Lu
Subject: feature/android 198b8160cfe: Update Android port
Date: Sat, 28 Jan 2023 03:29:45 -0500 (EST)

branch: feature/android
commit 198b8160cfeeb178d3b2073c8d03afdafe338908
Author: Po Lu <luangruo@yahoo.com>
Commit: Po Lu <luangruo@yahoo.com>

    Update Android port
    
    * doc/emacs/android.texi (Android File System): Describe an
    easier way to disable scoped storage.
    * java/AndroidManifest.xml.in: Add new permission to allow that.
    * java/README: Add more text describing Java.
    * java/org/gnu/emacs/EmacsContextMenu.java (Item): New fields
    `isCheckable' and `isChecked'.
    (EmacsContextMenu, addItem): New arguments.
    (inflateMenuItems): Set checked status as appropriate.
    
    * java/org/gnu/emacs/EmacsCopyArea.java (perform): Disallow
    operations where width and height are less than or equal to
    zero.
    * lisp/menu-bar.el (menu-bar-edit-menu): Make
    execute-extended-command available as a menu item.
    * src/androidmenu.c (android_init_emacs_context_menu)
    (android_menu_show):
    * src/menu.c (have_boxes): Implement menu check boxes.
---
 doc/emacs/android.texi                   | 20 +++++++---
 java/AndroidManifest.xml.in              |  4 ++
 java/README                              | 63 ++++++++++++++++++++++++++++++--
 java/org/gnu/emacs/EmacsContextMenu.java | 22 +++++++++--
 java/org/gnu/emacs/EmacsCopyArea.java    |  6 +++
 lisp/menu-bar.el                         |  5 +++
 src/androidmenu.c                        | 17 +++++++--
 src/menu.c                               |  2 +-
 8 files changed, 123 insertions(+), 16 deletions(-)

diff --git a/doc/emacs/android.texi b/doc/emacs/android.texi
index 98d7f1e1d9e..ae4080994b8 100644
--- a/doc/emacs/android.texi
+++ b/doc/emacs/android.texi
@@ -177,17 +177,27 @@ makes the system more secure.  Unfortunately, it also 
means that Emacs
 cannot access files in those directories, despite holding the
 necessary permissions.  Thankfully, the Open Handset Alliance's
 version of Android allows this restriction to be disabled on a
-per-program basis; the corresponding option in the system settings
-panel is:
+per-program basis; on Android 10, the corresponding option in the
+system settings panel is:
 
 @indentedblock
 System -> Developer Options -> App Compatibility Changes -> Emacs ->
 DEFAULT_SCOPED_STORAGE
 @end indentedblock
 
-  After you disable this setting and grant Emacs the ``Files and
-Media'' permission, it will be able to access files under
-@file{/sdcard} as usual.
+  And on Android 11 and later, the corresponding option in the systems
+settings panel is:
+
+@indentedblock
+System -> Apps -> Special App Access -> All files access -> Emacs
+@end indentedblock
+
+  After you disable or enable this setting as appropriate and grant
+Emacs the ``Files and Media'' permission, it will be able to access
+files under @file{/sdcard} as usual.
+
+  These settings are not present on many proprietary versions of
+Android.
 
 @node Android Environment
 @section Running Emacs under Android
diff --git a/java/AndroidManifest.xml.in b/java/AndroidManifest.xml.in
index 527ce74c474..09e4e788e0b 100644
--- a/java/AndroidManifest.xml.in
+++ b/java/AndroidManifest.xml.in
@@ -52,6 +52,10 @@ along with GNU Emacs.  If not, see 
<https://www.gnu.org/licenses/>. -->
   <uses-permission android:name="android.permission.RECORD_AUDIO" />
   <uses-permission android:name="android.permission.CAMERA" />
 
+  <!-- This is required on Android 11 or later to access /sdcard.  -->
+
+  <uses-permission android:name="android.permission.MANAGE_EXTERNAL_STORAGE"/>
+
   <uses-sdk android:minSdkVersion="@ANDROID_MIN_SDK@"
            android:targetSdkVersion="33"/>
 
diff --git a/java/README b/java/README
index 44f5a415162..3bce2556403 100644
--- a/java/README
+++ b/java/README
@@ -292,15 +292,15 @@ public class EmacsFrobinicator
   }
 }
 
-Java arrays are similar to C arrays in that they can not grow. But
+Java arrays are similar to C arrays in that they can not grow.  But
 they are very much unlike C arrays in that they are always references
-(as opposed to decaying into pointers in various situations), and
+(as opposed to decaying into pointers in only some situations), and
 contain information about their length.
 
 If another function named ``frobinicate1'' takes an array as an
 argument, then it need not take the length of the array.
 
-Instead, it simply iterates over the array like so:
+Instead, it may simply iterate over the array like so:
 
 int i, k;
 
@@ -339,10 +339,65 @@ struct emacs_array_container
 
 or, possibly even better,
 
-typedef int my_array[10];
+typedef int emacs_array_container[10];
 
 Alas, Java has no equivalent of `typedef'.
 
+Like in C, Java string literals are delimited by double quotes.
+Unlike C, however, strings are not NULL-terminated arrays of
+characters, but a distinct type named ``String''.  They store their
+own length, characters in Java's 16-bit ``char'' type, and are capable
+of holding NULL bytes.
+
+Instead of writing:
+
+wchar_t character;
+extern char *s;
+size_t s;
+
+  for (/* determine n, s in a loop.  */)
+    s += mbstowc (&character, s, n);
+
+or:
+
+const char *byte;
+
+for (byte = my_string; *byte; ++byte)
+  /* do something with *byte.  */;
+
+or perhaps even:
+
+size_t length, i;
+char foo;
+
+length = strlen (my_string);
+
+for (i = 0; i < length; ++i)
+  foo = my_string[i];
+
+you write:
+
+char foo;
+int i;
+
+for (i = 0; i < myString.length (); ++i)
+  foo = myString.charAt (0);
+
+Java also has stricter rules on what can be used as a truth value in a
+conditional.  While in C, any non-zero value is true, Java requires
+that every truth value be of the boolean type ``boolean''.
+
+What this means is that instead of simply writing:
+
+  if (foo || bar)
+
+where foo can either be 1 or 0, and bar can either be NULL or a
+pointer to something, you must explicitly write:
+
+  if (foo != 0 || bar != null)
+
+in Java.
+
 JAVA NATIVE INTERFACE
 
 Java also provides an interface for C code to interface with Java.
diff --git a/java/org/gnu/emacs/EmacsContextMenu.java 
b/java/org/gnu/emacs/EmacsContextMenu.java
index 056d8fb692c..92429410d03 100644
--- a/java/org/gnu/emacs/EmacsContextMenu.java
+++ b/java/org/gnu/emacs/EmacsContextMenu.java
@@ -56,7 +56,7 @@ public class EmacsContextMenu
     public int itemID;
     public String itemName;
     public EmacsContextMenu subMenu;
-    public boolean isEnabled;
+    public boolean isEnabled, isCheckable, isChecked;
 
     @Override
     public boolean
@@ -108,10 +108,15 @@ public class EmacsContextMenu
 
   /* Add a normal menu item to the context menu with the id ITEMID and
      the name ITEMNAME.  Enable it if ISENABLED, else keep it
-     disabled.  */
+     disabled.
+
+     If this is not a submenu and ISCHECKABLE is set, make the item
+     checkable.  Likewise, if ISCHECKED is set, make the item
+     checked.  */
 
   public void
-  addItem (int itemID, String itemName, boolean isEnabled)
+  addItem (int itemID, String itemName, boolean isEnabled,
+          boolean isCheckable, boolean isChecked)
   {
     Item item;
 
@@ -119,6 +124,8 @@ public class EmacsContextMenu
     item.itemID = itemID;
     item.itemName = itemName;
     item.isEnabled = isEnabled;
+    item.isCheckable = isCheckable;
+    item.isChecked = isChecked;
 
     menuItems.add (item);
   }
@@ -198,6 +205,15 @@ public class EmacsContextMenu
            /* If the item ID is zero, then disable the item.  */
            if (item.itemID == 0 || !item.isEnabled)
              menuItem.setEnabled (false);
+
+           /* Now make the menu item display a checkmark as
+              appropriate.  */
+
+           if (item.isCheckable)
+             menuItem.setCheckable (true);
+
+           if (item.isChecked)
+             menuItem.setChecked (true);
          }
       }
   }
diff --git a/java/org/gnu/emacs/EmacsCopyArea.java 
b/java/org/gnu/emacs/EmacsCopyArea.java
index 7a97d706794..f8974e17c2e 100644
--- a/java/org/gnu/emacs/EmacsCopyArea.java
+++ b/java/org/gnu/emacs/EmacsCopyArea.java
@@ -99,6 +99,12 @@ public class EmacsCopyArea
     if (src_y + height > srcBitmap.getHeight ())
       height = srcBitmap.getHeight () - src_y;
 
+    /* If width and height are empty or negative, then skip the entire
+       CopyArea operation lest createBitmap throw an exception.  */
+
+    if (width <= 0 || height <= 0)
+      return;
+
     rect = new Rect (dest_x, dest_y, dest_x + width,
                     dest_y + height);
 
diff --git a/lisp/menu-bar.el b/lisp/menu-bar.el
index d020cf6e90a..2d907fb3827 100644
--- a/lisp/menu-bar.el
+++ b/lisp/menu-bar.el
@@ -472,6 +472,11 @@
 (defvar menu-bar-edit-menu
   (let ((menu (make-sparse-keymap "Edit")))
 
+    (bindings--define-key menu [execute-extended-command]
+      '(menu-item "Execute Command" execute-extended-command
+                  :enable t
+                  :help "Read a command name, its arguments, then call it."))
+
     ;; ns-win.el said: Add spell for platform consistency.
     (if (featurep 'ns)
         (bindings--define-key menu [spell]
diff --git a/src/androidmenu.c b/src/androidmenu.c
index 7b27825ad60..acad775f26a 100644
--- a/src/androidmenu.c
+++ b/src/androidmenu.c
@@ -98,7 +98,7 @@ android_init_emacs_context_menu (void)
   FIND_METHOD_STATIC (create_context_menu, "createContextMenu",
                      "(Ljava/lang/String;)Lorg/gnu/emacs/EmacsContextMenu;");
 
-  FIND_METHOD (add_item, "addItem", "(ILjava/lang/String;Z)V");
+  FIND_METHOD (add_item, "addItem", "(ILjava/lang/String;ZZZ)V");
   FIND_METHOD (add_submenu, "addSubmenu", "(Ljava/lang/String;"
               "Ljava/lang/String;)Lorg/gnu/emacs/EmacsContextMenu;");
   FIND_METHOD (add_pane, "addPane", "(Ljava/lang/String;)V");
@@ -241,7 +241,7 @@ android_menu_show (struct frame *f, int x, int y, int 
menuflags,
   Lisp_Object pane_name, prefix;
   const char *pane_string;
   specpdl_ref count, count1;
-  Lisp_Object item_name, enable, def, tem, entry;
+  Lisp_Object item_name, enable, def, tem, entry, type, selected;
   jmethodID method;
   jobject store;
   bool rc;
@@ -250,6 +250,7 @@ android_menu_show (struct frame *f, int x, int y, int 
menuflags,
   struct android_dismiss_menu_data data;
   struct android_menu_subprefix *subprefix, *temp_subprefix;
   struct android_menu_subprefix *subprefix_1;
+  bool checkmark;
 
   count = SPECPDL_INDEX ();
 
@@ -351,6 +352,8 @@ android_menu_show (struct frame *f, int x, int y, int 
menuflags,
          item_name = AREF (menu_items, i + MENU_ITEMS_ITEM_NAME);
          enable = AREF (menu_items, i + MENU_ITEMS_ITEM_ENABLE);
          def = AREF (menu_items, i + MENU_ITEMS_ITEM_DEFINITION);
+         type = AREF (menu_items, i + MENU_ITEMS_ITEM_TYPE);
+         selected = AREF (menu_items, i + MENU_ITEMS_ITEM_SELECTED);
 
          /* This is an actual menu item (or submenu).  Add it to the
             menu.  */
@@ -392,12 +395,20 @@ android_menu_show (struct frame *f, int x, int y, int 
menuflags,
              title_string = (!NILP (item_name)
                              ? android_build_string (item_name)
                              : NULL);
+
+             /* Determine whether or not to display a check box.  */
+
+             checkmark = (EQ (type, QCtoggle)
+                          || EQ (type, QCradio));
+
              (*android_java_env)->CallVoidMethod (android_java_env,
                                                   current_context_menu,
                                                   menu_class.add_item,
                                                   (jint) item_id,
                                                   title_string,
-                                                  (jboolean) !NILP (enable));
+                                                  (jboolean) !NILP (enable),
+                                                  (jboolean) checkmark,
+                                                  (jboolean) !NILP (selected));
              android_exception_check ();
 
              if (title_string)
diff --git a/src/menu.c b/src/menu.c
index e02ee880119..6ab34a16996 100644
--- a/src/menu.c
+++ b/src/menu.c
@@ -48,7 +48,7 @@ static bool
 have_boxes (void)
 {
 #if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (HAVE_NTGUI) || 
defined (HAVE_NS) \
-  || defined (HAVE_HAIKU)
+  || defined (HAVE_HAIKU) || defined (HAVE_ANDROID)
   if (FRAME_WINDOW_P (XFRAME (Vmenu_updating_frame)))
     return 1;
 #endif



reply via email to

[Prev in Thread] Current Thread [Next in Thread]