Skip to content

Commit 5fa314a

Browse files
Merge branch 'master' into feat/tool-menuitems-and-components
2 parents 0a4647c + 44625a4 commit 5fa314a

81 files changed

Lines changed: 906 additions & 350 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.mcp.json

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
{
2+
"mcpServers": {
3+
"figma-dev-mode-mcp-server": {
4+
"url": "http://127.0.0.1:3845/mcp"
5+
}
6+
}
7+
}

CLAUDE.md

Lines changed: 137 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -47,20 +47,12 @@ MCP servers must be configured in Claude Desktop's configuration file. Without t
4747

4848
### Setting Up Figma MCP Server
4949

50-
1. **Create or update the configuration file**:
51-
```bash
52-
cat > ~/Library/Application\ Support/Claude/claude_desktop_config.json << 'EOF'
53-
{
54-
"mcpServers": {
55-
"figma-dev-mode-mcp-server": {
56-
"command": "npx",
57-
"args": ["-y", "@figma/mcp-server-figma-dev-mode"],
58-
"description": "Figma Dev Mode MCP server for extracting design specifications, code, and images from Figma files"
59-
}
60-
}
61-
}
62-
EOF
63-
```
50+
1. **Enable the Figma desktop MCP server**:
51+
- Open Figma Desktop app
52+
- Toggle to Dev Mode (`Shift+D`)
53+
- In the MCP server section of the inspect panel, click "Enable desktop MCP server"
54+
- The server runs at `http://127.0.0.1:3845/mcp`
55+
- The project `.mcp.json` already configures the connection for Claude Code
6456

6557
2. **Restart Claude Code**:
6658
- Stop Claude Code with `Ctrl+C` in the terminal
@@ -69,9 +61,12 @@ EOF
6961

7062
3. **Verify MCP tools are available**:
7163
- After restart, MCP tools should appear as:
72-
- `mcp__figma-dev-mode-mcp-server__get_code`
73-
- `mcp__figma-dev-mode-mcp-server__get_image`
64+
- `mcp__figma-dev-mode-mcp-server__get_design_context`
65+
- `mcp__figma-dev-mode-mcp-server__get_screenshot`
7466
- `mcp__figma-dev-mode-mcp-server__get_metadata`
67+
- `mcp__figma-dev-mode-mcp-server__get_variable_defs`
68+
- `mcp__figma-dev-mode-mcp-server__create_design_system_rules`
69+
- `mcp__figma-dev-mode-mcp-server__get_figjam`
7570

7671
### Figma Requirements
7772

@@ -83,19 +78,11 @@ For the Figma MCP server to work properly:
8378
### Troubleshooting MCP Issues
8479

8580
If MCP tools are not available:
86-
1. **Check configuration exists**: `cat ~/Library/Application\ Support/Claude/claude_desktop_config.json`
87-
2. **Verify correct package name**: Should be `@figma/mcp-server-figma-dev-mode` NOT `claude-talk-to-figma-mcp`
88-
3. **Verify server name matches**: Should be `figma-dev-mode-mcp-server` to match tool names
89-
4. **Verify Figma is running**: `ps aux | grep -i figma`
81+
1. **Verify Figma Desktop is running**: `ps aux | grep -i figma`
82+
2. **Verify Dev Mode is enabled**: Press `Shift+D` in Figma, enable MCP server in inspect panel
83+
3. **Check server is responding**: `curl -s http://127.0.0.1:3845/mcp`
84+
4. **Verify `.mcp.json` exists** in project root with correct URL (`http://127.0.0.1:3845/mcp`)
9085
5. **Restart Claude Code**: MCP connections are only established at startup
91-
6. **Check npx availability**: Ensure Node.js/npm is installed for npx command
92-
93-
### Why MCP Configuration is Required
94-
95-
- MCP servers are external processes that Claude Code connects to
96-
- Configuration tells Claude where to find and how to start MCP servers
97-
- Without the configuration file, Claude Code has no knowledge of available MCP servers
98-
- Previous sessions' MCP usage (recorded in `.claude/settings.local.json`) doesn't automatically enable MCP in new sessions
9986

10087
## Build Commands
10188

@@ -540,6 +527,119 @@ The shortcut bar displays different button combinations based on wallet state:
540527
4. Implement action handler in `HomeViewController+Shortcuts.swift`
541528
5. Update `reloadShortcuts()` logic if needed
542529

530+
### Figma MCP Asset Download Workflow (MANDATORY)
531+
532+
#### Overview
533+
The Figma MCP server exposes image assets via temporary localhost URLs (e.g., `http://localhost:3845/assets/{hash}.svg`). These URLs are **ephemeral** — they only exist while Figma Desktop is running and the MCP server is active. **Image files MUST be downloaded and saved to the project's asset catalog** so they can be committed to git and verified in the UI.
534+
535+
#### ⚠️ CRITICAL: Always Download Assets During Development
536+
When implementing UI from Figma designs, you MUST:
537+
1. **Download every image asset** referenced in the design context to a local file
538+
2. **Save it to the correct asset catalog location** in the project
539+
3. **Verify the asset displays correctly** in the running app before committing
540+
4. **Never reference localhost URLs in code** — they are only a transport mechanism
541+
542+
#### Step-by-Step Asset Download Process
543+
544+
**Step 1: Get design context from Figma MCP**
545+
Use `get_design_context` to retrieve the design. Image URLs appear as constants:
546+
```javascript
547+
const imgMayaLogo = "http://localhost:3845/assets/4b039921e0c1cdbe2b8ca56814e78264985c97a0.svg";
548+
```
549+
550+
**Step 2: Download each image asset**
551+
```bash
552+
# Download SVG asset from Figma MCP server
553+
curl -s -o /path/to/project/DashWallet/Resources/AppAssets.xcassets/IconName.imageset/icon.svg \
554+
"http://localhost:3845/assets/{hash}.svg"
555+
556+
# Download PNG asset if needed
557+
curl -s -o /path/to/project/DashWallet/Resources/AppAssets.xcassets/IconName.imageset/icon.png \
558+
"http://localhost:3845/assets/{hash}.png"
559+
```
560+
561+
**Step 3: Create or update Contents.json**
562+
563+
> **Shortcut bar icons**: Use `"original"` so that SVG fill colors are preserved in both UIKit (shortcut bar) and SwiftUI (selection sheet). Template rendering strips colors and applies system tint, which causes icons to appear grey in SwiftUI `Button` labels.
564+
565+
```json
566+
{
567+
"images" : [
568+
{
569+
"filename" : "icon.svg",
570+
"idiom" : "universal"
571+
}
572+
],
573+
"info" : {
574+
"author" : "xcode",
575+
"version" : 1
576+
},
577+
"properties" : {
578+
"preserves-vector-representation" : true,
579+
"template-rendering-intent" : "original"
580+
}
581+
}
582+
```
583+
584+
**Step 4: Verify the asset in the running app**
585+
- Build and run the app in Simulator
586+
- Navigate to the screen that uses the asset
587+
- Confirm the icon/image renders correctly (right icon, right color, right size)
588+
- Only after visual verification should the asset be staged for commit
589+
590+
**Step 5: Verify the file is valid before committing**
591+
```bash
592+
# Confirm file type
593+
file /path/to/imageset/icon.svg
594+
# Expected: SVG Scalable Vector Graphics image
595+
596+
# Confirm non-zero file size
597+
ls -la /path/to/imageset/icon.svg
598+
```
599+
600+
#### Batch Download Pattern
601+
When a design has multiple assets, download them all at once:
602+
```bash
603+
# Example: Download all assets for a new screen
604+
curl -s -o asset1.svg "http://localhost:3845/assets/{hash1}.svg"
605+
curl -s -o asset2.svg "http://localhost:3845/assets/{hash2}.svg"
606+
curl -s -o asset3.svg "http://localhost:3845/assets/{hash3}.svg"
607+
```
608+
609+
#### Important Notes
610+
- **Localhost URLs expire** when Figma Desktop closes or the MCP server stops
611+
- **Always download immediately** when you get design context — don't defer downloads
612+
- **SVG preferred over PNG** — SVGs scale perfectly and have smaller file sizes
613+
- **Verify before committing** — wrong or placeholder assets are a common source of UI bugs
614+
- **Asset catalog structure**: Each image needs its own `.imageset` folder with a `Contents.json`
615+
616+
#### ⚠️ CRITICAL: Clean SVGs for iOS Compatibility
617+
Figma MCP exports SVGs with **web-specific features that iOS cannot render**. You MUST clean every SVG after downloading:
618+
619+
| Figma SVG Feature | iOS Problem | Fix |
620+
|---|---|---|
621+
| `fill="var(--fill-0, #78C4F5)"` | CSS custom properties not supported — paths render invisible | Replace with plain hex: `fill="#78C4F5"` |
622+
| `width="100%" height="100%"` | iOS needs explicit pixel dimensions | Use viewBox dimensions: `width="36" height="36"` |
623+
| `preserveAspectRatio="none"` | Web-specific, causes rendering issues | Remove attribute |
624+
| `style="display: block;"` | Web-specific inline style | Remove attribute |
625+
| `overflow="visible"` | Web-specific | Remove attribute |
626+
627+
**Example cleanup:**
628+
```xml
629+
<!-- ❌ RAW from Figma MCP — will NOT render on iOS -->
630+
<svg preserveAspectRatio="none" width="100%" height="100%" overflow="visible"
631+
style="display: block;" viewBox="0 0 36 36" fill="none" xmlns="http://www.w3.org/2000/svg">
632+
<path d="M18 0C8.06..." fill="var(--fill-0, #78C4F5)"/>
633+
</svg>
634+
635+
<!-- ✅ CLEANED for iOS asset catalog -->
636+
<svg width="36" height="36" viewBox="0 0 36 36" fill="none" xmlns="http://www.w3.org/2000/svg">
637+
<path d="M18 0C8.06..." fill="#78C4F5"/>
638+
</svg>
639+
```
640+
641+
**If icons appear blank after adding SVGs**, the first thing to check is whether the SVG contains `var(--fill-0, ...)` or `width="100%"`.
642+
543643
### Icon Implementation Best Practices
544644

545645
#### When Updating Icons from Figma
@@ -549,14 +649,19 @@ The shortcut bar displays different button combinations based on wallet state:
549649
find /path/to/project -name "*.svg" -o -name "*.png" | grep -i "icon_name"
550650
```
551651

552-
2. **Use SVG directly from Figma** - Don't convert to PNG unnecessarily
553-
- Download SVG from Figma localhost server
652+
2. **Download SVG directly from Figma MCP** - Don't convert to PNG unnecessarily
653+
```bash
654+
# Download from Figma MCP localhost server and save to asset catalog
655+
curl -s -o /path/to/imageset/icon.svg "http://localhost:3845/assets/{hash}.svg"
656+
```
554657
- Save directly to appropriate imageset folder
555-
- Update Contents.json to reference SVG
658+
- Update Contents.json to reference the SVG filename
659+
- Verify the downloaded file is valid: `file /path/to/icon.svg`
556660

557-
3. **Verify icon usage** - Always test that the correct icon appears
661+
3. **Verify icon in running app** - Always build and visually confirm the correct icon appears
558662
- Wrong icons often indicate using placeholder or copied assets
559663
- Check that imageset name matches the one referenced in code
664+
- Run the app and navigate to the relevant screen before considering the task complete
560665

561666
4. **Clean up old assets** - Remove unused PNG files when replacing with SVG
562667
```bash

DashSyncCurrentCommit

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
753f9446cfd20ae5da996104a5870df839005d4c
1+
e272a368fa8b5a3fcaa637f5631352980dcc557f

DashWallet.xcodeproj/project.pbxproj

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1018,6 +1018,8 @@
10181018
C94F5E8829D3E7E30034FD57 /* GoogleService-Info.plist in Resources */ = {isa = PBXBuildFile; fileRef = C94F5E8729D3E7E30034FD57 /* GoogleService-Info.plist */; };
10191019
C94F5E8A29D3FCCF0034FD57 /* ShortcutAction.swift in Sources */ = {isa = PBXBuildFile; fileRef = C94F5E8929D3FCCF0034FD57 /* ShortcutAction.swift */; };
10201020
C94F5E8E29D404850034FD57 /* ShortcutCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = C94F5E8D29D404850034FD57 /* ShortcutCell.swift */; };
1021+
75B3C1A22E36100100CAFE02 /* ShortcutSelectionView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 75B3C1A12E36100100CAFE01 /* ShortcutSelectionView.swift */; };
1022+
75B3C1B22E36100100CAFE05 /* ShortcutCustomizeBannerView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 75B3C1B12E36100100CAFE04 /* ShortcutCustomizeBannerView.swift */; };
10211023
C94F5E9029D4060A0034FD57 /* ShortcutsView.swift in Sources */ = {isa = PBXBuildFile; fileRef = C94F5E8F29D4060A0034FD57 /* ShortcutsView.swift */; };
10221024
C956AF0C2A5B591A002FAB75 /* DashInputField.swift in Sources */ = {isa = PBXBuildFile; fileRef = C94D98202A4CC78F00F3BEE1 /* DashInputField.swift */; };
10231025
C956AF0D2A5B592E002FAB75 /* TappableLabel.swift in Sources */ = {isa = PBXBuildFile; fileRef = C9829CDD2A562822007132E4 /* TappableLabel.swift */; };
@@ -1393,6 +1395,8 @@
13931395
C9D2C84B2A320AA000D15901 /* UITableView+DashWallet.swift in Sources */ = {isa = PBXBuildFile; fileRef = 47F005FE297164600029EB10 /* UITableView+DashWallet.swift */; };
13941396
C9D2C84C2A320AA000D15901 /* TransferAmountViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 47C661B128FDC72700028A8D /* TransferAmountViewController.swift */; };
13951397
C9D2C84D2A320AA000D15901 /* ShortcutCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = C94F5E8D29D404850034FD57 /* ShortcutCell.swift */; };
1398+
75B3C1A32E36100100CAFE03 /* ShortcutSelectionView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 75B3C1A12E36100100CAFE01 /* ShortcutSelectionView.swift */; };
1399+
75B3C1B32E36100100CAFE06 /* ShortcutCustomizeBannerView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 75B3C1B12E36100100CAFE04 /* ShortcutCustomizeBannerView.swift */; };
13961400
C9D2C84F2A320AA000D15901 /* UIColor+DWStyle.m in Sources */ = {isa = PBXBuildFile; fileRef = 2A44312022CCA2A0009BAF7F /* UIColor+DWStyle.m */; };
13971401
C9D2C8502A320AA000D15901 /* DWEnvironment.m in Sources */ = {isa = PBXBuildFile; fileRef = FBEF3AF021823CD800917AB6 /* DWEnvironment.m */; };
13981402
C9D2C8512A320AA000D15901 /* AtmItemCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 47AE8BC928C1305E00490F5E /* AtmItemCell.swift */; };
@@ -3084,6 +3088,8 @@
30843088
C94F5E8729D3E7E30034FD57 /* GoogleService-Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = "GoogleService-Info.plist"; sourceTree = "<group>"; };
30853089
C94F5E8929D3FCCF0034FD57 /* ShortcutAction.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ShortcutAction.swift; sourceTree = "<group>"; };
30863090
C94F5E8D29D404850034FD57 /* ShortcutCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ShortcutCell.swift; sourceTree = "<group>"; };
3091+
75B3C1A12E36100100CAFE01 /* ShortcutSelectionView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ShortcutSelectionView.swift; sourceTree = "<group>"; };
3092+
75B3C1B12E36100100CAFE04 /* ShortcutCustomizeBannerView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ShortcutCustomizeBannerView.swift; sourceTree = "<group>"; };
30873093
C94F5E8F29D4060A0034FD57 /* ShortcutsView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ShortcutsView.swift; sourceTree = "<group>"; };
30883094
C956AF152A5C3301002FAB75 /* DWPressableButton.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DWPressableButton.h; sourceTree = "<group>"; };
30893095
C956AF162A5C3302002FAB75 /* DWPressableButton.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = DWPressableButton.m; sourceTree = "<group>"; };
@@ -3830,6 +3836,8 @@
38303836
children = (
38313837
2A2CD71F22F9B1B7008C7BC9 /* Models */,
38323838
C94F5E8D29D404850034FD57 /* ShortcutCell.swift */,
3839+
75B3C1B12E36100100CAFE04 /* ShortcutCustomizeBannerView.swift */,
3840+
75B3C1A12E36100100CAFE01 /* ShortcutSelectionView.swift */,
38333841
2A1AF6DC23C7681B00442AF5 /* DWShortcutCollectionViewCell~ipad.xib */,
38343842
2A1AF6DD23C7681B00442AF5 /* DWShortcutCollectionViewCell~iphone.xib */,
38353843
C94F5E8F29D4060A0034FD57 /* ShortcutsView.swift */,
@@ -9011,6 +9019,8 @@
90119019
47F005FF297164600029EB10 /* UITableView+DashWallet.swift in Sources */,
90129020
47C661B228FDC72700028A8D /* TransferAmountViewController.swift in Sources */,
90139021
C94F5E8E29D404850034FD57 /* ShortcutCell.swift in Sources */,
9022+
75B3C1B22E36100100CAFE05 /* ShortcutCustomizeBannerView.swift in Sources */,
9023+
75B3C1A22E36100100CAFE02 /* ShortcutSelectionView.swift in Sources */,
90149024
2A44312122CCA2A0009BAF7F /* UIColor+DWStyle.m in Sources */,
90159025
FBEF3AF121823CD800917AB6 /* DWEnvironment.m in Sources */,
90169026
47AE8BF028C1306000490F5E /* AtmItemCell.swift in Sources */,
@@ -9847,6 +9857,8 @@
98479857
C9D2C84B2A320AA000D15901 /* UITableView+DashWallet.swift in Sources */,
98489858
C9D2C84C2A320AA000D15901 /* TransferAmountViewController.swift in Sources */,
98499859
C9D2C84D2A320AA000D15901 /* ShortcutCell.swift in Sources */,
9860+
75B3C1B32E36100100CAFE06 /* ShortcutCustomizeBannerView.swift in Sources */,
9861+
75B3C1A32E36100100CAFE03 /* ShortcutSelectionView.swift in Sources */,
98509862
C943B4BB2A40A54600AF23C5 /* DWRequestsViewController.m in Sources */,
98519863
C9D2C84F2A320AA000D15901 /* UIColor+DWStyle.m in Sources */,
98529864
C9D2C8502A320AA000D15901 /* DWEnvironment.m in Sources */,

DashWallet/AppDelegate.m

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -97,7 +97,22 @@ - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(
9797
#if DASHPAY
9898
[DWGlobalOptions sharedInstance].dpInvitationFlowEnabled = YES;
9999
#endif
100-
100+
101+
// Shortcut customization banner state machine
102+
DWGlobalOptions *bannerOptions = [DWGlobalOptions sharedInstance];
103+
if (bannerOptions.shortcutBannerState == 0) {
104+
if (bannerOptions.shouldDisplayOnboarding) {
105+
// New install — defer banner to second app open
106+
bannerOptions.shortcutBannerState = 1;
107+
} else {
108+
// Update from prior version — show on this open
109+
bannerOptions.shortcutBannerState = 2;
110+
}
111+
} else if (bannerOptions.shortcutBannerState == 1) {
112+
// New install, second+ launch — ready to show
113+
bannerOptions.shortcutBannerState = 2;
114+
}
115+
101116
[DSLogger sharedInstance];
102117
[FIRApp configure];
103118
[ExploreDashObjcWrapper configure];
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
{
2+
"images" : [
3+
{
4+
"filename" : "atm.svg",
5+
"idiom" : "universal"
6+
}
7+
],
8+
"info" : {
9+
"author" : "xcode",
10+
"version" : 1
11+
},
12+
"properties" : {
13+
"preserves-vector-representation" : true,
14+
"template-rendering-intent" : "original"
15+
}
16+
}
Lines changed: 4 additions & 0 deletions
Loading
Binary file not shown.
Binary file not shown.
Binary file not shown.

0 commit comments

Comments
 (0)