{"id":19543299,"url":"https://github.com/uutils/ansi-width","last_synced_at":"2025-04-19T15:05:21.428Z","repository":{"id":206207471,"uuid":"716058301","full_name":"uutils/ansi-width","owner":"uutils","description":" Calculate the width of a string when printed to the terminal","archived":false,"fork":false,"pushed_at":"2024-09-20T05:27:29.000Z","size":25,"stargazers_count":3,"open_issues_count":1,"forks_count":1,"subscribers_count":4,"default_branch":"main","last_synced_at":"2024-11-11T03:18:14.035Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/uutils.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-11-08T11:33:56.000Z","updated_at":"2024-09-20T05:27:16.000Z","dependencies_parsed_at":null,"dependency_job_id":"61bd5f74-570d-483d-898b-8086450da112","html_url":"https://github.com/uutils/ansi-width","commit_stats":null,"previous_names":["uutils/ansi-width"],"tags_count":1,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/uutils%2Fansi-width","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/uutils%2Fansi-width/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/uutils%2Fansi-width/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/uutils%2Fansi-width/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/uutils","download_url":"https://codeload.github.com/uutils/ansi-width/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":233085614,"owners_count":18622801,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-11-11T03:18:16.331Z","updated_at":"2025-01-08T19:11:06.694Z","avatar_url":"https://github.com/uutils.png","language":"Rust","funding_links":[],"categories":[],"sub_categories":[],"readme":"[![Crates.io](https://img.shields.io/crates/v/ansi-width.svg)](https://crates.io/crates/ansi-width)\n[![Discord](https://img.shields.io/badge/discord-join-7289DA.svg?logo=discord\u0026longCache=true\u0026style=flat)](https://discord.gg/wQVJbvJ)\n[![License](http://img.shields.io/badge/license-MIT-blue.svg)](https://github.com/uutils/ansi-width/blob/main/LICENSE)\n[![dependency status](https://deps.rs/repo/github/uutils/ansi-width/status.svg)](https://deps.rs/repo/github/uutils/ansi-width)\n\n[![CodeCov](https://codecov.io/gh/uutils/ansi-width/branch/main/graph/badge.svg)](https://codecov.io/gh/uutils/ansi-width)\n\n# ANSI width\n\nMeasure the width of a string when printed to the terminal\n\nFor ASCII, this is identical to the length of the string in bytes. However,\nthere are 2 special cases:\n\n- Many unicode characters (CJK, emoji, etc.) span multiple columns.\n- ANSI escape codes should be ignored.\n\nThe first case is handled by the `unicode-width` crate. This function extends\nthat crate by ignoring ANSI escape codes.\n\n## Limitations\n\n- We cannot know the width of a `TAB` character in the terminal emulator.\n- Backspace is also treated as zero width.\n\n## A Primer on ANSI escape codes (and how this crate works)\n\nANSI codes are created using special character sequences in a string. These\nsequences start with the ESC character: `'\\x1b'`, followed by some other\ncharacter to determine the type of the escape code. That second character\ndetermines how long the sequence continues:\n\n- `ESC [`: until a character in the range `'\\x40'..='\\x7E'` is found.\n- `ESC ]`: until an `ST` is found.\n\nAn `ST` is a String Terminator and is given by the sequence `ESC \\` (or in Rust\nsyntax `'\\x1b\\x5c'`).\n\nThis is the subset of sequences that this library supports, since these are used\nby most applications that need this functionality. If you have a use case for\nother codes, please open an issue on the\n[GitHub repository](https://github.com/uutils/ansi-width).\n\n`ansi-width` does not parse the actual ANSI codes to improve performance, it can\nonly skip the ANSI codes.\n\n## Examples\n\n```rust\nuse ansi_width::ansi_width;\n\n// ASCII string\nassert_eq!(ansi_width(\"123456\"), 6);\n\n// Accents\nassert_eq!(ansi_width(\"café\"), 4);\n\n// Emoji (2 crab emoji)\nassert_eq!(ansi_width(\"🦀🦀\"), 4);\n\n// CJK characters (“Nǐ hǎo” or “Hello” in Chinese)\nassert_eq!(ansi_width(\"你好\"), 4);\n\n// ANSI colors\nassert_eq!(ansi_width(\"\\u{1b}[31mRed\\u{1b}[0m\"), 3);\n\n// ANSI hyperlink\nassert_eq!(\n    ansi_width(\"\\x1b]8;;http://example.com\\x1b\\\\This is a link\\x1b]8;;\\x1b\\\\\"),\n    14\n);\n```\n\n## Alternatives\n\n- [`str::len`](https://doc.rust-lang.org/std/primitive.str.html#method.len): Returns only the length in bytes and therefore only works for\n  ASCII characters.\n- [`unicode-width`](https://crates.io/crates/unicode-width): Does not take ANSI\n  characters into account by design (see\n  [this issue](https://github.com/unicode-rs/unicode-width/issues/24)). This\n  might be what you want if you don't care about ANSI codes. `unicode-width` is\n  used internally by this crate as well.\n- [`textwrap::core::display_width`](https://docs.rs/textwrap/latest/textwrap/core/fn.display_width.html):\n  Very similar functionality to this crate and it also supports hyperlinks since version 0.16.1. The \n  advantage of this crate is that it does not require pulling in the rest of `textwrap`'s functionality\n  (even though that functionality is excellent if you need it).\n- [`console::measure_text_width`](https://docs.rs/console/latest/console/fn.measure_text_width.html):\n  Similar to `textwrap` and very well-tested. However, it constructs a new\n  string internally without ANSI codes first and then measures the width of\n  that. The parsing is more robust than this crate though.\n\n## References\n\nThe information above is based on:\n\n- \u003chttps://en.wikipedia.org/wiki/ANSI_escape_code\u003e\n- \u003chttps://www.ecma-international.org/wp-content/uploads/ECMA-48_5th_edition_june_1991.pdf\u003e\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fuutils%2Fansi-width","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fuutils%2Fansi-width","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fuutils%2Fansi-width/lists"}