theme-ui#useThemeUI TypeScript Examples

The following examples show how to use theme-ui#useThemeUI. You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: [handle].tsx    From nextjs-shopify with MIT License 6 votes vote down vote up
export default function Handle({
  product,
  page,
}: InferGetStaticPropsType<typeof getStaticProps>) {
  const router = useRouter()
  const isLive = !Builder.isEditing && !Builder.isPreviewing
  const { theme } = useThemeUI()
  // This includes setting the noindex header because static files always return a status 200 but the rendered not found page page should obviously not be indexed
  if (!product && isLive) {
    return (
      <>
        <Head>
          <meta name="robots" content="noindex" />
          <meta name="title"></meta>
        </Head>
        <DefaultErrorPage statusCode={404} />
      </>
    )
  }

  return router.isFallback && isLive ? (
    <h1>Loading...</h1> // TODO (BC) Add Skeleton Views
  ) : (
    <BuilderComponent
      isStatic
      key={product!.id}
      model={builderModel}
      data={{ product, theme }}
      {...(page && { content: page })}
    />
  )
}
Example #2
Source File: index.tsx    From theme-ui-sketchy with MIT License 6 votes vote down vote up
ThemeJson = () => {
  const theme = useThemeUI()
  return (
    <textarea
      value={JSON.stringify(theme, null, 2)}
      rows={16}
      readOnly
      sx={{
        width: "100%",
        fontFamily: "monospace",
        bg: "muted",
        p: 2,
        border: 0,
        borderRadius: "sketchy3",
      }}
    />
  )
}
Example #3
Source File: Logo.tsx    From slice-machine with Apache License 2.0 6 votes vote down vote up
Logo: React.FC = () => {
  const { theme } = useThemeUI();
  return (
    <Box p={2}>
      <Link href="/" passHref>
        <ThemeLink variant="links.invisible">
          <Flex sx={{ alignItems: "center" }}>
            <SliceMachineLogo
              width="32px"
              height="32px"
              fill={theme.colors?.text as string}
            />
            <Heading as="h5" sx={{ ml: 2 }}>
              Slice Machine
            </Heading>
          </Flex>
        </ThemeLink>
      </Link>
    </Box>
  );
}
Example #4
Source File: index.tsx    From slice-machine with Apache License 2.0 6 votes vote down vote up
CodeBlock: React.FC<{
  children: string;
  lang?: Language;
  sx?: ThemeUIStyleObject;
  codeStyle?: React.CSSProperties;
}> = ({ children, lang, sx, codeStyle }) => {
  const { theme } = useThemeUI();
  const text = lang
    ? hljs.highlight(children, { language: lang }).value
    : hljs.highlightAuto(children, DEFAULT_LANGUAGES).value;

  return (
    <Flex as="pre" sx={sx}>
      <code
        className="hljs"
        style={{
          overflowX: "auto",
          padding: "3px 5px",
          borderRadius: "6px",
          border: "1px solid",
          borderColor: String(theme.colors?.textClear),
          ...codeStyle,
        }}
        dangerouslySetInnerHTML={{ __html: text }}
      />
    </Flex>
  );
}
Example #5
Source File: _app.tsx    From slice-machine with Apache License 2.0 6 votes vote down vote up
RemoveDarkMode: React.FunctionComponent = ({ children }) => {
  const { setColorMode } = useThemeUI();
  useEffect(() => {
    if (setColorMode) {
      setColorMode("light");
    }
  }, []);

  return <>{children}</>;
}
Example #6
Source File: onboarding.tsx    From slice-machine with Apache License 2.0 6 votes vote down vote up
WelcomeSlide = ({ onClick }: { onClick: () => void }) => {
  const { theme } = useThemeUI();

  return (
    <>
      <Flex sx={{ ...imageSx }}>
        <SliceMachineLogo
          width={imageSx.width}
          height={imageSx.height}
          fill={theme.colors?.purple as string}
        />
      </Flex>
      <Header>Welcome to Slice Machine</Header>
      <SubHeader>Prismic’s local component development tool</SubHeader>
      <Button data-cy="get-started" onClick={onClick} title="start onboarding">
        Get Started
      </Button>
    </>
  );
}
Example #7
Source File: CodeBlockWithCopy.tsx    From slice-machine with Apache License 2.0 5 votes vote down vote up
CodeBlockWithCopy: React.FC<{ children: string }> = ({ children }) => {
  const { theme } = useThemeUI();
  const [isCopied, setIsCopied] = useState(false);

  const copy = (): void => {
    children &&
      navigator.clipboard.writeText(children).then(() => {
        setIsCopied(true);
        setTimeout(() => {
          setIsCopied(false);
        }, 1200);
      });
  };

  return (
    <Box sx={{ position: "relative" }}>
      <CodeBlock codeStyle={{ padding: "16px", width: "100%" }}>
        {children}
      </CodeBlock>
      <Button
        onClick={copy}
        sx={{
          position: "absolute",
          top: "4px",
          right: "4px",
          width: 24,
          height: 24,
          display: "flex",
          justifyContent: "center",
          alignItems: "center",
          p: 0,
        }}
      >
        {isCopied ? (
          <MdCheck
            size={16}
            color={theme?.colors?.success as string | undefined}
          />
        ) : (
          <MdContentCopy size={14} />
        )}
      </Button>
    </Box>
  );
}
Example #8
Source File: CodeBlock.tsx    From slice-machine with Apache License 2.0 5 votes vote down vote up
CodeBlock: React.FC<CodeBlockProps> = ({ code, lang }) => {
  const { theme } = useThemeUI();

  const [isCopied, setIsCopied] = useState(false);

  const copy = (): void => {
    code &&
      navigator.clipboard.writeText(code).then(() => {
        setIsCopied(true);
        setTimeout(() => {
          setIsCopied(false);
        }, 1200);
      });
  };

  return code ? (
    <Flex
      sx={{
        p: 2,
        px: 3,
        alignItems: "center",
        borderTop: "1px solid",
        borderColor: "borders",
        justifyContent: "space-between",
      }}
    >
      <Flex
        sx={{
          alignItems: "center",
          display: ["none", "none", "flex"],
          maxWidth: "80%",
        }}
      >
        <BsCode
          size={26}
          color={theme?.colors?.icons as string | undefined}
          style={{
            border: "1px solid",
            borderColor: theme?.colors?.borders as string | undefined,
            borderRadius: "3px",
            padding: "4px",
            marginRight: "2px",
          }}
        />
        <Code
          sx={{
            margin: "0px 8px",
            border: "none",
            borderRadius: "3px",
            fontSize: "13px",
          }}
          lang={lang}
        >
          {code}
        </Code>
      </Flex>
      <Box>
        <Button onClick={copy} variant="textButton">
          {isCopied ? (
            <MdCheck
              size={16}
              color={theme?.colors?.success as string | undefined}
              style={buttonIconStyle}
            />
          ) : (
            <BiCopy size={16} style={buttonIconStyle} />
          )}
          <Text
            as="span"
            sx={{ display: ["none", "inline", "none", "inline"] }}
          >
            &nbsp;Copy
          </Text>
        </Button>
      </Box>
    </Flex>
  ) : null;
}
Example #9
Source File: Navbar.tsx    From nextjs-shopify with MIT License 4 votes vote down vote up
Navbar: FC = () => {
  const [announcement, setAnnouncement] = useState()
  const { theme } = useThemeUI()
  const { navigationLinks, logo } = useUI()
  const cart = useCart()

  useEffect(() => {
    async function fetchContent() {
      const items = cart?.lineItems || []
      const anouncementContent = await builder
        .get('announcement-bar', {
          cacheSeconds: 120,
          userAttributes: {
            itemInCart: items.map((item: any) => item.variant.product.handle),
          } as any,
        })
        .toPromise()
      setAnnouncement(anouncementContent)
    }
    fetchContent()
  }, [cart?.lineItems])

  return (
    <React.Fragment>
      <BuilderComponent
        content={announcement}
        data={{ theme }}
        model="announcement-bar"
      />
      <Themed.div
        as="header"
        sx={{
          margin: `0 auto`,
          maxWidth: 1920,
          py: 2,
          px: 2,
          display: 'flex',
          justifyContent: 'space-between',
          alignItems: 'center',
          position: 'relative',
        }}
      >
        <Themed.div
          sx={{
            display: ['none', 'none', 'flex'],
            flexBasis: 0,
            minWidth: 240,
            justifyContent: 'space-evenly',
          }}
        >
          {navigationLinks?.map((link, index) => (
            <Themed.a
              key={index}
              sx={{ padding: 10, minWidth: 90 }}
              as={Link}
              href={link.link}
            >
              {link.title}
            </Themed.a>
          ))}
        </Themed.div>
        <Themed.div
          sx={{
            transform: 'translateX(-50%)',
            left: '50%',
            position: 'absolute',
          }}
        >
          <Themed.h1
            sx={{
              fontSize: 20,
              fontWeight: 'bold',
            }}
          >
            {logo && logo.image && (
              <Themed.a
                as={Link}
                href="/"
                sx={{
                  letterSpacing: -1,
                  textDecoration: `none`,
                  paddingLeft: '5px',
                }}
              >
                <Image
                  layout="fixed"
                  width={logo.width}
                  height={logo.height}
                  src={logo.image}
                ></Image>
              </Themed.a>
            )}
            {logo && logo.text && !logo.image && (
              <Themed.a
                as={Link}
                href="/"
                sx={{
                  letterSpacing: -1,
                  textDecoration: `none`,
                  paddingLeft: '5px',
                }}
              >
                {logo.text}
              </Themed.a>
            )}
          </Themed.h1>
        </Themed.div>
        <Themed.div
          sx={{
            display: 'flex',
            minWidth: 140,
            width: '100%',
            justifyContent: ['space-between', 'flex-end'],
          }}
        >
          <Searchbar />
          <UserNav />
        </Themed.div>
      </Themed.div>
    </React.Fragment>
  )
}
Example #10
Source File: index.tsx    From slice-machine with Apache License 2.0 4 votes vote down vote up
function ListItem<F extends TabField, S extends AnyObjectSchema>({
  item,
  index,
  deleteItem,
  enterEditMode,
  modelFieldName,
  renderFieldAccessor,

  HintElement,

  CustomEditElement,
  CustomEditElements,
  widget,

  draggableId,

  children,
}: ListItemProps<F, S>): JSX.Element {
  const { theme } = useThemeUI();
  const {
    key,
    // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment
    value: { config },
  } = item;

  return (
    <Fragment>
      <Draggable draggableId={draggableId} index={index}>
        {(provided) => (
          <Fragment>
            <Li
              ref={provided.innerRef}
              {...provided.draggableProps}
              Component={Box}
              sx={{
                p: 0,
                mx: 0,
                my: 3,
              }}
            >
              <Flex sx={{ width: "100%" }}>
                <SliceMachineIconButton
                  label="Reorder slice field (drag and drop)"
                  Icon={FaBars}
                  color={theme.colors?.icons as string}
                  mr={1}
                  mt={3}
                  {...provided.dragHandleProps}
                />
                <Box
                  sx={{
                    bg: "headSection",
                    width: "100%",
                    borderRadius: "3px",
                    border: (t) => `1px solid ${String(t.colors?.borders)}`,
                  }}
                >
                  <Flex
                    sx={{
                      p: 3,
                      alignItems: "center",
                      justifyContent: "space-between",
                      width: "100%",
                    }}
                  >
                    <ItemHeader
                      theme={theme}
                      // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment, @typescript-eslint/no-unsafe-member-access
                      text={config?.label || key}
                      sliceFieldName={
                        renderFieldAccessor && renderFieldAccessor(key)
                      }
                      WidgetIcon={widget.Meta.icon}
                    />
                    <Flex>
                      {CustomEditElements ? CustomEditElements : null}
                      {CustomEditElement ? (
                        CustomEditElement
                      ) : (
                        <SliceMachineIconButton
                          size={22}
                          Icon={AiOutlineEdit}
                          label="Edit slice field"
                          sx={{ cursor: "pointer", color: theme.colors?.icons }}
                          onClick={() =>
                            enterEditMode(
                              [key, item.value],
                              modelFieldName,
                              index
                            )
                          }
                        />
                      )}
                      <Menu>
                        <MenuButton
                          className="sliceMenuButton"
                          style={{
                            padding: "0",
                            cursor: "pointer",
                            width: "32px",
                            height: "32px",
                            border: "none",
                            background: "transparent",
                            outline: "0",
                          }}
                        >
                          <BsThreeDotsVertical
                            size={20}
                            color={theme.colors?.icons as string}
                            style={{ pointerEvents: "none" }}
                          />
                        </MenuButton>
                        <MenuList
                          style={{
                            background: theme.colors?.gray as string,
                            border: "1px solid",
                            borderRadius: "3px",
                            borderColor: theme.colors?.borders as string,
                            outline: "0",
                          }}
                        >
                          <MenuItem
                            style={{ padding: "6px", cursor: "pointer" }}
                            onSelect={() => deleteItem(key)}
                          >
                            Delete field
                          </MenuItem>
                        </MenuList>
                      </Menu>
                    </Flex>
                  </Flex>
                  {HintElement ? HintElement : null}
                </Box>
              </Flex>
              {children}
            </Li>
          </Fragment>
        )}
      </Draggable>
    </Fragment>
  );
}
Example #11
Source File: Tabs.tsx    From slice-machine with Apache License 2.0 4 votes vote down vote up
CustomTypeTabs: React.FC<CustomTypeTabsProps> = ({ sx, renderTab }) => {
  const { currentCustomType } = useSelector((store: SliceMachineStoreType) => ({
    currentCustomType: selectCurrentCustomType(store),
  }));
  const { theme } = useThemeUI();
  const { createCustomTypeTab, updateCustomTypeTab, deleteCustomTypeTab } =
    useSliceMachineActions();

  const [tabIndex, setTabIndex] = useState<number>(0);
  const [state, setState] = useState<ModalState | undefined>();

  if (!currentCustomType) return null;

  return (
    <Box sx={{ bg: "backgroundClear" }}>
      <FlexWrapper
        // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment
        sx={sx}
      >
        <Tabs
          selectedIndex={tabIndex}
          onSelect={(index) => setTabIndex(index)}
          style={{ width: "100%" }}
        >
          <TabList>
            {currentCustomType.tabs.map((tab, i) => (
              <Tab
                key={tab.key}
                style={{
                  display: "flex",
                  height: "48px",
                }}
              >
                <Flex sx={{ alignItems: "center" }}>
                  {tab.key}
                  &nbsp;
                  {i === tabIndex ? (
                    <Icon
                      theme={theme}
                      onClick={(
                        e: React.MouseEvent<HTMLButtonElement, MouseEvent>
                      ) => {
                        e.preventDefault();
                        setState({
                          title: "Edit Tab",
                          type: ModalType.UPDATE,
                          key: tab.key,
                          allowDelete: currentCustomType.tabs.length > 1,
                        });
                      }}
                    />
                  ) : null}
                </Flex>
              </Tab>
            ))}
            <Tab
              key={"new-tab"}
              style={{ height: "48px" }}
              disabled
              onClick={() =>
                setState({ title: "Add Tab", type: ModalType.CREATE })
              }
            >
              <Button variant="transparent" sx={{ m: 0, color: "text" }}>
                <AiOutlinePlus style={{ position: "relative", top: "2px" }} />{" "}
                Add Tab
              </Button>
            </Tab>
          </TabList>
          {currentCustomType.tabs.map((tab) => (
            <TabPanel key={tab.key}>{renderTab(tab)}</TabPanel>
          ))}
          <TabPanel key={"new-tab"} />
        </Tabs>
      </FlexWrapper>
      {state?.type === ModalType.CREATE ? (
        <CreateModal
          {...state}
          isOpen
          tabIds={currentCustomType.tabs.map((e) => e.key.toLowerCase())}
          close={() => setState(undefined)}
          onSubmit={({ id }: { id: string }) => {
            createCustomTypeTab(id);
            // current.tabs is not updated yet
            setTabIndex(currentCustomType.tabs.length);
          }}
        />
      ) : null}
      {state?.type === ModalType.UPDATE ? (
        <UpdateModal
          {...state}
          isOpen
          tabIds={currentCustomType.tabs
            .filter((e) => e.key !== state.key)
            .map((e) => e.key.toLowerCase())}
          close={() => setState(undefined)}
          onSubmit={({
            id,
            actionType,
          }: {
            id: string;
            actionType: UpdateModalActionType;
          }) => {
            if (actionType === UpdateModalActionType.UPDATE) {
              updateCustomTypeTab(state.key, id);
            }
            if (actionType === UpdateModalActionType.DELETE) {
              deleteCustomTypeTab(state.key);
              setTabIndex(0);
            }
          }}
        />
      ) : null}
    </Box>
  );
}