@maccesar/titools 2.6.1 → 2.7.1
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/README.md +38 -36
- package/package.json +1 -1
- package/skills/ti-branding/SKILL.md +11 -6
- package/skills/ti-branding/scripts/lib/gen-android-adaptive.sh +19 -7
- package/skills/ti-branding/scripts/lib/gen-ios.sh +22 -6
- package/skills/ti-branding/scripts/lib/gen-marketplace.sh +23 -8
- package/skills/ti-branding/scripts/lib/gen-notification.sh +18 -6
- package/skills/ti-branding/scripts/ti-branding +163 -69
package/README.md
CHANGED
|
@@ -48,7 +48,9 @@ What you get:
|
|
|
48
48
|
- ti-pro research agent
|
|
49
49
|
- Session hook that auto-detects Titanium projects (`tiapp.xml`, Alloy, PurgeTSS)
|
|
50
50
|
- Slash commands: `/ti-check`, `/ti-new-screen`, `/ti-audit`
|
|
51
|
-
- Auto-updates via marketplace
|
|
51
|
+
- Auto-updates via marketplace (opt-in — see note below)
|
|
52
|
+
|
|
53
|
+
> **Note on auto-updates:** Claude Code disables auto-updates by default for third-party marketplaces like this one. To receive new versions automatically, open `/plugin` → **Marketplaces** tab and enable auto-update for `maccesar-titools`. When an update is applied, Claude Code prompts you to run `/reload-plugins` to activate the new code.
|
|
52
54
|
|
|
53
55
|
### Option B: CLI (Claude Code, Gemini CLI, Codex CLI)
|
|
54
56
|
|
|
@@ -89,15 +91,15 @@ Why NPM?
|
|
|
89
91
|
|
|
90
92
|
### Which option should I use?
|
|
91
93
|
|
|
92
|
-
|
|
|
93
|
-
|
|
94
|
-
| **Claude Code**
|
|
95
|
-
| **Gemini CLI**
|
|
96
|
-
| **Codex CLI**
|
|
97
|
-
| **Knowledge Index** | Not included
|
|
98
|
-
| **Auto-updates**
|
|
99
|
-
| **Slash commands**
|
|
100
|
-
| **Session hook**
|
|
94
|
+
| | Plugin (Option A) | CLI (Option B) |
|
|
95
|
+
| ------------------- | ------------------------------------------ | ------------------------- |
|
|
96
|
+
| **Claude Code** | Recommended | Supported |
|
|
97
|
+
| **Gemini CLI** | Not available | Supported |
|
|
98
|
+
| **Codex CLI** | Not available | Supported |
|
|
99
|
+
| **Knowledge Index** | Not included | Included (`titools sync`) |
|
|
100
|
+
| **Auto-updates** | Marketplace (opt-in, enable in `/plugin`) | SessionStart hook (daily) |
|
|
101
|
+
| **Slash commands** | `/ti-check`, `/ti-new-screen`, `/ti-audit` | Not available |
|
|
102
|
+
| **Session hook** | Auto-detects Titanium projects | Auto-update only |
|
|
101
103
|
|
|
102
104
|
Use **Option A** if you only use Claude Code. Use **Option B** if you use multiple AI assistants or want the Knowledge Index feature.
|
|
103
105
|
|
|
@@ -176,17 +178,17 @@ The knowledge index is based on the latest Titanium SDK documentation. If your p
|
|
|
176
178
|
|
|
177
179
|
## Skills overview
|
|
178
180
|
|
|
179
|
-
| Skill | Purpose | Best For
|
|
180
|
-
| ------------ | ------------------------------- |
|
|
181
|
-
| alloy-guides | Alloy MVC reference | Models, Views, Controllers, Widgets
|
|
182
|
-
| alloy-howtos | Alloy CLI and debugging | Project setup, CLI commands, errors
|
|
183
|
-
| purgetss | Utility-first styling | UI styling and animations
|
|
184
|
-
| ti-api | Complete API reference | Properties, methods, events, constants
|
|
181
|
+
| Skill | Purpose | Best For |
|
|
182
|
+
| ------------ | ------------------------------- | ------------------------------------------------------------------------------- |
|
|
183
|
+
| alloy-guides | Alloy MVC reference | Models, Views, Controllers, Widgets |
|
|
184
|
+
| alloy-howtos | Alloy CLI and debugging | Project setup, CLI commands, errors |
|
|
185
|
+
| purgetss | Utility-first styling | UI styling and animations |
|
|
186
|
+
| ti-api | Complete API reference | Properties, methods, events, constants |
|
|
185
187
|
| ti-branding | Icon and splash generator | App icons, adaptive icons, splash, notifications, store artwork, legacy cleanup |
|
|
186
|
-
| ti-expert | Architecture and implementation | Starting point for most tasks
|
|
187
|
-
| ti-guides | SDK fundamentals | Hyperloop, distribution, configuration
|
|
188
|
-
| ti-howtos | Native feature integration | Location, Push, Media, Platform APIs
|
|
189
|
-
| ti-ui | UI/UX patterns | Complex layouts, ListViews, platform UI
|
|
188
|
+
| ti-expert | Architecture and implementation | Starting point for most tasks |
|
|
189
|
+
| ti-guides | SDK fundamentals | Hyperloop, distribution, configuration |
|
|
190
|
+
| ti-howtos | Native feature integration | Location, Push, Media, Platform APIs |
|
|
191
|
+
| ti-ui | UI/UX patterns | Complex layouts, ListViews, platform UI |
|
|
190
192
|
|
|
191
193
|
Note: `ti-guides`, `ti-howtos`, `ti-ui`, `alloy-guides`, and `alloy-howtos` are based on official Titanium SDK and Alloy documentation. `purgetss` is opinionated in workflow and conventions, but its reference files are audited against the official PurgeTSS documentation for verifiable classes and behavior. `ti-expert` and `purgetss` reflect personal coding conventions (biased toward PurgeTSS).
|
|
192
194
|
|
|
@@ -200,11 +202,11 @@ In addition to skills, this repository includes sub-agents for Claude Code. Sub-
|
|
|
200
202
|
|
|
201
203
|
Deep-dive research specialist that preloads all 8 titanium-related documentation skills.
|
|
202
204
|
|
|
203
|
-
| Aspect | Details
|
|
204
|
-
| ---------------- |
|
|
205
|
-
| Location | `~/.claude/agents/ti-pro.md`
|
|
206
|
-
| Model | Sonnet (comprehensive analysis)
|
|
207
|
-
| Tools | Read-only (Read, Grep, Glob)
|
|
205
|
+
| Aspect | Details |
|
|
206
|
+
| ---------------- | ------------------------------------------------------- |
|
|
207
|
+
| Location | `~/.claude/agents/ti-pro.md` |
|
|
208
|
+
| Model | Sonnet (comprehensive analysis) |
|
|
209
|
+
| Tools | Read-only (Read, Grep, Glob) |
|
|
208
210
|
| Preloaded Skills | All 8 Titanium documentation skills injected at startup |
|
|
209
211
|
|
|
210
212
|
When to use the agent vs skills:
|
|
@@ -238,11 +240,11 @@ Key difference:
|
|
|
238
240
|
|
|
239
241
|
When installed as a plugin, TiTools provides slash commands for common tasks:
|
|
240
242
|
|
|
241
|
-
| Command
|
|
242
|
-
|
|
243
|
-
| `/ti-check`
|
|
243
|
+
| Command | Description |
|
|
244
|
+
| ----------------------- | ----------------------------------------------------------------------------------- |
|
|
245
|
+
| `/ti-check` | Verify project setup: SDK version, Alloy structure, PurgeTSS config, common issues |
|
|
244
246
|
| `/ti-new-screen <name>` | Create a new Alloy screen (controller + view + style) following project conventions |
|
|
245
|
-
| `/ti-audit`
|
|
247
|
+
| `/ti-audit` | Audit project for anti-patterns, memory leaks, and best practice violations |
|
|
246
248
|
|
|
247
249
|
These commands automatically invoke the relevant skills:
|
|
248
250
|
- `/ti-check` reads `tiapp.xml` and reports project health
|
|
@@ -660,8 +662,8 @@ titools auto-update --silent # No output (for hooks)
|
|
|
660
662
|
```
|
|
661
663
|
|
|
662
664
|
Options:
|
|
663
|
-
| Option | Description
|
|
664
|
-
| -------------- |
|
|
665
|
+
| Option | Description |
|
|
666
|
+
| -------------- | --------------------------------- |
|
|
665
667
|
| `-s, --silent` | Suppress all output except errors |
|
|
666
668
|
|
|
667
669
|
What it does:
|
|
@@ -798,11 +800,11 @@ The TiTools skills include **Community-Discovered Patterns** — verified iOS be
|
|
|
798
800
|
|
|
799
801
|
When using Large Titles with a ScrollView inside NavigationWindow or TabGroup, three Window properties must be set together. Without all three, the ScrollView content overlaps behind the navigation bar — or the large title renders with a visible delay.
|
|
800
802
|
|
|
801
|
-
| Class
|
|
802
|
-
|
|
803
|
-
| `auto-adjust-scroll-view-insets` | `autoAdjustScrollViewInsets` | Adjusts ScrollView insets to prevent content overlap
|
|
804
|
-
| `extend-edges-all`
|
|
805
|
-
| `large-title-enabled`
|
|
803
|
+
| Class | Property | Purpose |
|
|
804
|
+
| -------------------------------- | ---------------------------- | ----------------------------------------------------- |
|
|
805
|
+
| `auto-adjust-scroll-view-insets` | `autoAdjustScrollViewInsets` | Adjusts ScrollView insets to prevent content overlap |
|
|
806
|
+
| `extend-edges-all` | `extendEdges` | Content extends behind bars (blur/translucent effect) |
|
|
807
|
+
| `large-title-enabled` | `largeTitleEnabled` | Large title that collapses on scroll |
|
|
806
808
|
|
|
807
809
|
**Recommended:** set the base properties as global Window defaults in `config.cjs`:
|
|
808
810
|
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: ti-branding
|
|
3
|
-
description: "Generate complete app branding assets for modern Titanium SDK 13.x projects — launcher icons, adaptive icons, splash-screen icons, notification icons, and marketplace artwork — from a single SVG or PNG master. Use when the user asks to brand their app, update the app icon, set up splash screens, prepare store assets, fix generic/placeholder icons, add a notification icon, generate a launcher for Android 8+/13+, replace the TiTools default icon, or anything related to visual identity of a Titanium app (Alloy or Classic). Auto-detects Alloy vs Classic layout. Outputs iOS `DefaultIcon-ios.png` (flattened), Android adaptive triplet (foreground + background + monochrome) across 5 densities, Android legacy launcher × 5, marketplace artwork (1024² + 512
|
|
4
|
-
argument-hint: "[master-path] [--bg-color <hex>] [--padding <pct>] [--with-notification] [--with-splash-icon] [--cleanup-legacy] [--aggressive] [--dry-run]"
|
|
3
|
+
description: "Generate complete app branding assets for modern Titanium SDK 13.x projects — launcher icons, adaptive icons, splash-screen icons, notification icons, and marketplace artwork — from a single SVG or PNG master. Use when the user asks to brand their app, update the app icon, set up splash screens, prepare store assets, fix generic/placeholder icons, add a notification icon, generate a launcher for Android 8+/13+, replace the TiTools default icon, or anything related to visual identity of a Titanium app (Alloy or Classic). Auto-detects Alloy vs Classic layout. Outputs iOS `DefaultIcon.png` (alpha-preserved source) + `DefaultIcon-ios.png` (alpha-flattened for Apple), Android adaptive triplet (foreground + background + monochrome) across 5 densities, Android legacy launcher × 5, marketplace artwork (1024² + 512², alpha-preserved), and optionally notification icons and Android 12+ splash icons. Targets SDK 13.0–13.2 minimums without legacy cruft (post-Xcode 14 iOS minimums, no 9-patch splash, no pre-adaptive Android icons). Delegates raster work to ImageMagick + librsvg (system tools) — zero npm/pip dependencies. Invoke this skill whenever the user mentions icons, splash screens, branding, launcher, adaptive icon, mipmap, appiconset, DefaultIcon, iTunesConnect, Play Store artwork, or any visual asset for a Titanium app."
|
|
4
|
+
argument-hint: "[master-path] [--bg-color <hex>] [--padding <pct>] [--with-notification] [--with-splash-icon] [--cleanup-legacy] [--aggressive] [--in-place] [--monochrome-master <path>] [--notes] [--dry-run]"
|
|
5
5
|
allowed-tools: Read, Glob, Bash, Write, Edit
|
|
6
6
|
---
|
|
7
7
|
|
|
@@ -29,9 +29,10 @@ Every invocation produces (in a staging directory, reviewed before copy):
|
|
|
29
29
|
|
|
30
30
|
| Asset | Path in project | Why |
|
|
31
31
|
|---|---|---|
|
|
32
|
-
| `DefaultIcon
|
|
33
|
-
| `
|
|
34
|
-
| `
|
|
32
|
+
| `DefaultIcon.png` (1024×1024, alpha preserved) | Project root | Universal source — Titanium's `ti create` template ships this with alpha. Used for Android / Alloy references and as the alpha-intact source of truth. |
|
|
33
|
+
| `DefaultIcon-ios.png` (1024×1024, no alpha) | Project root | iOS SDK generates the full appiconset from this at build time. Flattened because Apple rejects alpha channels on App Store icon uploads. |
|
|
34
|
+
| `iTunesConnect.png` (1024×1024, alpha preserved) | Project root | App Store artwork template. Matches `ti create` default — alpha preserved so the developer can composite over any background before upload. |
|
|
35
|
+
| `MarketplaceArtwork.png` (512×512, alpha preserved) | Project root | Google Play feature graphic template. Matches `ti create` default — alpha preserved. |
|
|
35
36
|
| `ic_launcher_foreground.png` × 5 densities | `app/platform/android/res/mipmap-{m,h,x,xx,xxx}hdpi/` | Adaptive icon foreground layer. Logo centered in 108dp canvas with configurable padding (default 22% ≈ 66dp safe-zone). |
|
|
36
37
|
| `ic_launcher_background.png` × 5 densities | idem | Adaptive icon background layer — solid `--bg-color`. |
|
|
37
38
|
| `ic_launcher_monochrome.png` × 5 densities | idem | Android 13+ themed icons (all non-transparent pixels → white). |
|
|
@@ -68,12 +69,16 @@ Options:
|
|
|
68
69
|
| Flag | Default | Purpose |
|
|
69
70
|
|---|---|---|
|
|
70
71
|
| `--bg-color <hex>` | `#FFFFFF` | Solid color for adaptive background layer. Also used for iOS alpha flatten. |
|
|
71
|
-
| `--padding <pct>` | `
|
|
72
|
+
| `--padding <pct>` | `20` | Safe-zone padding per side. Material spec floor is 19.44% — default of 20 gives a tiny buffer while keeping the logo visibly prominent across launcher masks. Range 0–40. |
|
|
73
|
+
| `--ios-padding <pct>` | `4` | iOS + marketplace aesthetic padding per side. iOS icons have no launcher mask — this is purely aesthetic breathing room. Apple's HIG + production apps typically use 2-6%. Override with `--ios-padding 8` for more conservative (prior default) or `--ios-padding 2` for near-edge La Baraja-style. Range 0–40. |
|
|
72
74
|
| `--with-notification` | off | Emit `ic_stat_notify.png` × 5 densities. |
|
|
73
75
|
| `--with-splash-icon` | off | Emit `splash_icon.png` × 5 densities (Android 12+ SplashScreen API). |
|
|
74
76
|
| `--cleanup-legacy` | off | After generating (or standalone), scan the project for legacy branding artifacts — iOS launch image PNGs, Android `default.png`, `appicon.png`, `res-long-*/res-notlong-*`, etc. — and remove them. Context-aware: reads `tiapp.xml` to decide what's safe. See `references/cleanup-legacy.md`. |
|
|
75
77
|
| `--aggressive` | off | With `--cleanup-legacy`, also remove `ldpi` density folders (<1% of active devices globally in 2026). Off by default to be conservative. |
|
|
76
78
|
| `--output <dir>` | `<project>/.ti-branding/` | Staging directory. Review before copying to `app/`. |
|
|
79
|
+
| `--in-place` | off | Skip the staging directory and write files directly into the project root. **Overwrites existing icons.** Ideal right after `ti create` when you want to replace the default Titanium/Alloy icons in one command. `--output` takes precedence if both are passed. |
|
|
80
|
+
| `--monochrome-master <path>` | — | Optional dedicated silhouette master for `ic_launcher_monochrome.png` + `ic_stat_notify.png`. Use this when your colored logo has multi-color detail that would collapse into a featureless blob when naively whitened (e.g. a painter's palette with 4 color dots — provide a monochrome variant with cutout holes instead so the detail survives in themed icons and notification status bar). Falls back to whitening the main master when not provided. |
|
|
81
|
+
| `--notes` | off | Print the full tiapp.xml snippets (iOS launch storyboard, Android launcher wiring, Android 12+ splash theme with Option A/B, FCM notification tint) and the padding tuning guide. Default output is a compact summary (~15 lines). |
|
|
77
82
|
| `--dry-run` | off | Print what would be generated/removed without writing or deleting. Works with both generation and `--cleanup-legacy`. |
|
|
78
83
|
|
|
79
84
|
## Safety reminders
|
|
@@ -13,8 +13,9 @@
|
|
|
13
13
|
gen_android_adaptive() {
|
|
14
14
|
local master="$1"
|
|
15
15
|
local bg="$2"
|
|
16
|
-
local padding="$3"
|
|
17
|
-
local res_root="$4"
|
|
16
|
+
local padding="$3" # percent per side
|
|
17
|
+
local res_root="$4" # e.g. /path/app/platform/android/res
|
|
18
|
+
local mono_master="${5:-}" # optional dedicated silhouette master
|
|
18
19
|
|
|
19
20
|
local densities=(mdpi hdpi xhdpi xxhdpi xxxhdpi)
|
|
20
21
|
local sizes=(108 162 216 324 432)
|
|
@@ -38,11 +39,22 @@ gen_android_adaptive() {
|
|
|
38
39
|
-strip \
|
|
39
40
|
"$dir/ic_launcher_background.png"
|
|
40
41
|
|
|
41
|
-
# Monochrome:
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
"$
|
|
42
|
+
# Monochrome: white silhouette with alpha. If a dedicated mono master was
|
|
43
|
+
# provided, render it fresh with the same padding. Otherwise derive from
|
|
44
|
+
# the colored foreground (naive whitening — may flatten complex logos).
|
|
45
|
+
if [[ -n "$mono_master" ]]; then
|
|
46
|
+
magick "$mono_master" \
|
|
47
|
+
-resize "${inner}x${inner}" \
|
|
48
|
+
-background none -gravity center -extent "${size}x${size}" \
|
|
49
|
+
-channel RGB -fill white -colorize 100 +channel \
|
|
50
|
+
-strip \
|
|
51
|
+
"$dir/ic_launcher_monochrome.png"
|
|
52
|
+
else
|
|
53
|
+
magick "$dir/ic_launcher_foreground.png" \
|
|
54
|
+
-channel RGB -fill white -colorize 100 +channel \
|
|
55
|
+
-strip \
|
|
56
|
+
"$dir/ic_launcher_monochrome.png"
|
|
57
|
+
fi
|
|
46
58
|
done
|
|
47
59
|
|
|
48
60
|
# anydpi-v26 binder directory (XML copied by caller from assets/ic_launcher.xml)
|
|
@@ -1,12 +1,17 @@
|
|
|
1
1
|
#!/usr/bin/env bash
|
|
2
|
-
# gen-ios.sh — produce
|
|
2
|
+
# gen-ios.sh — produce Titanium's two root-level iOS/Android icons:
|
|
3
3
|
#
|
|
4
|
-
#
|
|
5
|
-
#
|
|
6
|
-
# breathing room around the logo. Default 8% per side (logo fills 84% of the
|
|
7
|
-
# canvas), which matches Apple's HIG aesthetic for branded wordmarks.
|
|
4
|
+
# DefaultIcon.png 1024×1024, alpha preserved (universal / Android source)
|
|
5
|
+
# DefaultIcon-ios.png 1024×1024, alpha flattened over bg-color (iOS)
|
|
8
6
|
#
|
|
9
|
-
#
|
|
7
|
+
# This matches what `titanium` / `alloy new` ships out of the box: a fresh
|
|
8
|
+
# Alloy project contains both files in the project root, with DefaultIcon.png
|
|
9
|
+
# keeping transparency and DefaultIcon-ios.png flattened (Apple rejects alpha
|
|
10
|
+
# on App Store icon uploads).
|
|
11
|
+
#
|
|
12
|
+
# Padding is purely visual breathing room — iOS app icons have no launcher
|
|
13
|
+
# mask. Default 8% per side (logo fills 84% of the canvas), which matches
|
|
14
|
+
# Apple's HIG aesthetic for branded wordmarks.
|
|
10
15
|
|
|
11
16
|
gen_ios() {
|
|
12
17
|
local tight="$1" # tight master (aspect-preserved, transparent bg)
|
|
@@ -19,6 +24,16 @@ gen_ios() {
|
|
|
19
24
|
local size=1024
|
|
20
25
|
local inner=$(( size * (100 - 2 * padding) / 100 ))
|
|
21
26
|
|
|
27
|
+
# DefaultIcon.png — alpha preserved (matches `ti create` default for the
|
|
28
|
+
# universal icon source; Alloy/Android use this directly).
|
|
29
|
+
magick "$tight" \
|
|
30
|
+
-resize "${inner}x${inner}" \
|
|
31
|
+
-background none -gravity center -extent "${size}x${size}" \
|
|
32
|
+
-strip \
|
|
33
|
+
"$out_root/DefaultIcon.png"
|
|
34
|
+
|
|
35
|
+
# DefaultIcon-ios.png — flattened over bg-color. This is the file iOS
|
|
36
|
+
# actually ships; Apple rejects alpha on App Store icon uploads.
|
|
22
37
|
magick "$tight" \
|
|
23
38
|
-resize "${inner}x${inner}" \
|
|
24
39
|
-background none -gravity center -extent "${size}x${size}" \
|
|
@@ -26,5 +41,6 @@ gen_ios() {
|
|
|
26
41
|
-strip \
|
|
27
42
|
"$out_root/DefaultIcon-ios.png"
|
|
28
43
|
|
|
44
|
+
log_ok "DefaultIcon.png (1024×1024, ${padding}% padding, alpha preserved)"
|
|
29
45
|
log_ok "DefaultIcon-ios.png (1024×1024, ${padding}% padding, alpha flattened over $bg)"
|
|
30
46
|
}
|
|
@@ -1,28 +1,43 @@
|
|
|
1
1
|
#!/usr/bin/env bash
|
|
2
2
|
# gen-marketplace.sh — store-submission artwork.
|
|
3
3
|
#
|
|
4
|
-
# iTunesConnect.png
|
|
5
|
-
# MarketplaceArtwork.png
|
|
4
|
+
# iTunesConnect.png 1024×1024 (App Store)
|
|
5
|
+
# MarketplaceArtwork.png 512×512 (Google Play)
|
|
6
6
|
#
|
|
7
|
-
#
|
|
8
|
-
#
|
|
9
|
-
#
|
|
7
|
+
# Alpha handling depends on whether --bg-color was EXPLICITLY provided
|
|
8
|
+
# (tracked via the 5th argument, `flatten`):
|
|
9
|
+
# - flatten=0 (no --bg-color) → alpha preserved, matches `ti create` default
|
|
10
|
+
# - flatten=1 (--bg-color X) → alpha flattened on bg-color. Prevents the
|
|
11
|
+
# dark-mode-muddy-icon issue on Play Store
|
|
12
|
+
# and macOS App Store when the master has
|
|
13
|
+
# significant transparent areas.
|
|
14
|
+
#
|
|
15
|
+
# Uses the same --ios-padding as the iOS master (default 8%) so the three
|
|
16
|
+
# square icons share the same visual weight.
|
|
10
17
|
|
|
11
18
|
gen_marketplace() {
|
|
12
19
|
local tight="$1"
|
|
13
20
|
local bg="$2"
|
|
14
21
|
local padding="$3" # ios-padding percent per side
|
|
15
22
|
local out_root="$4"
|
|
23
|
+
local flatten="${5:-0}" # 1 when --bg-color was explicitly provided
|
|
16
24
|
|
|
17
25
|
mkdir -p "$out_root"
|
|
18
26
|
|
|
27
|
+
local flatten_args=()
|
|
28
|
+
local alpha_label="alpha"
|
|
29
|
+
if [[ "$flatten" == "1" ]]; then
|
|
30
|
+
flatten_args=(-background "$bg" -alpha remove -alpha off)
|
|
31
|
+
alpha_label="flat on $bg"
|
|
32
|
+
fi
|
|
33
|
+
|
|
19
34
|
# App Store (1024²)
|
|
20
35
|
local size_ios=1024
|
|
21
36
|
local inner_ios=$(( size_ios * (100 - 2 * padding) / 100 ))
|
|
22
37
|
magick "$tight" \
|
|
23
38
|
-resize "${inner_ios}x${inner_ios}" \
|
|
24
39
|
-background none -gravity center -extent "${size_ios}x${size_ios}" \
|
|
25
|
-
|
|
40
|
+
"${flatten_args[@]}" \
|
|
26
41
|
-strip \
|
|
27
42
|
"$out_root/iTunesConnect.png"
|
|
28
43
|
|
|
@@ -32,9 +47,9 @@ gen_marketplace() {
|
|
|
32
47
|
magick "$tight" \
|
|
33
48
|
-resize "${inner_play}x${inner_play}" \
|
|
34
49
|
-background none -gravity center -extent "${size_play}x${size_play}" \
|
|
35
|
-
|
|
50
|
+
"${flatten_args[@]}" \
|
|
36
51
|
-strip \
|
|
37
52
|
"$out_root/MarketplaceArtwork.png"
|
|
38
53
|
|
|
39
|
-
log_ok "Marketplace artwork: iTunesConnect.png (1024², ${padding}% padding), MarketplaceArtwork.png (512², ${padding}% padding)"
|
|
54
|
+
log_ok "Marketplace artwork: iTunesConnect.png (1024², ${padding}% padding, ${alpha_label}), MarketplaceArtwork.png (512², ${padding}% padding, ${alpha_label})"
|
|
40
55
|
}
|
|
@@ -4,11 +4,21 @@
|
|
|
4
4
|
# all non-transparent pixels become white and color information is discarded.
|
|
5
5
|
#
|
|
6
6
|
# Sizes per Android spec: mdpi=24px, hdpi=36, xhdpi=48, xxhdpi=72, xxxhdpi=96.
|
|
7
|
+
#
|
|
8
|
+
# Notification icons are NOT masked by the launcher, so they render as drawn.
|
|
9
|
+
# We trim any transparent padding baked into the master first, then scale the
|
|
10
|
+
# logo to fill the canvas edge-to-edge on its longer axis (with a 1px
|
|
11
|
+
# anti-aliasing margin per side). This matches what first-party Android apps
|
|
12
|
+
# ship (Gmail, Slack, Chrome) — the logo reaches the edge instead of sitting
|
|
13
|
+
# in a visibly padded box in the status bar.
|
|
14
|
+
#
|
|
15
|
+
# Material's 22dp-inside-24dp "live area" is a conservative guideline; in
|
|
16
|
+
# practice notification icons benefit from going closer to the edge because
|
|
17
|
+
# the status bar is already tiny.
|
|
7
18
|
|
|
8
19
|
gen_notification() {
|
|
9
20
|
local master="$1"
|
|
10
|
-
local
|
|
11
|
-
local res_root="$3"
|
|
21
|
+
local res_root="$2"
|
|
12
22
|
|
|
13
23
|
local densities=(mdpi hdpi xhdpi xxhdpi xxxhdpi)
|
|
14
24
|
local sizes=(24 36 48 72 96)
|
|
@@ -16,13 +26,15 @@ gen_notification() {
|
|
|
16
26
|
for i in "${!densities[@]}"; do
|
|
17
27
|
local d="${densities[$i]}"
|
|
18
28
|
local size="${sizes[$i]}"
|
|
19
|
-
#
|
|
20
|
-
|
|
21
|
-
|
|
29
|
+
# Edge-to-edge with a 1px anti-aliasing margin per side.
|
|
30
|
+
local inner=$(( size - 2 ))
|
|
31
|
+
(( inner < 1 )) && inner=1
|
|
22
32
|
local dir="$res_root/drawable-$d"
|
|
23
33
|
mkdir -p "$dir"
|
|
24
34
|
|
|
35
|
+
# Trim baked-in transparent padding from the master, then scale to inner.
|
|
25
36
|
magick "$master" \
|
|
37
|
+
-trim +repage \
|
|
26
38
|
-resize "${inner}x${inner}" \
|
|
27
39
|
-channel RGB -fill white -colorize 100 +channel \
|
|
28
40
|
-background none -gravity center -extent "${size}x${size}" \
|
|
@@ -30,5 +42,5 @@ gen_notification() {
|
|
|
30
42
|
"$dir/ic_stat_notify.png"
|
|
31
43
|
done
|
|
32
44
|
|
|
33
|
-
log_ok "Notification icons (white+alpha) × 5 densities"
|
|
45
|
+
log_ok "Notification icons (white+alpha, edge-to-edge) × 5 densities"
|
|
34
46
|
}
|
|
@@ -34,15 +34,21 @@ source "$LIB_DIR/gen-splash-icon.sh"
|
|
|
34
34
|
# -----------------------------------------------------------------------------
|
|
35
35
|
|
|
36
36
|
MASTER=""
|
|
37
|
+
MONOCHROME_MASTER=""
|
|
37
38
|
BG_COLOR="#FFFFFF"
|
|
38
|
-
|
|
39
|
-
|
|
39
|
+
BG_COLOR_EXPLICIT=0
|
|
40
|
+
PADDING=20
|
|
41
|
+
IOS_PADDING=4
|
|
40
42
|
WITH_NOTIFICATION=0
|
|
41
43
|
WITH_SPLASH_ICON=0
|
|
42
44
|
CLEANUP_LEGACY=0
|
|
43
45
|
AGGRESSIVE=0
|
|
44
46
|
OUTPUT=""
|
|
47
|
+
OUTPUT_EXPLICIT=0
|
|
45
48
|
DRY_RUN=0
|
|
49
|
+
IN_PLACE=0
|
|
50
|
+
IS_IN_PLACE=0
|
|
51
|
+
NOTES=0
|
|
46
52
|
PROJECT_ROOT="$(pwd)"
|
|
47
53
|
|
|
48
54
|
# -----------------------------------------------------------------------------
|
|
@@ -82,11 +88,13 @@ ARGUMENTS:
|
|
|
82
88
|
OPTIONS:
|
|
83
89
|
--bg-color <hex> Background color for adaptive layer + iOS alpha flatten.
|
|
84
90
|
Default: #FFFFFF
|
|
85
|
-
--padding <pct> Android safe-zone padding per side (0–40). Default:
|
|
86
|
-
(
|
|
91
|
+
--padding <pct> Android safe-zone padding per side (0–40). Default: 20
|
|
92
|
+
(Material spec floor is 19.44%; default 20 gives a
|
|
93
|
+
tiny buffer while keeping the logo visibly prominent.)
|
|
87
94
|
--ios-padding <pct> iOS/marketplace aesthetic padding per side (0–40).
|
|
88
|
-
Default:
|
|
89
|
-
is purely breathing room
|
|
95
|
+
Default: 4. iOS icons have no launcher mask — this
|
|
96
|
+
is purely breathing room. Production reference apps
|
|
97
|
+
(Mail, Safari, La Baraja) use 2-6% per side.
|
|
90
98
|
--with-notification Also generate ic_stat_notify.png × 5 densities.
|
|
91
99
|
--with-splash-icon Also generate splash_icon.png × 5 densities (Android 12+).
|
|
92
100
|
--cleanup-legacy After generating (or standalone), remove legacy branding
|
|
@@ -96,6 +104,17 @@ OPTIONS:
|
|
|
96
104
|
(<1% global market in 2026). Off by default.
|
|
97
105
|
--output <dir> Staging directory. Default: <project>/.ti-branding
|
|
98
106
|
--project <dir> Project root (default: current working directory).
|
|
107
|
+
--in-place Skip the staging directory — write files directly into
|
|
108
|
+
the project root. OVERWRITES existing icons. --output
|
|
109
|
+
takes precedence when both are passed.
|
|
110
|
+
--monochrome-master <p> Optional dedicated silhouette master for
|
|
111
|
+
ic_launcher_monochrome.png + ic_stat_notify.png.
|
|
112
|
+
Use when the colored logo has multi-color detail
|
|
113
|
+
that would collapse into a featureless blob when
|
|
114
|
+
naively whitened. Falls back to main master if omitted.
|
|
115
|
+
--notes Print full tiapp.xml snippets + padding tuning guide
|
|
116
|
+
after the run. Default is a compact summary — use this
|
|
117
|
+
when you need the config snippets to paste into tiapp.xml.
|
|
99
118
|
--dry-run Print what would be generated without writing files.
|
|
100
119
|
-h, --help Show this help.
|
|
101
120
|
|
|
@@ -113,15 +132,18 @@ EOF
|
|
|
113
132
|
while [[ $# -gt 0 ]]; do
|
|
114
133
|
case "$1" in
|
|
115
134
|
-h|--help) usage; exit 0 ;;
|
|
116
|
-
--bg-color) BG_COLOR="$2"; shift 2 ;;
|
|
135
|
+
--bg-color) BG_COLOR="$2"; BG_COLOR_EXPLICIT=1; shift 2 ;;
|
|
117
136
|
--padding) PADDING="$2"; shift 2 ;;
|
|
118
137
|
--ios-padding) IOS_PADDING="$2"; shift 2 ;;
|
|
119
138
|
--with-notification) WITH_NOTIFICATION=1; shift ;;
|
|
120
139
|
--with-splash-icon) WITH_SPLASH_ICON=1; shift ;;
|
|
121
140
|
--cleanup-legacy) CLEANUP_LEGACY=1; shift ;;
|
|
122
141
|
--aggressive) AGGRESSIVE=1; shift ;;
|
|
123
|
-
--output) OUTPUT="$2"; shift 2 ;;
|
|
142
|
+
--output) OUTPUT="$2"; OUTPUT_EXPLICIT=1; shift 2 ;;
|
|
124
143
|
--project) PROJECT_ROOT="$2"; shift 2 ;;
|
|
144
|
+
--in-place) IN_PLACE=1; shift ;;
|
|
145
|
+
--monochrome-master) MONOCHROME_MASTER="$2"; shift 2 ;;
|
|
146
|
+
--notes) NOTES=1; shift ;;
|
|
125
147
|
--dry-run) DRY_RUN=1; shift ;;
|
|
126
148
|
--) shift; break ;;
|
|
127
149
|
-*) log_err "Unknown option: $1"; usage >&2; exit 2 ;;
|
|
@@ -172,6 +194,14 @@ if [[ ! "$BG_COLOR" =~ ^#[0-9A-Fa-f]{6}$ ]]; then
|
|
|
172
194
|
exit 2
|
|
173
195
|
fi
|
|
174
196
|
|
|
197
|
+
# Resolve staging dir:
|
|
198
|
+
# explicit --output wins over --in-place (avoids ambiguity)
|
|
199
|
+
# --in-place (no --output) → write directly into the project root
|
|
200
|
+
# neither → default to .ti-branding/ inside the project
|
|
201
|
+
if [[ $IN_PLACE -eq 1 && $OUTPUT_EXPLICIT -eq 0 ]]; then
|
|
202
|
+
OUTPUT="$PROJECT_ROOT"
|
|
203
|
+
IS_IN_PLACE=1
|
|
204
|
+
fi
|
|
175
205
|
OUTPUT="${OUTPUT:-$PROJECT_ROOT/.ti-branding}"
|
|
176
206
|
|
|
177
207
|
# -----------------------------------------------------------------------------
|
|
@@ -191,11 +221,16 @@ if [[ -n "$MASTER" ]]; then
|
|
|
191
221
|
log_info "Master: $MASTER"
|
|
192
222
|
log_info "Background: $BG_COLOR"
|
|
193
223
|
log_info "Padding: Android ${PADDING}% / iOS ${IOS_PADDING}% per side"
|
|
194
|
-
|
|
224
|
+
if [[ $IS_IN_PLACE -eq 1 ]]; then
|
|
225
|
+
log_info "Writing IN PLACE to: $PROJECT_ROOT"
|
|
226
|
+
else
|
|
227
|
+
log_info "Staging: $OUTPUT"
|
|
228
|
+
fi
|
|
195
229
|
fi
|
|
196
230
|
[[ $WITH_NOTIFICATION -eq 1 ]] && log_info "Extras: + notification icons"
|
|
197
231
|
[[ $WITH_SPLASH_ICON -eq 1 ]] && log_info "Extras: + Android 12+ splash icon"
|
|
198
232
|
[[ $CLEANUP_LEGACY -eq 1 ]] && log_info "Cleanup: --cleanup-legacy$([[ $AGGRESSIVE -eq 1 ]] && echo " --aggressive")"
|
|
233
|
+
[[ $IS_IN_PLACE -eq 1 && $DRY_RUN -eq 0 ]] && log_warn "⚠ --in-place mode: files in your project will be OVERWRITTEN. Commit first if you want a rollback."
|
|
199
234
|
[[ $DRY_RUN -eq 1 ]] && log_warn "DRY RUN — no files will be written"
|
|
200
235
|
|
|
201
236
|
# -----------------------------------------------------------------------------
|
|
@@ -227,13 +262,27 @@ log_step "3/6 Preparing masters (square for iOS, tight for Android)"
|
|
|
227
262
|
PREPARED_BASE="$OUTPUT/_master"
|
|
228
263
|
MASTER_SQUARE="${PREPARED_BASE}_square.png"
|
|
229
264
|
MASTER_TIGHT="${PREPARED_BASE}_tight.png"
|
|
265
|
+
MONO_TIGHT=""
|
|
230
266
|
if [[ $DRY_RUN -eq 0 ]]; then
|
|
231
267
|
mkdir -p "$OUTPUT"
|
|
232
268
|
prepare_master "$MASTER" "$PREPARED_BASE"
|
|
233
269
|
log_ok "Square master: $MASTER_SQUARE"
|
|
234
270
|
log_ok "Tight master: $MASTER_TIGHT"
|
|
271
|
+
|
|
272
|
+
# Optional: prepare a dedicated monochrome master if provided.
|
|
273
|
+
if [[ -n "$MONOCHROME_MASTER" ]]; then
|
|
274
|
+
if [[ ! -f "$MONOCHROME_MASTER" ]]; then
|
|
275
|
+
log_err "Monochrome master not found: $MONOCHROME_MASTER"
|
|
276
|
+
exit 2
|
|
277
|
+
fi
|
|
278
|
+
local_mono_base="$OUTPUT/_master_mono"
|
|
279
|
+
prepare_master "$MONOCHROME_MASTER" "$local_mono_base"
|
|
280
|
+
MONO_TIGHT="${local_mono_base}_tight.png"
|
|
281
|
+
log_ok "Monochrome master (for ic_launcher_monochrome + ic_stat_notify): $MONO_TIGHT"
|
|
282
|
+
fi
|
|
235
283
|
else
|
|
236
284
|
log_info "[dry-run] would prepare: $MASTER_SQUARE + $MASTER_TIGHT"
|
|
285
|
+
[[ -n "$MONOCHROME_MASTER" ]] && log_info "[dry-run] would prepare monochrome master from: $MONOCHROME_MASTER"
|
|
237
286
|
fi
|
|
238
287
|
|
|
239
288
|
# Resolve target paths based on project layout
|
|
@@ -247,14 +296,14 @@ ROOT_STAGING="$OUTPUT"
|
|
|
247
296
|
log_step "4/6 Generating iOS master + marketplace artwork (square)"
|
|
248
297
|
if [[ $DRY_RUN -eq 0 ]]; then
|
|
249
298
|
gen_ios "$MASTER_TIGHT" "$BG_COLOR" "$IOS_PADDING" "$ROOT_STAGING"
|
|
250
|
-
gen_marketplace "$MASTER_TIGHT" "$BG_COLOR" "$IOS_PADDING" "$ROOT_STAGING"
|
|
299
|
+
gen_marketplace "$MASTER_TIGHT" "$BG_COLOR" "$IOS_PADDING" "$ROOT_STAGING" "$BG_COLOR_EXPLICIT"
|
|
251
300
|
else
|
|
252
|
-
log_info "[dry-run] would emit DefaultIcon-ios.png, iTunesConnect.png, MarketplaceArtwork.png"
|
|
301
|
+
log_info "[dry-run] would emit DefaultIcon.png, DefaultIcon-ios.png, iTunesConnect.png, MarketplaceArtwork.png"
|
|
253
302
|
fi
|
|
254
303
|
|
|
255
304
|
log_step "5/6 Generating Android adaptive + legacy launcher icons (tight)"
|
|
256
305
|
if [[ $DRY_RUN -eq 0 ]]; then
|
|
257
|
-
gen_android_adaptive "$MASTER_TIGHT" "$BG_COLOR" "$PADDING" "$ANDROID_RES"
|
|
306
|
+
gen_android_adaptive "$MASTER_TIGHT" "$BG_COLOR" "$PADDING" "$ANDROID_RES" "$MONO_TIGHT"
|
|
258
307
|
gen_android_legacy "$MASTER_TIGHT" "$BG_COLOR" "$PADDING" "$ANDROID_RES"
|
|
259
308
|
cp "$ASSETS_DIR/ic_launcher.xml" "$ANDROID_RES/mipmap-anydpi-v26/ic_launcher.xml"
|
|
260
309
|
log_ok "Adaptive icon XML bind: $ANDROID_RES/mipmap-anydpi-v26/ic_launcher.xml"
|
|
@@ -265,7 +314,8 @@ fi
|
|
|
265
314
|
if [[ $WITH_NOTIFICATION -eq 1 || $WITH_SPLASH_ICON -eq 1 ]]; then
|
|
266
315
|
log_step "6/6 Generating optional extras"
|
|
267
316
|
if [[ $WITH_NOTIFICATION -eq 1 && $DRY_RUN -eq 0 ]]; then
|
|
268
|
-
|
|
317
|
+
# Use monochrome master if provided, else fall back to main (whitened by the generator).
|
|
318
|
+
gen_notification "${MONO_TIGHT:-$MASTER_TIGHT}" "$ANDROID_RES"
|
|
269
319
|
elif [[ $WITH_NOTIFICATION -eq 1 ]]; then
|
|
270
320
|
log_info "[dry-run] would emit ic_stat_notify.png × 5 densities"
|
|
271
321
|
fi
|
|
@@ -285,11 +335,62 @@ fi
|
|
|
285
335
|
|
|
286
336
|
log_step "Done"
|
|
287
337
|
if [[ $DRY_RUN -eq 0 ]]; then
|
|
288
|
-
|
|
338
|
+
# In --in-place mode, intermediate master files (_master_square.png /
|
|
339
|
+
# _master_tight.png) land directly in the project root alongside the real
|
|
340
|
+
# branded assets. Clean them up so the user is only left with the 4 icons.
|
|
341
|
+
if [[ $IS_IN_PLACE -eq 1 ]]; then
|
|
342
|
+
rm -f "$OUTPUT/_master_square.png" "$OUTPUT/_master_tight.png"
|
|
343
|
+
log_ok "All assets written IN PLACE at: $PROJECT_ROOT"
|
|
344
|
+
else
|
|
345
|
+
log_ok "All assets staged at: $OUTPUT"
|
|
346
|
+
fi
|
|
347
|
+
|
|
348
|
+
# ---------------------------------------------------------------------------
|
|
349
|
+
# Post-generation output — compact summary by default, full notes with --notes.
|
|
350
|
+
# ---------------------------------------------------------------------------
|
|
351
|
+
|
|
352
|
+
if [[ $NOTES -eq 0 ]]; then
|
|
353
|
+
# Compact summary — only config/destination + 3-line next steps + hint.
|
|
354
|
+
echo
|
|
355
|
+
echo "${C_BOLD}Summary${C_RESET}"
|
|
356
|
+
echo " Background: ${BG_COLOR} Padding: Android ${PADDING}% / iOS ${IOS_PADDING}%"
|
|
357
|
+
if [[ $IS_IN_PLACE -eq 1 ]]; then
|
|
358
|
+
echo " Written in place to: $PROJECT_ROOT"
|
|
359
|
+
else
|
|
360
|
+
echo " Staged at: $OUTPUT"
|
|
361
|
+
fi
|
|
362
|
+
echo
|
|
363
|
+
echo "${C_BOLD}Next steps${C_RESET}"
|
|
364
|
+
if [[ $IS_IN_PLACE -eq 1 ]]; then
|
|
365
|
+
echo " • Preview the new icons in ${C_YELLOW}Preview.app${C_RESET}."
|
|
366
|
+
echo " • If something looks wrong: ${C_DIM}git checkout -- .${C_RESET}"
|
|
367
|
+
echo " • Rebuild: ${C_DIM}ti clean && ti build -p android -T emulator${C_RESET}"
|
|
368
|
+
else
|
|
369
|
+
case "$PROJECT_TYPE" in
|
|
370
|
+
alloy)
|
|
371
|
+
echo " • Preview in ${C_YELLOW}Preview.app${C_RESET}, then copy to project:"
|
|
372
|
+
echo " ${C_DIM}cp $OUTPUT/{DefaultIcon,DefaultIcon-ios,iTunesConnect,MarketplaceArtwork}.png $PROJECT_ROOT/${C_RESET}"
|
|
373
|
+
echo " ${C_DIM}cp -R $OUTPUT/app/platform/android/res/. $PROJECT_ROOT/app/platform/android/res/${C_RESET}"
|
|
374
|
+
;;
|
|
375
|
+
classic)
|
|
376
|
+
echo " • Preview in ${C_YELLOW}Preview.app${C_RESET}, then copy to project:"
|
|
377
|
+
echo " ${C_DIM}cp $OUTPUT/{DefaultIcon,DefaultIcon-ios,iTunesConnect,MarketplaceArtwork}.png $PROJECT_ROOT/${C_RESET}"
|
|
378
|
+
echo " ${C_DIM}cp -R $OUTPUT/platform/android/res/. $PROJECT_ROOT/platform/android/res/${C_RESET}"
|
|
379
|
+
;;
|
|
380
|
+
*)
|
|
381
|
+
echo " • Review ${C_YELLOW}$OUTPUT/${C_RESET} and copy files to their final paths manually."
|
|
382
|
+
;;
|
|
383
|
+
esac
|
|
384
|
+
echo " • Cleanup staging: ${C_DIM}rm -rf $OUTPUT${C_RESET}"
|
|
385
|
+
fi
|
|
386
|
+
echo
|
|
387
|
+
log_info "Pass ${C_BOLD}--notes${C_RESET} to print tiapp.xml snippets + padding tuning guide."
|
|
388
|
+
echo
|
|
389
|
+
exit 0
|
|
390
|
+
fi
|
|
289
391
|
|
|
290
392
|
# ---------------------------------------------------------------------------
|
|
291
|
-
#
|
|
292
|
-
# made, how to adjust, and what tiapp.xml glue is still needed.
|
|
393
|
+
# Full notes (with --notes) — tiapp.xml snippets, padding tuning, etc.
|
|
293
394
|
# ---------------------------------------------------------------------------
|
|
294
395
|
|
|
295
396
|
echo
|
|
@@ -302,11 +403,11 @@ if [[ $DRY_RUN -eq 0 ]]; then
|
|
|
302
403
|
echo
|
|
303
404
|
echo " If the logo looks ${C_DIM}pegado / cramped${C_RESET}: re-run with higher padding"
|
|
304
405
|
echo " --padding ${C_YELLOW}25-30${C_RESET} (Android)"
|
|
305
|
-
echo " --ios-padding ${C_YELLOW}
|
|
406
|
+
echo " --ios-padding ${C_YELLOW}8-12${C_RESET} (iOS)"
|
|
306
407
|
echo
|
|
307
408
|
echo " If the logo looks ${C_DIM}too small / lost${C_RESET}: re-run with lower padding"
|
|
308
409
|
echo " --padding ${C_YELLOW}19${C_RESET} (Android spec floor)"
|
|
309
|
-
echo " --ios-padding ${C_YELLOW}
|
|
410
|
+
echo " --ios-padding ${C_YELLOW}2-3${C_RESET} (matches first-party apps like Mail, Safari)"
|
|
310
411
|
|
|
311
412
|
echo
|
|
312
413
|
echo "${C_BOLD}Configuration reminders${C_RESET}"
|
|
@@ -339,72 +440,58 @@ EOF
|
|
|
339
440
|
|
|
340
441
|
if [[ $WITH_SPLASH_ICON -eq 1 ]]; then
|
|
341
442
|
case "$PROJECT_TYPE" in
|
|
342
|
-
alloy) SPLASH_DIR="app/platform/android/res/values
|
|
343
|
-
classic) SPLASH_DIR="platform/android/res/values
|
|
344
|
-
*) SPLASH_DIR="platform/android/res/values
|
|
443
|
+
alloy) SPLASH_DIR="app/platform/android/res/values" ;;
|
|
444
|
+
classic) SPLASH_DIR="platform/android/res/values" ;;
|
|
445
|
+
*) SPLASH_DIR="platform/android/res/values" ;;
|
|
345
446
|
esac
|
|
346
447
|
|
|
347
448
|
echo
|
|
348
|
-
echo " ${C_BOLD}3. Android 12+ splash screen —
|
|
449
|
+
echo " ${C_BOLD}3. Android 12+ splash screen — RECOMMENDED: match Titanium activity theme${C_RESET}"
|
|
349
450
|
echo
|
|
350
|
-
echo " ${C_YELLOW}Titanium SDK 13.x
|
|
351
|
-
echo "
|
|
352
|
-
echo "
|
|
451
|
+
echo " ${C_YELLOW}Titanium SDK 13.x${C_RESET} shows a system splash using your launcher icon on"
|
|
452
|
+
echo " Android 12+. If the system splash background does NOT match your first"
|
|
453
|
+
echo " Titanium activity background, you get a visible ${C_BOLD}FLICKER${C_RESET} at the end of"
|
|
454
|
+
echo " the splash (navy → white → content) right before index.js renders."
|
|
353
455
|
echo
|
|
354
|
-
echo "
|
|
355
|
-
echo "
|
|
356
|
-
echo "
|
|
456
|
+
echo " ${C_BOLD}Fix${C_RESET}: define a custom theme that inherits from a ${C_BOLD}Titanium parent${C_RESET} theme"
|
|
457
|
+
echo " and applies to the whole application. Keeps the ActionBar intact while"
|
|
458
|
+
echo " synchronizing the splash background with the activity background."
|
|
357
459
|
echo
|
|
358
|
-
echo " ${C_BOLD}Option A — Native platform (API 31+ only, no lib needed)${C_RESET}"
|
|
359
|
-
echo " ${C_DIM}Simpler. Works without adding any Gradle dependency. API <31 falls back${C_RESET}"
|
|
360
|
-
echo " ${C_DIM}to Titanium's default splash (your launcher icon).${C_RESET}"
|
|
361
460
|
echo " ${C_DIM}Create ${SPLASH_DIR}/splash_theme.xml:${C_RESET}"
|
|
362
461
|
cat <<EOF
|
|
363
462
|
<?xml version="1.0" encoding="utf-8"?>
|
|
364
463
|
<resources>
|
|
365
|
-
<style name="Theme.App.
|
|
464
|
+
<style name="Theme.App.Splash" parent="@style/Theme.Titanium.Light.NoTitle">
|
|
366
465
|
<item name="android:windowSplashScreenBackground">${BG_COLOR}</item>
|
|
367
|
-
<item name="android:windowSplashScreenAnimatedIcon">@
|
|
466
|
+
<item name="android:windowSplashScreenAnimatedIcon">@mipmap/ic_launcher</item>
|
|
368
467
|
</style>
|
|
369
468
|
</resources>
|
|
370
469
|
EOF
|
|
371
470
|
echo
|
|
372
|
-
echo " ${
|
|
373
|
-
echo " ${C_DIM}More complete (backward-compat, postSplashScreenTheme handoff). Requires${C_RESET}"
|
|
374
|
-
echo " ${C_DIM}adding the androidx.core:core-splashscreen library as a Gradle dep, which${C_RESET}"
|
|
375
|
-
echo " ${C_DIM}Titanium 13.x does NOT ship by default. To add it, create/edit${C_RESET}"
|
|
376
|
-
echo " ${C_DIM}app/platform/android/build.gradle with:${C_RESET}"
|
|
471
|
+
echo " ${C_DIM}Then in tiapp.xml under <android><manifest>:${C_RESET}"
|
|
377
472
|
cat <<'EOF'
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
EOF
|
|
382
|
-
echo " ${C_DIM}Then ${SPLASH_DIR}/splash_theme.xml uses the library theme:${C_RESET}"
|
|
383
|
-
cat <<EOF
|
|
384
|
-
<?xml version="1.0" encoding="utf-8"?>
|
|
385
|
-
<resources>
|
|
386
|
-
<style name="Theme.App.SplashScreen" parent="Theme.SplashScreen">
|
|
387
|
-
<item name="windowSplashScreenBackground">${BG_COLOR}</item>
|
|
388
|
-
<item name="windowSplashScreenAnimatedIcon">@drawable/splash_icon</item>
|
|
389
|
-
<item name="postSplashScreenTheme">@style/Theme.AppDerived</item>
|
|
390
|
-
</style>
|
|
391
|
-
</resources>
|
|
473
|
+
<application android:icon="@mipmap/ic_launcher"
|
|
474
|
+
android:theme="@style/Theme.App.Splash"
|
|
475
|
+
android:usesCleartextTraffic="false"/>
|
|
392
476
|
EOF
|
|
393
477
|
echo
|
|
394
|
-
echo " ${C_BOLD}
|
|
395
|
-
echo "
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
478
|
+
echo " ${C_BOLD}Parent theme options${C_RESET} (pick per your ActionBar needs):"
|
|
479
|
+
echo " ${C_DIM}@style/Theme.Titanium.Light — ActionBar + title bar${C_RESET}"
|
|
480
|
+
echo " ${C_DIM}@style/Theme.Titanium.Light.NoTitle — ActionBar, no title (common)${C_RESET}"
|
|
481
|
+
echo " ${C_DIM}@style/Theme.Titanium.Light.Fullscreen — no ActionBar, no status bar${C_RESET}"
|
|
482
|
+
echo " ${C_DIM}(plus Dark variants)${C_RESET}"
|
|
483
|
+
echo
|
|
484
|
+
echo " ${C_YELLOW}⚠ Inherit ONLY from Titanium parents${C_RESET} (${C_BOLD}Theme.Titanium.*${C_RESET}). Do NOT"
|
|
485
|
+
echo " inherit from ${C_DIM}@android:style/Theme.DeviceDefault.NoActionBar${C_RESET} on"
|
|
486
|
+
echo " ${C_BOLD}<application>${C_RESET} — that strips the ActionBar from every screen."
|
|
400
487
|
echo
|
|
401
|
-
echo " ${
|
|
402
|
-
echo "
|
|
403
|
-
echo "
|
|
404
|
-
echo "
|
|
488
|
+
echo " ${C_DIM}The splash_icon.png × 5 files are OPTIONAL — the theme above points${C_RESET}"
|
|
489
|
+
echo " ${C_DIM}windowSplashScreenAnimatedIcon at the launcher icon, which is usually${C_RESET}"
|
|
490
|
+
echo " ${C_DIM}what you want. Point it at @drawable/splash_icon only if you designed${C_RESET}"
|
|
491
|
+
echo " ${C_DIM}a distinct custom splash icon.${C_RESET}"
|
|
405
492
|
echo
|
|
406
|
-
echo " ${C_DIM}
|
|
407
|
-
echo " ${C_DIM}
|
|
493
|
+
echo " ${C_DIM}Reference: LM - La Baraja uses this exact pattern in production with${C_RESET}"
|
|
494
|
+
echo " ${C_DIM}zero flicker on Android 12+.${C_RESET}"
|
|
408
495
|
fi
|
|
409
496
|
|
|
410
497
|
if [[ $WITH_NOTIFICATION -eq 1 ]]; then
|
|
@@ -438,24 +525,31 @@ EOF
|
|
|
438
525
|
echo
|
|
439
526
|
echo "${C_BOLD}Next steps${C_RESET}"
|
|
440
527
|
echo
|
|
441
|
-
|
|
528
|
+
if [[ $IS_IN_PLACE -eq 1 ]]; then
|
|
529
|
+
echo " 1. Preview the new icons in ${C_YELLOW}Preview.app${C_RESET} — the files in your project"
|
|
530
|
+
echo " were overwritten directly (no staging directory was used)."
|
|
531
|
+
echo " 2. If something looks wrong, restore from git: ${C_DIM}git checkout -- .${C_RESET}"
|
|
532
|
+
echo " 3. Rebuild: ${C_DIM}ti clean && ti build -p android -T emulator${C_RESET}"
|
|
533
|
+
else
|
|
534
|
+
echo " 1. Preview in ${C_YELLOW}Preview.app${C_RESET} (never use ${C_DIM}open${C_RESET} without -a — triggers heavy editors)"
|
|
442
535
|
case "$PROJECT_TYPE" in
|
|
443
536
|
alloy)
|
|
444
537
|
echo " 2. If good, copy to project:"
|
|
445
|
-
echo " cp $OUTPUT/DefaultIcon-ios.png $OUTPUT/iTunesConnect.png $OUTPUT/MarketplaceArtwork.png $PROJECT_ROOT/"
|
|
538
|
+
echo " cp $OUTPUT/DefaultIcon.png $OUTPUT/DefaultIcon-ios.png $OUTPUT/iTunesConnect.png $OUTPUT/MarketplaceArtwork.png $PROJECT_ROOT/"
|
|
446
539
|
echo " cp -R $OUTPUT/app/platform/android/res/. $PROJECT_ROOT/app/platform/android/res/"
|
|
447
540
|
;;
|
|
448
541
|
classic)
|
|
449
542
|
echo " 2. If good, copy to project:"
|
|
450
|
-
echo " cp $OUTPUT/DefaultIcon-ios.png $OUTPUT/iTunesConnect.png $OUTPUT/MarketplaceArtwork.png $PROJECT_ROOT/"
|
|
543
|
+
echo " cp $OUTPUT/DefaultIcon.png $OUTPUT/DefaultIcon-ios.png $OUTPUT/iTunesConnect.png $OUTPUT/MarketplaceArtwork.png $PROJECT_ROOT/"
|
|
451
544
|
echo " cp -R $OUTPUT/platform/android/res/. $PROJECT_ROOT/platform/android/res/"
|
|
452
545
|
;;
|
|
453
546
|
*)
|
|
454
547
|
echo " 2. Review staging dir and copy files to their final paths manually."
|
|
455
548
|
;;
|
|
456
549
|
esac
|
|
457
|
-
|
|
458
|
-
|
|
550
|
+
echo " 3. Cleanup staging: rm -rf $OUTPUT"
|
|
551
|
+
echo " 4. Rebuild: ${C_DIM}ti clean && ti build -p android -T emulator${C_RESET}"
|
|
552
|
+
fi
|
|
459
553
|
echo
|
|
460
554
|
else
|
|
461
555
|
log_info "Dry-run complete. Re-run without --dry-run to write files."
|