daisyUI。尾风CSS组件用于减少标记

1,538 阅读4分钟

尽管Tailwind CSS受到了极大的欢迎,但许多开发者还是很难适应这个框架,主要原因是随着应用程序的扩展,标记的可读性下降。

daisyUI是一个可定制的Tailwind CSS组件库,可以防止前端应用程序的冗长标记。daisyUI的重点是为用户界面定制和创建主题,它使用纯CSS和Tailwind实用类,允许开发人员编写干净的HTML。

在这篇文章中,我们将通过在React中构建一个图片库来探索daisyUI,该图片库可以获取和组织照片,学习如何在不编写冗长标记的情况下实现Tailwind的性能和定制。

要跟上这个教程,你将需要以下条件。

  • React和JavaScript的基本知识
  • 在你的机器上安装Node.js和npm
  • 关于Tailwind CSS和实用类的基本知识

让我们开始吧!

本教程中的示例应用程序的代码可以在GitHub上找到。

生成一个新的React应用程序

首先,我们将创建一个新的React应用程序,并使用Create React App引导它;在你的终端运行下面的命令。

npx create-react-app daisyui-app

虽然我把这个例子项目命名为daisyui-app ,但你可以用你选择的任何名字来替换它。接下来,导航到你的项目目录,通过运行以下命令启动你的开发服务器。

cd daisyui-app && yarn start 

上面的命令将打开一个浏览器标签,显示默认的模板应用程序。最后,你需要按照本文所列的步骤,为你的应用程序设置Tailwind CSS

安装依赖项

随着我们的新React项目的生成和Tailwind CSS为Create React App的配置,让我们在我们的应用程序中安装以下所需的依赖项。

  • daisyUI:为我们的应用程序提供构建和造型的组件。
  • Tailwind CSS:为我们的daisyUI组件提供实用类。
  • PostCSS:用于对JavaScript插件进行样式设计
  • Axios:处理API请求

在你的终端中运行以下代码。

yarn add daisyui tailwindcss postcss axios

接下来,导航到你的tailwind.config.js 文件,添加以下代码。

plugins: [require("daisyui")],

上面的代码在我们的Tailwind CSS配置中包含了对daisyUI的支持,提供了对Tailwind实用类的访问,我们将用它来定制我们的daisyUI组件样式。

构建一个照片库应用程序

在本节中,我们将构建我们的应用程序所需的三个组件:一个用于我们应用程序标题的Intro 组件,一个用于我们应用程序导航条的Navbar 组件,以及一个用于显示和组织照片的Photo 组件。

为了访问图片并为我们的应用程序建立组件,我们将使用Unsplash。如果你还没有,请建立一个账户。

Intro 组件

Intro 组件将包含一个来自Unsplash的图片URL和一个用于我们应用程序登陆页面的背景图片。在你的components/intro/intro.jsx 文件中,添加以下代码。

const Intro = () => {
    const imgURL =
        "https://images.unsplash.com/photo-1606819717115-9159c900370b?ixid=MnwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHx8&ixlib=rb-1.2.1&auto=format&fit=crop&w=800&q=80";
    return (
        <div
            className="hero h-96"
            style={{
                backgroundImage: `url(${imgURL})`,
            }}
        >
            <div className="hero-overlay bg-opacity-60" />
            <div className="text-center hero-content text-neutral-content">
                <div className="w-full">
                    <h1 className="mb-6 text-5xl font-bold">
                        Hello there, welcome to our daisy gallery
                    </h1>
                    <p className="text-lg">
                        Built with images from{" "}
                        <a
                            href="https://unsplash.com/developers"
                            className="hover underline mt-8 bg-white px-2 py-1.5 rounded-sm text-black"
                        >
                            Unsplash API
                        </a>
                    </p>
                </div>
            </div>
        </div>
    );
};
export default Intro;

在上面的代码中,我们创建了一个Intro 组件;在里面,我们初始化了一个imgURL ,它包含了我们登陆页面上的图片的URL。

接下来,我们使用Tailwind的CSS类为我们应用程序的登陆页面组件定制了样式。我们还添加了一个指向Unsplash开发者API的链接。现在,你的应用程序应该看起来像下面的图片。

Unsplash Developers API New Daisyui App

建立一个Navbar 组件

现在,让我们建立一个简单的Navbar 组件,并使用daisyUI的组件类来添加自定义功能。

const Navbar = () => {

    return (
        <div className="navbar flex-col shadow-lg bg-neutral text-neutral-content">
            <div className="flex-1 px-2 mx-2">
                <span className="text-lg font-bold">Daisy Photo Gallery</span>
            </div>
        </div>
    );
};

export default Navbar;

在上面的代码中,我们通过使用font-bold ,使我们的导航条的字体变粗,并使用text-leg 组件指定一个大字体。

建立我们的Photo 组件

接下来,我们将建立一个简单的Photo 组件来渲染从Unsplash获取的图片;为了渲染我们的Photo 组件,我们将把它包在一个figure 组件中。

const Photo = ({ imgURL }) => {
    return (
        <>
            <div className="card">
                <figure>
                  <img src={imgURL} alt="unsplash img" />
                </figure>
            </div>
        </>
    );
};

export default Photo;

在上面的代码块中,我们对我们的Photo 组件进行解构,并将我们的UnsplashimgURL 。接下来,我们使用daisyUI的card 组件类为我们的照片创建了一个卡片。最后,我们将我们的图片包裹在figure 标签中,缩小它们的尺寸以适应我们的Photo 组件容器。

取出和组织照片

现在,我们将使用我们的组件从Unsplash API中获取随机照片,然后创建类别来组织它们。首先,让我们通过向我们的App.js 文件添加以下代码块来导入我们的包。

import { useState, useEffect } from "react";
import axios from "axios";
import Intro from "./components/Intro/Intro";
import Navbar from "./components/Navbar/Navbar";
import Photo from "./components/Photo/Photo";

在上面的代码中,我们导入了我们的组件,以及useStateuseEffect 钩子。接下来,我们将通过添加下面的代码来初始化一个app 组件。

const App = () =&gt; {
    const [selectedCategory, setSelectedCategory] = useState("RANDOM");
    const [photos, setPhotos] = useState([]);
    const [categories] = useState([
        "RANDOM",
        "TECHNOLOGIES",
        "ARTS",
        "SPORTS",
        "GAMES",
    ]);

在我们的app 组件内,我们使用React的useState 变量为categoriesPhotos 创建了状态。然后,我们创建了一个不同类别的数组,包括RANDOM,TECHNOLOGIES,ARTS,SPORTS, 和GAMES

现在,让我们写一个函数,从我们的Unsplash API获取随机照片。

const fetchRandomPhotos = async () =&gt; {
        try {
            const res = await axios.get("https://api.unsplash.com/photos/random", {
                params: {
                    client_id: process.env.REACT_APP_UNSPLASH_ACCESS_KEY,
                    count: 12,
                },
            });
            const photoArr = res.data?.map((photo) =&gt; photo?.urls?.regular);
            setPhotos(photoArr);
        } catch (error) {
            setPhotos([]);
            console.error(error?.response?.data?.message);
        }
    };

在上面的代码块中,我们创建了getRandomPhotos 函数,它从我们的Unsplash API中获取随机照片。为了设置我们所有的图片,我们映射了照片数组。为了验证,我们传递了我们的client_id ,这是从我们的Unsplash开发者API仪表板上得到的。最后,我们指定图片的数量为count: 12

现在,我们要写一个函数,根据照片类别返回照片。

  const fetchPhotoBasedonCategory = async () =&gt; {
        try {
            const res = await axios.get("https://api.unsplash.com/search/photos", {
                params: {
                    client_id: process.env.REACT_APP_UNSPLASH_ACCESS_KEY,
                    query: selectedCategory.toLowerCase(),
                },
            });
            const photoArr = res.data?.results?.map((photo) =&gt; photo?.urls?.regular);
            setPhotos(photoArr);
        } catch (error) {
            setPhotos([])
            console.error(error?.response?.data?.message);
        }
    };

与我们的getRandomPhotos 函数类似,我们指定了类别,并使用map 对照片列表进行排序,只返回用户指定类别的照片。为了渲染一张图片,我们从Unsplash映射出图片数组,只设置指定的图片数量。我们还将任何错误记录到控制台。

useEffect(() => {
        if (selectedCategory === "RANDOM") {
            return fetchRandomPhotos();
        }
        fetchPhotoBasedonCategory();
        // eslint-disable-next-line react-hooks/exhaustive-deps
    }, [selectedCategory]);

    return (
        <>
            <Navbar />
            <main className="mb-10">
                <Intro />
                <nav>
                    <div className="tabs mt-10 justify-center">
                        {categories.map((category) => (
                            <p
                                key={category}
                                onClick={() => setSelectedCategory(category)}
                                role="button"
                                className={`tab tab-bordered 
                            ${selectedCategory === category && "tab-active"}`}
                            >
                                {category}
                            </p>
                        ))}
                    </div>
                </nav>
                <section className="mt-4 mx-auto w-10/12 relative">
                    <div className="grid grid-cols-3 justify-center gap-3">
                        {photos?.length ? (
                            photos.map((photo) => <Photo key={photo} imgURL={photo} />)
                        ) : (
                            <p className="mt-10 alert alert-info absolute left-1/2 -ml-20">
                                No photo at the moment!
                            </p>
                        )}
                    </div>
                </section>
            </main>
        </>
    );
};

export default App;

在上面的代码块中,我们使用React的useEffect Hook来指定RANDOM ,如果用户选择了random 类别。如果用户指定了一个类别,API会返回所选类别的图片。

最后,我们渲染了我们的整个应用程序,并为类别部分添加了一个onClick 事件。此外,我们添加了一个函数来指定只向用户显示所选类别的图片。最后,我们添加了一个消息,当我们的API中没有照片可用时。虽然这是很不可能的,但这是很好的做法。

如果做得正确,我们的应用程序应该类似于下面的图片。

Final Daisyui Unsplash React Photo App

结论

随着组件类的增加,如btncard 、和footer ,daisyUI通过允许开发者编写干净的HTML,显著改善了Tailwind CSS。在本教程中,我们探索了用CSS变量和Tailwind CSS实用类构建和定制我们自己的React应用程序。

虽然我们的例子侧重于构建一个图片库,但你可以把本教程中的信息应用到你自己的应用程序中,享受Tailwind的造型性能,而不会在你扩展项目时损害你代码的可读性。我希望你喜欢这个教程!

The postdaisyUI:用于减少标记的Tailwind CSS组件首次出现在LogRocket博客上。