class Numo::Gnuplot

Constants

DATA_FORMAT
KNOWN_EXT
POOL
VERSION

Attributes

gnuplot_version[R]
history[R]
last_message[R]

Public Class Methods

default() click to toggle source
# File lib/numo/gnuplot.rb, line 25
def self.default
  POOL[0] ||= self.new
end
new(gnuplot_command="gnuplot") click to toggle source
# File lib/numo/gnuplot.rb, line 54
def initialize(gnuplot_command="gnuplot")
  @history = []
  @debug = false
  r0,@iow = IO.pipe
  @ior,w2 = IO.pipe
  IO.popen(gnuplot_command,:in=>r0,:err=>w2)
  r0.close
  w2.close
  @gnuplot_version = send_cmd("print GPVAL_VERSION")[0].chomp
  if /\.(\w+)$/ =~ (filename = ENV['NUMO_GNUPLOT_OUTPUT'])
    ext = $1
    ext = KNOWN_EXT[ext] || ext
    opts = ENV['NUMO_GNUPLOT_OPTION'] || ''
    set terminal:[ext,opts]
    set output:filename
  end
end

Public Instance Methods

clear() click to toggle source

The `clear` command erases the current screen or output device as specified by `set output`. This usually generates a formfeed on hardcopy devices.

# File lib/numo/gnuplot.rb, line 197
def clear
  send_cmd "clear"
  nil
end
debug_off() click to toggle source

turn off debug

# File lib/numo/gnuplot.rb, line 257
def debug_off
  @debug = false
end
debug_on() click to toggle source

turn on debug

# File lib/numo/gnuplot.rb, line 252
def debug_on
  @debug = true
end
exit() click to toggle source

The `exit` and `quit` commands will exit `gnuplot`.

# File lib/numo/gnuplot.rb, line 203
def exit
  send_cmd "exit"
  nil
end
fit(*args) click to toggle source

The `fit` command can fit a user-supplied expression to a set of data points (x,z) or (x,y,z), using an implementation of the nonlinear least-squares (NLLS) Marquardt-Levenberg algorithm.

# File lib/numo/gnuplot.rb, line 109
def fit(*args)
  range, items = parse_fit_args(args)
  r = range.map{|x| "#{x} "}.join
  c = items.cmd_str
  puts send_cmd("fit #{r}#{c}")
  nil
end
help(s=nil) click to toggle source

The `help` command displays built-in help.

# File lib/numo/gnuplot.rb, line 146
def help(s=nil)
  puts send_cmd "help #{s}\n\n"
end
kernel_raise(plot_window_nb=nil)
Alias for: raise
load(filename) click to toggle source

The `load` command executes each line of the specified input file.

# File lib/numo/gnuplot.rb, line 174
def load(filename)
  run "load #{OptArg.quote(filename)}"
  nil
end
lower(plot_window_nb=nil)
Alias for: lower_plot
lower_plot(plot_window_nb=nil) click to toggle source

The `lower` command lowers plot window(s)

# File lib/numo/gnuplot.rb, line 189
def lower_plot(plot_window_nb=nil)
  send_cmd "lower #{plot_window_nb}"
  nil
end
Also aliased as: lower
output(filename,**opts) click to toggle source

output current plot to file with terminal setting from extension (not Gnuplot command)

# File lib/numo/gnuplot.rb, line 234
def output(filename,**opts)
  term = opts.delete(:term) || opts.delete(:terminal)
  if term.nil? && /\.(\w+)$/ =~ filename
    term = $1
  end
  term = KNOWN_EXT[term] || term
  if term.nil?
    kernel_raise GnuplotError,"file extension is not given"
  end
  set :terminal, term, *opts
  set output:filename
  refresh
  unset :terminal
  unset :output
end
pause(*args) click to toggle source

The `pause` command used to wait for events on window. Carriage return entry (-1 is given for argument) and text display option is disabled.

pause 10
pause 'mouse'
pause mouse:%w[keypress button1 button2 button3 close any]
# File lib/numo/gnuplot.rb, line 168
def pause(*args)
  send_cmd("pause #{OptArg.parse(*args)}").join.chomp
  nil
end
plot(*args) click to toggle source

draw 2D functions and data.

# File lib/numo/gnuplot.rb, line 77
def plot(*args)
  contents = parse_plot_args(PlotItem,args)
  _plot_splot("plot",contents)
  nil
end
quit() click to toggle source

The `exit` and `quit` commands will exit `gnuplot`.

# File lib/numo/gnuplot.rb, line 209
def quit
  send_cmd "quit"
  nil
end
raise(plot_window_nb=nil)
Also aliased as: kernel_raise
Alias for: raise_plot
raise_plot(plot_window_nb=nil) click to toggle source

The `raise` command raises plot window(s)

# File lib/numo/gnuplot.rb, line 182
def raise_plot(plot_window_nb=nil)
  send_cmd "raise #{plot_window_nb}"
  nil
end
Also aliased as: raise
refresh() click to toggle source

The `refresh` reformats and redraws the current plot using the data already read in.

# File lib/numo/gnuplot.rb, line 216
def refresh
  send_cmd "refresh"
  nil
end
replot(arg=nil) click to toggle source

replot is not recommended, use refresh

# File lib/numo/gnuplot.rb, line 101
def replot(arg=nil)
  run "replot #{arg}", @last_data
  nil
end
reset(x=nil) click to toggle source

The `reset` command causes all graph-related options that can be set with the `set` command to take on their default values.

# File lib/numo/gnuplot.rb, line 157
def reset(x=nil)
  run "reset #{x}"
  nil
end
run(s,data=nil) click to toggle source

private methods

# File lib/numo/gnuplot.rb, line 291
def run(s,data=nil)
  res = send_cmd(s,data)
  if !res.empty?
    if /.*?End\sof\sanimation\ssequence.*?/im =~ res.to_s
      return nil
    end
    if res.size < 7
      if /^\s*(line \d+: )?warning:/i =~ res[0]
        $stderr.puts res.join.strip
        return nil
      else
        msg = "\n"+res.join.strip
      end
    else
      msg = "\n"+res[0..5].join.strip+"\n :\n"
    end
    kernel_raise GnuplotError,msg
  end
  nil
end
send(cmd) click to toggle source

send command-line string to Gnuplot directly

# File lib/numo/gnuplot.rb, line 262
def send(cmd)
  puts send_cmd(cmd)
end
set(*args) click to toggle source

The `set` command is used to set lots of options.

# File lib/numo/gnuplot.rb, line 134
def set(*args)
  run "set #{OptArg.parse(*args)}"
  nil
end
show(*args) click to toggle source

The `show` command shows their settings.

# File lib/numo/gnuplot.rb, line 151
def show(*args)
  puts send_cmd "show #{OptArg.parse(*args)}"
end
splot(*args) click to toggle source

draws 2D projections of 3D surfaces and data.

# File lib/numo/gnuplot.rb, line 84
def splot(*args)
  contents = parse_plot_args(SPlotItem,args)
  _plot_splot("splot",contents)
  nil
end
stats(filename,*args) click to toggle source

This command prepares a statistical summary of the data in one or two columns of a file.

# File lib/numo/gnuplot.rb, line 127
def stats(filename,*args)
  fn = OptArg.quote(filename)
  opt = OptArg.parse(*args)
  puts send_cmd "stats #{fn} #{opt}"
end
to_s() click to toggle source

for irb workspace name

# File lib/numo/gnuplot.rb, line 285
def to_s
  "gnuplot"
end
unset(*args) click to toggle source

The `unset` command is used to return to their default state.

# File lib/numo/gnuplot.rb, line 140
def unset(*args)
  run "unset #{OptArg.parse(*args)}"
  nil
end
update(*filenames) click to toggle source

This command writes the current values of the fit parameters into the given file, formatted as an initial-value file (as described in the `fit`section). This is useful for saving the current values for later use or for restarting a converged or stopped fit.

# File lib/numo/gnuplot.rb, line 121
def update(*filenames)
  puts send_cmd("update "+filenames.map{|f| OptArg.quote(f)}.join(" "))
end
var(name) click to toggle source

`var` returns Gnuplot variable (not Gnuplot command)

# File lib/numo/gnuplot.rb, line 222
def var(name)
  res = send_cmd("print #{name}").join("").chomp
  if /undefined variable:/ =~ res
    kernel_raise GnuplotError,res.strip
  end
  res
end

Private Instance Methods

_plot_splot(cmd,contents) click to toggle source
# File lib/numo/gnuplot.rb, line 90
def _plot_splot(cmd,contents)
  r = contents.shift.map{|x| "#{x} "}.join
  c = contents.map{|x| x.cmd_str}.join(", ")
  d = contents.map{|x| x.data_str}.join
  run "#{cmd} #{r}#{c}", d
  @last_data = d
  nil
end
parse_fit_args(args) click to toggle source
# File lib/numo/gnuplot.rb, line 435
def parse_fit_args(args)
  range = []
  while !args.empty?
    case a = args.first
    when Range
      range << range_to_s(args.shift)
    when String
      if /^\[.*\]$/ =~ a
        range << args.shift
      else
        break
      end
    else
      break
    end
  end
  items = FitItem.new(args.shift, args.shift)
  args.each do |arg|
    case arg
    when Range
      range << range_to_s(arg)
    when Array
      if arg.all?{|e| e.kind_of?(Range)}
        arg.each{|e| range << range_to_s(e)}
      else
        items << arg
      end
    else
      items << arg
    end
  end
  return [range,items]
end
parse_plot_args(cPlotItem,args) click to toggle source
# File lib/numo/gnuplot.rb, line 376
def parse_plot_args(cPlotItem,args)
  range = []
  while !args.empty?
    case a = args.first
    when Range
      range << range_to_s(args.shift)
    when String
      if /^\[.*\]$/ =~ a
        range << args.shift
      else
        break
      end
    else
      break
    end
  end
  item = cPlotItem.new # first item is range
  list = [range,item]
  args.each do |arg|
    case arg
    when Range
      list.first << range_to_s(arg)
    when Array
      if arg.all?{|e| e.kind_of?(Range)}
        arg.each{|e| list.first << range_to_s(e)}
      elsif PlotItem.is_data(arg)
        item << arg
      else
        list.pop if list.last.empty?
        list << item = cPlotItem.new(*arg) # next PlotItem
      end
    when Hash
      item << arg
      list << item = cPlotItem.new # next PlotItem
    when String
      list.pop if list.last.empty?
      list << item = cPlotItem.new(arg) # next PlotItem
    else
      item << arg
    end
  end
  list.pop if list.last.empty?
  return list
end
range_to_s(*a) click to toggle source
# File lib/numo/gnuplot.rb, line 422
def range_to_s(*a)
  case a.size
  when 1
    a = a[0]
    "[#{a.first}:#{a.last}]"
  when 2
    "[#{a[0]}:#{a[1]}]"
  else
    kernel_raise ArgumentError,"wrong number of argument"
  end
end
send_cmd(s,data=nil) click to toggle source
# File lib/numo/gnuplot.rb, line 312
def send_cmd(s,data=nil)
  if @debug
    puts "<"+s
    if data && !data.empty?
      if data.size > 144
        s1 = data[0..71]
        s2 = data[-72..-1]
        if s1.force_encoding("UTF-8").ascii_only? &&
            s2.force_encoding("UTF-8").ascii_only?
          a = [nil]*6
          if /\A(.+?)$(.+)?/m =~ s1
            a[0..1] = $1,$2
            if a[1] && /\A(.+?)?$(.+)?/m =~ a[1].strip
              a[1..2] = $1,$2
              a[1] = a[1]+"..." if !a[2]
            else
              a[0] = a[0]+"..."
            end
          end
          if /(.+)?^(.+?)\z/m =~ s2
            a[4..5] = $1,$2
            if a[4] && /(.+)?^(.+?)?\z/m =~ a[4].strip
              a[3..4] = $1,$2
              a[4] = "..."+a[4] if !a[3]
            else
              a[5] = "..."+a[5]
            end
          end
          if a[2] || a[3]
            a[2..3] = ["...",nil]
          end
          a.each{|l| puts "<"+l if l}
        else
          c = data[0..31].inspect
          c += "..." if data.size > 32
          puts "<"+c
        end
      else
        if data.force_encoding("UTF-8").ascii_only?
          data.split(/\n/).each{|l| puts "<"+l}
        else
          c = data[0..31].inspect
          c += "..." if data.size > 32
          puts "<"+c
        end
      end
    end
  end
  @iow.puts s
  @iow.puts data
  @iow.flush
  @iow.puts "print '_end_of_cmd_'"
  @iow.flush
  @history << s
  @last_message = []
  while line=@ior.gets
    break if /^_end_of_cmd_$/ =~ line.chomp
    puts ">"+line if @debug
    @last_message << line
  end
  @last_message
end