Widget Customization
Customize the appearance and behavior of the Feedhog feedback widget.
Widget Customization
The Feedhog widget can be customized to match your brand and integrate seamlessly with your application.
Appearance Options
Position
Control where the widget appears on the page:
// Script tag
window.feedhogSettings = {
apiKey: 'fhpk_your_public_key',
position: 'bottom-right' // bottom-right, bottom-left, top-right, top-left
};
// React
<FeedhogWidget
apiKey="fhpk_your_public_key"
position="bottom-left"
/>Primary Color
Set your brand color for the trigger button and accent elements:
// Script tag
window.feedhogSettings = {
apiKey: 'fhpk_your_public_key',
primaryColor: '#8b5cf6' // Purple
};
// React
<FeedhogWidget
apiKey="fhpk_your_public_key"
primaryColor="#8b5cf6"
/>Common brand colors:
#3b82f6- Blue (default)#8b5cf6- Purple#10b981- Green#f59e0b- Amber#ef4444- Red#ec4899- Pink#06b6d4- Cyan
Trigger Button Text
Customize the floating button label:
// Script tag
window.feedhogSettings = {
apiKey: 'fhpk_your_public_key',
triggerText: 'Share Ideas'
};
// React
<FeedhogWidget
apiKey="fhpk_your_public_key"
triggerText="Share Ideas"
/>Ideas for trigger text:
- "Feedback" (default)
- "Share Ideas"
- "Got Ideas?"
- "Help Us Improve"
- "Suggest a Feature"
- "Report a Bug"
Modal Text
Customize the feedback modal's header:
// Script tag
window.feedhogSettings = {
apiKey: 'fhpk_your_public_key',
title: 'What would you like to see?',
subtitle: 'Help us build better products for you'
};
// React
<FeedhogWidget
apiKey="fhpk_your_public_key"
title="What would you like to see?"
subtitle="Help us build better products for you"
/>Custom Trigger Button
Hide the default trigger and create your own:
Basic Custom Button
'use client';
import { FeedhogWidget } from '@feedhog/widget/react';
export function CustomFeedback() {
return (
<>
<FeedhogWidget
apiKey="fhpk_your_public_key"
showTrigger={false}
/>
<button
onClick={() => window.FeedhogWidget?.open()}
className="fixed bottom-4 right-4 bg-blue-500 text-white px-4 py-2 rounded-full shadow-lg hover:bg-blue-600"
>
💡 Have an idea?
</button>
</>
);
}Integration with UI Library
Using shadcn/ui:
'use client';
import { FeedhogWidget } from '@feedhog/widget/react';
import { Button } from '@/components/ui/button';
import { MessageSquarePlus } from 'lucide-react';
export function FeedbackTrigger() {
return (
<>
<FeedhogWidget
apiKey="fhpk_your_public_key"
showTrigger={false}
/>
<Button
onClick={() => window.FeedhogWidget?.open()}
className="fixed bottom-6 right-6"
size="lg"
>
<MessageSquarePlus className="mr-2 h-5 w-5" />
Share Feedback
</Button>
</>
);
}Multiple Trigger Locations
Add feedback triggers in different parts of your app:
'use client';
import { FeedhogWidget } from '@feedhog/widget/react';
import { Button } from '@/components/ui/button';
export function AppLayout({ children }: { children: React.ReactNode }) {
return (
<>
<header className="flex justify-between p-4">
<Logo />
<nav>
<Button
variant="ghost"
onClick={() => window.FeedhogWidget?.open()}
>
Feedback
</Button>
</nav>
</header>
<main>{children}</main>
<footer className="p-4 text-center">
<a
href="#"
onClick={(e) => {
e.preventDefault();
window.FeedhogWidget?.open();
}}
>
Send us feedback
</a>
</footer>
<FeedhogWidget
apiKey="fhpk_your_public_key"
showTrigger={false}
/>
</>
);
}Context-Aware Trigger
Pre-fill context based on where the user clicked:
'use client';
import { FeedhogWidget } from '@feedhog/widget/react';
export function FeatureCard({ feature }: { feature: Feature }) {
return (
<div className="border rounded-lg p-4">
<h3>{feature.title}</h3>
<p>{feature.description}</p>
<button
onClick={() => {
// Store context that could be captured
sessionStorage.setItem('feedbackContext', JSON.stringify({
feature: feature.id,
page: window.location.pathname
}));
window.FeedhogWidget?.open();
}}
>
Request changes
</button>
</div>
);
}Complete Configuration Examples
SaaS Dashboard
'use client';
import { FeedhogWidget } from '@feedhog/widget/react';
import { useAuth } from '@/hooks/use-auth';
export function DashboardFeedback() {
const { user } = useAuth();
return (
<FeedhogWidget
apiKey={process.env.NEXT_PUBLIC_FEEDHOG_API_KEY!}
position="bottom-right"
primaryColor="#6366f1" // Indigo to match dashboard
triggerText="Feedback"
title="How can we improve?"
subtitle="Your feedback helps us build a better product"
user={user ? {
externalId: user.id,
email: user.email,
name: user.name,
metadata: {
plan: user.plan,
accountId: user.accountId,
role: user.role
}
} : undefined}
/>
);
}E-commerce
'use client';
import { FeedhogWidget } from '@feedhog/widget/react';
import { useCustomer } from '@/hooks/use-customer';
export function StoreFeedback() {
const { customer } = useCustomer();
return (
<FeedhogWidget
apiKey={process.env.NEXT_PUBLIC_FEEDHOG_API_KEY!}
position="bottom-left"
primaryColor="#059669" // Green for positive vibes
triggerText="Help Us"
title="Share your shopping experience"
subtitle="We read every piece of feedback"
user={customer ? {
externalId: customer.id,
email: customer.email,
name: customer.firstName,
metadata: {
totalOrders: customer.orderCount,
customerSince: customer.createdAt
}
} : undefined}
/>
);
}Developer Tool
'use client';
import { FeedhogWidget } from '@feedhog/widget/react';
import { useSession } from '@/hooks/use-session';
export function DevToolFeedback() {
const { session } = useSession();
return (
<FeedhogWidget
apiKey={process.env.NEXT_PUBLIC_FEEDHOG_API_KEY!}
position="top-right"
primaryColor="#f59e0b" // Amber for visibility
triggerText="Report Issue"
title="Found a bug or have a feature request?"
subtitle="Help us make this tool better"
user={session ? {
externalId: session.userId,
email: session.email,
metadata: {
plan: session.plan,
apiVersion: session.apiVersion
}
} : undefined}
/>
);
}Shadow DOM Isolation
The widget uses Shadow DOM to prevent CSS conflicts:
- Your site's CSS won't affect the widget
- The widget's CSS won't affect your site
- No need for CSS reset or scoping
This means:
- Global styles won't break the widget
- Tailwind/CSS frameworks work without conflicts
- Dark mode toggles won't affect widget (it has its own theme)
Z-Index Considerations
The widget uses high z-index values to stay on top. If you have modals or overlays that should appear above the widget, you may need to adjust your z-index:
/* Example: Make your modal appear above the widget */
.my-modal {
z-index: 10001; /* Widget uses ~10000 */
}Accessibility
The widget is built with accessibility in mind:
- Keyboard navigable (Tab, Enter, Escape)
- ARIA labels on interactive elements
- Focus management in modals
- Screen reader announcements
To ensure good accessibility:
- Keep trigger text descriptive
- Don't hide the trigger unless you provide an accessible alternative
- Ensure custom triggers have proper ARIA attributes
<button
onClick={() => window.FeedhogWidget?.open()}
aria-label="Open feedback form"
>
<FeedbackIcon />
</button>