win 0.0.3 → 0.0.4
Sign up to get free protection for your applications and to get access to all the features.
- data/VERSION +1 -1
- data/lib/win/library.rb +33 -14
- data/lib/win/window.rb +4 -1
- data/spec/win/window_spec.rb +8 -0
- data/win.gemspec +2 -2
- metadata +2 -2
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.0.
|
1
|
+
0.0.4
|
data/lib/win/library.rb
CHANGED
@@ -1,6 +1,12 @@
|
|
1
1
|
require 'ffi'
|
2
2
|
require 'win/extensions'
|
3
3
|
|
4
|
+
# Related Windows API functions are grouped by topic and defined in separate namespaces (modules),
|
5
|
+
# that also contain related constants and convenience methods. For example, Win::DDE module
|
6
|
+
# contains only functions related to DDE protocol such as DdeInitialize() as well as constants
|
7
|
+
# such as DMLERR_NO_ERROR, APPCLASS_STANDARD, etc. So if you need only DDE-related functions,
|
8
|
+
# there is no need to load all the other modules, clogging your namespaces - just require 'win/dde'
|
9
|
+
# and be done with it. Win is just a top level namespace (container) that holds all the other modules.
|
4
10
|
module Win
|
5
11
|
|
6
12
|
module Errors # :nodoc:
|
@@ -11,12 +17,18 @@ module Win
|
|
11
17
|
end
|
12
18
|
end
|
13
19
|
|
20
|
+
# WIN::Library is a module that extends FFI::Library and is used to connect to Windows API functions
|
21
|
+
# and wrap them into Ruby methods using 'function' declaration. If you do not see your favorite Windows
|
22
|
+
# API functions among those already defined, you can easily 'include Win::Library’ into your module
|
23
|
+
# and declare them using ‘function’ class method (macro) - it does a lot of heavy lifting for you and
|
24
|
+
# can be customized with options and code blocks to give you reusable API wrapper methods with the exact
|
25
|
+
# behavior you need.
|
14
26
|
module Library
|
15
27
|
|
16
|
-
# API wrapper for
|
28
|
+
# Win::Library::API is a wrapper for callable function API object that mimics Win32::API
|
17
29
|
class API
|
18
30
|
|
19
|
-
# The name of the DLL that
|
31
|
+
# The name of the DLL(s) that export this API function
|
20
32
|
attr_reader :dll_name
|
21
33
|
|
22
34
|
# Ruby namespace (module) where this API function is attached
|
@@ -25,9 +37,8 @@ module Win
|
|
25
37
|
# The name of the function passed to the constructor
|
26
38
|
attr_reader :function_name
|
27
39
|
|
28
|
-
# The name of the actual function
|
29
|
-
#
|
30
|
-
# effective function name would be either 'GetUserNameA' or 'GetUserNameW'.
|
40
|
+
# The name of the actual Windows API function. For example, if you passed 'GetUserName' to the
|
41
|
+
# constructor, then the effective function name would be either 'GetUserNameA' or 'GetUserNameW'.
|
31
42
|
attr_accessor :effective_function_name
|
32
43
|
|
33
44
|
# The prototype, returned as an array of FFI types
|
@@ -45,6 +56,7 @@ module Win
|
|
45
56
|
@dll_name = dll_name
|
46
57
|
end
|
47
58
|
|
59
|
+
# Calls underlying CamelCase Windows API function with supplied args
|
48
60
|
def call( *args )
|
49
61
|
@namespace.send(@function_name.to_sym, *args)
|
50
62
|
end
|
@@ -273,22 +285,25 @@ module Win
|
|
273
285
|
# Defines new method wrappers for Windows API function call:
|
274
286
|
# - Defines method with original (CamelCase) API function name and original signature (matches MSDN description)
|
275
287
|
# - Defines method with snake_case name (converted from CamelCase function name) with enhanced API signature
|
276
|
-
# When
|
277
|
-
#
|
278
|
-
#
|
288
|
+
# When defined snake_case method is called, it converts the arguments you provided into ones required by
|
289
|
+
# original API (adding defaults, mute and transitory args as necessary), executes API function call
|
290
|
+
# and (optionally) transforms the result before returning it. If a block is attached to
|
291
|
+
# method invocation, raw result is yielded to this block before final transformation take place
|
279
292
|
# - Defines aliases for enhanced method with more Rubyesque names for getters, setters and tests:
|
280
293
|
# GetWindowText -> window_test, SetWindowText -> window_text=, IsZoomed -> zoomed?
|
281
294
|
#
|
282
|
-
# You may modify default behavior of defined method by providing optional &
|
283
|
-
# If you do so,
|
284
|
-
# object, arguments and (optional) runtime block
|
285
|
-
#
|
295
|
+
# You may modify default behavior of defined method by providing optional &def_block to function.
|
296
|
+
# If you do so, snake_case method is defined based on your def_block. It receives callable API
|
297
|
+
# object for function being defined, arguments and (optional) runtime block with which the method
|
298
|
+
# will be called. Results coming from &def_block are then transformed and returned.
|
299
|
+
# So, your &def_block should define all the behavior of defined method. You can use define_block to:
|
286
300
|
# - Change original signature of API function, provide argument defaults, check argument types
|
287
|
-
# - Pack arguments into strings for [in] or [in/out] parameters that expect a pointer
|
288
|
-
# - Allocate
|
301
|
+
# - Pack arguments into strings/structs for [in] or [in/out] parameters that expect a pointer
|
302
|
+
# - Allocate buffers/structs for pointers required by API functions [out] parameters
|
289
303
|
# - Unpack [out] and [in/out] parameters returned as pointers
|
290
304
|
# - Explicitly return results of API call that are returned in [out] and [in/out] parameters
|
291
305
|
# - Convert attached runtime blocks into callback functions and stuff them into [in] callback parameters
|
306
|
+
# - do other stuff that you think is appropriate to make Windows API function behavior more Ruby-like
|
292
307
|
#
|
293
308
|
# Accepts following options:
|
294
309
|
# :dll:: Use this dll instead of default 'user32'
|
@@ -395,6 +410,10 @@ module Win
|
|
395
410
|
args.any?{|arg| arg == 0 } ? args.map{||nil} : args
|
396
411
|
end
|
397
412
|
|
413
|
+
##
|
414
|
+
# :singleton-method: namespace
|
415
|
+
# This method is meta-generated when Win::Library module is included into other module/class
|
416
|
+
# it holds reference to including module for use by Win::Library::API and class methods.
|
398
417
|
end
|
399
418
|
|
400
419
|
def self.included(klass)
|
data/lib/win/window.rb
CHANGED
@@ -1,6 +1,9 @@
|
|
1
1
|
require 'win/library'
|
2
2
|
|
3
3
|
module Win
|
4
|
+
|
5
|
+
# Contains constants, functions and wrappers related to Windows manipulation
|
6
|
+
#
|
4
7
|
module Window
|
5
8
|
include Win::Library
|
6
9
|
|
@@ -155,7 +158,6 @@ module Win
|
|
155
158
|
num_chars = api.call(*args)
|
156
159
|
return nil if num_chars == 0
|
157
160
|
string = string.force_encoding('utf-16LE').encode(encode) if encode
|
158
|
-
p string
|
159
161
|
string.rstrip
|
160
162
|
end
|
161
163
|
end
|
@@ -474,6 +476,7 @@ module Win
|
|
474
476
|
return d
|
475
477
|
end
|
476
478
|
|
479
|
+
# Thin wrapper around window handle
|
477
480
|
class Window
|
478
481
|
include Win::Window
|
479
482
|
extend Win::Window
|
data/spec/win/window_spec.rb
CHANGED
@@ -237,9 +237,11 @@ module WinWindowTest
|
|
237
237
|
spec{ use{ GetWindowText(any_handle, buffer = "\00"* 1024, buffer.size)}}
|
238
238
|
# Improved with block to accept window handle as a single arg and return (rstripped) text string
|
239
239
|
spec{ use{ text = get_window_text(handle = 0)}}
|
240
|
+
spec{ use{ text = window_text(handle = 0)}}
|
240
241
|
# Unicode version of get_window_text (strings returned encoded as utf-8)
|
241
242
|
spec{ use{ GetWindowTextW(any_handle, buffer = "\00"* 1024, buffer.size)}}
|
242
243
|
spec{ use{ text = get_window_text_w(any_handle)}} # result encoded as utf-8
|
244
|
+
spec{ use{ text = window_text_w(handle = 0)}}
|
243
245
|
|
244
246
|
it 'returns nil if incorrect window handle given' do
|
245
247
|
get_window_text(not_a_handle).should == nil
|
@@ -250,6 +252,8 @@ module WinWindowTest
|
|
250
252
|
test_app do |app|
|
251
253
|
get_window_text(app.handle).should == TEST_WIN_TITLE
|
252
254
|
get_window_text_w(app.handle).should == TEST_WIN_TITLE
|
255
|
+
window_text(app.handle).should == TEST_WIN_TITLE
|
256
|
+
window_text_w(app.handle).should == TEST_WIN_TITLE
|
253
257
|
end
|
254
258
|
end
|
255
259
|
end
|
@@ -258,14 +262,18 @@ module WinWindowTest
|
|
258
262
|
spec{ use{ GetClassName(any_handle, buffer = "\00"* 1024, buffer.size)}}
|
259
263
|
# Improved with block to accept window handle as a single arg and return class name string
|
260
264
|
spec{ use{ class_name = get_class_name(any_handle)}}
|
265
|
+
spec{ use{ class_name = class_name(any_handle)}}
|
261
266
|
# Unicode version of get_class_name (strings returned encoded as utf-8)
|
262
267
|
spec{ use{ GetClassNameW(any_handle, buffer = "\00"* 1024, buffer.size)}}
|
263
268
|
spec{ use{ class_name = get_class_name_w(handle = 0)}} # result encoded as utf-8
|
269
|
+
spec{ use{ class_name = class_name_w(any_handle)}}
|
264
270
|
|
265
271
|
it 'returns correct window class name' do
|
266
272
|
test_app do |app|
|
267
273
|
get_class_name(app.handle).should == TEST_WIN_CLASS
|
268
274
|
get_class_name_w(app.handle).should == TEST_WIN_CLASS
|
275
|
+
class_name(app.handle).should == TEST_WIN_CLASS
|
276
|
+
class_name_w(app.handle).should == TEST_WIN_CLASS
|
269
277
|
end
|
270
278
|
end
|
271
279
|
end
|
data/win.gemspec
CHANGED
@@ -5,11 +5,11 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = %q{win}
|
8
|
-
s.version = "0.0.
|
8
|
+
s.version = "0.0.4"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["arvicco"]
|
12
|
-
s.date = %q{2010-02-
|
12
|
+
s.date = %q{2010-02-11}
|
13
13
|
s.description = %q{A collection of Windows functions predefined for you using FFI}
|
14
14
|
s.email = %q{arvitallian@gmail.com}
|
15
15
|
s.extra_rdoc_files = [
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: win
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- arvicco
|
@@ -9,7 +9,7 @@ autorequire:
|
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
11
|
|
12
|
-
date: 2010-02-
|
12
|
+
date: 2010-02-11 00:00:00 +03:00
|
13
13
|
default_executable:
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|