unicode-display_width 2.3.0 → 2.4.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 1fce5b196a16187b338dee6aaba7f4bf499bfc12eee213085c29296851671bc4
4
- data.tar.gz: 4554e159dbc6242ab9e8e285282a6bb4361d715997df21ef81b1d9c90665b4cd
3
+ metadata.gz: 26234cf1d4a965966cfab38151afe61c8f0a4c2d4f31fc006a319997af7bf076
4
+ data.tar.gz: eb5c24564cc94da5378b1d5b9065f90a70fcbcff50f914cc858634825694a544
5
5
  SHA512:
6
- metadata.gz: 57824a99da0e7db191264802c8cd01e47319b1387643f4d2ea269a5ab86cfdd2c3d188bcdddc71d56c3cecfd1538940bc68b7d870f424e39cf1d9849cf8123d1
7
- data.tar.gz: 655e5048a23f2576e076511d267cf5df7e382c7531e9f1e954c05e3aea5fbbf3975c1af6b4b7fadc4c433283a96afeb02e5621ca925af4bda605d9a6e3ffafeb
6
+ metadata.gz: 8687c39d5c62292c8d124ca9a3889c30f5f7d8e64b7e5ff79fc3b58137708bfeb844b36d32a5f73920f5e63a3cb60fc4a3f465f8505ccb8134e30d2445fc1af3
7
+ data.tar.gz: 37b073e36650f21bca8aa40cf9809a882fcd84642824ca8380542c80f3cb7a5f78c43eabe9abd6f09a73f6ee2cb5c49f60aa8b1ec72bcc8100cd411cdda15a5a
data/CHANGELOG.md CHANGED
@@ -1,5 +1,16 @@
1
1
  # CHANGELOG
2
2
 
3
+ ## 2.4.1
4
+
5
+ - Improve general performance!
6
+ - Further improve performance for ASCII strings
7
+
8
+ *You should really upgrade - it's much faster now!*
9
+
10
+ ## 2.4.0
11
+ - Improve performance for ASCII-only strings, by @fatkodima
12
+ - Require Ruby 2.4
13
+
3
14
  ## 2.3.0
4
15
 
5
16
  - Unicode 15.0
data/README.md CHANGED
@@ -1,12 +1,14 @@
1
1
  ## Unicode::DisplayWidth [![[version]](https://badge.fury.io/rb/unicode-display_width.svg)](https://badge.fury.io/rb/unicode-display_width) [<img src="https://github.com/janlelis/unicode-display_width/workflows/Test/badge.svg" />](https://github.com/janlelis/unicode-display_width/actions?query=workflow%3ATest)
2
2
 
3
- Determines the monospace display width of a string in Ruby. Implementation based on [EastAsianWidth.txt](https://www.unicode.org/Public/UNIDATA/EastAsianWidth.txt) and other data, 100% in Ruby. It does not rely on the OS vendor (like [wcwidth()](https://github.com/janlelis/wcswidth-ruby)) to provide an up-to-date method for measuring string width.
3
+ Determines the monospace display width of a string in Ruby. Useful for all kinds of terminal-based applications. Implementation based on [EastAsianWidth.txt](https://www.unicode.org/Public/UNIDATA/EastAsianWidth.txt) and other data, 100% in Ruby. It does not rely on the OS vendor (like [wcwidth()](https://github.com/janlelis/wcswidth-ruby)) to provide an up-to-date method for measuring string width.
4
4
 
5
5
  Unicode version: **15.0.0** (September 2022)
6
6
 
7
7
  Supported Rubies: **3.1**, **3.0**, **2.7**
8
8
 
9
- Old Rubies which might still work: **2.6**, **2.5**, **2.4**, **2.3**, **2.2**, **2.1**, **2.0**, **1.9**
9
+ Old Rubies which might still work: **2.6**, **2.5**, **2.4**
10
+
11
+ For even older Rubies, use version 2.3.0 of this gem: **2.3**, **2.2**, **2.1**, **2.0**, **1.9**
10
12
 
11
13
  ## Version 2.0 — Breaking Changes
12
14
 
@@ -39,7 +41,7 @@ Width | Characters | Comment
39
41
  -------|------------------------------|--------------------------------------------------
40
42
  X | (user defined) | Overwrites any other values
41
43
  -1 | `"\b"` | Backspace (total width never below 0)
42
- 0 | `"\0"`, `"\x05"`, `"\a"`, `"\n"`, `"\v"`, `"\f"`, `"\r"`, `"\x0E"`, `"\x0F"` | [C0 control codes](https://en.wikipedia.org/wiki/C0_and_C1_control_codes#C0_.28ASCII_and_derivatives.29) that do not change horizontal width
44
+ 0 | `"\0"`, `"\x05"`, `"\a"`, `"\n"`, `"\v"`, `"\f"`, `"\r"`, `"\x0E"`, `"\x0F"` | [C0 control codes](https://en.wikipedia.org/wiki/C0_and_C1_control_codes#C0_.28ASCII_and_derivatives.29) which do not change horizontal width
43
45
  1 | `"\u{00AD}"` | SOFT HYPHEN
44
46
  2 | `"\u{2E3A}"` | TWO-EM DASH
45
47
  3 | `"\u{2E3B}"` | THREE-EM DASH
@@ -89,6 +91,9 @@ You can overwrite how to handle specific code points by passing a hash (or even
89
91
  Unicode::DisplayWidth.of("a\tb", 1, "\t".ord => 10)) # => tab counted as 10, so result is 12
90
92
  ```
91
93
 
94
+ Please note that using overwrites disables some perfomance optimizations of this gem.
95
+
96
+
92
97
  #### Emoji Support
93
98
 
94
99
  Emoji width support is included, but in must be activated manually. It will adjust the string's size for modifier and zero-width joiner sequences. You also need to add the [unicode-emoji](https://github.com/janlelis/unicode-emoji) gem to your Gemfile:
@@ -2,7 +2,7 @@
2
2
 
3
3
  module Unicode
4
4
  class DisplayWidth
5
- VERSION = "2.3.0"
5
+ VERSION = "2.4.1"
6
6
  UNICODE_VERSION = "15.0.0"
7
7
  DATA_DIRECTORY = File.expand_path(File.dirname(__FILE__) + "/../../../data/")
8
8
  INDEX_FILENAME = DATA_DIRECTORY + "/display_width.marshal.gz"
@@ -5,23 +5,39 @@ require_relative "display_width/index"
5
5
 
6
6
  module Unicode
7
7
  class DisplayWidth
8
- DEPTHS = [0x10000, 0x1000, 0x100, 0x10].freeze
8
+ INITIAL_DEPTH = 0x10000
9
+ ASCII_NON_ZERO_REGEX = /[\0\x05\a\b\n\v\f\r\x0E\x0F]/
9
10
 
10
11
  def self.of(string, ambiguous = 1, overwrite = {}, options = {})
11
- res = string.codepoints.inject(0){ |total_width, codepoint|
12
- index_or_value = INDEX
13
- codepoint_depth_offset = codepoint
14
- DEPTHS.each{ |depth|
15
- index_or_value = index_or_value[codepoint_depth_offset / depth]
16
- codepoint_depth_offset = codepoint_depth_offset % depth
17
- break unless index_or_value.is_a? Array
18
- }
19
- width = index_or_value.is_a?(Array) ? index_or_value[codepoint_depth_offset] : index_or_value
12
+ # Optimization for ASCII-only strings without certain control symbols
13
+ if overwrite.empty? && string.ascii_only?
14
+ if string.match?(ASCII_NON_ZERO_REGEX)
15
+ res = string.gsub(ASCII_NON_ZERO_REGEX, "").size - string.count("\b")
16
+ return res < 0 ? 0 : res
17
+ else
18
+ return string.size
19
+ end
20
+ end
21
+
22
+ # Sum of all chars widths
23
+ res = string.codepoints.sum{ |codepoint|
24
+ next overwrite[codepoint] if overwrite[codepoint]
25
+ next 1 if codepoint > 15 && codepoint < 161 # very common
26
+
27
+ width = INDEX
28
+ depth = INITIAL_DEPTH
29
+ while (width = width[codepoint / depth]).is_a? Array
30
+ codepoint %= depth
31
+ depth /= 16
32
+ end
20
33
  width = ambiguous if width == :A
21
- total_width + (overwrite[codepoint] || width || 1)
34
+ width || 1
22
35
  }
23
36
 
37
+ # Substract emoji error
24
38
  res -= emoji_extra_width_of(string, ambiguous, overwrite) if options[:emoji]
39
+
40
+ # Return result + prevent negative lengths
25
41
  res < 0 ? 0 : res
26
42
  end
27
43
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: unicode-display_width
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.3.0
4
+ version: 2.4.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jan Lelis
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-09-14 00:00:00.000000000 Z
11
+ date: 2023-01-03 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rspec
@@ -62,7 +62,7 @@ homepage: https://github.com/janlelis/unicode-display_width
62
62
  licenses:
63
63
  - MIT
64
64
  metadata:
65
- changelog_uri: https://github.com/janlelis/unicode-display_width/blob/master/CHANGELOG.md
65
+ changelog_uri: https://github.com/janlelis/unicode-display_width/blob/main/CHANGELOG.md
66
66
  source_code_uri: https://github.com/janlelis/unicode-display_width
67
67
  bug_tracker_uri: https://github.com/janlelis/unicode-display_width/issues
68
68
  rubygems_mfa_required: 'true'
@@ -74,14 +74,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
74
74
  requirements:
75
75
  - - ">="
76
76
  - !ruby/object:Gem::Version
77
- version: 1.9.3
77
+ version: 2.4.0
78
78
  required_rubygems_version: !ruby/object:Gem::Requirement
79
79
  requirements:
80
80
  - - ">="
81
81
  - !ruby/object:Gem::Version
82
82
  version: '0'
83
83
  requirements: []
84
- rubygems_version: 3.3.7
84
+ rubygems_version: 3.4.1
85
85
  signing_key:
86
86
  specification_version: 4
87
87
  summary: Determines the monospace display width of a string in Ruby.