oscope 0.2.2

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 62f3fea7c558c554da6c06e07596148818615f16
4
+ data.tar.gz: f8b970dd6433c4a38b32ea4eb7098a92358d934c
5
+ SHA512:
6
+ metadata.gz: 3ce59ab95c5ab2820c292459c89c92ccf4121a170cdc2a19347f27511bb26eb4e2873c8651adfe66e7f24d6877d1325f711488b151106cf6bda8a9aefe9fd4ba
7
+ data.tar.gz: d52f3f2eaa740f8ac3aa1168d91397bb6394b389091f05eced8de8c0528276d02893d57404422368ff6f5a11ba237316da87140c1d2aac07fae0b1dcf785f72a
data/Gemfile ADDED
@@ -0,0 +1,15 @@
1
+ source "http://rubygems.org"
2
+ # Add dependencies required to use your gem here.
3
+ # Example:
4
+ # gem "activesupport", ">= 2.3.5"
5
+
6
+ gem 'airby', '~>0.1.0', git: 'git://github.chi.matasano.com/td/airby.git', branch: :master
7
+ gem "ffi", "~>1.9.6"
8
+
9
+ # Add dependencies to develop your gem here.
10
+ # Include everything needed to run rake, tests, features, etc.
11
+ group :development do
12
+ gem 'yard', '~>0.8.7'
13
+ gem "bundler", "~> 1.0"
14
+ gem "jeweler", "~> 1.8.7"
15
+ end
data/LICENSE ADDED
@@ -0,0 +1,22 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2014 tduehr
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
22
+
@@ -0,0 +1,45 @@
1
+ oscope
2
+ ======
3
+
4
+ SCPI driver for VISA instruments. Currently, only the ds1102d oscilloscope is defined. All other SCPI instruments should work if oscope is provided the commands.
5
+
6
+ ### Example
7
+
8
+ ```ruby
9
+ require 'oscope/rigol/ds1102d'
10
+
11
+ scope = Oscope::Rigol::Ds1102d.new
12
+ scope.open(scope.session.find_resources('USB*').first)
13
+ # get timebase settings
14
+ scope.timebase.scale.to_f
15
+ scope.timebase.offset.to_f
16
+
17
+ # get channel settings
18
+ scope.channel(1).scale.to_f
19
+ scope.channel(1).offset.to_f
20
+ scope.channel(2).scale.to_f
21
+ scope.channel(2).offset.to_f
22
+ scope.acquire.sampling_rate('chan2').to_f
23
+
24
+ # get channel waveforms
25
+ scope.waveform.data 'chan2'
26
+ scope.waveform.data 'chan1'
27
+ scope.waveform.data 'digital'
28
+ ```
29
+
30
+ ### Contributing to oscope
31
+
32
+
33
+ * Check out the latest master to make sure the feature hasn't been implemented or the bug hasn't been fixed yet.
34
+ * Check out the issue tracker to make sure someone already hasn't requested it and/or contributed it.
35
+ * Fork the project.
36
+ * Start a feature/bugfix branch.
37
+ * Commit and push until you are happy with your contribution.
38
+ * Make sure to add tests for it. This is important so I don't break it in a future version unintentionally.
39
+ * Please try not to mess with the Rakefile, version, or history. If you want to have your own version, or is otherwise necessary, that is fine, but please isolate to its own commit so I can cherry-pick around it.
40
+
41
+ #### Copyright
42
+
43
+ Copyright (c) 2015 tduehr. See LICENSE for
44
+ further details.
45
+
@@ -0,0 +1,36 @@
1
+ # encoding: utf-8
2
+
3
+ require 'rubygems'
4
+ require 'bundler'
5
+ begin
6
+ Bundler.setup(:default, :development)
7
+ rescue Bundler::BundlerError => e
8
+ $stderr.puts e.message
9
+ $stderr.puts "Run `bundle install` to install missing gems"
10
+ exit e.status_code
11
+ end
12
+ require 'rake'
13
+
14
+ require 'jeweler'
15
+ Jeweler::Tasks.new do |gem|
16
+ gem.name = "oscope"
17
+ gem.homepage = "http://github.com/tduehr/oscope"
18
+ gem.license = "MIT"
19
+ gem.summary = %Q{SCPI command interface}
20
+ gem.description = %Q{SCPI (IEEE 488.2) interface. Only the Rigol DS1102D oscilloscope is implemented currently. All SCPI interfaces *should* be supported.}
21
+ gem.email = "tduehr@gmail.com"
22
+ gem.authors = ["tduehr"]
23
+ end
24
+ Jeweler::RubygemsDotOrgTasks.new
25
+
26
+ require 'rake/testtask'
27
+ Rake::TestTask.new(:test) do |test|
28
+ test.libs << 'lib' << 'test'
29
+ test.pattern = 'test/**/test_*.rb'
30
+ test.verbose = true
31
+ end
32
+
33
+ task :default => :test
34
+
35
+ require 'yard'
36
+ YARD::Rake::YardocTask.new
@@ -0,0 +1,5 @@
1
+ ---
2
+ :major: 0
3
+ :minor: 2
4
+ :patch: 2
5
+ :build:
@@ -0,0 +1,66 @@
1
+ # Generated by jeweler
2
+ # DO NOT EDIT THIS FILE DIRECTLY
3
+ # Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
4
+ # -*- encoding: utf-8 -*-
5
+ # stub: oscope 0.2.2 ruby lib
6
+
7
+ Gem::Specification.new do |s|
8
+ s.name = "oscope"
9
+ s.version = "0.2.2"
10
+
11
+ s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
12
+ s.require_paths = ["lib"]
13
+ s.authors = ["tduehr"]
14
+ s.date = "2015-02-03"
15
+ s.description = "SCPI (IEEE 488.2) interface. Only the Rigol DS1102D oscilloscope is implemented currently. All SCPI interfaces *should* be supported."
16
+ s.email = "tduehr@gmail.com"
17
+ s.extra_rdoc_files = [
18
+ "LICENSE",
19
+ "README.md"
20
+ ]
21
+ s.files = [
22
+ "Gemfile",
23
+ "LICENSE",
24
+ "README.md",
25
+ "Rakefile",
26
+ "VERSION.yml",
27
+ "oscope.gemspec",
28
+ "oscope/relation.rb",
29
+ "oscope/relation/base.rb",
30
+ "oscope/relation/channel.rb",
31
+ "oscope/relation/group.rb",
32
+ "oscope/relation/key.rb",
33
+ "oscope/relation/query.rb",
34
+ "oscope/relation/write.rb",
35
+ "oscope/rigol/ds1102d.rb"
36
+ ]
37
+ s.homepage = "http://github.com/tduehr/oscope"
38
+ s.licenses = ["MIT"]
39
+ s.rubygems_version = "2.4.5"
40
+ s.summary = "SCPI command interface"
41
+
42
+ if s.respond_to? :specification_version then
43
+ s.specification_version = 4
44
+
45
+ if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
46
+ s.add_runtime_dependency(%q<airby>, ["~> 0.1.0"])
47
+ s.add_runtime_dependency(%q<ffi>, ["~> 1.9.6"])
48
+ s.add_development_dependency(%q<yard>, ["~> 0.8.7"])
49
+ s.add_development_dependency(%q<bundler>, ["~> 1.0"])
50
+ s.add_development_dependency(%q<jeweler>, ["~> 1.8.7"])
51
+ else
52
+ s.add_dependency(%q<airby>, ["~> 0.1.0"])
53
+ s.add_dependency(%q<ffi>, ["~> 1.9.6"])
54
+ s.add_dependency(%q<yard>, ["~> 0.8.7"])
55
+ s.add_dependency(%q<bundler>, ["~> 1.0"])
56
+ s.add_dependency(%q<jeweler>, ["~> 1.8.7"])
57
+ end
58
+ else
59
+ s.add_dependency(%q<airby>, ["~> 0.1.0"])
60
+ s.add_dependency(%q<ffi>, ["~> 1.9.6"])
61
+ s.add_dependency(%q<yard>, ["~> 0.8.7"])
62
+ s.add_dependency(%q<bundler>, ["~> 1.0"])
63
+ s.add_dependency(%q<jeweler>, ["~> 1.8.7"])
64
+ end
65
+ end
66
+
@@ -0,0 +1,10 @@
1
+ class Oscope
2
+ module Relation
3
+ end
4
+ end
5
+
6
+ require 'oscope/relation/base'
7
+ require 'oscope/relation/group'
8
+ require 'oscope/relation/channel'
9
+ require 'oscope/relation/group'
10
+ require 'oscope/relation/key'
@@ -0,0 +1,53 @@
1
+ class Oscope
2
+ module Relation
3
+ class Base
4
+ attr_reader :scope, :command
5
+ def initialize scope, command, commands
6
+ @scope = scope
7
+ @command = command
8
+ @subcommands = commands
9
+ end
10
+
11
+ def subcommands
12
+ @subcommands.keys
13
+ end
14
+
15
+ def inspect
16
+ "\#<Relation:0x#{(__id__ * 2).to_s(16).rjust(14, '0')} #{@command}>"
17
+ end
18
+
19
+ def method_missing meth, *args, &block
20
+ subs = @subcommands[meth.to_s]
21
+ super unless subs
22
+ meth = meth.to_s.split('_').join
23
+ if subs.kind_of?(::Hash) # sub-sub-commands
24
+ self.class.new @scope, "#{@command}:#{meth.upcase}", subs
25
+ else
26
+ raise ArgumentError unless subs.include? args.size
27
+ if meth.end_with? "=" # set something
28
+ write ["#{@command}:#{meth[0..-2]}", args.join(',')].join(" ")
29
+ else # get something
30
+ query_full ["#{@command}:#{meth}?", args.join(',')].join(" ")
31
+ end
32
+ end
33
+ end
34
+
35
+ def respond_to_missing? meth
36
+ subcommands.include? meth || super
37
+ end
38
+
39
+ private
40
+ def write comm
41
+ @scope.session.write comm
42
+ end
43
+
44
+ def query comm
45
+ @scope.session.query comm
46
+ end
47
+
48
+ def query_full comm
49
+ @scope.session.query_full comm
50
+ end
51
+ end
52
+ end
53
+ end
@@ -0,0 +1,32 @@
1
+ class Oscope
2
+ module Relation
3
+ class Channel < Base
4
+ # ZERO = [0]
5
+ # ONE = [1]
6
+ # ONE_ZERO = [0,1]
7
+
8
+ def initialize scope, command, commands, chan, chan_subcomm = nil
9
+ super scope, command, commands
10
+ @channel_commands = chan_subcomm || {
11
+ 'acquire' => {'sampling_rate' => ZERO, 'sampling_rate=' => ONE},
12
+ 'trigger' => {
13
+ 'edge' => {'source' => ZERO},
14
+ 'slope' => {'source' => ZERO},
15
+ 'video' => {'source' => ZERO},
16
+ 'pulse' => {'source' => ZERO},
17
+ 'duration' => {'source' => ZERO},
18
+ 'pattern' => {'source' => ZERO},
19
+ 'alternation' => {'source' => ZERO}
20
+ },
21
+ 'waveform' => {'data' => ZERO}
22
+ }
23
+
24
+ @channel = chan
25
+ end
26
+
27
+ def subcommands
28
+ @subcommands + @channel_commands
29
+ end
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,31 @@
1
+ class Oscope
2
+ module Relation
3
+ class Group < Base
4
+ SUBS = %w{state state= size size=}
5
+ def initialize scope, n
6
+ @scope = scope
7
+ @command = ":la:group#{n}"
8
+ end
9
+
10
+ def subcommands
11
+ SUBS
12
+ end
13
+
14
+ def state
15
+ query_full "#{@command}?"
16
+ end
17
+
18
+ def state= stat
19
+ write "#{@command} #{stat}"
20
+ end
21
+
22
+ def size
23
+ query_full "#{@command}:size?"
24
+ end
25
+
26
+ def size= len
27
+ write "#{@command}:size #{len}"
28
+ end
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,37 @@
1
+ class Oscope
2
+ module Relation
3
+ class Key < Base
4
+ COMM = ":key"
5
+ SUBS = %w{
6
+ lock run auto channel1 channel2 math ref f1 f2 f3 f4 f5 menu_off measure
7
+ cursor acquire display storage utility menu_time menu_trig trig_50 force
8
+ v_pos_inc v_pos_dec v_scale_inc v_scale_dec h_scale_inc h_scale_dec
9
+ trig_lvl_inc trig_lvl_dec h_pos_inc h_pos_dec prompt_v prompt_h function
10
+ p_function n_function la prompt_v_pos prompt_h_pos prompt_trig_lvl off
11
+ }
12
+
13
+ def initialize scope
14
+ @scope = scope
15
+ @command = COMM
16
+ end
17
+
18
+ def subcommands
19
+ SUBS
20
+ end
21
+
22
+ def method_missing meth, *args, &block
23
+ super unless SUBS.include? meth.to_s
24
+ write ":key:#{meth}"
25
+ end
26
+
27
+ def lock= state; write ":key:lock #{state}"; end
28
+ def lock; query_full ":key:lock"; end
29
+
30
+ def menu_time; write ":key:mnutime"; end
31
+ def menu_trig; write ":key:mnutrig"; end
32
+ def menu_time; write ":key:trig%50"; end
33
+ def p_function; write ':key:+function'; end
34
+ def n_function; write ':key:-function'; end
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,10 @@
1
+ class Oscope
2
+ module Relation
3
+ class Write < Base
4
+ attr_accessor argument
5
+ def initialize scope, command, arg = nil
6
+
7
+ end
8
+ end
9
+ end
10
+ end
@@ -0,0 +1,10 @@
1
+ class Oscope
2
+ module Relation
3
+ class Write < Base
4
+ def initialize scope, command, arg
5
+
6
+ end
7
+
8
+ end
9
+ end
10
+ end
@@ -0,0 +1,420 @@
1
+ require 'airby'
2
+
3
+ module Oscope
4
+ module Rigol
5
+ # @note The command +display+ has been replaced with +sdisplay+
6
+ class Ds1102d
7
+ def self.mode_hash modes, mode_comm, addl_comm = {}
8
+ Hash.new{|h,k| h[k] = modes[k].merge(mode_comm) if modes.has_key? k}.merge(addl_comm)
9
+ end
10
+
11
+ ZERO = [0]
12
+ ONE = [1]
13
+ ONE_ZERO = [0,1]
14
+
15
+ ALTERNATION = {
16
+ 'edge' => {'slope' => ZERO,'slope=' => ONE},
17
+ 'slope' => {
18
+ 'window' => ZERO,
19
+ 'level_a' => ZERO,
20
+ 'level_b' => ZERO,
21
+ 'window=' => ONE,
22
+ 'level_a=' => ONE,
23
+ 'level_b=' => ONE
24
+ },
25
+ 'video' => {
26
+ 'polarity' => ZERO,
27
+ 'standard' => ZERO,
28
+ 'line' => ZERO,
29
+ 'polarity=' => ONE,
30
+ 'standard=' => ONE,
31
+ 'line=' => ONE
32
+ }
33
+ }
34
+
35
+ MODE = {
36
+ 'edge' => {
37
+ 'slope' => ZERO,
38
+ 'sensitivity' => ZERO,
39
+ 'slope=' => ONE,
40
+ 'sensitivity=' => ONE
41
+ },
42
+ 'pulse' => {
43
+ 'mode' => ZERO,
44
+ 'sensitivity' => ZERO,
45
+ 'width' => ZERO,
46
+ 'mode=' => ONE,
47
+ 'sensitivity=' => ONE,
48
+ 'width=' => ONE
49
+ },
50
+ 'video' => {
51
+ 'line' => ZERO,
52
+ 'mode' => ZERO,
53
+ 'polarity' => ZERO,
54
+ 'sensitivity' => ZERO,
55
+ 'standard' => ZERO,
56
+ 'line=' => ONE,
57
+ 'mode=' => ONE,
58
+ 'polarity=' => ONE,
59
+ 'sensitivity=' => ONE,
60
+ 'standard=' => ONE
61
+ },
62
+ 'slope' => {
63
+ 'level_a' => ZERO,
64
+ 'level_b' => ZERO,
65
+ 'mode' => ZERO,
66
+ 'sensitivity' => ZERO,
67
+ 'time' => ZERO,
68
+ 'window' => ZERO,
69
+ 'level_a=' => ONE,
70
+ 'level_b=' => ONE,
71
+ 'mode=' => ONE,
72
+ 'sensitivity=' => ONE,
73
+ 'time=' => ONE,
74
+ 'window=' => ONE
75
+ },
76
+ 'pattern' => {
77
+ 'pattern' => ZERO,
78
+ 'pattern=' => [2,4]
79
+ },
80
+ 'duration' => {
81
+ 'pattern' => ZERO,
82
+ 'time' => ZERO,
83
+ 'qualifier' => ZERO,
84
+ 'pattern=' => [2],
85
+ 'time=' => ONE,
86
+ 'qualifier=' => ONE
87
+ },
88
+ 'alternation' => mode_hash( ALTERNATION, {
89
+ 'level' => ZERO,
90
+ 'time' => ZERO,
91
+ 'coupling' => ZERO,
92
+ 'sensitivity' => ZERO,
93
+ 'holdoff' => ZERO,
94
+ 'level=' => ONE,
95
+ 'time=' => ONE,
96
+ 'coupling=' => ONE,
97
+ 'sensitivity=' => ONE,
98
+ 'holdoff=' => ONE
99
+ }, {
100
+ 'type' => ZERO,
101
+ 'source' => ZERO,
102
+ 'time_scale' => ZERO,
103
+ 'time_offset' => ZERO
104
+ }
105
+ )
106
+ }
107
+ attr_accessor :session, :options
108
+
109
+ def self.open resource, opts = {}
110
+ ret = self.new resource, opts = {}
111
+ if block_given?
112
+ begin
113
+ yield ret
114
+ ensure
115
+ ret.close
116
+ end
117
+ end
118
+ ret
119
+ end
120
+
121
+ def open resource = nil
122
+ @resource = resource if resource
123
+ @session.open @resource
124
+
125
+ self
126
+ end
127
+
128
+ def initialize resource = nil, opts = {}
129
+ if opts[:session]
130
+ @session = opts.delete(:session)
131
+ elsif resource
132
+ @session = Airby::Session.new(resource)
133
+ else
134
+ @session = Airby::Session.new
135
+ @session.open @session.find_resources("?*").first unless opts[:no_auto]
136
+ end
137
+ @resource = @session.address
138
+
139
+ @session.buffer_grow opts[:buffer_size] if opts[:buffer_size]
140
+ @options = opts
141
+ end
142
+
143
+ def mode_hash modes, mode_comm, addl_comm = {}
144
+ self.class.mode_hash modes, mode_comm, addl_comm
145
+ end
146
+
147
+ # @group General Commands
148
+
149
+ # get device identification string
150
+ # @return [String]
151
+ def ident
152
+ @session.ident
153
+ end
154
+
155
+ # Reset device parameters
156
+ # @return [void]
157
+ def reset
158
+ @session.reset
159
+ end
160
+
161
+ # @endgroup
162
+
163
+ # @group System Commands
164
+
165
+ # initiates ongoing data collection within the device
166
+ def run
167
+ @session.write ':RUN'
168
+ end
169
+
170
+ # instructs oscilloscope to determine optimal display parameters for waveform
171
+ def auto
172
+ @session.write ':AUTO'
173
+ end
174
+
175
+ # writes a bmp to the USB disk of the current screen information
176
+ def hardcopy
177
+ @session.write ':HARDCOPY'
178
+ end
179
+
180
+ # @endgroup
181
+
182
+ # @group Acquire Commands
183
+
184
+ def acquire
185
+ Relation::Base.new self, ":ACQUIRE", {
186
+ 'type' => ZERO,
187
+ 'type=' => ONE,
188
+ 'mode' => ZERO,
189
+ 'mode=' => ONE,
190
+ 'averages' => ZERO,
191
+ 'averages=' => ONE,
192
+ 'sampling_rate' => ONE,
193
+ 'memdepth' => ZERO,
194
+ 'memdepth=' => ONE
195
+ }
196
+ end
197
+
198
+ # @endgroup
199
+
200
+ # @group Display Commands
201
+
202
+ def sdisplay
203
+ Relation::Base.new self, ':DISPLAY', {
204
+ 'type' => ZERO,
205
+ 'type=' => ONE,
206
+ 'grid' => ZERO,
207
+ 'grid=' => ONE,
208
+ 'persist' => ZERO,
209
+ 'persist=' => ONE,
210
+ 'mnudisplay' => ZERO,
211
+ 'mnudisplay=' => ONE,
212
+ 'mnustatus' => ZERO,
213
+ 'mnustatus=' => ONE,
214
+ 'clear' => ZERO,
215
+ 'brightness' => ZERO,
216
+ 'brightness=' => ONE,
217
+ 'intensity' => ZERO,
218
+ 'intensity=' => ONE
219
+ }
220
+ end
221
+
222
+ # @endgroup
223
+
224
+ # @group Timebase Commands
225
+ def timebase
226
+ Relation::Base.new self, ':TIMEBASE', {
227
+ 'mode' => ZERO,
228
+ 'mode=' => ONE,
229
+ 'delayed' => {
230
+ 'offset' => ZERO,
231
+ 'offset=' => ONE,
232
+ 'scale' => ZERO,
233
+ 'scale=' => ONE
234
+ },
235
+ 'offset' => ZERO,
236
+ 'offset=' => ONE,
237
+ 'scale' => ZERO,
238
+ 'scale=' => ONE,
239
+ 'format' => ZERO,
240
+ 'format=' => ONE
241
+ }
242
+ end
243
+ # @endgroup
244
+
245
+ # @group Trigger Commands
246
+ def trigger
247
+ hsh = mode_hash MODE, {
248
+ 'source' => ZERO,
249
+ 'level' => ZERO,
250
+ 'sweep' => ZERO,
251
+ 'coupling' => ZERO,
252
+ 'source=' => ONE,
253
+ 'level=' => ONE,
254
+ 'sweep=' => ONE,
255
+ 'coupling=' => ONE
256
+ },
257
+ {
258
+ 'mode' => ZERO,
259
+ 'holdoff' => ZERO,
260
+ 'status' => ZERO,
261
+ 'mode=' => ONE,
262
+ 'holdoff=' => ONE
263
+ }
264
+
265
+ Relation::Base.new self, ':TRIGGER', hsh
266
+ end
267
+
268
+ def trig_50
269
+ @session.write(':TRIG%50')
270
+ end
271
+
272
+ def force_trig
273
+ @session.write ':FORCETRIG'
274
+ end
275
+
276
+ # @endgroup
277
+
278
+ # @group Storage Commands
279
+ def storage
280
+ Relation::Base.new self, ':STORAGE', {'factory' => {'load' => ZERO}}
281
+ end
282
+ # @endgroup
283
+
284
+ # @group Math Commands
285
+ def fft
286
+ Relation::Base.new self, ':FFT', {'sdisplay' => ZERO, 'sdisplay=' => ONE}
287
+ end
288
+
289
+ def math
290
+ Relation::Base.new self, ':MATH', {
291
+ 'sdisplay' => ZERO,
292
+ 'operate' => ZERO,
293
+ 'sdisplay=' => ONE,
294
+ 'operate=' => ONE
295
+ }
296
+ end
297
+ # @endgroup
298
+
299
+ # @group Channel Commands
300
+ def channel chan
301
+ raise ArgumentError 'channel must be 1 or 2' unless chan == 1 || chan == 2
302
+ Relation::Base.new self, ":CHANNEL#{chan}", {
303
+ 'bw_limit' => ZERO,
304
+ 'coupling' => ZERO,
305
+ 'sdisplay' => ZERO,
306
+ 'invert' => ZERO,
307
+ 'offset' => ZERO,
308
+ 'probe' => ZERO,
309
+ 'scale' => ZERO,
310
+ 'filter' => ZERO,
311
+ 'memory_depth' => ZERO,
312
+ 'vernier' => ZERO,
313
+ 'bw_limit=' => ONE,
314
+ 'coupling=' => ONE,
315
+ 'sdisplay=' => ONE,
316
+ 'invert=' => ONE,
317
+ 'offset=' => ONE,
318
+ 'probe=' => ONE,
319
+ 'scale=' => ONE,
320
+ 'filter=' => ONE,
321
+ 'vernier=' => ONE
322
+ }
323
+ end
324
+ # @endgroup
325
+
326
+ # @group Measure Commands
327
+ def measure
328
+ ret = Relation::Base.new self, ':MEASURE', {
329
+ 'vpp' => ONE_ZERO,
330
+ 'vmax' => ONE_ZERO,
331
+ 'vmin' => ONE_ZERO,
332
+ 'vamplitude' => ONE_ZERO,
333
+ 'vtop' => ONE_ZERO,
334
+ 'vbase' => ONE_ZERO,
335
+ 'vaverage' => ONE_ZERO,
336
+ 'vrms' => ONE_ZERO,
337
+ 'overshoot' => ONE_ZERO,
338
+ 'preshoot' => ONE_ZERO,
339
+ 'frequency' => ONE_ZERO,
340
+ 'rise_time' => ONE_ZERO,
341
+ 'fall_time' => ONE_ZERO,
342
+ 'period' => ONE_ZERO,
343
+ 'pwidth' => ZERO,
344
+ 'nwidth' => ZERO,
345
+ 'pduty_cycle' => ZERO,
346
+ 'nduty_cycle' => ZERO,
347
+ 'pdelay' => ZERO,
348
+ 'ndelay' => ZERO,
349
+ 'total' => ZERO,
350
+ 'total=' => ONE,
351
+ 'source' => ZERO,
352
+ 'source=' => ONE
353
+ }
354
+ class << ret
355
+ def clear
356
+ @scope.write "#{@command}:CLEAR"
357
+ end
358
+ end
359
+ ret
360
+ end
361
+
362
+ # @endgroup
363
+
364
+ # @group Waveform Commands
365
+ def waveform
366
+ Relation::Base.new self, ':WAVEFORM', {'data' => ONE_ZERO, 'points' => {'mode' => ZERO, 'mode=' => ONE}}
367
+ end
368
+ # @endgroup
369
+
370
+ # @group Logic Analyzer Commands
371
+ def group(n)
372
+ raise ArgumentError 'group must be 1 or 2' unless n == 1 || n == 2
373
+ Relation::Group.new self, n
374
+ end
375
+
376
+ def logic_analyzer
377
+ Relation::Base.new self, ':la', {
378
+ 'sdisplay' => ZERO,
379
+ 'threshold' => ZERO,
380
+ 'position' => {'reset' => ZERO},
381
+ 'group1' => {'size' => ZERO},
382
+ 'group2' => {'size' => ZERO},
383
+ 'sdisplay=' => ONE,
384
+ 'threshold=' => ONE,
385
+ }
386
+ end
387
+
388
+ def digital(m)
389
+ raise ArgumentError 'digital channel must be 0..15' unless (m && m >=0 && m < 16)
390
+ Relation::Base.new self, ":digital#{m}", {
391
+ 'turn' => ZERO,
392
+ 'turn=' => ONE,
393
+ 'position' => ZERO,
394
+ 'position=' => ONE
395
+ }
396
+ end
397
+ # @endgroup
398
+
399
+ # @group Key Commands
400
+ def key
401
+ Relation::Key.new self
402
+ end
403
+ # @endgroup
404
+
405
+ # @group Other Commands
406
+ def counter
407
+ Relation::Base.new self, ":COUNTER", {'value' => ZERO, 'enable' => ZERO, 'enable=' => ONE}
408
+ end
409
+
410
+ def beep
411
+ Relation::Base.new self, ':beep', {'enable' => ZERO, 'enable=' => ONE, 'action' => ZERO}
412
+ end
413
+ # @endgroup
414
+
415
+ def connected?; !!@session.connected?; end
416
+ end
417
+ end
418
+ end
419
+
420
+ require 'oscope/relation'
metadata ADDED
@@ -0,0 +1,130 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: oscope
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.2.2
5
+ platform: ruby
6
+ authors:
7
+ - tduehr
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2015-02-03 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: airby
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: 0.1.0
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: 0.1.0
27
+ - !ruby/object:Gem::Dependency
28
+ name: ffi
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: 1.9.6
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: 1.9.6
41
+ - !ruby/object:Gem::Dependency
42
+ name: yard
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: 0.8.7
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: 0.8.7
55
+ - !ruby/object:Gem::Dependency
56
+ name: bundler
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - "~>"
60
+ - !ruby/object:Gem::Version
61
+ version: '1.0'
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - "~>"
67
+ - !ruby/object:Gem::Version
68
+ version: '1.0'
69
+ - !ruby/object:Gem::Dependency
70
+ name: jeweler
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - "~>"
74
+ - !ruby/object:Gem::Version
75
+ version: 1.8.7
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - "~>"
81
+ - !ruby/object:Gem::Version
82
+ version: 1.8.7
83
+ description: SCPI (IEEE 488.2) interface. Only the Rigol DS1102D oscilloscope is implemented
84
+ currently. All SCPI interfaces *should* be supported.
85
+ email: tduehr@gmail.com
86
+ executables: []
87
+ extensions: []
88
+ extra_rdoc_files:
89
+ - LICENSE
90
+ - README.md
91
+ files:
92
+ - Gemfile
93
+ - LICENSE
94
+ - README.md
95
+ - Rakefile
96
+ - VERSION.yml
97
+ - oscope.gemspec
98
+ - oscope/relation.rb
99
+ - oscope/relation/base.rb
100
+ - oscope/relation/channel.rb
101
+ - oscope/relation/group.rb
102
+ - oscope/relation/key.rb
103
+ - oscope/relation/query.rb
104
+ - oscope/relation/write.rb
105
+ - oscope/rigol/ds1102d.rb
106
+ homepage: http://github.com/tduehr/oscope
107
+ licenses:
108
+ - MIT
109
+ metadata: {}
110
+ post_install_message:
111
+ rdoc_options: []
112
+ require_paths:
113
+ - lib
114
+ required_ruby_version: !ruby/object:Gem::Requirement
115
+ requirements:
116
+ - - ">="
117
+ - !ruby/object:Gem::Version
118
+ version: '0'
119
+ required_rubygems_version: !ruby/object:Gem::Requirement
120
+ requirements:
121
+ - - ">="
122
+ - !ruby/object:Gem::Version
123
+ version: '0'
124
+ requirements: []
125
+ rubyforge_project:
126
+ rubygems_version: 2.4.5
127
+ signing_key:
128
+ specification_version: 4
129
+ summary: SCPI command interface
130
+ test_files: []