ui: Replace emdashes with hyphens across memscope
diff --git a/ui/src/plugins/dev.perfetto.Memscope/views/dashboard.ts b/ui/src/plugins/dev.perfetto.Memscope/views/dashboard.ts
index adc9401..70f3a69 100644
--- a/ui/src/plugins/dev.perfetto.Memscope/views/dashboard.ts
+++ b/ui/src/plugins/dev.perfetto.Memscope/views/dashboard.ts
@@ -318,7 +318,7 @@
         m(
           '.pf-memscope-snapshot-info__overrun',
           m('span.material-icons', 'warning'),
-          'Exceeds interval — increase snapshot rate',
+          'Exceeds interval - increase snapshot rate',
         ),
     );
   }
diff --git a/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/smaps_detail.ts b/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/smaps_detail.ts
index adf671c..b1edc0e 100644
--- a/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/smaps_detail.ts
+++ b/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/smaps_detail.ts
@@ -304,7 +304,7 @@
           {label: 'Swap', get: (r) => r.swap},
         ];
 
-    const fmtCell = (n: number) => (n > 0 ? formatBytes(n) : '—');
+    const fmtCell = (n: number) => (n > 0 ? formatBytes(n) : '-');
     const numCells = (r: SmapsPathRow) =>
       cols.map((c) => m('td.pf-memscope-table__num', fmtCell(c.get(r))));
     const sumCells = (list: SmapsPathRow[]) =>
diff --git a/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/bitmaps_section.ts b/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/bitmaps_section.ts
index ffd59f2..98c7b56 100644
--- a/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/bitmaps_section.ts
+++ b/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/bitmaps_section.ts
@@ -51,7 +51,7 @@
 
 const TITLE = 'What about bitmaps?';
 const SUBTITLE =
-  'Usually the largest and most reducible cost on Android — pulled out on ' +
+  'Usually the largest and most reducible cost on Android - pulled out on ' +
   'their own.';
 
 // One reachable-bitmap group at the latest dump: (dimensions, storage backing)
@@ -376,7 +376,7 @@
           retainerNote,
         ]
       : [
-          'This trace format does not record bitmap dimensions — only ' +
+          'This trace format does not record bitmap dimensions - only ' +
             'counts and sizes are available.',
         ];
 
diff --git a/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/java_section.ts b/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/java_section.ts
index 301995b..9743482 100644
--- a/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/java_section.ts
+++ b/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/java_section.ts
@@ -49,7 +49,7 @@
 
 const TITLE = 'How much Java memory did you use, and where did it go?';
 const SUBTITLE =
-  'From the full heap graph — complete and exact, with retention but no ' +
+  'From the full heap graph - complete and exact, with retention but no ' +
   'callstacks.';
 
 // Per-class aggregation row at a dump. All sizes/counts are reachable-only (see
@@ -555,7 +555,7 @@
         m('b', shortClassName(topRetainer.typeName)),
         ' retains ',
         m('b', formatBytes(retained)),
-        ' — ',
+        ' - ',
         m(
           'b',
           `${Math.round((retained / reachableTotal) * 100)}% of the ` +
@@ -614,7 +614,7 @@
         withDelta(
           c.reachableNativeSizeBytes > 0
             ? formatBytes(c.reachableNativeSizeBytes)
-            : '—',
+            : '-',
           b !== undefined
             ? c.reachableNativeSizeBytes - b.reachableNativeSizeBytes
             : undefined,
diff --git a/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/memory_map.ts b/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/memory_map.ts
index cfbdfc2..c72948a 100644
--- a/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/memory_map.ts
+++ b/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/memory_map.ts
@@ -65,7 +65,7 @@
 const MEMMAP_BLOCK_INFO: Record<string, string> = {
   'File-backed':
     'Memory backed by files on disk: code (.so/.oat), fonts and resources. ' +
-    'Mostly clean — the kernel can drop and re-read it under pressure.',
+    'Mostly clean - the kernel can drop and re-read it under pressure.',
   'Anonymous':
     'Memory not backed by any file: heaps and runtime allocations. This is ' +
     'what your process truly costs; it can only be reclaimed by swapping.',
@@ -79,14 +79,14 @@
     'Native allocator arenas (scudo / jemalloc / libc malloc / GWP-ASan) ' +
     'and the legacy [heap]. What malloc() costs you in resident memory.',
   'Java':
-    'Dalvik/ART managed heap and runtime spaces — everything the Java ' +
+    'Dalvik/ART managed heap and runtime spaces - everything the Java ' +
     'garbage collector manages.',
   'Thread stacks': 'Stack memory for every live thread in the process.',
   'Other anon':
     'Anonymous memory not attributable to a specific allocator: plain ' +
     'mmap() regions, untagged buffers, IPC shared memory.',
   'Native libs (.so)':
-    'Shared libraries (.so) mapped into the process — code and read-only ' +
+    'Shared libraries (.so) mapped into the process - code and read-only ' +
     'data, mostly clean and shared between processes.',
   'Java code (.jar/.oat)':
     'Compiled and bytecode Java artifacts (.jar/.oat/.odex/.vdex/.art) ' +
@@ -101,7 +101,7 @@
     'Native resident memory the profiler could not attribute: allocator ' +
     'metadata, fragmentation and allocations that predate the trace.',
   'Reachable':
-    'Java heap still reachable from GC roots at the nearest heap dump — live ' +
+    'Java heap still reachable from GC roots at the nearest heap dump - live ' +
     'objects the collector cannot free.',
   'Unreachable / other':
     'Managed heap not accounted for as reachable at the nearest dump: ' +
@@ -294,7 +294,7 @@
               },
               comparing && baseIdx !== undefined
                 ? `Diffing snapshot #${baseIdx + 1} → #${selIdx + 1}`
-                : `Snapshot #${selIdx + 1} — t=${snap.x.toFixed(0)}s`,
+                : `Snapshot #${selIdx + 1} - t=${snap.x.toFixed(0)}s`,
             ),
             m(
               'span.pf-memscope-memmap__section-hint',
diff --git a/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/native_section.ts b/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/native_section.ts
index 4cf558e..4d843a5 100644
--- a/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/native_section.ts
+++ b/ui/src/plugins/dev.perfetto.Memscope/views/landing_page/summary/native_section.ts
@@ -41,7 +41,7 @@
 
 const TITLE = 'How much native memory did you use, and where did it go?';
 const SUBTITLE =
-  "Aggregated by allocation callstack — the clearest signal when it's " +
+  "Aggregated by allocation callstack - the clearest signal when it's " +
   'available.';
 
 // One top-unreleased heapprofd callsite with its app-only frame chain
@@ -399,7 +399,7 @@
             {intent: Intent.Warning},
             'The native profiler only sees allocations made ',
             m('b', 'after'),
-            " tracing started — it can't explain the past. Leaks present " +
+            " tracing started - it can't explain the past. Leaks present " +
               'before t=0 are invisible here; trust the composition totals ' +
               'above for the full resident picture.',
           ),
diff --git a/ui/src/plugins/dev.perfetto.Memscope/views/tabs/processes.ts b/ui/src/plugins/dev.perfetto.Memscope/views/tabs/processes.ts
index ba32975..49c62c1 100644
--- a/ui/src/plugins/dev.perfetto.Memscope/views/tabs/processes.ts
+++ b/ui/src/plugins/dev.perfetto.Memscope/views/tabs/processes.ts
@@ -65,7 +65,7 @@
   height = 16,
 ): m.Children {
   if (values.length < 2) {
-    return m('span.pf-memscope-sparkline-empty', '—');
+    return m('span.pf-memscope-sparkline-empty', '-');
   }
   let min = values[0];
   let max = values[0];