@maccesar/titools 2.8.0 → 2.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +1 -1
- package/skills/purgetss/SKILL.md +25 -0
- package/skills/purgetss/references/EXAMPLES.md +86 -24
- package/skills/purgetss/references/app-branding.md +412 -0
- package/skills/purgetss/references/appearance-module.md +161 -0
- package/skills/purgetss/references/apply-directive.md +87 -31
- package/skills/purgetss/references/arbitrary-values.md +4 -0
- package/skills/purgetss/references/class-categories.md +10 -7
- package/skills/purgetss/references/class-index.md +25 -18
- package/skills/purgetss/references/cli-commands.md +219 -8
- package/skills/purgetss/references/configurable-properties.md +11 -7
- package/skills/purgetss/references/custom-rules.md +7 -3
- package/skills/purgetss/references/customization-deep-dive.md +52 -4
- package/skills/purgetss/references/dynamic-component-creation.md +29 -14
- package/skills/purgetss/references/grid-layout.md +20 -8
- package/skills/purgetss/references/icon-fonts.md +4 -0
- package/skills/purgetss/references/installation-setup.md +3 -8
- package/skills/purgetss/references/ios-large-titles.md +141 -0
- package/skills/purgetss/references/migration-guide.md +162 -25
- package/skills/purgetss/references/multi-density-images.md +363 -0
- package/skills/purgetss/references/opacity-modifier.md +4 -0
- package/skills/purgetss/references/performance-tips.md +5 -0
- package/skills/purgetss/references/platform-modifiers.md +4 -0
- package/skills/purgetss/references/semantic-colors.md +386 -0
- package/skills/purgetss/references/smart-mappings.md +50 -28
- package/skills/purgetss/references/tikit-components.md +3 -1
- package/skills/purgetss/references/titanium-resets.md +46 -15
- package/skills/purgetss/references/ui-ux-design.md +32 -6
package/package.json
CHANGED
package/skills/purgetss/SKILL.md
CHANGED
|
@@ -112,6 +112,20 @@ purgetss create 'MyApp' -d -v fa
|
|
|
112
112
|
# -v: Copy icon fonts (fa, mi, ms, f7)
|
|
113
113
|
```
|
|
114
114
|
|
|
115
|
+
## What's New in v7.6.0
|
|
116
|
+
|
|
117
|
+
- `brand` command — complete Titanium branding set (launcher icons, adaptive, iOS 18+ Dark/Tinted, marketplace) from logos in `./purgetss/brand/`
|
|
118
|
+
- `images` command — multi-density UI images (Android res-*dpi + iPhone @1x/@2x/@3x) from `./purgetss/images/`
|
|
119
|
+
- `semantic` command — Titanium semantic colors for Light/Dark mode (palette mode + single mode)
|
|
120
|
+
- `brand:` and `images:` config sections auto-injected into older configs
|
|
121
|
+
- Percentages as strings (`'15%'`) for self-documenting clarity in brand/images configs
|
|
122
|
+
|
|
123
|
+
## What's New in v7.5.3
|
|
124
|
+
|
|
125
|
+
- Appearance module — Light/Dark/System mode switching with persistence
|
|
126
|
+
- Default font family classes (`font-sans`, `font-serif`, `font-mono`) generated automatically with platform-appropriate values
|
|
127
|
+
- XML validation — detects illegal `--` inside XML comments during pre-validation
|
|
128
|
+
|
|
115
129
|
## What's New in v7.5.0
|
|
116
130
|
|
|
117
131
|
- `extend` support for Window, View, and ImageView in `config.cjs`
|
|
@@ -380,6 +394,8 @@ purgetss create 'MyApp' -d -v fa
|
|
|
380
394
|
> - **[Class Index](references/class-index.md)** - Naming conventions, 416-property table, prohibited classes, verification commands (LOAD FIRST when unsure about a class)
|
|
381
395
|
> - **[Class Categories](references/class-categories.md)** - Complete prefix inventory by category (layout, colors, typography, states, etc.)
|
|
382
396
|
> - **[Dynamic Component Creation](references/dynamic-component-creation.md)** - `$.UI.create()` and `Alloy.createStyle()` for creating components in Controllers (READ FIRST for dynamic components)
|
|
397
|
+
> - **[Appearance Module](references/appearance-module.md)** - Light/Dark/System mode switching with persistence (v7.5.3)
|
|
398
|
+
> - **[Semantic Colors](references/semantic-colors.md)** - Titanium semantic colors for Light/Dark mode via `semantic` command (v7.6.0)
|
|
383
399
|
>
|
|
384
400
|
> ### Setup & Configuration
|
|
385
401
|
> - [Installation & Setup](references/installation-setup.md) - First run, VS Code, LiveView
|
|
@@ -392,6 +408,10 @@ purgetss create 'MyApp' -d -v fa
|
|
|
392
408
|
> - [Apply Directive](references/apply-directive.md) - Extracting utility combinations
|
|
393
409
|
> - [Configurable Properties](references/configurable-properties.md) - All 80+ customizable properties
|
|
394
410
|
>
|
|
411
|
+
> ### Appearance & Theming
|
|
412
|
+
> - **[Appearance Module](references/appearance-module.md)** - Light/Dark/System mode switching with persistence (v7.5.3)
|
|
413
|
+
> - **[Semantic Colors](references/semantic-colors.md)** - `semantic` command + runtime usage for Light/Dark mode (v7.6.0)
|
|
414
|
+
>
|
|
395
415
|
> ### Layout & Styling
|
|
396
416
|
> - **[UI/UX Design Patterns](references/ui-ux-design.md)** - Complete guide to mobile UI components with PurgeTSS (cards, lists, forms, buttons, navigation, modals, accessibility)
|
|
397
417
|
> - [Grid Layout System](references/grid-layout.md) - 12-column grid, responsive layouts
|
|
@@ -400,6 +420,11 @@ purgetss create 'MyApp' -d -v fa
|
|
|
400
420
|
> - [Platform Modifiers](references/platform-modifiers.md) - ios:, android:, tablet:, handheld:
|
|
401
421
|
> - [Opacity Modifier](references/opacity-modifier.md) - Color transparency with /50 syntax
|
|
402
422
|
> - [Titanium Resets](references/titanium-resets.md) - Default styles for Ti elements
|
|
423
|
+
> - [iOS Large Titles](references/ios-large-titles.md) - Best practice for iOS Large Title navigation
|
|
424
|
+
>
|
|
425
|
+
> ### App Assets
|
|
426
|
+
> - [App Branding](references/app-branding.md) - `brand` command for launcher icons, adaptive, iOS 18+ Dark/Tinted, marketplace assets (v7.6.0)
|
|
427
|
+
> - [Multi-Density Images](references/multi-density-images.md) - `images` command for Android res-*dpi + iPhone @1x/@2x/@3x UI images (v7.6.0)
|
|
403
428
|
>
|
|
404
429
|
> ### Performance
|
|
405
430
|
> - [Performance Tips](references/performance-tips.md) - Optimizing PurgeTSS apps (bridge crossings, ListView, animations)
|
|
@@ -2,7 +2,11 @@
|
|
|
2
2
|
|
|
3
3
|
Complete examples of common patterns with anti-patterns and correct implementations.
|
|
4
4
|
|
|
5
|
-
##
|
|
5
|
+
## Community-Discovered Patterns
|
|
6
|
+
|
|
7
|
+
The examples below catalog anti-patterns observed in real Titanium + PurgeTSS projects, paired with the correct approach. They are not exhaustive rules from official docs — they reflect pitfalls the community has hit often enough to warrant dedicated guidance.
|
|
8
|
+
|
|
9
|
+
### Titanium Layout Patterns
|
|
6
10
|
|
|
7
11
|
> **🚨 NO FLEXBOX IN TITANIUM**
|
|
8
12
|
> Titanium does NOT support CSS Flexbox. All examples use `horizontal`, `vertical`, or `composite` layouts.
|
|
@@ -108,7 +112,7 @@ Complete examples of common patterns with anti-patterns and correct implementati
|
|
|
108
112
|
|
|
109
113
|
---
|
|
110
114
|
|
|
111
|
-
|
|
115
|
+
### Manual .tss Files Anti-Pattern
|
|
112
116
|
|
|
113
117
|
**❌ WRONG (Creating manual .tss files):**
|
|
114
118
|
```xml
|
|
@@ -158,7 +162,7 @@ alloy compile
|
|
|
158
162
|
|
|
159
163
|
---
|
|
160
164
|
|
|
161
|
-
|
|
165
|
+
### Grid with Percentages
|
|
162
166
|
|
|
163
167
|
**❌ WRONG (Children with % widths, parent without w-screen):**
|
|
164
168
|
```xml
|
|
@@ -179,7 +183,7 @@ alloy compile
|
|
|
179
183
|
|
|
180
184
|
---
|
|
181
185
|
|
|
182
|
-
|
|
186
|
+
### Gap Usage
|
|
183
187
|
|
|
184
188
|
**❌ WRONG (gap adds margin all around, breaks % widths):**
|
|
185
189
|
```xml
|
|
@@ -200,7 +204,7 @@ alloy compile
|
|
|
200
204
|
|
|
201
205
|
---
|
|
202
206
|
|
|
203
|
-
|
|
207
|
+
### Padding on Container Views
|
|
204
208
|
|
|
205
209
|
**❌ WRONG (Padding on Views doesn't work in Titanium):**
|
|
206
210
|
```xml
|
|
@@ -220,7 +224,7 @@ alloy compile
|
|
|
220
224
|
|
|
221
225
|
---
|
|
222
226
|
|
|
223
|
-
|
|
227
|
+
### `w-full` vs `w-screen`
|
|
224
228
|
|
|
225
229
|
**❌ WRONG (Using percentage-based width):**
|
|
226
230
|
```xml
|
|
@@ -244,7 +248,7 @@ alloy compile
|
|
|
244
248
|
|
|
245
249
|
---
|
|
246
250
|
|
|
247
|
-
|
|
251
|
+
### `rounded-full` Without Size
|
|
248
252
|
|
|
249
253
|
**❌ WRONG (rounded-full alone doesn't exist):**
|
|
250
254
|
```xml
|
|
@@ -266,7 +270,7 @@ alloy compile
|
|
|
266
270
|
|
|
267
271
|
---
|
|
268
272
|
|
|
269
|
-
|
|
273
|
+
### Square Brackets for Arbitrary Values
|
|
270
274
|
|
|
271
275
|
**❌ WRONG (Using square brackets like Tailwind CSS):**
|
|
272
276
|
```xml
|
|
@@ -288,7 +292,7 @@ alloy compile
|
|
|
288
292
|
|
|
289
293
|
---
|
|
290
294
|
|
|
291
|
-
|
|
295
|
+
### Layout Defaults
|
|
292
296
|
|
|
293
297
|
**❌ WRONG (Explicit composite class):**
|
|
294
298
|
```xml
|
|
@@ -318,18 +322,76 @@ alloy compile
|
|
|
318
322
|
|
|
319
323
|
---
|
|
320
324
|
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
325
|
+
### ScrollView Without `content-w-screen` / `content-h-auto`
|
|
326
|
+
|
|
327
|
+
**WRONG (ScrollView with children that overflow horizontally or never scroll vertically):**
|
|
328
|
+
```xml
|
|
329
|
+
<ScrollView class="w-screen h-screen">
|
|
330
|
+
<View class="vertical">
|
|
331
|
+
<Label text="Very long content..." />
|
|
332
|
+
<!-- many items -->
|
|
333
|
+
</View>
|
|
334
|
+
</ScrollView>
|
|
335
|
+
```
|
|
336
|
+
|
|
337
|
+
**CORRECT (Explicit content sizing on the ScrollView itself):**
|
|
338
|
+
```xml
|
|
339
|
+
<ScrollView class="w-screen h-screen content-w-screen content-h-auto">
|
|
340
|
+
<View class="vertical">
|
|
341
|
+
<Label text="Very long content..." />
|
|
342
|
+
<!-- many items -->
|
|
343
|
+
</View>
|
|
344
|
+
</ScrollView>
|
|
345
|
+
```
|
|
346
|
+
|
|
347
|
+
**Why:** `content-w-screen` sets `contentWidth: Ti.UI.FILL` so the scroll area matches the viewport horizontally; `content-h-auto` sets `contentHeight: Ti.UI.SIZE` so vertical scroll expands to fit children. Omitting these often produces a ScrollView that never scrolls or clips content unexpectedly.
|
|
348
|
+
|
|
349
|
+
---
|
|
350
|
+
|
|
351
|
+
### Deprecated `theme.View.DEFAULT` vs `theme.extend.View`
|
|
352
|
+
|
|
353
|
+
**WRONG (old shape — deprecated in recent PurgeTSS):**
|
|
354
|
+
```javascript
|
|
355
|
+
// purgetss/config.cjs
|
|
356
|
+
module.exports = {
|
|
357
|
+
theme: {
|
|
358
|
+
View: {
|
|
359
|
+
DEFAULT: { backgroundColor: '#ffffff' }
|
|
360
|
+
}
|
|
361
|
+
}
|
|
362
|
+
}
|
|
363
|
+
```
|
|
364
|
+
|
|
365
|
+
**CORRECT (new `extend` shape):**
|
|
366
|
+
```javascript
|
|
367
|
+
// purgetss/config.cjs
|
|
368
|
+
module.exports = {
|
|
369
|
+
theme: {
|
|
370
|
+
extend: {
|
|
371
|
+
View: { backgroundColor: '#ffffff' }
|
|
372
|
+
}
|
|
373
|
+
}
|
|
374
|
+
}
|
|
375
|
+
```
|
|
376
|
+
|
|
377
|
+
**Why:** The nested `DEFAULT` key is a legacy artifact. Component-level theme overrides now live directly under `theme.extend.<Component>` and are merged with built-in defaults. Using the old shape silently produces unexpected styles on newer PurgeTSS versions.
|
|
378
|
+
|
|
379
|
+
---
|
|
380
|
+
|
|
381
|
+
### Quick Reference Table
|
|
382
|
+
|
|
383
|
+
| Anti-Pattern | Why It Fails | Correct Approach |
|
|
384
|
+
| ------------------------------------- | ------------------------------------ | -------------------------------------------- |
|
|
385
|
+
| `flex-row` | Flexbox not supported | `horizontal` |
|
|
386
|
+
| `flex-col` | Flexbox not supported | `vertical` |
|
|
387
|
+
| `justify-*` | Flexbox not supported | Use margins/positioning |
|
|
388
|
+
| `items-center` | Flexbox mental model | Use layout + positioning |
|
|
389
|
+
| `p-4` on View | No padding on containers | `m-4` on children |
|
|
390
|
+
| `w-full` | Percentage-based | `w-screen` (Ti.UI.FILL) |
|
|
391
|
+
| `rounded-full` | Needs size suffix | `rounded-full-12` |
|
|
392
|
+
| `composite` class | Already default | Omit it |
|
|
393
|
+
| `w-[100px]` | Wrong syntax | `w-(100px)` |
|
|
394
|
+
| Manual `.tss` | Overwritten by PurgeTSS | Use utility classes |
|
|
395
|
+
| `gap` with `%` widths | Total exceeds 100% | Use explicit margins |
|
|
396
|
+
| ScrollView without `content-*` sizing | No/unexpected scroll | Add `content-w-screen` + `content-h-auto` |
|
|
397
|
+
| `theme.View.DEFAULT` | Legacy shape in newer PurgeTSS | `theme.extend.View` |
|
|
@@ -0,0 +1,412 @@
|
|
|
1
|
+
# App Icons & Branding
|
|
2
|
+
|
|
3
|
+
The `purgetss brand` command (shipped in PurgeTSS v7.6.0) generates the complete Titanium branding set from a single SVG or PNG logo: launcher icons across every Android density, the adaptive-icon trio (foreground + background + monochrome), iOS 18+ Dark and Tinted variants, marketplace artwork, and optional notification/splash icons. Alloy and Classic layouts are auto-detected.
|
|
4
|
+
|
|
5
|
+
For the terse flag reference, see the [`brand` command reference](./cli-commands.md#brand-command). For sibling UI assets, see [Multi-Density Images](./multi-density-images.md).
|
|
6
|
+
|
|
7
|
+
> **INFO**
|
|
8
|
+
>
|
|
9
|
+
> The `brand` command at a glance
|
|
10
|
+
> `purgetss brand` turns one logo into every asset a Titanium app needs to ship — launcher icons, adaptive icons, iOS 18+ Dark/Tinted variants, marketplace artwork, and optional notification/splash icons. Works on both Alloy and Classic projects.
|
|
11
|
+
|
|
12
|
+
## Quick start
|
|
13
|
+
|
|
14
|
+
Drop a logo file into `purgetss/brand/`, then run the command. That's the whole workflow.
|
|
15
|
+
|
|
16
|
+
```bash
|
|
17
|
+
mkdir -p purgetss/brand # if the folder doesn't exist yet
|
|
18
|
+
cp docs/my-logo.svg purgetss/brand/logo.svg
|
|
19
|
+
|
|
20
|
+
purgetss brand
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
On a first run the command:
|
|
24
|
+
|
|
25
|
+
1. Creates the `brand:` section in `purgetss/config.cjs` with sensible defaults (if missing).
|
|
26
|
+
2. Generates every branding file directly into the project (in-place).
|
|
27
|
+
3. Prints a compact summary of what was written.
|
|
28
|
+
|
|
29
|
+
Pass `--dry-run` to preview without writing any files:
|
|
30
|
+
|
|
31
|
+
```bash
|
|
32
|
+
purgetss brand --dry-run
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
## The `purgetss/brand/` convention
|
|
36
|
+
|
|
37
|
+
`init` creates `purgetss/brand/` (alongside `fonts/` and `images/`) so the folder is already there the first time you look for it, even before you've dropped in a logo.
|
|
38
|
+
|
|
39
|
+
PurgeTSS auto-discovers logo files under this folder, the same way `purgetss/fonts/` works for fonts. Drop files with these names and you're done — no flags, no config:
|
|
40
|
+
|
|
41
|
+
```text
|
|
42
|
+
purgetss/brand/
|
|
43
|
+
├── logo.svg required — main logo (or logo.png)
|
|
44
|
+
├── logo-mono.svg optional — monochrome layer + notifications
|
|
45
|
+
├── logo-dark.svg optional — iOS 18+ dark variant
|
|
46
|
+
└── logo-tinted.svg optional — iOS 18+ tinted variant
|
|
47
|
+
```
|
|
48
|
+
|
|
49
|
+
Only `logo.svg` (or `logo.png`) is required. The other three are **opt-in refinements**:
|
|
50
|
+
|
|
51
|
+
| File | Required? | What it's for | Fallback when omitted |
|
|
52
|
+
| --- | --- | --- | --- |
|
|
53
|
+
| `logo.svg` / `logo.png` | **Required** | Main colored logo. Feeds every density and variant. | — |
|
|
54
|
+
| `logo-mono.svg` / `.png` | Optional | Android adaptive monochrome layer (themed icons on Android 13+) and notification icons. | Main logo is whitened automatically. |
|
|
55
|
+
| `logo-dark.svg` / `.png` | Optional | iOS 18+ Dark appearance variant. | Main logo on a transparent background (Apple HIG default). |
|
|
56
|
+
| `logo-tinted.svg` / `.png` | Optional | iOS 18+ Tinted appearance variant. | Grayscale of the main logo on black. |
|
|
57
|
+
|
|
58
|
+
Provide a dedicated `logo-mono` when the colored logo has detail that would collapse into a featureless blob under naive whitening (e.g. a painter's palette with colored dots — the monochrome variant should have cutouts instead).
|
|
59
|
+
|
|
60
|
+
Provide a dedicated `logo-dark` when dark-mode brand guidelines use a different lockup or color treatment; provide `logo-tinted` when you want a pre-simplified silhouette that tints better than a naive grayscale of the colored version.
|
|
61
|
+
|
|
62
|
+
> **INFO**
|
|
63
|
+
>
|
|
64
|
+
> Prefer SVG for the master
|
|
65
|
+
> SVG scales losslessly to every density Sharp needs to emit. A single `logo.svg` rasterizes perfectly at every `res-*dpi` output. PNG masters should be at least **1024×1024** to avoid upscaling artifacts.
|
|
66
|
+
|
|
67
|
+
### Overriding auto-discovery
|
|
68
|
+
|
|
69
|
+
You can also pass a path directly or point to a logo from the config. Useful when your masters live in `docs/` or another workflow folder:
|
|
70
|
+
|
|
71
|
+
```bash
|
|
72
|
+
purgetss brand ./docs/snap-logo.svg
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
Or in `purgetss/config.cjs`:
|
|
76
|
+
|
|
77
|
+
```javascript
|
|
78
|
+
brand: {
|
|
79
|
+
logo: './docs/snap-logo.svg',
|
|
80
|
+
monochromeLogo: './docs/snap-logo-mono.svg'
|
|
81
|
+
}
|
|
82
|
+
```
|
|
83
|
+
|
|
84
|
+
Precedence: **CLI flags win over config values, and config values win over auto-discovery.**
|
|
85
|
+
|
|
86
|
+
## The `brand:` config section
|
|
87
|
+
|
|
88
|
+
On the first run, `purgetss brand` injects a `brand:` block into your existing `purgetss/config.cjs` (between `purge:` and `theme:`) with these defaults:
|
|
89
|
+
|
|
90
|
+
```javascript
|
|
91
|
+
brand: {
|
|
92
|
+
splash: false, // also generate splash_icon.png × 5
|
|
93
|
+
padding: '15%', // Android safe-zone. Range: 12% tight (mature logos) — 20% conservative. Spec floor 19.44%.
|
|
94
|
+
iosPadding: '4%', // iOS aesthetic. Range: 2% bold — 8% conservative. No launcher mask.
|
|
95
|
+
darkBgColor: null, // opaque dark bg for DefaultIcon-Dark.png (null = transparent per Apple HIG)
|
|
96
|
+
bgColor: '#FFFFFF', // Android adaptive bg + iOS/marketplace flatten
|
|
97
|
+
notification: false, // also generate ic_stat_notify.png × 5
|
|
98
|
+
confirmOverwrites: true // prompt before overwriting files (set false to skip)
|
|
99
|
+
}
|
|
100
|
+
```
|
|
101
|
+
|
|
102
|
+
| Key | Default | Purpose |
|
|
103
|
+
| --- | --- | --- |
|
|
104
|
+
| `splash` | `false` | When `true`, also emits `splash_icon.png` × 5 densities. |
|
|
105
|
+
| `padding` | `'15%'` | Per-side safe-zone padding inside the 1024×1024 Android canvas. |
|
|
106
|
+
| `iosPadding` | `'4%'` | Aesthetic padding for the iOS square icon. Smaller than Android because iOS has no launcher mask. |
|
|
107
|
+
| `darkBgColor` | `null` | Opaque background baked into `DefaultIcon-Dark.png`. `null` = transparent per Apple HIG (iOS paints its own gradient). |
|
|
108
|
+
| `bgColor` | `'#FFFFFF'` | Triple-purpose (see [Brand color](#brand-color) below). |
|
|
109
|
+
| `notification` | `false` | When `true`, also emits `ic_stat_notify.png` × 5 densities. |
|
|
110
|
+
| `confirmOverwrites` | `true` | When `false`, the `[y/N/a]` prompt is skipped. |
|
|
111
|
+
|
|
112
|
+
Change whatever you want to override globally; CLI flags still win for one-off runs.
|
|
113
|
+
|
|
114
|
+
## Overwrite confirmation
|
|
115
|
+
|
|
116
|
+
`brand` writes directly into the project, so it asks before overwriting anything:
|
|
117
|
+
|
|
118
|
+
```text
|
|
119
|
+
In-place mode will OVERWRITE files in <project>. Commit first if you want a rollback.
|
|
120
|
+
Continue? [y/N/a]
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
- `y` / `yes` — write this time
|
|
124
|
+
- `N` / `no` / `Enter` — abort (nothing is written)
|
|
125
|
+
- `a` / `always` — write, then add `confirmOverwrites: false` to the `brand:` section of `config.cjs` so the prompt stays quiet on future runs
|
|
126
|
+
|
|
127
|
+
The prompt is skipped automatically when:
|
|
128
|
+
|
|
129
|
+
- `stdin` is not a TTY (the `alloy.jmk` hook, CI, a pipe)
|
|
130
|
+
- you pass `-y` / `--yes` — one-shot bypass
|
|
131
|
+
- `PURGETSS_YES=1` is set in the environment — lasts the whole shell session
|
|
132
|
+
- `confirmOverwrites: false` is already in the `brand:` config
|
|
133
|
+
|
|
134
|
+
```bash
|
|
135
|
+
purgetss brand -y # skip prompt once
|
|
136
|
+
PURGETSS_YES=1 purgetss brand # skip for the whole session
|
|
137
|
+
```
|
|
138
|
+
|
|
139
|
+
## What gets generated
|
|
140
|
+
|
|
141
|
+
The output is automatically routed to the right directory for your project layout.
|
|
142
|
+
|
|
143
|
+
**Alloy layout:**
|
|
144
|
+
|
|
145
|
+
```text
|
|
146
|
+
<project>/
|
|
147
|
+
├── DefaultIcon.png ← 1024×1024, universal fallback (Android-safe padding)
|
|
148
|
+
├── DefaultIcon-ios.png ← 1024×1024, iOS flattened on bgColor
|
|
149
|
+
├── DefaultIcon-Dark.png ← 1024×1024, iOS 18+ dark (transparent per Apple HIG)
|
|
150
|
+
├── DefaultIcon-Tinted.png ← 1024×1024, iOS 18+ tinted (grayscale on black)
|
|
151
|
+
├── iTunesConnect.png ← 1024×1024, App Store submission
|
|
152
|
+
├── MarketplaceArtwork.png ← 512×512, Google Play submission
|
|
153
|
+
└── app/
|
|
154
|
+
└── assets/android/res/
|
|
155
|
+
├── mipmap-mdpi/ ← 108×108 foreground + background + monochrome + legacy
|
|
156
|
+
├── mipmap-hdpi/ ← 162×162
|
|
157
|
+
├── mipmap-xhdpi/ ← 216×216
|
|
158
|
+
├── mipmap-xxhdpi/ ← 324×324
|
|
159
|
+
├── mipmap-xxxhdpi/ ← 432×432
|
|
160
|
+
└── mipmap-anydpi-v26/
|
|
161
|
+
└── ic_launcher.xml ← adaptive-icon binder
|
|
162
|
+
```
|
|
163
|
+
|
|
164
|
+
**Classic layout:**
|
|
165
|
+
|
|
166
|
+
```text
|
|
167
|
+
<project>/
|
|
168
|
+
├── DefaultIcon.png DefaultIcon-ios.png ... ← same root-level files as Alloy
|
|
169
|
+
└── platform/
|
|
170
|
+
└── android/res/
|
|
171
|
+
├── mipmap-*/ ← same 5 densities as Alloy
|
|
172
|
+
└── mipmap-anydpi-v26/ic_launcher.xml
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
## Android dark mode
|
|
176
|
+
|
|
177
|
+
> **INFO**
|
|
178
|
+
>
|
|
179
|
+
> No separate "dark icon" file on Android
|
|
180
|
+
> Unlike iOS 18+, Android has no dedicated dark-mode icon file. Instead, Android 13+ uses the **monochrome layer** of the adaptive icon and tints it based on the user's wallpaper + theme.
|
|
181
|
+
>
|
|
182
|
+
> The `brand` command generates `ic_launcher_monochrome.png` at every density by default — you don't need any extra flags to get themed icon support.
|
|
183
|
+
|
|
184
|
+
If you want to provide a dedicated silhouette (recommended for detailed logos):
|
|
185
|
+
|
|
186
|
+
```bash
|
|
187
|
+
cp docs/my-logo-mono.svg purgetss/brand/logo-mono.svg
|
|
188
|
+
purgetss brand
|
|
189
|
+
```
|
|
190
|
+
|
|
191
|
+
The monochrome layer is pure white (`RGB 255,255,255`) with alpha preserved. Android applies the user's tint on top at render time.
|
|
192
|
+
|
|
193
|
+
## iOS 18+ Dark and Tinted variants
|
|
194
|
+
|
|
195
|
+
iOS 18 added two appearance variants on top of the standard app icon: **Dark** (for the dark appearance of the Home Screen) and **Tinted** (for the user-accent-colored mode).
|
|
196
|
+
|
|
197
|
+
The `brand` command generates both by default:
|
|
198
|
+
|
|
199
|
+
- **`DefaultIcon-Dark.png`**: 1024×1024, **transparent by default** per Apple HIG. The system paints its own dark gradient behind the icon at render time. Override with `--dark-bg-color <hex>` to bake in an opaque dark tint instead.
|
|
200
|
+
- **`DefaultIcon-Tinted.png`**: 1024×1024, **grayscale on black (`#000000`)** per Apple HIG. iOS composites its own gradient background and multiplies the luminance by the user-selected accent color at render time.
|
|
201
|
+
|
|
202
|
+
### Skipping Dark or Tinted
|
|
203
|
+
|
|
204
|
+
```bash
|
|
205
|
+
purgetss brand --no-dark
|
|
206
|
+
purgetss brand --no-tinted
|
|
207
|
+
purgetss brand --no-dark --no-tinted
|
|
208
|
+
```
|
|
209
|
+
|
|
210
|
+
### Titanium SDK wiring status
|
|
211
|
+
|
|
212
|
+
> **WARNING**
|
|
213
|
+
>
|
|
214
|
+
> Upstream work in progress
|
|
215
|
+
> As of April 2026, Titanium SDK picks up `DefaultIcon-ios.png` automatically but does **not** yet wire `DefaultIcon-Dark.png` / `DefaultIcon-Tinted.png` into the generated iOS appiconset. Upstream tracking: [tidev/titanium-sdk#14122](https://github.com/tidev/titanium-sdk/issues/14122).
|
|
216
|
+
>
|
|
217
|
+
> Until that PR lands, after your first iOS build you may need to add the two PNGs manually into `build/iphone/Assets.xcassets/AppIcon.appiconset/` in Xcode (via the "Appearance" column in the asset catalog editor). Once #14122 merges, the command becomes fully end-to-end.
|
|
218
|
+
|
|
219
|
+
## Brand color
|
|
220
|
+
|
|
221
|
+
The `--bg-color` flag (or `brand.bgColor` in config) controls three things at once:
|
|
222
|
+
|
|
223
|
+
1. The **Android adaptive background layer**: a solid color that fills the full 108dp canvas behind your logo.
|
|
224
|
+
2. The **iOS alpha flatten** for `DefaultIcon-ios.png`. Apple rejects transparent App Store icons, so the logo is flattened on this color.
|
|
225
|
+
3. The **marketplace flatten** for `iTunesConnect.png` and `MarketplaceArtwork.png` when you pass a non-default value explicitly.
|
|
226
|
+
|
|
227
|
+
```bash
|
|
228
|
+
purgetss brand --bg-color "#0B1326"
|
|
229
|
+
```
|
|
230
|
+
|
|
231
|
+
If you never pass the flag, background stays `#FFFFFF` and the marketplace artwork keeps its alpha channel (matches Titanium's default).
|
|
232
|
+
|
|
233
|
+
## Padding guidance
|
|
234
|
+
|
|
235
|
+
`--padding` controls how much safe-zone padding (per side, expressed as a percentage) surrounds the logo inside the Android adaptive canvas. The default `15%` matches real-world production apps like Gmail and Chrome.
|
|
236
|
+
|
|
237
|
+
| Padding | Logo fill | When to use |
|
|
238
|
+
| ------- | --------- | ------------------------------------------------------------------------------------------------------ |
|
|
239
|
+
| `12%` | 76% | Logos with built-in breathing room (circular wordmarks, letterforms inside a shape). Tight, bold look. |
|
|
240
|
+
| `15%` | 70% | **Default**. Balanced, safe on Pixel, Oppo, Samsung, OneUI, and Nova. |
|
|
241
|
+
| `18%` | 64% | Defensive: for intricate logos, fine serifs, multi-element designs. |
|
|
242
|
+
| `20%` | 60% | Conservative, spec-compliant. Safe on every launcher, including legacy aggressive masks. |
|
|
243
|
+
|
|
244
|
+
A useful visual check is the "corners" heuristic: imagine a circle inscribed in your 1024×1024 canvas with the given padding. If your logo's outermost corners fit inside that circle, you're safe on circular launchers (Pixel default, Oppo Android 15). If they poke out, they'll be clipped.
|
|
245
|
+
|
|
246
|
+
The official Android spec floor is `19.44%` (108dp canvas, 66dp inscribed safe-zone circle). Modern launchers are more permissive: Gmail and Chrome ship at 10–14%, which is why `15%` is the default. The 19.44% floor is the theoretical worst-case for aggressive masks; if you're worried about legacy Samsung teardrop masks or similar, bump to `--padding 20` to stay inside the spec.
|
|
247
|
+
|
|
248
|
+
`--ios-padding` is a separate lever — iOS has no launcher mask, so the range is different:
|
|
249
|
+
|
|
250
|
+
| iOS padding | When to use |
|
|
251
|
+
| --- | --- |
|
|
252
|
+
| `2%` | Bold, edge-to-edge logos. |
|
|
253
|
+
| `4%` | **Default**. Balanced aesthetic. |
|
|
254
|
+
| `8%` | Conservative, generous whitespace around the mark. |
|
|
255
|
+
|
|
256
|
+
## Cleanup legacy branding artifacts
|
|
257
|
+
|
|
258
|
+
Projects that predate Android adaptive icons (API 26+) or modern iOS launch storyboards often accumulate obsolete assets: `res-long-*/res-notlong-*` qualifiers dead since Android 3.0, legacy `Default-*.png` launch images ignored when the storyboard is enabled, pre-adaptive `appicon.png`, and so on.
|
|
259
|
+
|
|
260
|
+
The `--cleanup-legacy` flag removes them with context-aware safety rules: it reads `tiapp.xml` to decide what's safe to delete based on your project's configuration. Always preview first:
|
|
261
|
+
|
|
262
|
+
```bash
|
|
263
|
+
purgetss brand --cleanup-legacy --dry-run
|
|
264
|
+
```
|
|
265
|
+
|
|
266
|
+
Review the output, then remove `--dry-run` to apply:
|
|
267
|
+
|
|
268
|
+
```bash
|
|
269
|
+
purgetss brand --cleanup-legacy
|
|
270
|
+
```
|
|
271
|
+
|
|
272
|
+
Add `--aggressive` to also remove `ldpi` density folders (less than 1% of active Android devices globally in 2026):
|
|
273
|
+
|
|
274
|
+
```bash
|
|
275
|
+
purgetss brand --cleanup-legacy --aggressive
|
|
276
|
+
```
|
|
277
|
+
|
|
278
|
+
> **DANGER**
|
|
279
|
+
>
|
|
280
|
+
> Commit first
|
|
281
|
+
> `--cleanup-legacy` deletes files permanently. Commit your project to git before running without `--dry-run` so `git restore` is available as a rollback.
|
|
282
|
+
|
|
283
|
+
## Troubleshooting
|
|
284
|
+
|
|
285
|
+
### The icon looks cropped or cramped on my phone
|
|
286
|
+
|
|
287
|
+
Your logo is probably landing too close to the launcher mask. Increase `--padding`:
|
|
288
|
+
|
|
289
|
+
```bash
|
|
290
|
+
purgetss brand --padding 20
|
|
291
|
+
```
|
|
292
|
+
|
|
293
|
+
Or set it in the config:
|
|
294
|
+
|
|
295
|
+
```javascript
|
|
296
|
+
brand: { padding: '20%' }
|
|
297
|
+
```
|
|
298
|
+
|
|
299
|
+
### The icon looks tiny / lost in the middle
|
|
300
|
+
|
|
301
|
+
Padding is too generous. Lower it:
|
|
302
|
+
|
|
303
|
+
```bash
|
|
304
|
+
purgetss brand --padding 12
|
|
305
|
+
```
|
|
306
|
+
|
|
307
|
+
### The monochrome version looks like a white blob
|
|
308
|
+
|
|
309
|
+
Your colored logo likely has multi-color detail that doesn't survive a naive whitening. Provide a dedicated silhouette:
|
|
310
|
+
|
|
311
|
+
```bash
|
|
312
|
+
cp docs/my-logo-mono.svg purgetss/brand/logo-mono.svg
|
|
313
|
+
purgetss brand
|
|
314
|
+
```
|
|
315
|
+
|
|
316
|
+
### iOS rejects the app icon upload ("contains transparency")
|
|
317
|
+
|
|
318
|
+
That's Apple's rule: App Store icons must have no alpha channel. `DefaultIcon-ios.png` is always flattened on `bgColor` for that reason. If you edited the file manually and reintroduced alpha, re-run `purgetss brand` to regenerate.
|
|
319
|
+
|
|
320
|
+
### The dark variant doesn't show on my iPhone
|
|
321
|
+
|
|
322
|
+
Dark variants require iOS 18+ and Titanium SDK automatic wiring (tracked upstream in [titanium-sdk#14122](https://github.com/tidev/titanium-sdk/issues/14122)). Until that PR merges, you may need to add `DefaultIcon-Dark.png` and `DefaultIcon-Tinted.png` manually into the Xcode appiconset after the first iOS build.
|
|
323
|
+
|
|
324
|
+
### I get "Input image exceeds pixel limit" on an SVG from Affinity / Illustrator
|
|
325
|
+
|
|
326
|
+
Affinity Designer and Adobe Illustrator often bake transforms into the exported SVG's `viewBox`, so the intrinsic dimensions end up at something absurd like `29559×13542 pt`. Rasterized at 1× density, that blows past Sharp's pixel limit and the command crashes.
|
|
327
|
+
|
|
328
|
+
PurgeTSS checks the `viewBox` on every SVG. When either side is over `4096 pt`, it prints a warning with the actual dimensions and switches to an adaptive density that caps the output pixel count regardless of input size. The warning tells you the source is oversized; the command still finishes.
|
|
329
|
+
|
|
330
|
+
If you want to clean up the source, re-export from the vector editor with a canvas-sized viewBox (`0 0 1024 1024`, for example). The rasterized output is identical either way, but a normalized viewBox keeps the SVG portable for other tools.
|
|
331
|
+
|
|
332
|
+
### I changed my bg color — do I need to regenerate the Android densities too?
|
|
333
|
+
|
|
334
|
+
Yes. `bgColor` bakes into every Android background layer and the iOS flatten. Re-run:
|
|
335
|
+
|
|
336
|
+
```bash
|
|
337
|
+
purgetss brand --bg-color "#NEW_COLOR"
|
|
338
|
+
```
|
|
339
|
+
|
|
340
|
+
All 5 Android densities, marketplace artwork, and iOS variants regenerate in one pass.
|
|
341
|
+
|
|
342
|
+
## Full flag reference
|
|
343
|
+
|
|
344
|
+
**Project & output**
|
|
345
|
+
|
|
346
|
+
| Flag | Purpose |
|
|
347
|
+
| --- | --- |
|
|
348
|
+
| `--project <path>` | Project root (defaults to cwd). |
|
|
349
|
+
| `--dry-run` | Preview what would be generated without writing any files. |
|
|
350
|
+
| `--output <dir>` | Stage into `<dir>` instead of writing in place. |
|
|
351
|
+
| `-y`, `--yes` | Skip the overwrite confirmation prompt for this invocation. |
|
|
352
|
+
|
|
353
|
+
**Visual customization**
|
|
354
|
+
|
|
355
|
+
| Flag | Purpose |
|
|
356
|
+
| --- | --- |
|
|
357
|
+
| `--bg-color <hex>` | Background color for Android adaptive + iOS/marketplace flatten. |
|
|
358
|
+
| `--padding <n>` | Android safe-zone % (range `12–20`, default `15`). |
|
|
359
|
+
| `--ios-padding <n>` | iOS aesthetic padding % (range `2–8`, default `4`). |
|
|
360
|
+
|
|
361
|
+
**Optional asset types**
|
|
362
|
+
|
|
363
|
+
| Flag | Purpose |
|
|
364
|
+
| --- | --- |
|
|
365
|
+
| `--notification` | Also emit `ic_stat_notify.png × 5`. |
|
|
366
|
+
| `--splash` | Also emit `splash_icon.png × 5`. |
|
|
367
|
+
|
|
368
|
+
**Logo variants & overrides**
|
|
369
|
+
|
|
370
|
+
| Flag | Purpose |
|
|
371
|
+
| --- | --- |
|
|
372
|
+
| `--monochrome-logo <path>` | Override `purgetss/brand/logo-mono.{svg,png}`. |
|
|
373
|
+
| `--dark-logo <path>` | Override `purgetss/brand/logo-dark.{svg,png}`. |
|
|
374
|
+
| `--dark-bg-color <hex>` | Opaque dark bg for `DefaultIcon-Dark.png` (default: transparent per Apple HIG). |
|
|
375
|
+
| `--tinted-logo <path>` | Override `purgetss/brand/logo-tinted.{svg,png}`. |
|
|
376
|
+
| `--no-dark` | Skip `DefaultIcon-Dark.png`. |
|
|
377
|
+
| `--no-tinted` | Skip `DefaultIcon-Tinted.png`. |
|
|
378
|
+
|
|
379
|
+
**Legacy cleanup**
|
|
380
|
+
|
|
381
|
+
| Flag | Purpose |
|
|
382
|
+
| --- | --- |
|
|
383
|
+
| `--cleanup-legacy` | Remove obsolete branding artifacts (reads `tiapp.xml` for safety rules). |
|
|
384
|
+
| `--aggressive` | With `--cleanup-legacy`, also remove `ldpi` density folders. |
|
|
385
|
+
|
|
386
|
+
**Diagnostics**
|
|
387
|
+
|
|
388
|
+
| Flag | Purpose |
|
|
389
|
+
| --- | --- |
|
|
390
|
+
| `--notes` | Print full `tiapp.xml` snippets + padding tuning guide. |
|
|
391
|
+
| `--debug` | Print extra diagnostics. |
|
|
392
|
+
|
|
393
|
+
### Examples
|
|
394
|
+
|
|
395
|
+
```bash
|
|
396
|
+
purgetss brand # uses purgetss/brand/logo.svg + config
|
|
397
|
+
purgetss brand --bg-color "#0B1326" # override bg color
|
|
398
|
+
purgetss brand --notification --splash # add notification + splash
|
|
399
|
+
purgetss brand --no-tinted # skip iOS 18+ tinted variant
|
|
400
|
+
purgetss brand --dry-run # preview without writing
|
|
401
|
+
purgetss brand --cleanup-legacy --dry-run # preview legacy cleanup
|
|
402
|
+
```
|
|
403
|
+
|
|
404
|
+
## Community-Discovered Patterns
|
|
405
|
+
|
|
406
|
+
- **Titanium SDK wiring lag for iOS 18+ variants.** Titanium SDK currently wires `DefaultIcon-ios.png` into the generated appiconset automatically, but `DefaultIcon-Dark.png` and `DefaultIcon-Tinted.png` are not picked up yet. Until [tidev/titanium-sdk#14122](https://github.com/tidev/titanium-sdk/issues/14122) merges, the practical workaround is: run `ti build -p ios` once, then open `build/iphone/Assets.xcassets/AppIcon.appiconset/` in Xcode and drag the two PNGs into the "Appearance" column of the asset catalog editor. The generated PNGs are already named and sized correctly — no resizing needed.
|
|
407
|
+
- **Modern launchers ship tighter than the spec.** The Android adaptive-icon spec floor is `19.44%` padding, but shipped apps like Gmail and Chrome use `10–14%`. PurgeTSS's `15%` default sits in that real-world range rather than the conservative spec floor, which is why icons look tight-but-balanced out of the box.
|
|
408
|
+
|
|
409
|
+
## See also
|
|
410
|
+
|
|
411
|
+
- [`brand` command reference](./cli-commands.md#brand-command) — terse flag list.
|
|
412
|
+
- [Multi-Density Images](./multi-density-images.md) — sibling `images` command for UI assets.
|