changeset 21760:31b4b614ed55

text.m: Improve matlab compatibility (bug #47904) * text.m: Raise an error if called with more than one point and number of text labels does not equal number of points. Raise an error if number of coordinates (x,y,or z) do not match each other. Add BIST input validation tests.
author Rik <rik@octave.org>
date Fri, 20 May 2016 22:59:00 -0700
parents b002b4331a12
children ff2b9f7069c5
files scripts/plot/appearance/text.m
diffstat 1 files changed, 56 insertions(+), 46 deletions(-) [+]
line wrap: on
line diff
--- a/scripts/plot/appearance/text.m	Fri May 20 16:16:10 2016 -0700
+++ b/scripts/plot/appearance/text.m	Fri May 20 22:59:00 2016 -0700
@@ -64,13 +64,18 @@
     nx = numel (x);
     ny = numel (y);
     nz = numel (z);
+    if (nx != ny || nx != nz)
+      error ("text: number of X, Y, and Z coordinates must match");
+    endif
+
     if (ischar (string))
 
       do_keyword_repl = true;
       nt = rows (string);
-      if (nx == 1 && nt == 1)
-        ## Single text object with one line
+      if (nx == 1 && (nt == 1 || nt == 0))
+        ## Single text object with one line or empty line
         string = {string};
+        nt = 1;
       elseif (nx == 1 && nt > 1)
         ## Single text object with multiple lines
         ## FIXME: "default" or "factory" as first row
@@ -79,12 +84,14 @@
         do_keyword_repl = false;
         string = {string};
       elseif (nx > 1 && nt == nx)
-        ## Mutiple text objects with different strings
+        ## Multiple text objects with different strings
         string = cellstr (string);
-      else
-        ## Mutiple text objects with same string
+      elseif (nx > 1 && nt == 1)
+        ## Multiple text objects with same string
         string = repmat ({string}, [nx, 1]);
         nt = nx;
+      else
+        error ("text: Invalid combination of points and text strings");
       endif
 
       ## Escape special keywords
@@ -100,11 +107,13 @@
         string = {cellstr(string)};
         nt = 1;
       elseif (nx > 1 && nt == nx)
-        ## Mutiple text objects with different strings
-      else
-        ## Mutiple text objects with same string
+        ## Multiple text objects with different strings
+      elseif (nx > 1 && nt == 1)
+        ## Multiple text objects with same string
         string = repmat ({cellstr(string)}, [nx, 1]);
         nt = nx;
+      else
+        error ("text: Invalid combination of points and text strings");
       endif
 
     else
@@ -126,7 +135,6 @@
 
   ## Get axis argument which may be in a 'parent' PROP/VAL pair
   [hax, varargin] = __plt_get_axis_arg__ ("text", varargin{:});
-
   if (isempty (hax))
     hax = gca ();
   else
@@ -142,27 +150,20 @@
     pos = [x(:), y(:), z(:)];
   endif
 
-  if (nx == ny && nx == nz && (nt == nx || nt == 1 || nx == 1))
-    htmp = zeros (nt, 1);
-    if (nx == 1)
-      htmp = __go_text__ (hax, "string", string{1},
-                               ## varargin first, in case "Units" set for pos.
-                               varargin{:},
-                               "position", pos);
-    elseif (nx == nt)
-      for n = 1:nt
-        htmp(n) = __go_text__ (hax, "string", string{n},
-                                    varargin{:},
-                                    "position", pos(n,:));
-      endfor
-      __request_drawnow__ ();
-    else
-      error ("text: dimension mismatch for coordinates and STRING");
-    endif
-  elseif (nt == nx || nt == 1 || nx == 1)
-    error ("text: dimension mismatch for coordinates");
+  ## Call __go_text__ to do the work
+  htmp = zeros (nt, 1);
+  if (nx == 1)
+    htmp = __go_text__ (hax, "string", string{1},
+                             ## varargin first, in case "Units" set for pos.
+                             varargin{:},
+                             "position", pos);
   else
-    error ("text: dimension mismatch between coordinates and strings");
+    for n = 1:nt
+      htmp(n) = __go_text__ (hax, "string", string{n},
+                                  varargin{:},
+                                  "position", pos(n,:));
+    endfor
+    __request_drawnow__ ();
   endif
 
   if (nargout > 0)
@@ -296,16 +297,31 @@
 %!   assert (get (h(1), "string"), "string1");
 %!   assert (get (h(2), "string"), "string2");
 %!
-%!   ### Tests repeated with cell input ###
-%!   clf;
+%!   ## Test special keyword processing
+%!   h = text (0.5, 0.5, "default");
+%!   assert (get (h, "string"), "default");
+%!   h = text (0.5, 0.5, "factory");
+%!   assert (get (h, "string"), "factory");
 %!
+%!   ## Test special null ("") string 
+%!   h = text (0.5, 0.5, "");
+%!   assert (get (h, "string"), "");
+%!
+%! unwind_protect_cleanup
+%!   close (hf);
+%! end_unwind_protect
+
+## Tests repeated with cell input ##
+%!test
+%! hf = figure ("visible", "off");
+%! unwind_protect
 %!   ## Single object with one line
 %!   h = text (0.5, 0.5, {"single object with one line"});
 %!   obs = get (h, "string");
 %!   assert (class (obs), "cell");
 %!   assert (obs, {"single object with one line"});
 %!
-%!   ## Single object with multiple lines
+%!   # Single object with multiple lines
 %!   h = text (0.5, 0.3, {"cell2str (1,1)", "cell2str (1,2)";
 %!                        "cell2str (2,1)", "cell2str (2,2)"});
 %!   obs = get (h, "string");
@@ -326,14 +342,6 @@
 %!   assert (get (h(1), "string"), {"two objects with same cellstr"});
 %!   assert (get (h(2), "string"), {"two objects with same cellstr"});
 %!
-%!   ## Multiple objects with same multi-line string which has empty cell
-%!   ## NOTE: Matlab does not support this syntax
-%!   h = text ([0.7, 0.7], [0.3 0.5], {"Line1"; []; "Line3"});
-%!   assert (class (get (h(1), "string")), "cell");
-%!   assert (class (get (h(2), "string")), "cell");
-%!   assert (get (h(1), "string"), {"Line1"; ""; "Line3"});
-%!   assert (get (h(2), "string"), {"Line1"; ""; "Line3"});
-%!
 %!   ## Multiple objects with multiple lines
 %!   h = text ([0.1, 0.1], [0.7, 0.8], {"cellstr1", "cellstr2"});
 %!   assert (class (get (h(1), "string")), "char");
@@ -341,13 +349,15 @@
 %!   assert (get (h(1), "string"), "cellstr1");
 %!   assert (get (h(2), "string"), "cellstr2");
 %!
-%!   ## Test special keyword processing
-%!   h = text (0.5, 0.5, "default");
-%!   assert (get (h, "string"), "default");
-%!   h = text (0.5, 0.5, "factory");
-%!   assert (get (h, "string"), "factory");
-%!
 %! unwind_protect_cleanup
 %!   close (hf);
 %! end_unwind_protect
 
+## Test input validation
+%!error <X, Y, and Z coordinates must match> text (1, [2 3], "foobar")
+%!error <X, Y, and Z coordinates must match> text (1, 2, [3 4], "foobar")
+%!error <Invalid combination> text ([1 2], [3, 4], ['a'; 'b'; 'c'])
+%!error <Invalid combination> text ([1 2], [3, 4], {'a', 'b', 'c'})
+%!error <STRING must be a character string> text (1, 2, 3)
+%!error text ("abc")
+