Repository: biomejs/biome (language: rust)

Issue:
📎 Port `number-no-trailing-zeros` from `stylelint-stylistic`
### Description

Add a new lint rule and port the functionality of `number-no-trailing-zeros` from `stylelint-stylistic`.

Suggested name: `noTrailingZeros`

Source: https://github.com/stylelint-stylistic/stylelint-stylistic/blob/main/lib/rules/number-no-trailing-zeros/README.md

**Want to contribute?** Lets you know you are interested! We will assign you to the issue to prevent several people to work on the same issue. Don't worry, we can unassign you later if you are no longer interested in the issue! Read our [contributing guide](https://github.com/biomejs/biome/blob/main/CONTRIBUTING.md) and [analyzer contributing guide](https://github.com/biomejs/biome/blob/main/crates/biome_analyze/CONTRIBUTING.md).


Discussion / hints:

Fix patch:
diff --git a/.changeset/improve_formatting_of_numbers_in_css.md b/.changeset/improve_formatting_of_numbers_in_css.md
new file mode 100644
index 000000000000..d18686b743b1
--- /dev/null
+++ b/.changeset/improve_formatting_of_numbers_in_css.md
@@ -0,0 +1,14 @@
+---
+"@biomejs/biome": patch
+---
+
+Fix [#5031](https://github.com/biomejs/biome/issues/5031). Improve CSS formatting for numbers:
+
+```diff
+.class {
+-	padding: .5em;
+-	marding: 1.0;
++	padding: 0.5em;	
++	marding: 1;
+}
+```
diff --git a/crates/biome_css_formatter/src/css/value/number.rs b/crates/biome_css_formatter/src/css/value/number.rs
index eef907352711..6dc86eb4aa67 100644
--- a/crates/biome_css_formatter/src/css/value/number.rs
+++ b/crates/biome_css_formatter/src/css/value/number.rs
@@ -1,11 +1,11 @@
 use crate::prelude::*;
 use biome_css_syntax::CssNumber;
-use biome_formatter::token::number::format_number_token;
+use biome_formatter::token::number::{format_number_token, NumberFormatOptions};
 
 #[derive(Debug, Clone, Default)]
 pub(crate) struct FormatCssNumber;
 impl FormatNodeRule<CssNumber> for FormatCssNumber {
     fn fmt_fields(&self, node: &CssNumber, f: &mut CssFormatter) -> FormatResult<()> {
-        format_number_token(&node.value_token()?).fmt(f)
+        format_number_token(&node.value_token()?, NumberFormatOptions::default()).fmt(f)
     }
 }
diff --git a/crates/biome_css_formatter/src/css/value/regular_dimension.rs b/crates/biome_css_formatter/src/css/value/regular_dimension.rs
index b713aa63f3b3..25e7f7fdff71 100644
--- a/crates/biome_css_formatter/src/css/value/regular_dimension.rs
+++ b/crates/biome_css_formatter/src/css/value/regular_dimension.rs
@@ -1,6 +1,9 @@
 use crate::{prelude::*, utils::string_utils::FormatTokenAsLowercase};
 use biome_css_syntax::{CssRegularDimension, CssRegularDimensionFields};
-use biome_formatter::write;
+use biome_formatter::{
+    token::number::{format_number_token, NumberFormatOptions},
+    write,
+};
 
 #[derive(Debug, Clone, Default)]
 pub(crate) struct FormatCssRegularDimension;
@@ -14,7 +17,7 @@ impl FormatNodeRule<CssRegularDimension> for FormatCssRegularDimension {
         write!(
             f,
             [
-                FormatTokenAsLowercase::from(value_token?),
+                format_number_token(&value_token?, NumberFormatOptions::default()),
                 FormatTokenAsLowercase::from(unit_token?),
             ]
         )
diff --git a/crates/biome_formatter/src/token/number.rs b/crates/biome_formatter/src/token/number.rs
index f28a44e8d0a4..0a2a9bd48204 100644
--- a/crates/biome_formatter/src/token/number.rs
+++ b/crates/biome_formatter/src/token/number.rs
@@ -6,11 +6,32 @@ use std::num::NonZeroUsize;
 use crate::prelude::*;
 use crate::{CstFormatContext, Format};
 
-pub fn format_number_token<L>(token: &SyntaxToken<L>) -> CleanedNumberLiteralText<L>
+#[derive(Debug, Default, Clone, Copy)]
+pub struct NumberFormatOptions {
+    /// Controls how numbers with trailing decimal zeroes are formatted.
+    ///
+    /// Prettier behaves differently when printing numbers like `x.00000` in different languages:
+    /// - In JavaScript: `x.00000` is printed as `x.0`
+    /// - In CSS: `x.00000` is printed as `x`
+    keep_one_trailing_decimal_zero: bool,
+}
+
+impl NumberFormatOptions {
+    pub fn keep_one_trailing_decimal_zero(self) -> Self {
+        Self {
+            keep_one_trailing_decimal_zero: true,
+        }
+    }
+}
+
+pub fn format_number_token<L>(
+    token: &SyntaxToken<L>,
+    options: NumberFormatOptions,
+) -> CleanedNumberLiteralText<L>
 where
     L: Language,
 {
-    CleanedNumberLiteralText { token }
+    CleanedNumberLiteralText { token, options }
 }
 
 pub struct CleanedNumberLiteralText<'token, L>
@@ -18,6 +39,7 @@ where
     L: Language,
 {
     token: &'token SyntaxToken<L>,
+    options: NumberFormatOptions,
 }
 
 impl<L, C> Format<C> for CleanedNumberLiteralText<'_, L>
@@ -29,7 +51,7 @@ where
         format_replaced(
             self.token,
             &syntax_token_cow_slice(
-                format_trimmed_number(self.token.text_trimmed()),
+                format_trimmed_number(self.token.text_trimmed(), self.options),
                 self.token,
                 self.token.text_trimmed_range().start(),
             ),
@@ -55,7 +77,7 @@ struct FormatNumberLiteralExponent {
     first_non_zero_index: Option<NonZeroUsize>,
 }
 // Regex-free version of https://github.com/prettier/prettier/blob/ca246afacee8e6d5db508dae01730c9523bbff1d/src/common/util.js#L341-L356
-fn format_trimmed_number(text: &str) -> Cow<str> {
+fn format_trimmed_number(text: &str, options: NumberFormatOptions) -> Cow<str> {
     use FormatNumberLiteralState::*;
 
     let text = text.to_ascii_lowercase_cow();
@@ -93,9 +115,8 @@ fn format_trimmed_number(text: &str) -> Cow<str> {
                 }),
                 (curr_index, Some(b'e') | None),
             ) => {
-                // The decimal part equals zero, ignore it completely.
-                // Caveat: Prettier still prints a single `.0` unless there was *only* a trailing dot.
-                if curr_index > dot_index + 1 {
+                // The decimal part equals zero, ignore it completely. However when the `keep_one_trailing_decimal_zero` option is enabled, print `.0` unless there was *only* a trailing dot.
+                if curr_index > dot_index + 1 && options.keep_one_trailing_decimal_zero {
                     cleaned_text.push_str(&text[copied_or_ignored_chars..=*dot_index]);
                     cleaned_text.push('0');
                 } else {
@@ -243,54 +264,107 @@ fn format_trimmed_number(text: &str) -> Cow<str> {
 mod tests {
     use std::borrow::Cow;
 
+    use crate::token::number::NumberFormatOptions;
+
     use super::format_trimmed_number;
 
     #[test]
     fn removes_unnecessary_plus_and_zeros_from_scientific_notation() {
-        assert_eq!("1e2", format_trimmed_number("1e02"));
-        assert_eq!("1e2", format_trimmed_number("1e+2"));
+        assert_eq!(
+            "1e2",
+            format_trimmed_number("1e02", NumberFormatOptions::default())
+        );
+        assert_eq!(
+            "1e2",
+            format_trimmed_number("1e+2", NumberFormatOptions::default())
+        );
     }
 
     #[test]
     fn removes_unnecessary_scientific_notation() {
-        assert_eq!("1", format_trimmed_number("1e0"));
-        assert_eq!("1", format_trimmed_number("1e-0"));
+        assert_eq!(
+            "1",
+            format_trimmed_number("1e0", NumberFormatOptions::default())
+        );
+        assert_eq!(
+            "1",
+            format_trimmed_number("1e-0", NumberFormatOptions::default())
+        );
     }
     #[test]
     fn does_not_get_bamboozled_by_hex() {
-        assert_eq!("0xe0", format_trimmed_number("0xe0"));
-        assert_eq!("0x10e0", format_trimmed_number("0x10e0"));
+        assert_eq!(
+            "0xe0",
+            format_trimmed_number("0xe0", NumberFormatOptions::default())
+        );
+        assert_eq!(
+            "0x10e0",
+            format_trimmed_number("0x10e0", NumberFormatOptions::default())
+        );
     }
 
     #[test]
     fn makes_sure_numbers_always_start_with_a_digit() {
-        assert_eq!("0.2", format_trimmed_number(".2"));
+        assert_eq!(
+            "0.2",
+            format_trimmed_number(".2", NumberFormatOptions::default())
+        );
     }
 
     #[test]
     fn removes_extraneous_trailing_decimal_zeroes() {
-        assert_eq!("0.1", format_trimmed_number("0.10"));
+        assert_eq!(
+            "0.1",
+            format_trimmed_number("0.10", NumberFormatOptions::default())
+        );
     }
     #[test]
     fn keeps_one_trailing_decimal_zero() {
-        assert_eq!("0.0", format_trimmed_number("0.00"));
+        assert_eq!(
+            "0.0",
+            format_trimmed_number(
+                "0.00",
+                NumberFormatOptions {
+                    keep_one_trailing_decimal_zero: true
+                }
+            )
+        );
     }
 
     #[test]
     fn removes_trailing_dot() {
-        assert_eq!("1", format_trimmed_number("1."));
+        assert_eq!(
+            "1",
+            format_trimmed_number("1.", NumberFormatOptions::default())
+        );
     }
 
     #[test]
     fn cleans_all_at_once() {
-        assert_eq!("0.0", format_trimmed_number(".00e-0"));
+        assert_eq!(
+            "0.0",
+            format_trimmed_number(
+                ".00e-0",
+                NumberFormatOptions {
+                    keep_one_trailing_decimal_zero: true
+                }
+            )
+        );
     }
 
     #[test]
     fn keeps_the_input_string_if_no_change_needed() {
         assert!(matches!(
-            format_trimmed_number("0.1e2"),
+            format_trimmed_number("0.1e2", NumberFormatOptions::default()),
             Cow::Borrowed("0.1e2")
         ));
     }
+
+    #[test]
+    fn keep_one_trailing_decimal_zero() {
+        assert_eq!(
+            "1",
+            format_trimmed_number("1.0", NumberFormatOptions::default())
+        );
+    }
 }
diff --git a/crates/biome_js_formatter/src/js/expressions/number_literal_expression.rs b/crates/biome_js_formatter/src/js/expressions/number_literal_expression.rs
index 08b6405f71d4..480ca14ccdf3 100644
--- a/crates/biome_js_formatter/src/js/expressions/number_literal_expression.rs
+++ b/crates/biome_js_formatter/src/js/expressions/number_literal_expression.rs
@@ -1,6 +1,7 @@
 use crate::prelude::*;
 
 use biome_formatter::token::number::format_number_token;
+use biome_formatter::token::number::NumberFormatOptions;
 use biome_js_syntax::parentheses::NeedsParentheses;
 use biome_js_syntax::JsNumberLiteralExpression;
 use biome_js_syntax::JsNumberLiteralExpressionFields;
@@ -15,7 +16,11 @@ impl FormatNodeRule<JsNumberLiteralExpression> for FormatJsNumberLiteralExpressi
         f: &mut JsFormatter,
     ) -> FormatResult<()> {
         let JsNumberLiteralExpressionFields { value_token } = node.as_fields();
-        format_number_token(&value_token?).fmt(f)
+        format_number_token(
+            &value_token?,
+            NumberFormatOptions::default().keep_one_trailing_decimal_zero(),
+        )
+        .fmt(f)
     }
 
     fn needs_parentheses(&self, item: &JsNumberLiteralExpression) -> bool {
diff --git a/crates/biome_js_formatter/src/js/objects/literal_member_name.rs b/crates/biome_js_formatter/src/js/objects/literal_member_name.rs
index b5afb8ad45fc..7b2799092488 100644
--- a/crates/biome_js_formatter/src/js/objects/literal_member_name.rs
+++ b/crates/biome_js_formatter/src/js/objects/literal_member_name.rs
@@ -1,7 +1,7 @@
 use crate::prelude::*;
 use crate::utils::{FormatLiteralStringToken, StringLiteralParentKind};
 
-use biome_formatter::token::number::format_number_token;
+use biome_formatter::token::number::{format_number_token, NumberFormatOptions};
 use biome_formatter::write;
 use biome_js_syntax::JsLiteralMemberNameFields;
 use biome_js_syntax::{JsLiteralMemberName, JsSyntaxKind};
@@ -25,7 +25,11 @@ impl FormatNodeRule<JsLiteralMemberName> for FormatJsLiteralMemberName {
                     )]
                 ]
             }
-            JsSyntaxKind::JS_NUMBER_LITERAL => format_number_token(&value).fmt(f),
+            JsSyntaxKind::JS_NUMBER_LITERAL => format_number_token(
+                &value,
+                NumberFormatOptions::default().keep_one_trailing_decimal_zero(),
+            )
+            .fmt(f),
             _ => write![f, [value.format()]],
         }
     }
diff --git a/crates/biome_js_formatter/src/ts/types/number_literal_type.rs b/crates/biome_js_formatter/src/ts/types/number_literal_type.rs
index 2faf0c221e6f..68b47a4611be 100644
--- a/crates/biome_js_formatter/src/ts/types/number_literal_type.rs
+++ b/crates/biome_js_formatter/src/ts/types/number_literal_type.rs
@@ -1,6 +1,6 @@
 use crate::prelude::*;
 
-use biome_formatter::token::number::format_number_token;
+use biome_formatter::token::number::{format_number_token, NumberFormatOptions};
 use biome_formatter::write;
 use biome_js_syntax::{TsNumberLiteralType, TsNumberLiteralTypeFields};
 
@@ -15,7 +15,13 @@ impl FormatNodeRule<TsNumberLiteralType> for FormatTsNumberLiteralType {
         } = node.as_fields();
         write![
             f,
-            [minus_token.format(), format_number_token(&literal_token?)]
+            [
+                minus_token.format(),
+                format_number_token(
+                    &literal_token?,
+                    NumberFormatOptions::default().keep_one_trailing_decimal_zero()
+                )
+            ]
         ]
     }
 }
diff --git a/crates/biome_json_formatter/src/json/value/number_value.rs b/crates/biome_json_formatter/src/json/value/number_value.rs
index e8330a34ceb5..9630a2c4908d 100644
--- a/crates/biome_json_formatter/src/json/value/number_value.rs
+++ b/crates/biome_json_formatter/src/json/value/number_value.rs
@@ -1,5 +1,5 @@
 use crate::prelude::*;
-use biome_formatter::token::number::format_number_token;
+use biome_formatter::token::number::{format_number_token, NumberFormatOptions};
 use biome_json_syntax::JsonNumberValue;
 
 #[derive(Debug, Clone, Default)]
@@ -7,6 +7,10 @@ pub(crate) struct FormatJsonNumberValue;
 
 impl FormatNodeRule<JsonNumberValue> for FormatJsonNumberValue {
     fn fmt_fields(&self, node: &JsonNumberValue, f: &mut JsonFormatter) -> FormatResult<()> {
-        format_number_token(&node.value_token()?).fmt(f)
+        format_number_token(
+            &node.value_token()?,
+            NumberFormatOptions::default().keep_one_trailing_decimal_zero(),
+        )
+        .fmt(f)
     }
 }


Test patch:
diff --git a/crates/biome_css_formatter/tests/specs/css/color/functional_colors.css.snap b/crates/biome_css_formatter/tests/specs/css/color/functional_colors.css.snap
index 4396cc3408dd..4a9e5d522ea4 100644
--- a/crates/biome_css_formatter/tests/specs/css/color/functional_colors.css.snap
+++ b/crates/biome_css_formatter/tests/specs/css/color/functional_colors.css.snap
@@ -58,7 +58,7 @@ Quote style: Double Quotes
 	color: rgb(255, 0, 153);
 	color: rgb(100%, 0%, 60%);
 	color: rgba(51, 170, 51, 0.1);
-	color: hsl(.75turn, 60%, 70%);
+	color: hsl(0.75turn, 60%, 70%);
 	color: hsla(240, 100%, 50%, 0.05);
 }
 
diff --git a/crates/biome_css_formatter/tests/specs/css/nesting/nesting.css.snap b/crates/biome_css_formatter/tests/specs/css/nesting/nesting.css.snap
index e9827cffac19..b2dbed13bb63 100644
--- a/crates/biome_css_formatter/tests/specs/css/nesting/nesting.css.snap
+++ b/crates/biome_css_formatter/tests/specs/css/nesting/nesting.css.snap
@@ -391,7 +391,7 @@ figure {
 		background: hsl(0 0% 0% / 50%);
 
 		& > p {
-			font-size: .9rem;
+			font-size: 0.9rem;
 		}
 	}
 }
diff --git a/crates/biome_css_formatter/tests/specs/css/number.css b/crates/biome_css_formatter/tests/specs/css/number.css
index 621dba6153ab..4acb3e6bde11 100644
--- a/crates/biome_css_formatter/tests/specs/css/number.css
+++ b/crates/biome_css_formatter/tests/specs/css/number.css
@@ -18,3 +18,7 @@ sup {
 	margin-right: calc(var(--bs-gutter-x) * -.5);
 	margin-left: calc(var(--bs-gutter-x) * -.5);
 }
+
+.bar {
+	opacity: 1.0;
+}
\ No newline at end of file
diff --git a/crates/biome_css_formatter/tests/specs/css/number.css.snap b/crates/biome_css_formatter/tests/specs/css/number.css.snap
index 3c0f13f57b5e..a5c571cf3676 100644
--- a/crates/biome_css_formatter/tests/specs/css/number.css.snap
+++ b/crates/biome_css_formatter/tests/specs/css/number.css.snap
@@ -26,6 +26,9 @@ sup {
 	margin-left: calc(var(--bs-gutter-x) * -.5);
 }
 
+.bar {
+	opacity: 1.0;
+}
 ```
 
 
@@ -49,13 +52,13 @@ hr {
 }
 
 h3 {
-	font-size: calc(1.3rem + .6vw);
+	font-size: calc(1.3rem + 0.6vw);
 }
 h4 {
-	font-size: calc(1.275rem + .3vw);
+	font-size: calc(1.275rem + 0.3vw);
 }
 sup {
-	top: -.5em;
+	top: -0.5em;
 }
 .row {
 	--bs-gutter-x: 1.5rem;
@@ -64,4 +67,8 @@ sup {
 	margin-right: calc(var(--bs-gutter-x) * -0.5);
 	margin-left: calc(var(--bs-gutter-x) * -0.5);
 }
+
+.bar {
+	opacity: 1;
+}
 ```
diff --git a/crates/biome_css_formatter/tests/specs/css/range/mid_value.css.snap b/crates/biome_css_formatter/tests/specs/css/range/mid_value.css.snap
index 598cd2500d45..2da88774f4e7 100644
--- a/crates/biome_css_formatter/tests/specs/css/range/mid_value.css.snap
+++ b/crates/biome_css_formatter/tests/specs/css/range/mid_value.css.snap
@@ -2,7 +2,6 @@
 source: crates/biome_formatter_test/src/snapshot_builder.rs
 info: css/range/mid_value.css
 ---
-
 # Input
 
 ```css
@@ -29,8 +28,6 @@ Quote style: Double Quotes
 
 ```css
 div {
-    padding: 1px 20px 555000.000vh   ;
+    padding: 1px 20px 555000vh   ;
 }
 ```
-
-
diff --git a/crates/biome_css_formatter/tests/specs/prettier/css/case/case.css.snap b/crates/biome_css_formatter/tests/specs/prettier/css/case/case.css.snap
index f1e451ab594f..179984ac6a7a 100644
--- a/crates/biome_css_formatter/tests/specs/prettier/css/case/case.css.snap
+++ b/crates/biome_css_formatter/tests/specs/prettier/css/case/case.css.snap
@@ -106,15 +106,6 @@ x-panel {
    background-color: orange;
  }
  
-@@ -53,7 +53,7 @@
-   max-width: 500px;
-   margin: 0 auto;
-   border-radius: 8px;
--  transition: transform 0.2s ease-out;
-+  transition: transform .2s ease-out;
- }
- :host([hidden]) {
-   display: none;
 ```
 
 # Output
@@ -175,7 +166,7 @@ x-panel {
   max-width: 500px;
   margin: 0 auto;
   border-radius: 8px;
-  transition: transform .2s ease-out;
+  transition: transform 0.2s ease-out;
 }
 :host([hidden]) {
   display: none;
diff --git a/crates/biome_css_formatter/tests/specs/prettier/css/color/functional-syntax.css.snap b/crates/biome_css_formatter/tests/specs/prettier/css/color/functional-syntax.css.snap
deleted file mode 100644
index ff161f63e79b..000000000000
--- a/crates/biome_css_formatter/tests/specs/prettier/css/color/functional-syntax.css.snap
+++ /dev/null
@@ -1,47 +0,0 @@
----
-source: crates/biome_formatter_test/src/snapshot_builder.rs
-info: css/color/functional-syntax.css
----
-# Input
-
-```css
-.foo {
-    color: rgb(255, 0, 153);
-    color: rgb(100%, 0%, 60%);
-    color: rgba(51, 170, 51, 0.1);
-    color: hsl(.75turn, 60%, 70%);
-    color: hsl(270 60% 50% / .15);
-    color: hsla(240, 100%, 50%, .05)
-}
-
-```
-
-
-# Prettier differences
-
-```diff
---- Prettier
-+++ Biome
-@@ -2,7 +2,7 @@
-   color: rgb(255, 0, 153);
-   color: rgb(100%, 0%, 60%);
-   color: rgba(51, 170, 51, 0.1);
--  color: hsl(0.75turn, 60%, 70%);
-+  color: hsl(.75turn, 60%, 70%);
-   color: hsl(270 60% 50% / 0.15);
-   color: hsla(240, 100%, 50%, 0.05);
- }
-```
-
-# Output
-
-```css
-.foo {
-  color: rgb(255, 0, 153);
-  color: rgb(100%, 0%, 60%);
-  color: rgba(51, 170, 51, 0.1);
-  color: hsl(.75turn, 60%, 70%);
-  color: hsl(270 60% 50% / 0.15);
-  color: hsla(240, 100%, 50%, 0.05);
-}
-```
diff --git a/crates/biome_css_formatter/tests/specs/prettier/css/grid/grid.css.snap b/crates/biome_css_formatter/tests/specs/prettier/css/grid/grid.css.snap
index 1c90c3b3559f..8d97756575eb 100644
--- a/crates/biome_css_formatter/tests/specs/prettier/css/grid/grid.css.snap
+++ b/crates/biome_css_formatter/tests/specs/prettier/css/grid/grid.css.snap
@@ -128,18 +128,7 @@ div {
 ```diff
 --- Prettier
 +++ Biome
-@@ -9,20 +9,20 @@
- /* numbers */
- div {
-   grid-template-columns:
--    [full-start] minmax(1.5em, 1fr)
--    [main-start] minmax(0.4ch, 75ch)
--    [main-end] minmax(1em, 1fr)
-+    [full-start] minmax(1.50em, 1fr)
-+    [main-start] minmax(.40ch, 75ch)
-+    [main-end] minmax(1em, 1.000fr)
-     [full-end];
- }
+@@ -17,12 +17,12 @@
  
  /* casing */
  div {
@@ -170,9 +159,9 @@ div {
 /* numbers */
 div {
   grid-template-columns:
-    [full-start] minmax(1.50em, 1fr)
-    [main-start] minmax(.40ch, 75ch)
-    [main-end] minmax(1em, 1.000fr)
+    [full-start] minmax(1.5em, 1fr)
+    [main-start] minmax(0.4ch, 75ch)
+    [main-end] minmax(1em, 1fr)
     [full-end];
 }
 
diff --git a/crates/biome_css_formatter/tests/specs/prettier/css/numbers/numbers.css.snap b/crates/biome_css_formatter/tests/specs/prettier/css/numbers/numbers.css.snap
index 6c828285bd20..25eb7617ac49 100644
--- a/crates/biome_css_formatter/tests/specs/prettier/css/numbers/numbers.css.snap
+++ b/crates/biome_css_formatter/tests/specs/prettier/css/numbers/numbers.css.snap
@@ -87,41 +87,6 @@ info: css/numbers/numbers.css
 ```diff
 --- Prettier
 +++ Biome
-@@ -1,4 +1,4 @@
--@supports (margin: 0.5px ".30px" 1e2px) {
-+@supports (margin: .5px ".30px" 1e+2px) {
-   a {
-     a: 0;
-     a: 1;
-@@ -44,21 +44,21 @@
- 
-     a: 1;
-     a: 1.005;
--    a: 1;
-+    a: 1.0;
-     a: 1.5;
-     a: 1.5;
- 
-     a: 0.005;
--    a: 0;
--    a: 0;
-+    a: 0.0;
-+    a: 0.0;
- 
-     a: 500600.001230045;
-     a: 1.005e60;
--    a: 1e60;
-+    a: 1.0e60;
-     a: 0.005e60;
--    a: 0e60;
--    a: 0e60;
--    a: 0e60;
-+    a: 0.0e60;
-+    a: 0.0e60;
-+    a: 0.0e60;
-     a: 0e60;
-     a: 0e60;
-     a: 500600.001230045e60;
 @@ -72,4 +72,4 @@
  @media only screen and (-webkit-min-device-pixel-ratio: 0.5),
    only screen and (min-device-pixel-ratio: 0.5) {
@@ -133,7 +98,7 @@ info: css/numbers/numbers.css
 # Output
 
 ```css
-@supports (margin: .5px ".30px" 1e+2px) {
+@supports (margin: 0.5px ".30px" 1e2px) {
   a {
     a: 0;
     a: 1;
@@ -179,21 +144,21 @@ info: css/numbers/numbers.css
 
     a: 1;
     a: 1.005;
-    a: 1.0;
+    a: 1;
     a: 1.5;
     a: 1.5;
 
     a: 0.005;
-    a: 0.0;
-    a: 0.0;
+    a: 0;
+    a: 0;
 
     a: 500600.001230045;
     a: 1.005e60;
-    a: 1.0e60;
+    a: 1e60;
     a: 0.005e60;
-    a: 0.0e60;
-    a: 0.0e60;
-    a: 0.0e60;
+    a: 0e60;
+    a: 0e60;
+    a: 0e60;
     a: 0e60;
     a: 0e60;
     a: 500600.001230045e60;