1
0
mirror of https://github.com/vercel/commerce.git synced 2025-05-31 21:46:58 +00:00

fix last bug

This commit is contained in:
Lee Robinson 2024-07-28 22:56:37 -05:00
parent 16b222a22e
commit e938e0783d
4 changed files with 40 additions and 18 deletions

@ -2,11 +2,12 @@
import { ArrowLeftIcon, ArrowRightIcon } from '@heroicons/react/24/outline';
import { GridTileImage } from 'components/grid/tile';
import { useProduct } from 'components/product/product-context';
import { useProduct, useUpdateURL } from 'components/product/product-context';
import Image from 'next/image';
export function Gallery({ images }: { images: { src: string; altText: string }[] }) {
const { state, updateImage } = useProduct();
const updateURL = useUpdateURL();
const imageIndex = state.image ? parseInt(state.image) : 0;
const nextImageIndex = imageIndex + 1 < images.length ? imageIndex + 1 : 0;
@ -33,7 +34,10 @@ export function Gallery({ images }: { images: { src: string; altText: string }[]
<div className="absolute bottom-[15%] flex w-full justify-center">
<div className="mx-auto flex h-11 items-center rounded-full border border-white bg-neutral-50/80 text-neutral-500 backdrop-blur dark:border-black dark:bg-neutral-900/80">
<button
formAction={() => updateImage(previousImageIndex.toString())}
formAction={() => {
const newState = updateImage(previousImageIndex.toString());
updateURL(newState);
}}
aria-label="Previous product image"
className={buttonClassName}
>
@ -41,7 +45,10 @@ export function Gallery({ images }: { images: { src: string; altText: string }[]
</button>
<div className="mx-1 h-6 w-px bg-neutral-500"></div>
<button
formAction={() => updateImage(nextImageIndex.toString())}
formAction={() => {
const newState = updateImage(nextImageIndex.toString());
updateURL(newState);
}}
aria-label="Next product image"
className={buttonClassName}
>
@ -60,7 +67,10 @@ export function Gallery({ images }: { images: { src: string; altText: string }[]
return (
<li key={image.src} className="h-20 w-20">
<button
formAction={() => updateImage(index.toString())}
formAction={() => {
const newState = updateImage(index.toString());
updateURL(newState);
}}
aria-label="Select product image"
className="h-full w-full"
>

@ -11,14 +11,13 @@ type ProductState = {
type ProductContextType = {
state: ProductState;
updateOption: (name: string, value: string) => void;
updateImage: (index: string) => void;
updateOption: (name: string, value: string) => ProductState;
updateImage: (index: string) => ProductState;
};
const ProductContext = createContext<ProductContextType | undefined>(undefined);
export function ProductProvider({ children }: { children: React.ReactNode }) {
const router = useRouter();
const searchParams = useSearchParams();
const getInitialState = () => {
@ -38,17 +37,15 @@ export function ProductProvider({ children }: { children: React.ReactNode }) {
);
const updateOption = (name: string, value: string) => {
setOptimisticState({ [name]: value });
const newParams = new URLSearchParams(window.location.search);
newParams.set(name, value);
router.push(`?${newParams.toString()}`, { scroll: false });
const newState = { [name]: value };
setOptimisticState(newState);
return { ...state, ...newState };
};
const updateImage = (index: string) => {
setOptimisticState({ image: index });
const newParams = new URLSearchParams(window.location.search);
newParams.set('image', index);
router.push(`?${newParams.toString()}`, { scroll: false });
const newState = { image: index };
setOptimisticState(newState);
return { ...state, ...newState };
};
const value = useMemo(
@ -70,3 +67,15 @@ export function useProduct() {
}
return context;
}
export function useUpdateURL() {
const router = useRouter();
return (state: ProductState) => {
const newParams = new URLSearchParams(window.location.search);
Object.entries(state).forEach(([key, value]) => {
newParams.set(key, value);
});
router.push(`?${newParams.toString()}`, { scroll: false });
};
}

@ -1,7 +1,7 @@
'use client';
import clsx from 'clsx';
import { useProduct } from 'components/product/product-context';
import { useProduct, useUpdateURL } from 'components/product/product-context';
import { ProductOption, ProductVariant } from 'lib/shopify/types';
type Combination = {
@ -18,6 +18,7 @@ export function VariantSelector({
variants: ProductVariant[];
}) {
const { state, updateOption } = useProduct();
const updateURL = useUpdateURL();
const hasNoOptionsOrJustOneOption =
!options.length || (options.length === 1 && options[0]?.values.length === 1);
@ -62,7 +63,10 @@ export function VariantSelector({
return (
<button
formAction={() => updateOption(optionNameLowerCase, value)}
formAction={() => {
const newState = updateOption(optionNameLowerCase, value);
updateURL(newState);
}}
key={value}
aria-disabled={!isAvailableForSale}
disabled={!isAvailableForSale}

@ -8,7 +8,6 @@ export function WelcomeToast() {
// ignore if screen height is too small
if (window.innerHeight < 650) return;
if (!document.cookie.includes('welcome-toast=2')) {
console.log('Welcome to Next.js Commerce!');
toast('🛍️ Welcome to Next.js Commerce!', {
id: 'welcome-toast',
duration: Infinity,