ruby-gr 0.0.23 → 0.58.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/LICENSE.txt +2 -2
- data/README.md +65 -19
- data/lib/gr.rb +1117 -852
- data/lib/gr/ffi.rb +9 -2
- data/lib/gr/plot.rb +176 -85
- data/lib/gr3.rb +313 -238
- data/lib/gr3/ffi.rb +3 -1
- data/lib/gr_commons/define_methods.rb +5 -5
- data/lib/gr_commons/fiddley.rb +6 -6
- data/lib/gr_commons/gr_common_utils.rb +4 -4
- data/lib/gr_commons/gr_commons.rb +2 -2
- data/lib/gr_commons/gr_lib.rb +104 -0
- data/lib/gr_commons/gr_logger.rb +118 -0
- data/lib/gr_commons/jupyter_support.rb +7 -7
- data/lib/gr_commons/{extern.rb → try_extern.rb} +1 -1
- data/lib/gr_commons/version.rb +1 -1
- data/lib/grm.rb +21 -8
- data/lib/grm/ffi.rb +8 -4
- metadata +6 -20
- data/lib/gr/plot.rb.md +0 -172
- data/lib/gr_commons/search_shared_library.rb +0 -73
data/lib/gr3/ffi.rb
CHANGED
@@ -15,7 +15,7 @@ module GR3
|
|
15
15
|
raise LoadError, 'Could not find GR Framework'
|
16
16
|
end
|
17
17
|
|
18
|
-
extend GRCommons::
|
18
|
+
extend GRCommons::TryExtern
|
19
19
|
|
20
20
|
# https://github.com/sciapp/gr/blob/master/lib/gr3/gr3.h
|
21
21
|
# keep same order
|
@@ -138,5 +138,7 @@ module GR3
|
|
138
138
|
# try_extern 'void gr3_drawtrianglesurface(int n, const float *triangles)'
|
139
139
|
try_extern 'void gr_volume(int nx, int ny, int nz, double *data, ' \
|
140
140
|
'int algorithm, double *dmin_ptr, double *dmax_ptr)'
|
141
|
+
try_extern 'void gr3_setorthographicprojection' \
|
142
|
+
'(float left, float right, float bottom, float top, float znear, float zfar)'
|
141
143
|
end
|
142
144
|
end
|
@@ -5,8 +5,8 @@ module GRCommons
|
|
5
5
|
module DefineMethods
|
6
6
|
private
|
7
7
|
|
8
|
-
def define_ffi_methods(
|
9
|
-
|
8
|
+
def define_ffi_methods(ffi_module, prefix: '', default_type: :double)
|
9
|
+
ffi_module.ffi_methods.each do |method|
|
10
10
|
# Use delete_prefix (Ruby >= 2.5)
|
11
11
|
method_name = method.to_s.sub(/^#{prefix}/, '')
|
12
12
|
|
@@ -16,14 +16,14 @@ module GRCommons
|
|
16
16
|
args.map! do |arg|
|
17
17
|
case arg
|
18
18
|
when Array
|
19
|
-
|
19
|
+
GRCommonUtils.public_send(default_type, arg)
|
20
20
|
when ->(x) { defined?(Numo::NArray) && x.is_a?(Numo::NArray) }
|
21
|
-
|
21
|
+
GRCommonUtils.public_send(default_type, arg)
|
22
22
|
else
|
23
23
|
arg
|
24
24
|
end
|
25
25
|
end
|
26
|
-
|
26
|
+
ffi_module.public_send(method, *args)
|
27
27
|
end
|
28
28
|
end
|
29
29
|
end
|
data/lib/gr_commons/fiddley.rb
CHANGED
@@ -210,7 +210,7 @@ module GRCommons
|
|
210
210
|
end
|
211
211
|
|
212
212
|
define_method("put_array_of_int#{bits}") do |offset, ary|
|
213
|
-
put_bytes(offset, ary.pack(form
|
213
|
+
put_bytes(offset, ary.pack("#{form}*"))
|
214
214
|
end
|
215
215
|
|
216
216
|
define_method("write_array_of_int#{bits}") do |ary|
|
@@ -226,7 +226,7 @@ module GRCommons
|
|
226
226
|
end
|
227
227
|
|
228
228
|
define_method("get_array_of_int#{bits}") do |offset, num|
|
229
|
-
@ptr[offset, bytes * num].unpack(form
|
229
|
+
@ptr[offset, bytes * num].unpack("#{form}*")
|
230
230
|
end
|
231
231
|
|
232
232
|
define_method("read_array_of_int#{bits}") do |num|
|
@@ -244,7 +244,7 @@ module GRCommons
|
|
244
244
|
end
|
245
245
|
|
246
246
|
define_method("put_array_of_uint#{bits}") do |offset, ary|
|
247
|
-
put_bytes(offset, ary.pack(form2
|
247
|
+
put_bytes(offset, ary.pack("#{form2}*"))
|
248
248
|
end
|
249
249
|
|
250
250
|
define_method("write_array_of_uint#{bits}") do |ary|
|
@@ -260,7 +260,7 @@ module GRCommons
|
|
260
260
|
end
|
261
261
|
|
262
262
|
define_method("get_array_of_uint#{bits}") do |offset, num|
|
263
|
-
@ptr[offset, bytes * num].unpack(form2
|
263
|
+
@ptr[offset, bytes * num].unpack("#{form2}*")
|
264
264
|
end
|
265
265
|
|
266
266
|
define_method("read_array_of_uint#{bits}") do |num|
|
@@ -330,12 +330,12 @@ module GRCommons
|
|
330
330
|
|
331
331
|
# added
|
332
332
|
define_method('get_array_of_double') do |offset, num|
|
333
|
-
@ptr[offset, 8 * num].unpack('d
|
333
|
+
@ptr[offset, 8 * num].unpack('d*')
|
334
334
|
end
|
335
335
|
|
336
336
|
# added
|
337
337
|
define_method('get_array_of_float') do |offset, num|
|
338
|
-
@ptr[offset, 4 * num].unpack('f
|
338
|
+
@ptr[offset, 4 * num].unpack('f*')
|
339
339
|
end
|
340
340
|
|
341
341
|
# added
|
@@ -1,6 +1,6 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
-
|
3
|
+
require_relative 'fiddley'
|
4
4
|
|
5
5
|
module GRCommons
|
6
6
|
# This module provides functionality common to GR and GR3.
|
@@ -52,7 +52,7 @@ module GRCommons
|
|
52
52
|
if narray?(data)
|
53
53
|
Numo::UInt32.cast(data).to_binary
|
54
54
|
else
|
55
|
-
Fiddley::Utils.array2str(:
|
55
|
+
Fiddley::Utils.array2str(:uint32, data.to_a.flatten)
|
56
56
|
end
|
57
57
|
end
|
58
58
|
|
@@ -117,9 +117,9 @@ module GRCommons
|
|
117
117
|
when Hash
|
118
118
|
typ = type.keys[0]
|
119
119
|
len = type.values[0]
|
120
|
-
pt.
|
120
|
+
pt.public_send("read_array_of_#{typ}", len)
|
121
121
|
else
|
122
|
-
pt.
|
122
|
+
pt.public_send("read_#{type}")
|
123
123
|
end
|
124
124
|
end
|
125
125
|
|
@@ -7,8 +7,8 @@ end
|
|
7
7
|
# Change the default encoding to UTF-8.
|
8
8
|
ENV['GKS_ENCODING'] ||= 'utf8'
|
9
9
|
|
10
|
-
require_relative '
|
11
|
-
require_relative '
|
10
|
+
require_relative 'gr_lib'
|
11
|
+
require_relative 'try_extern'
|
12
12
|
require_relative 'define_methods'
|
13
13
|
require_relative 'gr_common_utils'
|
14
14
|
require_relative 'jupyter_support'
|
@@ -0,0 +1,104 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'pkg-config'
|
4
|
+
|
5
|
+
module GRCommons
|
6
|
+
# This module helps GR, GR and GRM to search the shared library.
|
7
|
+
#
|
8
|
+
# The order of priority:
|
9
|
+
# 1. RubyInstaller ( for Windows only )
|
10
|
+
# 2. Environment variable GRDIR
|
11
|
+
# 3. pkg-config : https://github.com/ruby-gnome/pkg-config
|
12
|
+
# The following packages (should) support pkg-config.
|
13
|
+
# - Linux
|
14
|
+
# - Red Data Tools https://github.com/red-data-tools/packages.red-data-tools.org
|
15
|
+
# - libgr-dev
|
16
|
+
# - libgr3-dev
|
17
|
+
# - libgrm-dev
|
18
|
+
# - Mac
|
19
|
+
# - Homebrew https://github.com/Homebrew/homebrew-core
|
20
|
+
# - libgr
|
21
|
+
# - Windows
|
22
|
+
# - MinGW https://github.com/msys2/MINGW-packages
|
23
|
+
# - mingw-w64-gr
|
24
|
+
module GRLib
|
25
|
+
class << self
|
26
|
+
# Check if using RubyInstaller or not.
|
27
|
+
def ruby_installer?
|
28
|
+
Object.const_defined?(:RubyInstaller)
|
29
|
+
end
|
30
|
+
|
31
|
+
# Return the directory path from the GRDIR environment variable.
|
32
|
+
def get_grdir_from_env(lib_names)
|
33
|
+
return nil unless ENV['GRDIR']
|
34
|
+
return ENV['GRDIR'] if Dir.exist?(ENV['GRDIR'])
|
35
|
+
|
36
|
+
warn "#{lib_names} : Dir GRDIR=#{ENV['GRDIR']} not found." # return nil
|
37
|
+
end
|
38
|
+
|
39
|
+
# Search the shared library.
|
40
|
+
# @note This method does not detect the Operating System.
|
41
|
+
#
|
42
|
+
# @param lib_names [Array] The actual file name of the shared library.
|
43
|
+
# @param pkg_name [String] The package name to be used when searching with pkg-configg
|
44
|
+
def search(lib_names, pkg_name)
|
45
|
+
# FIXME: There may be a better way to do it...
|
46
|
+
def lib_names.map_find(&block)
|
47
|
+
lazy.map(&block).find { |path| path }
|
48
|
+
end
|
49
|
+
|
50
|
+
# ENV['GRDIR']
|
51
|
+
# Verify that the directory exists.
|
52
|
+
grdir = get_grdir_from_env(lib_names)
|
53
|
+
|
54
|
+
# Windows + RubyInstaller
|
55
|
+
if ruby_installer?
|
56
|
+
grdir ||= File.join(RubyInstaller::Runtime.msys2_installation.msys_path,
|
57
|
+
RubyInstaller::Runtime.msys2_installation.mingwarch)
|
58
|
+
end
|
59
|
+
|
60
|
+
# Search grdir
|
61
|
+
if grdir
|
62
|
+
lib_path = lib_names.map_find do |lib_name|
|
63
|
+
recursive_search(lib_name, grdir)
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
67
|
+
# Search with pkg-config
|
68
|
+
lib_path ||= lib_names.map_find do |lib_name|
|
69
|
+
pkg_config_search(lib_name, pkg_name)
|
70
|
+
end
|
71
|
+
|
72
|
+
# Windows + RubyInstaller
|
73
|
+
if ruby_installer?
|
74
|
+
RubyInstaller::Runtime.add_dll_directory(File.dirname(lib_path))
|
75
|
+
# FIXME: Where should I write this code?
|
76
|
+
ENV['GKS_FONTPATH'] ||= grdir
|
77
|
+
end
|
78
|
+
|
79
|
+
lib_path
|
80
|
+
end
|
81
|
+
|
82
|
+
# Recursive file search in directories
|
83
|
+
# @param name [String] File to search for
|
84
|
+
# @param base_dir [String] Directory to search
|
85
|
+
# @return path [String, NilClass] Returns the first path found.
|
86
|
+
# If not found, nil is returned.
|
87
|
+
def recursive_search(name, base_dir)
|
88
|
+
Dir.chdir(base_dir) do
|
89
|
+
paths = Dir["**/#{name}"].sort
|
90
|
+
warn "More than one file found: #{paths}" if paths.size > 1
|
91
|
+
path = paths.first
|
92
|
+
File.expand_path(path) if path
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
96
|
+
# Use pkg-config to search for shared libraries
|
97
|
+
def pkg_config_search(lib_name, pkg_name)
|
98
|
+
PKGConfig.variable(pkg_name, 'sopath')
|
99
|
+
rescue PackageConfig::NotFoundError => e
|
100
|
+
warn "#{e.message} Cannot find #{lib_name}. "
|
101
|
+
end
|
102
|
+
end
|
103
|
+
end
|
104
|
+
end
|
@@ -0,0 +1,118 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# This script was created primarily for debugging purposes.
|
4
|
+
# Note: This script should be isolated.
|
5
|
+
# It should not be loaded when gr_commons/gr_commons is loaded.
|
6
|
+
|
7
|
+
require 'logger'
|
8
|
+
require 'pp'
|
9
|
+
|
10
|
+
module GRCommons
|
11
|
+
# Convenience class methods
|
12
|
+
|
13
|
+
class << self
|
14
|
+
# Create a new GRLogger
|
15
|
+
# @param out [String]
|
16
|
+
# @return [GRLogger]
|
17
|
+
# @example
|
18
|
+
# require 'gr_commons/gr_logger'
|
19
|
+
# GRCommons.gr_log("log.txt")
|
20
|
+
|
21
|
+
def gr_log(out = $stderr)
|
22
|
+
GRCommons::GRLogger.new(out)
|
23
|
+
end
|
24
|
+
|
25
|
+
# Return the last created GRLogger
|
26
|
+
# @return [GRLogger]
|
27
|
+
|
28
|
+
def gr_logger
|
29
|
+
GRCommons::GRLogger.logger
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
# If GR.rb call native functions of the GR framework,
|
34
|
+
# it will be recorded in the log file.
|
35
|
+
#
|
36
|
+
# @note Mainly used by developers for debugging.
|
37
|
+
#
|
38
|
+
# = How it works
|
39
|
+
# It prepend a module named Inspector to the singular class of the FFI module.
|
40
|
+
# It will inspects the GR function call of the FFI module
|
41
|
+
#
|
42
|
+
# @example
|
43
|
+
# require 'gr_commons/gr_logger'
|
44
|
+
# GRCommons::GRLogger.new("log.txt")
|
45
|
+
|
46
|
+
class GRLogger < Logger
|
47
|
+
# Return the last created GRLogger
|
48
|
+
|
49
|
+
def self.logger
|
50
|
+
@@logger ||= GRCommons::GRLogger.new
|
51
|
+
end
|
52
|
+
|
53
|
+
def initialize(out = $stderr)
|
54
|
+
super(out, level: :info)
|
55
|
+
@@logger ||= self
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
60
|
+
# GR
|
61
|
+
|
62
|
+
if Object.const_defined?(:GR)
|
63
|
+
module GR
|
64
|
+
module FFI
|
65
|
+
module Inspector
|
66
|
+
GR::FFI.ffi_methods.each do |s|
|
67
|
+
define_method(s) do |*args|
|
68
|
+
GRCommons.gr_logger.info "GR::FFI.#{s}\n#{args.pretty_inspect}\n"
|
69
|
+
super(*args)
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
class << self
|
74
|
+
prepend Inspector
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
# GR3
|
81
|
+
|
82
|
+
if Object.const_defined?(:GR3)
|
83
|
+
module GR3
|
84
|
+
module FFI
|
85
|
+
module Inspector
|
86
|
+
GR3::FFI.ffi_methods.each do |s|
|
87
|
+
define_method(s) do |*args|
|
88
|
+
GRCommons.gr_logger.info "GR3::FFI.#{s}\n#{args.pretty_inspect}\n"
|
89
|
+
super(*args)
|
90
|
+
end
|
91
|
+
end
|
92
|
+
end
|
93
|
+
class << self
|
94
|
+
prepend Inspector
|
95
|
+
end
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
# GRM
|
101
|
+
|
102
|
+
if Object.const_defined?(:GRM)
|
103
|
+
module GRM
|
104
|
+
module FFI
|
105
|
+
module Inspector
|
106
|
+
GRM::FFI.ffi_methods.each do |s|
|
107
|
+
define_method(s) do |*args|
|
108
|
+
GRCommons.gr_logger.info "GRM::FFI.#{s}\n#{args.pretty_inspect}\n"
|
109
|
+
super(*args)
|
110
|
+
end
|
111
|
+
end
|
112
|
+
end
|
113
|
+
class << self
|
114
|
+
prepend Inspector
|
115
|
+
end
|
116
|
+
end
|
117
|
+
end
|
118
|
+
end
|
@@ -8,7 +8,7 @@ module GRCommons
|
|
8
8
|
# Sets the environment variable when the module is extended.
|
9
9
|
def self.extended(_obj)
|
10
10
|
require 'tmpdir'
|
11
|
-
ENV['
|
11
|
+
ENV['GKS_WSTYPE'] = 'svg'
|
12
12
|
ENV['GKS_FILEPATH'] = Dir::Tmpname.create('plot-') {}
|
13
13
|
end
|
14
14
|
|
@@ -16,19 +16,19 @@ module GRCommons
|
|
16
16
|
def show(display = true)
|
17
17
|
emergencyclosegks
|
18
18
|
sleep 0.5
|
19
|
-
type = ENV['
|
19
|
+
type = ENV['GKS_WSTYPE']
|
20
20
|
case type
|
21
21
|
when 'svg'
|
22
|
-
data = File.read(ENV['GKS_FILEPATH']
|
22
|
+
data = File.read("#{ENV['GKS_FILEPATH']}.svg")
|
23
23
|
IRuby.display(data, mime: 'image/svg+xml') if display
|
24
24
|
when 'png', '322', '140'
|
25
|
-
data = File.read(ENV['GKS_FILEPATH']
|
25
|
+
data = File.read("#{ENV['GKS_FILEPATH']}.png")
|
26
26
|
IRuby.display(data, mime: 'image/png') if display
|
27
27
|
when 'jpg', '321', '144'
|
28
|
-
data = File.read(ENV['GKS_FILEPATH']
|
28
|
+
data = File.read("#{ENV['GKS_FILEPATH']}.jpg")
|
29
29
|
IRuby.display(data, mime: 'image/jpeg') if display
|
30
30
|
when 'gif', '130'
|
31
|
-
data = File.read(ENV['GKS_FILEPATH']
|
31
|
+
data = File.read("#{ENV['GKS_FILEPATH']}.gif")
|
32
32
|
IRuby.display(data, mime: 'image/gif') if display
|
33
33
|
when 'webm', 'ogg', 'mp4', 'mov'
|
34
34
|
require 'base64'
|
@@ -37,7 +37,7 @@ module GRCommons
|
|
37
37
|
else
|
38
38
|
"video/#{type}"
|
39
39
|
end
|
40
|
-
data = File.binread(ENV['GKS_FILEPATH']
|
40
|
+
data = File.binread("#{ENV['GKS_FILEPATH']}.#{type}")
|
41
41
|
if display
|
42
42
|
IRuby.display(
|
43
43
|
"<video autoplay controls><source type=\"#{mimespec}\" " \
|
data/lib/gr_commons/version.rb
CHANGED
data/lib/grm.rb
CHANGED
@@ -17,23 +17,36 @@ end
|
|
17
17
|
module GRM
|
18
18
|
class Error < StandardError; end
|
19
19
|
|
20
|
+
class NotFoundError < Error; end
|
21
|
+
|
20
22
|
class << self
|
21
23
|
attr_accessor :ffi_lib
|
22
24
|
end
|
23
25
|
|
24
26
|
require_relative 'gr_commons/gr_commons'
|
25
|
-
extend GRCommons::SearchSharedLibrary
|
26
27
|
|
27
28
|
# Platforms | path
|
28
29
|
# Windows | bin/libGRM.dll
|
29
|
-
# MacOSX | lib/libGRM.
|
30
|
+
# MacOSX | lib/libGRM.dylib ( <= v0.53.0 .so)
|
30
31
|
# Ubuntu | lib/libGRM.so
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
32
|
+
platform = RbConfig::CONFIG['host_os']
|
33
|
+
lib_names, pkg_name = \
|
34
|
+
case platform
|
35
|
+
when /mswin|msys|mingw|cygwin|bccwin|wince|emc/
|
36
|
+
[['libGRM.dll'], 'grm']
|
37
|
+
when /darwin|mac os/
|
38
|
+
[['libGRM.dylib', 'libGRM.so'], 'grm']
|
39
|
+
else
|
40
|
+
[['libGRM.so'], 'grm']
|
41
|
+
end
|
42
|
+
|
43
|
+
# On Windows + RubyInstaller,
|
44
|
+
# the environment variable GKS_FONTPATH will be set.
|
45
|
+
lib_path = GRCommons::GRLib.search(lib_names, pkg_name)
|
46
|
+
|
47
|
+
raise NotFoundError, "#{lib_names} not found" if lib_path.nil?
|
48
|
+
|
49
|
+
self.ffi_lib = lib_path
|
37
50
|
|
38
51
|
require_relative 'grm/version'
|
39
52
|
require_relative 'grm/ffi'
|