Design UI components with realistic skeuomorphic styling
Design-style skill for Skeuomorphism: realistic material textures, physical lighting/bevels, and hardware metaphors like real buttons.
Maintainer of this project? Claim this page to edit the listing.
13.6.1Add to Favorites
Why it matters
Create user interfaces that mimic real-world physical objects and textures, applying skeuomorphic design principles to make digital elements feel familiar and tactile through shadows, gradients, and material representations.
Outcomes
What it gets done
Apply realistic shadows, highlights, and depth effects to UI elements
Design buttons, switches, and controls that resemble physical counterparts
Create texture overlays and material finishes for digital surfaces
Balance skeuomorphic detail with usability and performance constraints
Install
Add it to your toolbox
Run in your project directory:
curl -fsSL https://spark.entire.vc/get/ag-skeuomorphism | bash Overview
Skeuomorphism
A design-style skill for Skeuomorphism - realistic material textures, layered physical lighting effects, and real-world hardware metaphors like a mechanical button press - with matching Web CSS and SwiftUI implementations. Use it for audio/hardware control panels, classic productivity tool revivals, or nostalgic apps that want to feel like real physical objects rather than flat digital surfaces.
What it does
Skeuomorphism is a design-style child skill ('digital interfaces that look and behave like their physical counterparts'), part of the design-it family and not meant to be triggered directly. Three core principles: Realistic Textures (leather, brushed metal, wood grain, paper - the UI should feel like a physical object you can touch), Physical Lighting & Depth (intense attention to specular highlights, drop shadows, inner shadows, bevels, and ambient occlusion), and Real-World Metaphors (switches that look like hardware toggles, dials with physical notches, notepads with binding rings).
When to use - and when NOT to
Use it when the user's request matches this tactile, physically-realistic aesthetic - audio/hardware control panels, classic productivity tools, or nostalgic app revivals that want to feel like real objects rather than flat digital surfaces. As a design sub-style, it's selected by the parent design-it skill's routing rather than invoked on its own.
Inputs and outputs
Visual DNA is highly dependent on the material being simulated - Industrial Chic for metal/hardware, Monochromatic Brown for wood/leather - with fonts matching the physical object (typewriter fonts for paper, LCD fonts for digital screens, embossed sans-serifs for hardware buttons), and screws, stitching, glare, and layered gradients as the primary visual tools. The web implementation's signature technique is a circular "physical button": a brushed-metal effect combining a linear gradient with a texture image via background-blend-mode: overlay, then a stack of four separate box-shadows simultaneously simulating a top highlight bevel (inset light), bottom shading (inset dark), a drop shadow, and a fine edge shadow - and on :active, the shadows invert to look pressed-in while the button translates down 2px, simulating a real mechanical press.
.skeuo-button {
box-shadow:
inset 0 2px 4px rgba(255,255,255,0.8),
inset 0 -2px 4px rgba(0,0,0,0.4),
0 4px 6px rgba(0,0,0,0.5);
}
.skeuo-button:active { transform: translateY(2px); }
Integrations
SwiftUI reproduces the same brushed-metal button by layering a Circle filled with a top-to-bottom gradient (light to darker grey) as the base metal, plus a second stroked Circle using a white-to-clear gradient positioned only at the top to fake the inner highlight bevel - composing the physical-lighting illusion from multiple stacked native shapes rather than CSS box-shadow layering, with the same tracked press state for an active/pressed visual response.
Who it's for
Designers and developers building audio/hardware control interfaces, classic productivity tool revivals, or nostalgic app UI that wants to feel like a real physical object - buttons you can imagine pressing, materials you can imagine touching - rather than flat digital surfaces.
Source README
Skeuomorphism
"Digital interfaces that look and behave like their physical counterparts."
When to Use
Use this sub-style when the user's request matches the aesthetic described above. This is a child reference of the design-it skill and is not meant to be triggered directly.
Core Principles
- Realistic Textures: Leather, brushed metal, wood grain, paper. The UI should feel like a physical object you can touch.
- Physical Lighting & Depth: Intense attention to specular highlights, drop shadows, inner shadows, bevels, and ambient occlusion.
- Real-world Metaphors: Switches that look like hardware toggles, dials with physical notches, notepads with binding rings.
Visual DNA
- Colors: Highly dependent on the material being simulated. For rich, classic skeuomorphism, use the Industrial Chic (for metal/hardware) or Monochromatic Brown (for wood/leather) palettes.
- Typography: Fonts that match the physical object (e.g., typewriter fonts for paper, LCD fonts for digital screens, embossed sans-serifs for hardware buttons).
- Details: Screws, stitching, glare, and gradients are your primary tools.
Web Implementation
- Heavy use of layered background images (textures), complex gradients, and multiple box-shadows.
- CSS Example:
.skeuo-button {
/* Brushed metal effect */
background: linear-gradient(180deg, #e0e0e0 0%, #a0a0a0 100%),
url('brushed-metal-texture.png');
background-blend-mode: overlay;
border: 1px solid #7a7a7a;
border-radius: 50%;
width: 80px;
height: 80px;
/* Bevel, inner highlight, and drop shadow */
box-shadow:
inset 0 2px 4px rgba(255,255,255,0.8), /* Top highlight */
inset 0 -2px 4px rgba(0,0,0,0.4), /* Bottom shading */
0 4px 6px rgba(0,0,0,0.5), /* Drop shadow */
0 1px 1px rgba(0,0,0,0.2);
}
.skeuo-button:active {
/* Pressing the physical button */
box-shadow:
inset 0 4px 8px rgba(0,0,0,0.6),
inset 0 -1px 2px rgba(255,255,255,0.4),
0 1px 1px rgba(0,0,0,0.2);
transform: translateY(2px);
}
App Implementation
SwiftUI
struct SkeuoButton: View {
@State private var isPressed = false
var body: some View {
Button(action: {}) {
Text("POWER")
.font(.system(size: 14, weight: .bold))
.foregroundColor(.white)
.textCase(.uppercase)
}
.frame(width: 80, height: 80)
.background(
ZStack {
// Brushed metal base
Circle()
.fill(
LinearGradient(
colors: [Color(white: 0.88), Color(white: 0.63)],
startPoint: .top,
endPoint: .bottom
)
)
// Inner highlight (top bevel)
Circle()
.stroke(
LinearGradient(
colors: [.white.opacity(0.8), .clear],
startPoint: .top,
endPoint: .center
),
lineWidth: 2
)
.padding(1)
}
)
.clipShape(Circle())
// Outer bezel ring
.overlay(Circle().stroke(Color(white: 0.5), lineWidth: 1))
// Physical drop shadow
.shadow(color: .black.opacity(isPressed ? 0.2 : 0.5), radius: isPressed ? 2 : 6,
x: 0, y: isPressed ? 1 : 4)
.scaleEffect(isPressed ? 0.96 : 1.0)
.animation(.easeOut(duration: 0.1), value: isPressed)
.simultaneousGesture(
DragGesture(minimumDistance: 0)
.onChanged { _ in isPressed = true }
.onEnded { _ in isPressed = false }
)
}
}
- Stack multiple shapes (
Circle,RoundedRectangle) with different gradients to build up realistic depth. - Use
.overlay()with stroked shapes for highlight bezels along the edges. - The pressed state should reduce shadow AND scale - simulating a physical push.
Flutter
class SkeuoButton extends StatefulWidget {
@override
State<SkeuoButton> createState() => _SkeuoButtonState();
}
class _SkeuoButtonState extends State<SkeuoButton> {
bool _isPressed = false;
@override
Widget build(BuildContext context) {
return GestureDetector(
onTapDown: (_) => setState(() => _isPressed = true),
onTapUp: (_) => setState(() => _isPressed = false),
onTapCancel: () => setState(() => _isPressed = false),
child: AnimatedContainer(
duration: const Duration(milliseconds: 100),
width: 80,
height: 80,
decoration: BoxDecoration(
shape: BoxShape.circle,
// Brushed metal gradient
gradient: LinearGradient(
colors: [Colors.grey[300]!, Colors.grey[600]!],
begin: Alignment.topCenter,
end: Alignment.bottomCenter,
),
border: Border.all(color: Colors.grey[500]!, width: 1),
boxShadow: [
// Outer drop shadow
BoxShadow(
color: Colors.black.withOpacity(_isPressed ? 0.2 : 0.5),
blurRadius: _isPressed ? 4 : 12,
offset: Offset(0, _isPressed ? 2 : 6),
),
// Inner top highlight (faked with a light inset)
BoxShadow(
color: Colors.white.withOpacity(0.6),
blurRadius: 1,
offset: const Offset(0, -1),
spreadRadius: -1,
),
],
),
transform: Matrix4.identity()..scale(_isPressed ? 0.96 : 1.0),
alignment: Alignment.center,
child: const Text('POWER',
style: TextStyle(color: Colors.white, fontWeight: FontWeight.bold,
fontSize: 14, shadows: [
Shadow(color: Colors.black54, offset: Offset(0, 1), blurRadius: 2),
])),
),
);
}
}
- Use
AnimatedContainerfor smooth press transitions. AdjustboxShadow,transform, and gradient on tap. - Layer
BoxShadowentries: one for the outer drop shadow, one for the inner top-edge highlight. - For complex textures (leather, wood), use
DecorationImagewith an asset file insideBoxDecoration.
React Native
const SkeuoButton = () => {
const [pressed, setPressed] = useState(false);
return (
<Pressable
onPressIn={() => setPressed(true)}
onPressOut={() => setPressed(false)}
style={{
width: 80,
height: 80,
borderRadius: 40,
alignItems: 'center',
justifyContent: 'center',
// Metal gradient must be done via an image or LinearGradient component
backgroundColor: '#A0A0A0',
borderWidth: 1,
borderColor: '#7A7A7A',
// Shadow changes on press
shadowColor: '#000',
shadowOffset: { width: 0, height: pressed ? 1 : 4 },
shadowOpacity: pressed ? 0.2 : 0.5,
shadowRadius: pressed ? 2 : 6,
elevation: pressed ? 2 : 8,
transform: [{ scale: pressed ? 0.96 : 1 }],
}}
>
<Text style={{
color: '#FFF',
fontWeight: '700',
fontSize: 14,
textShadowColor: 'rgba(0,0,0,0.5)',
textShadowOffset: { width: 0, height: 1 },
textShadowRadius: 2,
}}>
POWER
</Text>
</Pressable>
);
};
- For realistic textures, use
ImageBackgroundwith exported texture assets (leather.png, brushed-metal.png). - Use
PressablewithonPressIn/onPressOutto animate shadow depth, scale, and opacity changes. - Complex gradient bevels require
react-native-linear-gradientorexpo-linear-gradient.
Jetpack Compose
@Composable
fun SkeuoButton() {
var isPressed by remember { mutableStateOf(false) }
val scale by animateFloatAsState(if (isPressed) 0.96f else 1f)
val elevation by animateDpAsState(if (isPressed) 2.dp else 8.dp)
Box(
modifier = Modifier
.size(80.dp)
.graphicsLayer { scaleX = scale; scaleY = scale }
.shadow(elevation, CircleShape)
.clip(CircleShape)
.background(
Brush.verticalGradient(
colors = listOf(Color(0xFFE0E0E0), Color(0xFFA0A0A0))
)
)
.border(1.dp, Color(0xFF7A7A7A), CircleShape)
.pointerInput(Unit) {
detectTapGestures(
onPress = {
isPressed = true
tryAwaitRelease()
isPressed = false
}
)
},
contentAlignment = Alignment.Center,
) {
Text("POWER",
color = Color.White,
fontWeight = FontWeight.Bold,
fontSize = 14.sp,
style = TextStyle(shadow = Shadow(
color = Color.Black.copy(alpha = 0.5f),
offset = Offset(0f, 2f),
blurRadius = 4f,
)))
}
}
- Use
Brush.verticalGradient()for metallic surfaces andModifier.border()withCircleShapefor bezels. - Animate
shadowelevation andgraphicsLayer { scaleX/scaleY }on press for realistic physical push. - For textures, use
Modifier.paint(painterResource(R.drawable.brushed_metal))as a background.
Do's and Don'ts
- DO: Ensure the metaphor makes sense for the user's task.
- DON'T: Overuse it to the point of clutter. Keep the interactive elements highly realistic, but let the structural layout remain clean.
Limitations
- This is a styling reference and does not replace environment-specific validation, accessibility testing, or expert review.
- Ensure appropriate contrast ratios and responsive behaviors are verified separately.
FAQ
Common questions
Discussion
Questions & comments ยท 0
Sign In Sign in to leave a comment.