* Bug 16167 fixed: clf('reset') could remove native menus 77/21077/6
Samuel GOUGEON [Wed, 28 Aug 2019 13:28:31 +0000 (15:28 +0200)]
  http://bugzilla.scilab.org/16167

Test:
get(0).showhiddenhandles = "on";
f = scf(1234);
addmenu(1234,"Test")
addmenu(1234,"Bug 16167")
f.children
// clf('reset')
plot()  // includes a clf("reset')
f.children
// Check that native menus are still here,
// while "Test" and "Bug 16167" ones have been removed.

Resetting native menus is not really the purpose of the report.
I don't know any easy way to do it (the implemented attempt fails,
due to copy() failure (and likely swap_handles() also).
Closing the figure -- that may be docked -- and reopening a new one
is not convenient either.

Change-Id: I5cbb61cacceb65ca33c698f05b35fdfd2aa91865

scilab/CHANGES.md
scilab/modules/graphics/macros/clf.sci

index e197e6c..d7803f4 100644 (file)
@@ -456,6 +456,7 @@ Bug Fixes
 * [#16163](https://bugzilla.scilab.org/16163): `prbs_a()` did not comply with the requested number of switches. The biased number of actual switches was unpredictable, preventing to manage its statistical distribution. The probability of the initial state was biased. For instance, prbs_a(n,0) always returned ones(1,n).
 * [#16164](https://bugzilla.scilab.org/16164): Help pages in elementary_functions/signal_processing were mislocated.
 * [#16166](https://bugzilla.scilab.org/16166): `noisegen` is crooky, even threatening, and very poor. It is tagged as obsolete and will be removed from Scilab 6.1.x.
+* [#16167](https://bugzilla.scilab.org/16167): When get(0).showHiddenHandles is "on", clf('reset') unexpectedly removed native menus.
 * [#16168](https://bugzilla.scilab.org/16168): On some Linux installations, `test_run` always failed.
 * [#16174](https://bugzilla.scilab.org/16174): `libraryinfo` yielded 0x0 matrix of strings for libs without macro
 * [#16177](https://bugzilla.scilab.org/16177): In the uicontrol help page, the first example was bugged.
index d0869d8..b479969 100644 (file)
@@ -1,7 +1,7 @@
 // Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
 // Copyright (C) INRIA
 // Copyright (C) 2012 - 2016 - Scilab Enterprises
-// Copyright (C) 2017 - 2018 - Samuel GOUGEON
+// Copyright (C) 2017 - 2019 - Samuel GOUGEON
 //
 // This file is hereby licensed under the terms of the GNU GPL v2.0,
 // pursuant to article 5.3.4 of the CeCILL v.2.1.
@@ -48,6 +48,7 @@ function clf(varargin)
             h = gcf()
             job = varargin(1)
         end
+
     elseif nbArg==2 then
         if type(varargin(1))==1 then     // win num given
             num = varargin(1)
@@ -59,6 +60,7 @@ function clf(varargin)
             h = varargin(1);
         end
         job = varargin(2);
+
     else
         msg = _("%s: Wrong number of input argument(s): %d to %d expected.")
         error(msprintf(msg, "clf", 0, 2))
@@ -74,7 +76,7 @@ function clf(varargin)
         return
     end
 
-    // check that all the handles are figures
+    // check that all the handles are figures or uicontrol frames
     for k = 1:nbHandles
         curFig = h(k);
         if curFig.type <> "Figure" & (curFig.type <> "uicontrol" | curFig.style <> "frame")
@@ -83,6 +85,14 @@ function clf(varargin)
         end
     end
 
+    // Creation of a template figure, to get native menus to preserve or reset
+    if or(h.type=="Figure") & get(get(0),"showhiddenhandles")=="on"
+        tmpfig = figure("visible","off")
+        menus = tmpfig.children(tmpfig.children.type=="uimenu")
+    else
+        menus = []
+    end
+
     // delete childrens
     for k = 1:nbHandles
         curFig = h(k)
@@ -107,13 +117,17 @@ function clf(varargin)
             // Forces drawlater
             immediateMode = curFig.immediate_drawing;
             curFig.immediate_drawing = "off";
-            delete(curFig.children);
             curFig.info_message = "";            // Clears the infobar message
             curFig.event_handler_enable = "off"; // Disables the event handler
+            // Deletes children, but manages native menus
+            clf_clear_children(curFig, job, menus);
             // Restores the drawlater entry status:
             curFig.immediate_drawing = immediateMode;
         end
     end
+    if isdef("tmpfig","l") then
+        close(tmpfig)
+    end
 
     // reset figures to default values if needed
     if (job == "reset") then
@@ -186,3 +200,37 @@ function clf(varargin)
     end
 endfunction
 
+// --------------------------------------------------------------------------
+
+function clf_clear_children(h, job, menus)
+    // internal only called for Figures (not for frames)
+    c = curFig.children
+    if  menus==[] then
+        delete(c)  // native menus are not seen and not deleted
+    else
+        // Native menus must be preserved
+        labels = menus.label
+        tmp = c.type <> "uimenu"
+        delete(c(tmp)) // But a default axes might have been recreated
+        c = curFig.children
+        for i = length(c):-1:1
+            if c(i).type <> "uimenu"    // Possible default axes
+                continue
+            end
+            tmp = c(i).label
+            j = find(c(i).label==menus.label)
+            if j==[]
+                delete(c(i))    // Not native menu
+            else
+                // We keep the menu. We possibly reset it
+                if job=="reset"
+                    // the template menu is inserted as children(1):
+                    // hm = copy(menus(j), h)   // yields an error
+                    // swap_handles(hm,c(i))
+                    // delete(curFig.children(1))
+                    // => How to restore default native menus?
+                end
+            end
+        end
+    end
+endfunction